Simple: If I test a signed vs an unsigned variable in GCC, when compiling -Wall
I will get a warning.
Using this code:
#include <stdio.h>
int main(int argc, char* argv[])
{
/* const */ unsigned int i = 0;
if (i != argc)
return 1;
return 0;
}
I get this warning:
<source>: In function 'int main(int, char**)':
<source>:6:8: warning: comparison of integer expressions of different signedness: 'unsigned int' and 'int' [-Wsign-compare]
6 | if (i != argc)
| ~~^~~~~~~
Compiler returned: 0
However, if I uncomment this const
- the compiler is happy. I can reproduce this on almost every GCC version (see https://godbolt.org/z/b6eoc1). Is is this a bug in GCC?
I think that what you are missing is compiler optimization. Without const, that variable is a variable, meaning that it can change. Since it is an unsigned int, it means that indeed it can be larger than an integer.
const unsigned int i = 2147483648;
You will get your error back if you assign a value greater than the largest value of int to that unsigned int.
However if it is const, the compiler knows its value, it knows, that it will not change, and there will be no problem with the comparison.
If you take a look at the assembly, you will see that without const, it actually takes the value of the variable to compare:
movl $0, -4(%rbp)
movl -20(%rbp), %eax
cmpl %eax, -4(%rbp)
Now, if it is const, it will not bother with the variable at all, it just takes the value:
movl $0, -4(%rbp)
cmpl $0, -20(%rbp)
I'd say it's a compiler bug in the -Wsign-compare
option.
Test by compiling your example with -Wall -Wextra -O3
. With -O3
added, the warning suddenly goes away in the const
case. Even though the generated machine code with or without const
is identical. This doesn't make any sense.
Naturally, neither const
nor the generated machine code has any effect on the signedness of the C operands, so the warning shouldn't come inconsistently depending on type qualifiers or optimizer settings.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With