20

While speaking with a colleague of mine, they said that:

foo() {
    int *p;
    {
        int x = 5;
        p = &x;
    }
    int y = *p;
}

creates undefined behavior because lifetime rules and scope rules do not specify.

However:

foo() {
    int *p;
    {
        static int x = 5;
        p = &x;
    }
    int y = *p;
}

is not undefined! You end up with "indirect scoping" issues.

The use of terminology does not sound correct.
I know that static has nothing to do with scoping.
Is it true that the second case has defined behavior?

curiousguy
  • 8,038
  • 2
  • 40
  • 58
Trevor Hickey
  • 36,288
  • 32
  • 162
  • 271
  • Comments are not for extended discussion; this conversation has been [moved to chat](http://chat.stackoverflow.com/rooms/114724/discussion-on-question-by-trevor-hickey-is-accessing-a-static-out-of-scope-undef). – George Stocker Jun 15 '16 at 10:15

2 Answers2

30

Yes the second case has well defined behavior. A static variable is basically a global variable whose name is scoped to the scope it is declared in. It is initialized the first time the scope is entered and then it lives on for the life of the program.

So when we reach

int y = *p;

p points to a variable that you can no longer reach (can't get back to that code) but still has a valid lifetime.

To quote the standard [basic.stc.static]

All variables which do not have dynamic storage duration, do not have thread storage duration, and are not local have static storage duration. The storage for these entities shall last for the duration of the program

emphasis mine

The first case is undefined as the lifetime of the local scope x ends at the } and trying to refer to it after its lifetime ends is undefined behavior.

Barry
  • 286,269
  • 29
  • 621
  • 977
NathanOliver
  • 171,901
  • 28
  • 288
  • 402
  • In the second case, is `*p = 42;` undefined? – nalzok Jun 14 '16 at 03:47
  • 3
    @sunqingyao: It's fine, why wouldn't it be? C does not require that storage locations have names. Otherwise, `malloc` would be useless. – rici Jun 14 '16 at 04:08
1

quoting from here

The static storage class instructs the compiler to keep a local variable in existence during the life-time of the program instead of creating and destroying it each time it comes into and goes out of scope. Therefore, making local variables static allows them to maintain their values between function calls.

so yes in the second case x is in existence during the complete life-time of the program.

hence has defined behavior.

mssirvi
  • 147
  • 3
  • 14
  • 1
    What are you quoting? – Barry Jun 13 '16 at 18:20
  • There is a difference between static storage and the `static` _storage-class **specifier**_. – too honest for this site Jun 13 '16 at 18:33
  • @Olaf can you please provide some links on this difference between static storage and storage class specifier, so it will be helpful for me to understand it better ? – mssirvi Jun 13 '16 at 18:39
  • The standard is quite clear about this. It is not my answer. It might be different in C++; i commented under the impression the question is about C - still you should verify yourself, I'm not that familiar with the C++ standard. And please don't cite 2nd/3rd level resources if an authoritative resource is at hand. – too honest for this site Jun 13 '16 at 18:41
  • i felt, this is explained in more simple language than the authoritative resource. anyway i will take care about it in future posts. – mssirvi Jun 13 '16 at 18:44
  • There is nothing wrong citing the standard and then explaining it. – too honest for this site Jun 13 '16 at 18:45