Re: Are there any methods like isDestroyed or isDisposed to detect whether some object is destroyed or not?
On Sat, 13 Dec 2014 07:03:22 + Andrey Derzhavin via Digitalmars-d-learn wrote: > Hello! > > We have object, for example, objA. > > ObjectAType objA = new ObjectAType(...); > > // we have a many references to objA > > void someFunction1(...) > { > // destroying the objA > destroy(one_of_the_refToObjA); > > // > } > > > void someFunction2() > { > // "segmentation fault" if the objA is destroyed > another_refToObjA.method1(); > > // I need a safe way (without using signals) to detect whether > object > // destroyed or not, like this > // if (!isDestroyed(another_refToObjA)) > // another_refToObjA.method1(); > > } > > // call functions > someFunction1(..); > > // . some other operations... > > // the objectA (objA) is destroyed, but debugger shows us a not > null reference > // to that objA. However, when we try to call some methods of > objectA or > // try to use it's variables we get a "segmentation fault" error > (in > // someFunction2, when objA is destroyed). > someFunction2(...); > > Thanks. first. you'd better to not write such code, it's completely unreliable. second. you can check if the block is allocated by using GC.addrOf(). third. and this is completely unreliable, 'cause memory can be reused. so the only right answer is: "don't do that!" use list of free objects, for example, and write `free()` function that will move the object to that list (and possibly set some flags to mark it as "freed"). let me stress it again: you *CAN'T* reliably detect if some object was manually destroyed. don't even think you can do this in working code, you will never made such code fully working. signature.asc Description: PGP signature
Re: Are there any methods like isDestroyed or isDisposed to detect whether some object is destroyed or not?
On Sat, 13 Dec 2014 07:03:22 + Andrey Derzhavin via Digitalmars-d-learn wrote: p.s. you can emulate "weak links" if this is what you want to have. i.e. references to object that will not stop GC to collect that object and which will be auto-nullified if the object was collected. see this module, for example: http://repo.or.cz/w/iv.d.git/blob/HEAD:/weakref.d signature.asc Description: PGP signature
Re: Are there any methods like isDestroyed or isDisposed to detect whether some object is destroyed or not?
On Sat, 13 Dec 2014 07:03:22 + Andrey Derzhavin via Digitalmars-d-learn wrote: p.p.s. please-please-please don't invent other hacks with `rt_attachDisposeEvent()`! such hackery will not do you good in the long term. signature.asc Description: PGP signature
Re: Are there any methods like isDestroyed or isDisposed to detect whether some object is destroyed or not?
"Andrey Derzhavin" writes: > Hello! > > We have object, for example, objA. > > ObjectAType objA = new ObjectAType(...); > > // we have a many references to objA > > void someFunction1(...) > { >// destroying the objA >destroy(one_of_the_refToObjA); > >// > } > > > void someFunction2() > { >// "segmentation fault" if the objA is destroyed >another_refToObjA.method1(); > >// I need a safe way (without using signals) to detect whether > object >// destroyed or not, like this >// if (!isDestroyed(another_refToObjA)) >// another_refToObjA.method1(); > > } > > // call functions > someFunction1(..); > > // . some other operations... > > // the objectA (objA) is destroyed, but debugger shows us a not null > reference > // to that objA. However, when we try to call some methods of objectA > or > // try to use it's variables we get a "segmentation fault" error (in > // someFunction2, when objA is destroyed). > someFunction2(...); > > Thanks. Maybe this would work for you. If you own your ObjectAType class, you could add an ok flag. destroy() sets all members to .init value and TDPL says this will be the case (lookup "clear" which was renamed "destroy"). import std.stdio; class ObjectAType { bool ok; this() {ok = true;} } void main() { auto a = new ObjectAType; assert(a.ok); destroy(a); assert(!a.ok); // a has been destroyed. } -- dano
Re: Are there any methods like isDestroyed or isDisposed to detect whether some object is destroyed or not?
import std.stdio; class ObjectAType { bool ok; this() {ok = true;} } void main() { auto a = new ObjectAType; assert(a.ok); destroy(a); assert(!a.ok); // a has been destroyed. } This method of detection of collected objects is what I needed. Thanks to everybody for your advise.
Re: Are there any methods like isDestroyed or isDisposed to detect whether some object is destroyed or not?
On Saturday, 13 December 2014 at 21:20:43 UTC, Andrey Derzhavin wrote: import std.stdio; class ObjectAType { bool ok; this() {ok = true;} } void main() { auto a = new ObjectAType; assert(a.ok); destroy(a); assert(!a.ok); // a has been destroyed. } This method of detection of collected objects is what I needed. Thanks to everybody for your advise. Be careful - the memory could still have been reused. For example: assert(a.ok); destroy(a); // ... lots of code, maybe multi-threaded ... assert(!a.ok);// can fail If between `destroy()` and the second `assert()`, the memory of the object is collected, a new object (of the same or different type) can have been placed there. You will then read an arbitrary piece of data from that new object, which may or may not evaluate to `true`. The only case where this can be safe is when you can guarantee that there are no new memory allocations between the destruction and the test, or that the GC doesn't run. The first condition may also be no longer sufficient if the GC starts moving objects around (the current one doesn't). Really, in practice you just cannot safely access GC managed resources from inside a GC destructor. You're just asking for trouble if you try to hack around that fact.
Re: Are there any methods like isDestroyed or isDisposed to detect whether some object is destroyed or not?
"Marc "Schütz\"" writes: > On Saturday, 13 December 2014 at 21:20:43 UTC, Andrey Derzhavin wrote: >>> >>> import std.stdio; >>> >>> class ObjectAType { >>>bool ok; >>>this() {ok = true;} >>> } >>> >>> void main() >>> { >>>auto a = new ObjectAType; >>>assert(a.ok); >>>destroy(a); >>>assert(!a.ok); // a has been destroyed. >>> } >>> >> >> This method of detection of collected objects is what I needed. >> Thanks to everybody for your advise. > > Be careful - the memory could still have been reused. For example: > > assert(a.ok); > destroy(a); > // ... lots of code, maybe multi-threaded ... > assert(!a.ok);// can fail > > If between `destroy()` and the second `assert()`, the memory of the > object is collected, a new object (of the same or different type) can > have been placed there. You will then read an arbitrary piece of data > from that new object, which may or may not evaluate to `true`. In this case the object cannot be collected by gc because there is still a good reference to it (variable 'a'). I agree if delete was used instead of destroy that is would be unsafe. -- dano
Re: Are there any methods like isDestroyed or isDisposed to detect whether some object is destroyed or not?
On Sunday, 14 December 2014 at 16:05:13 UTC, Dan Olson wrote: "Marc "Schütz\"" writes: On Saturday, 13 December 2014 at 21:20:43 UTC, Andrey Derzhavin wrote: import std.stdio; class ObjectAType { bool ok; this() {ok = true;} } void main() { auto a = new ObjectAType; assert(a.ok); destroy(a); assert(!a.ok); // a has been destroyed. } This method of detection of collected objects is what I needed. Thanks to everybody for your advise. Be careful - the memory could still have been reused. For example: assert(a.ok); destroy(a); // ... lots of code, maybe multi-threaded ... assert(!a.ok);// can fail If between `destroy()` and the second `assert()`, the memory of the object is collected, a new object (of the same or different type) can have been placed there. You will then read an arbitrary piece of data from that new object, which may or may not evaluate to `true`. In this case the object cannot be collected by gc because there is still a good reference to it (variable 'a'). I agree if delete was used instead of destroy that is would be unsafe. -- dano Right, but I see it only as a simplified example. In a real program, that reference will most likely be a member of object whose destructor is being run.
Re: Are there any methods like isDestroyed or isDisposed to detect whether some object is destroyed or not?
On 12/13/14 2:03 AM, Andrey Derzhavin wrote: Hello! We have object, for example, objA. ObjectAType objA = new ObjectAType(...); // we have a many references to objA void someFunction1(...) { // destroying the objA destroy(one_of_the_refToObjA); // } void someFunction2() { // "segmentation fault" if the objA is destroyed another_refToObjA.method1(); // I need a safe way (without using signals) to detect whether object // destroyed or not, like this // if (!isDestroyed(another_refToObjA)) // another_refToObjA.method1(); } // call functions someFunction1(..); // . some other operations... // the objectA (objA) is destroyed, but debugger shows us a not null reference // to that objA. However, when we try to call some methods of objectA or // try to use it's variables we get a "segmentation fault" error (in // someFunction2, when objA is destroyed). someFunction2(...); Yes, you can tell if the typeinfo pointer is null, this is how the runtime does it. Unfortunately, typeid(objA) uses the pointer to look up the most derived type and results in a segfault. You can use the knowledge of the object layout (the typeinfo pointer is the first item in the memory block) to ascertain whether it's null or not, it's what the runtime does: bool isDestroyed(Object o) { return o is null || *(cast(void **)o) is null; } Although, I highly recommend not doing this. Instead of destroying an object, leave the object live and dispose of it using some other method (e.g. close, dispose, etc.). Then let the GC clean up the memory later when nothing refers to it. -Steve
Re: Are there any methods like isDestroyed or isDisposed to detect whether some object is destroyed or not?
Thank you very much, Steven!