rentzsch.com: tales from the red shed

Awesome GCC Literal Suffix Bug

Bugs

The setup:

$ cat bug.c
#include <stdio.h>

static float f(float x) {
  printf("f() called\n");
  return x + 1;
}

int main (int argc, const char *argv[]) {
#if TYPO
  float y = f(42f);
#else
  float y = f(42.f);
#endif
  printf("y: %f\n", y);
  return 0;
}

Let’s build+run it normally:

$ gcc -o bug bug.c && ./bug
f() called
y: 43.000000

OK, let’s insert the typo:

$ gcc -DTYPO=1 -o bug bug.c && ./bug
bug.c:10:14: error: invalid suffix "f" on integer constant

OK, still in the land of the sane. Now let’s add a couple of flags Xcode 2.4 normally adds for a Debug target, -arch and -fasm-blocks:

$ gcc -arch i386 -fasm-blocks -DTYPO=1 -o bug bug.c && ./bug
y: -1.999849

Lovely bug, isn’t it? When targeting Intel and CodeWarrior-style assembly blocks are enabled, 42f is no longer recognized as a syntax error.

It gets better. The entire statement hosting the errant literal just disappears. It’s as if you never even called it. Notice y’s wonky value on the last run: it was never initialized and just holds randomish memory.

Turns out not all literal suffixes have expose the bug, only the following ones: a b c d f g k m n o p q r s t v w x y z. Sigh.

Tuesday, September 11, 2007
03:48 AM