0

The code below will print 10, but the t1 object (created in the function assign) no longer exists by the time the print happens, so is the ptr pointer pointing to unallocated memory space that still holds the value 10?

#include <iostream>

class Test1 {
public:
     int a;
};

class Test2 {
public:
     Test1* ptr;
};

void assign(Test2& t2) {
     Test1 t1{10};
     t2.ptr = &t1;
}

int main() {
     Test2 t2;
     assign(t2);
     std::cout << t2.ptr->a << std::endl;
     return 0;
}
Jan Schultke
  • 17,446
  • 6
  • 47
  • 96
  • You should at least have a constructor that sets that `ptr` to `nullptr` for the sake of not having uninitialized data kicking around. – tadman Jun 08 '23 at 21:47
  • *so is the ptr pointer pointing to unallocated memory space that still holds the value 10* - it's Undefined Behaviour. Absolutely anything can happen, including [demons flying out of your nose](http://catb.org/jargon/html/N/nasal-demons.html). But it's possible that your explanation is correct, and the program didn't manage to overwrite that memory yet. – Yksisarvinen Jun 08 '23 at 21:49
  • 2
    C++ is not a language with garbage collection like e.g. java. It doesn't keep objects with automatic storage duration around after the scope they are declared in is left. You're referring to an object that has a lifetime that has already ended when `assign` returns, you've got undefined behaviour, which means your program could crash and burn or output something plausible; You just cannot rely on the program working reliably under these circumstances, even if it seems to work... – fabian Jun 08 '23 at 21:52
  • Your program's behavior is undefined. That means there is no "correct" behavior. Or you could think of it like any behavior is the "correct" behavior. The language specification makes no assertions as to what your program will do. That doesn't mean it won't do what _you_ expect it to. It doesn't mean it _will do_ what you expect it to do either. – Miles Budnek Jun 08 '23 at 22:23
  • *is the ptr pointer pointing to unallocated memory space that still holds the value 10?* In your case this seems to be the case, but this is not something you can count on. – user4581301 Jun 08 '23 at 22:28
  • Alas, `-fsanitize=address` doesn't catch this *stack-use-after-scope* bug; it only would catch it if it were a *heap-use-after-free*. – Eljay Jun 08 '23 at 23:03
  • You are asking why your Undefined Behavior doesn't behave as you expected. You should not have these expectations about Undefined Behavior. – Drew Dormann Jun 09 '23 at 01:35

1 Answers1

2

The provided code demonstrates a potential issue with accessing memory that may no longer be valid. In the assign function, a local variable t1 is created and its address is assigned to the ptr member of an object t2. However, t1 is destroyed at the end of the assign function, leaving t2.ptr pointing to an invalid memory location. Accessing t2.ptr in the main function can lead to undefined behavior. To ensure correct behavior, you need to ensure the lifetime of the object pointed to by ptr extends beyond the scope of assign.