digitalmars.D.learn - Preventing nested struct destructor accessing stack frame
- Nick Treleaven (16/16) Dec 16 2022 This code segfaults when the GC calls the dtor after the unittest
- Nick Treleaven (5/8) Dec 16 2022 This seems to work:
- ag0aep6g (6/12) Dec 19 2022 A quick test suggests that the context pointer is the last item in
- Nick Treleaven (5/19) Dec 23 2022 Great, thanks. The struct tupleof docs just link to the class
- Steven Schveighoffer (7/23) Dec 23 2022 Check if the struct is the init value?
This code segfaults when the GC calls the dtor after the unittest succeeds: ```d unittest { int i; struct S { ~this() { i++; } } (*new S).destroy; } ``` It seems destroy clears the context pointer. Is there a way to test if the context pointer is null in the dtor, to prevent the increment?
Dec 16 2022
On Friday, 16 December 2022 at 12:17:40 UTC, Nick Treleaven wrote:It seems destroy clears the context pointer. Is there a way to test if the context pointer is null in the dtor, to prevent the increment?This seems to work: ~this() trusted { if (&i > cast(void*)1024) i++; } It would be better if there was a struct property to get the context pointer though.
Dec 16 2022
On 16.12.22 14:07, Nick Treleaven wrote:This seems to work: ~this() trusted { if (&i > cast(void*)1024) i++; } It would be better if there was a struct property to get the context pointer though.A quick test suggests that the context pointer is the last item in `tupleof`. So this might do the trick: ~this() { if (this.tupleof[$ - 1] !is null) i++; } I don't know if it's guaranteed to work though. Might be an implementation detail.
Dec 19 2022
On Tuesday, 20 December 2022 at 06:31:09 UTC, ag0aep6g wrote:On 16.12.22 14:07, Nick Treleaven wrote:Great, thanks. The struct tupleof docs just link to the class tupleof docs, which say:This seems to work: ~this() trusted { if (&i > cast(void*)1024) i++; } It would be better if there was a struct property to get the context pointer though.A quick test suggests that the context pointer is the last item in `tupleof`. So this might do the trick: ~this() { if (this.tupleof[$ - 1] !is null) i++; } I don't know if it's guaranteed to work though. Might be an implementation detail.The order of the fields in the tuple matches the order in which the fields are declared.So I think for a struct the context pointer has to come after any fields.
Dec 23 2022
On 12/16/22 7:17 AM, Nick Treleaven wrote:This code segfaults when the GC calls the dtor after the unittest succeeds: ```d unittest { int i; struct S { ~this() { i++; } } (*new S).destroy; } ``` It seems destroy clears the context pointer. Is there a way to test if the context pointer is null in the dtor, to prevent the increment?Check if the struct is the init value? ```d ~this() { if(this !is this.init) ++i;} ``` Not ideal I guess, because really it's the context pointer you care about. -Steve
Dec 23 2022