Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

What happens when a variable goes out of scope?

In most managed languages (that is, the ones with a GC), local variables that go out of scope are inaccessible and have a higher GC-priority (hence, they'll be freed first).

Now, C is not a managed language, what happens to variables that go out of scope here?

I created a small test-case in C:

#include <stdio.h>
int main(void){
    int *ptr;

    {
        // New scope
        int tmp = 17;
        ptr = &tmp; // Just to see if the memory is cleared
    }

    //printf("tmp = %d", tmp); // Compile-time error (as expected)
    printf("ptr = %d\n", *ptr);

    return 0;
}

I'm using GCC 4.7.3 to compile and the program above prints 17, why? And when/under what circumstances will the local variables be freed?

like image 253
Lukas Knuth Avatar asked Dec 15 '12 00:12

Lukas Knuth


People also ask

What happens to a variable when it goes out of scope?

A variable declared inside a function has a function scope. It has been allocated memory when the function is called and once the function returns something the function execution ends and with it the variable goes out of scope i.e. it gets deleted from the memory.

What happens when a variable goes out of scope Mcq?

The variables are destroyed as soon as those go out of scope.

What does it mean for an object to go out of scope?

The metonymy "going out of scope" is used to express the idea that the dynamic activation/instantiation of the environment associated with some scope is terminating. And so the variables defined in that scope are going away (thus "out of scope").

What happens when a variable of reference data type goes out of scope in C#?

When the method ends, the variable goes out of scope and is destroyed. C# divides the world of types into value types and reference types. Value types are created on the stack. All the intrinsic types ( int, long ) are value types (as are structs, discussed later in this chapter), and thus are created on the stack.


1 Answers

The actual behavior of your code sample is determined by two primary factors: 1) the behavior is undefined by the language, 2) an optimizing compiler will generate machine code that does not physically match your C code.

For example, despite the fact that the behavior is undefined, GCC can (and will) easily optimize your code to a mere

printf("ptr = %d\n", 17);

which means that the output you see has very little to do with what happens to any variables in your code.

If you want the behavior of your code to better reflect what happens physically, you should declare your pointers volatile. The behavior will still be undefined, but at least it will restrict some optimizations.

Now, as to what happens to local variables when they go out of scope. Nothing physical happens. A typical implementation will allocate enough space in the program stack to store all variables at the deepest level of block nesting in the current function. This space is typically allocated in the stack in one shot at the function startup and released back at the function exit.

That means that the memory formerly occupied by tmp continues to remain reserved in the stack until the function exits. That also means that the same stack space can (and will) be reused by different variables having approximately the same level of "locality depth" in sibling blocks. The space will hold the value of the last variable until some other variable declared in some sibling block variable overrides it. In your example nobody overrides the space formerly occupied by tmp, so you will typically see the value 17 survive intact in that memory.

However, if you do this

int main(void) {
  volatile int *ptr;
  volatile int *ptrd;

  { // Block
    int tmp = 17;
    ptr = &tmp; // Just to see if the memory is cleared
  }

  { // Sibling block
    int d = 5;
    ptrd = &d;
  }

  printf("ptr = %d %d\n", *ptr, *ptrd);
  printf("%p %p\n", ptr, ptrd);
}

you will see that the space formerly occupied by tmp has been reused for d and its former value has been overriden. The second printf will typically output the same pointer value for both pointers.

like image 55
AnT Avatar answered Oct 10 '22 04:10

AnT