Thread overview | |||||
---|---|---|---|---|---|
|
October 25, 2006 weak pointers for Objects and delegates pointing to Objects | ||||
---|---|---|---|---|
| ||||
Attachments: | Who said D didn't support weak pointers? # private import internal.gc.gcbits; # private import internal.gc.gclinux; # private import internal.gc.gcx; # private import std.utf; # private import std.gc; # # class WeakPointerException : Exception{ # this(char[] msg){ # super(msg); # } # } # # class WeakPointer(T){ # private size_t[] hidden; # # this(T data){ # Object o; # static if(is(T == delegate)){ # o = getObject(data.ptr); # }else static if(is(T : Object)){ # o = data; # }else{ # static assert(0, "only delegates and Objects are supported"); # } # # if(!o){ # throw new WeakPointerException("destination not an Object"); # } # # synchronized(o){ # hidden = new size_t[T.sizeof]; # ubyte[] raw = (cast(ubyte*)&data)[0 .. T.sizeof]; # foreach(size_t i, ubyte element; raw){ # hidden[i] = element; # } # # o.notifyRegister(&dead); # } # } # # void dead(Object o){ # if(hidden.length && !o){ # static if(is(T == delegate)){ # (cast(Object)get().ptr).notifyUnRegister(&dead); # }else{ # get().notifyUnRegister(&dead); # } # } # hidden.length = 0; # } # # private static Object getObject(void* ptr){ # gc_t handle = cast(gc_t) getGCHandle(); # Gcx* engine = handle.gcx; # # Pool* pool = engine.findPool(ptr); # if(!pool){ # return null; # } # # Object o = cast(Object) ptr; # if(!o){ # return null; # } # # ClassInfo ci = o.classinfo; # if(!ci){ # return null; # } # # if(ci.name.length > (1 << 12)){ # return null; # } # # try{ # std.utf.validate(ci.name); # }catch{ # return null; # } # # return o; # } # # T get(){ # if(hidden.length < T.sizeof){ # throw new WeakPointerException("delegate isn't valid anymore"); # } # T result; # ubyte[] raw = (cast(ubyte*)&result)[0 .. T.sizeof]; # foreach(size_t i, size_t element; hidden){ # raw[i] = cast(ubyte)element; # } # return result; # } # # ~this(){ # dead(null); # } # } Usage sample: # import std.stdio; # # int main(){ # WeakPointer!(Object) weak; # # { # auto Object o = new Object(); # weak = new WeakPointer!(typeof(o))(o); # # try{ # weak.get(); # writefln("WEAK: is valid"); # }catch{ # writefln("WEAK: isn't valid"); # } # } # # try{ # weak.get(); # writefln("WEAK: is valid"); # }catch{ # writefln("WEAK: isn't valid"); # } # # return 0; # } Don't be irritated by additional output. http://d.puremagic.com/issues/show_bug.cgi?id=457 Thomas |
October 26, 2006 Re: weak pointers for Objects and delegates pointing to Objects | ||||
---|---|---|---|---|
| ||||
Posted in reply to Thomas Kuehne | Thomas Kuehne wrote:
> Who said D didn't support weak pointers?
So is this "problem solved?" Are there any issues or limitations with the weak pointer code you posted? If not, Great!
Weak refs were one of the last pieces of the puzzle for implementing rock-solid signals/slots from what I understood.
--bb
|
October 26, 2006 Re: weak pointers for Objects and delegates pointing to Objects | ||||
---|---|---|---|---|
| ||||
Posted in reply to Bill Baxter Attachments: | Bill Baxter schrieb am 2006-10-26:
> Thomas Kuehne wrote:
>
>> Who said D didn't support weak pointers?
>
> So is this "problem solved?" Are there any issues or limitations with the weak pointer code you posted? If not, Great!
Limitation:
Only objects and delegates pointing to object member functions are
supported.
I haven't yet looked through the GC code, but adding support
for all GC allocated types ought to be possible without major changes
there. Weak pointers to array elements though will most likely be impossible
without major changes.
Using GCC/GDC's "-finstrument-functions" should allow weak pointers for
all types stored on the stack as a pure library implementation. For
DMD that would require "-profile" as well as hijacking internal/trace.d.
Thomas
|
Copyright © 1999-2021 by the D Language Foundation