Bitwise Enum No Flags
ID |
csharp.bitwise_enum_no_flags |
Severity |
low |
Remediation Complexity |
trivial |
Remediation Risk |
low |
Remediation Effort |
low |
Resource |
Reliability |
Language |
CSharp |
Tags |
enum, reliability |
Description
Reports |, & and ^ bitwise expressions whose operands resolve to an enum that
does not carry the [Flags] attribute. Bitwise composition only makes sense for an
enum specifically designed as a bit set; on a plain enum the result is a value that
does not correspond to any declared member and that ToString() cannot round-trip.
Rationale
The [Flags] attribute documents the intent ("this enum is a bit set") and changes
the behaviour of ToString() and the HasFlag machinery. Composing values of a
plain enum with | or & silently produces out-of-range numeric values that defeat
exhaustive switches and serialize as a meaningless integer.
public enum Color { Red = 1, Green = 2, Blue = 4 }
[Flags]
public enum Permission { Read = 1, Write = 2, Execute = 4 }
public class Sample
{
public Color Mix()
{
return Color.Red | Color.Green; // FLAW — Color lacks [Flags]
}
public bool HasAny(Color a, Color b)
{
return (a & b) != 0; // FLAW — same enum without [Flags]
}
public Permission FullAccess()
{
return Permission.Read | Permission.Write; // OK — [Flags] enum
}
}
Remediation
Either add [Flags] to the enum and renumber its members as powers of two, or stop
composing values of an enum that is not meant to be a bit set. If the bitwise
composition is part of a larger expression involving non-enum integers, cast the enum
to int to make the integer arithmetic explicit.