digitalmars.D.learn - Gc/D_runtime prevents dangling pointers?
- tipdbmp (27/27) Jan 03 2018 char * get_dangling_ptr() {
- thedeemon (11/12) Jan 03 2018 What is your definition of a dangling pointer?
- tipdbmp (5/6) Jan 04 2018 A pointer pointing to freed memory, which presumably '&a[0]'
- thedeemon (9/15) Jan 04 2018 It allocates a larger array, but the old version is not freed up
- Steven Schveighoffer (5/11) Jan 04 2018 Yeah, to further clarify, the array runtime has no idea who is looking
char * get_dangling_ptr() { char[] a; a.reserve(15); a ~= 'x'; char *x = &a[0]; auto a_initial_ptr = a.ptr; foreach (_; 0 .. 30) { a ~= 'y'; //a.assumeSafeAppend() ~= 'y'; } assert(a.ptr != a_initial_ptr, "a should've reallocated"); // trying to reuse 'a's old memory foreach (_; 0 .. 10) { char[] b; b.reserve(15); foreach (__; 0 .. 15) { b ~= 'y'; } } return x; } void main() { import std.stdio : writefln; char *x = get_dangling_ptr(); writefln("ptr: %X; value: %s", x, *x); } x doesn't seem to be a dangling pointer, how come?
Jan 03 2018
On Wednesday, 3 January 2018 at 22:22:06 UTC, tipdbmp wrote:x doesn't seem to be a dangling pointer, how come?What is your definition of a dangling pointer? In the shown example we have a reference to a piece of memory containing 'x', so this memory is not freed, it's used by the program. So when you access it via the pointer you get that 'x' value, everything's ok. The comment also shows misunderstanding: when you allocate a new array you don't reuse the old memory, especially when it's still used, as it is here. This is how all GC'ed languages work: as long as you have live references to data, it's not freed and not reused. This makes all those references valid and not "dangling".
Jan 03 2018
What is your definition of a dangling pointer?A pointer pointing to freed memory, which presumably '&a[0]' should be because it reallocates. It seems that the '~=' operator "knows" that there's a reference to 'a's old memory and it keeps it around instead of freeing it. I just don't understand the mechanism behind this.
Jan 04 2018
On Thursday, 4 January 2018 at 11:05:25 UTC, tipdbmp wrote:It allocates a larger array, but the old version is not freed up front. Right because there might be live references to the old data. Your pointer is such live reference. So while this pointer references that old version of the array, it's not freed. Only after no references are left the GC will make it free (and only when next GC cycle happens, not immediately).What is your definition of a dangling pointer?A pointer pointing to freed memory, which presumably '&a[0]' should be because it reallocates.It seems that the '~=' operator "knows" that there's a reference to 'a's old memory and it keeps it around instead of freeing it.It's just not its job to free that memory. That memory is freed later by GC, when it's safe to do so.
Jan 04 2018
On 1/4/18 6:50 AM, thedeemon wrote:On Thursday, 4 January 2018 at 11:05:25 UTC, tipdbmp wrote:Yeah, to further clarify, the array runtime has no idea who is looking at the memory. It doesn't "know" about references, it just relies on the GC to clean up the garbage if it actually is garbage. -SteveIt seems that the '~=' operator "knows" that there's a reference to 'a's old memory and it keeps it around instead of freeing it.It's just not its job to free that memory. That memory is freed later by GC, when it's safe to do so.
Jan 04 2018