Search code examples
cstatic-memory-allocation

If a static variable is declared out side of a function, will the memory address be the same as if it's declared in a function


I was asked these 2 questions during an interview. I guess the address of a static variable will be the same no matter where it is declared. It will also have the same address from run to run. Correct me if I am wrong.

  1. If a static variable is declared out side of a function, will the memory address be the same as if it's declared in a function?

  2. If a static variable is declared out side of a function, will it have the same address every time you run the program?


Solution

  • Cunningham's Law will ensure quick correction of my mistakes:

    1. global and local static variables are treated similarly so they may indeed end up at the same address when moved:
    #include <stdio.h>
    
    #ifdef GLOBAL
    static int i;
    #endif
    // static int j;
    
    #ifndef GLOBAL
    void f(void) {
        static int i;
        printf("local:  %p\n" , (void *) &i);
    }
    #endif
    
    int main() {
    #ifdef GLOBAL
        printf("global: %p\n" , (void *) &i);
    #else
        f();
    #endif
    }
    

    You need to disable address randomization to observe it:

    $ sudo bash -c 'echo 0 >  /proc/sys/kernel/randomize_va_space';\
    gcc 1.c && ./a.out &&\
    gcc -DGLOBAL 1.c && ./a.out;\
    sudo bash -c 'echo 2 >  /proc/sys/kernel/randomize_va_space'
    local:  0x555555558034
    global: 0x555555558034
    

    If you add another global static int j (commented out above) after the global i then the effect goes away:

    local:  0x555555558038
    global: 0x555555558034
    

    So call me maybe!?

    1. No. Modern operating systems, specifically the program loader, use address space layout randomization (ASLR) so the address changes on every execution:
    $ ./a.out && ./a.out
    global: 0x563bcce14034
    global: 0x55cd4a497034