[Issue 24798] Under some circumstances, the compiler destroys the same object more than once

d-bugmail at puremagic.com d-bugmail at puremagic.com
Thu Oct 10 11:33:46 UTC 2024


https://issues.dlang.org/show_bug.cgi?id=24798

kinke <kinke at gmx.net> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
                 CC|                            |kinke at gmx.net

--- Comment #2 from kinke <kinke at gmx.net> ---
I've reduced it to this:
```
struct S {
    int val;
    ~this() {
        import core.stdc.stdio : printf;
        printf("dtor %d, %p\n", val, &this);
        val = 99;
    }
}

void main() {
    auto r = makeR();
    r.foo();
}

auto makeR() {
    auto s = S(1); // allocated in GC closure
    return R!s();
    // the frontend wrongly destructs `s` at the end of the function, see
-vcg-ast
}

struct R(alias s) {
    void foo() {
        assert(s.val != 99, "already destroyed");
    }
}
```

So the problem is that in `makeR`, `s` is correctly allocated in a GC closure
(because the return value has a hidden reference to it, so the local escapes
its stack frame), but the frontend still eagerly destructs it before exiting
the function. So calling `r.foo()` accesses a destructed `S` instance.

AFAIK, variables in GC closures cannot be destructed, because there's no
TypeInfo associated with the GC-allocated memory block. So the trade-off here
would probably be that the escaping `s` local would be never destructed.

--


More information about the Digitalmars-d-bugs mailing list