With f0
and f1
as below,
long long b;
void f0(int a) {
a %= 10;
if (a == 0) b = 11;
else if (a == 1) b = 13;
else if (a == 2) b = 17;
else if (a == 3) b = 19;
else if (a == 4) b = 23;
else if (a == 5) b = 29;
else if (a == 6) b = 31;
else if (a == 7) b = 37;
else if (a == 8) b = 41;
else if (a == 9) b = 43;
}
void f1(int a) {
a %= 10;
if (a == 0) b = 11;
else if (a == 1) b = 13;
else if (a == 2) b = 17;
else if (a == 3) b = 19;
else if (a == 4) b = 23;
else if (a == 5) b = 29;
else if (a == 6) b = 31;
else if (a == 7) b = 37;
else if (a == 8) b = 41;
else if (a == 9) b = 43;
else __builtin_unreachable();
}
assuming the argument a
is always positive in the program, the compiler should produce more optimized code for f1
because in f0
, a
can fall through the if-else block when it is negative, so the compiler should produce a default "do nothing and return" code. However in f1
, the possible range of a
is clearly stated with __builtin_unreachable
so that the compiler doesn't have to think when a
is out of range.
However, f1
actually runs slower, so I had a look at the disassembly. This is the control flow part of f0
.
jne .L2
addq $11, b(%rip)
ret
.p2align 4,,10
.p2align 3
.L2:
cmpl $9,