I'm trying to understand the exact behavior of storage class specifiers in C99, and some GCC behavior seems not to follow the spec, unless I misunderstand the spec. From 6.2.2 (2):
Within one translation unit, each declaration of an identifier with internal linkage denotes the same object or function.
However, I tested GCC (powerpc-apple-darwin9-gcc-4.2.1) with the following program:
#include <stdio.h>
static int f() {
static int x = 0;
return x++;
}
static int g() {
static int x = 0;
return x++;
}
int main(int argc, char *argv[]) {
printf("g() = %i\n", g());
printf("g() = %i\n", g());
printf("f() = %i\n", f());
printf("f() = %i\n", f());
return 0;
}
Compiled with -std=c99, It prints the following:
g() = 0
g() = 1
f() = 0
f() = 1
If I understand the spec correctly, it should print:
g() = 0
g() = 1
f() = 2
f() = 3
I understand why GCC would deviate from the spec here, I'm just wondering if there's a deeper explanation for this behavior.
In 6.2.2 (6) it says:
The following identifiers have no linkage: [...] a block scope identifier for an object declared without the storage-class specifier extern.
The static variables are block scope identifiers for objects, and they are not declared extern. Therefore they have no linkage, especially not internal linkage.
The next paragraph, 6.2.2/3, is important:
If the declaration of a file scope identifier for an object or a function contains the storage-class specifier static, the identifier has internal linkage.
(note the emphasized file scope identifier).
Your static variables x do not have file scope, they have block scope.
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