January 19, 2002 Re: vtable | ||||
---|---|---|---|---|
| ||||
Posted in reply to Walter | "Walter" <walter@digitalmars.com> wrote in message news:a2ad4l$128$1@digitaldaemon.com... > COM requires: > 1) the first entry in an object is a vptr > 2) the layout of the vtbl[] is exactly like C++ single inheritance > 3) stdcall calling conventions > 4) AddRef() and Release() memory management. > D Interfaces fail (1), (3), (4). Why (3)? Isn't extern(Windows) applicable to methods? I remember you used extern(C) for OutBuffer.printf() (and so did I for Stream.printf(), then =)), and it worked... > The solution is to recognize a special root object (strangely enough called > "IUnknown" <g>). Deriving from this, instead of from Object, means you wind > up with a COM style vtbl[], and it also sets the function calling conventions to stdcall. This has some effects like you can't do a .classinfo > on a COM object (no rtti). COM objects are also reference counted, and are not on the garbage collected heap. It's pretty okay. > It will be possible to write DLLs in D, I just haven't written the necessary > library support for it yet. ...which is pretty possible to do ourselves, right? Isn't is as simple as providing our own version of dmain2.d? |
January 19, 2002 Re: vtable | ||||
---|---|---|---|---|
| ||||
Posted in reply to Walter | "Walter" <walter@digitalmars.com> wrote in message news:a2ad7v$12e$1@digitaldaemon.com... > It's a great idea, but doesn't work if functions are overloaded. -Walter Overloaded ones could be skipped: enum vtable { foo, // foo bar = foo + 2, // bar, // bar, baz = bar + 3, } |
January 19, 2002 Re: vtable | ||||
---|---|---|---|---|
| ||||
Posted in reply to Pavel Minayev | Or even: enum vtable { foo, // bar, // bar, // bar, baz = foo + 4 } So no pointers for overloaded functions. Who needs them anyhow? =) |
January 19, 2002 Re: vtable | ||||
---|---|---|---|---|
| ||||
Posted in reply to Walter | Walter wrote:
> The solution is to recognize a special root object (strangely enough called
> "IUnknown" <g>). [details omitted]
>
> It sounds wartier than it actually is.
Actually, from the outside it sounds pretty elegant, even if
it's warty on the inside.
-RB
|
January 19, 2002 Re: vtable | ||||
---|---|---|---|---|
| ||||
Posted in reply to Pavel Minayev | "Pavel Minayev" <evilone@omen.ru> wrote in message news:a2aes3$24o$1@digitaldaemon.com... > "Walter" <walter@digitalmars.com> wrote in message news:a2ad4l$128$1@digitaldaemon.com... > > > COM requires: > > 1) the first entry in an object is a vptr > > 2) the layout of the vtbl[] is exactly like C++ single inheritance > > 3) stdcall calling conventions > > 4) AddRef() and Release() memory management. > > > D Interfaces fail (1), (3), (4). > > Why (3)? Isn't extern(Windows) applicable to methods? I remember > you used extern(C) for OutBuffer.printf() (and so did I for > Stream.printf(), then =)), and it worked... Yes, the extern works with methods. It just isn't the default. > > The solution is to recognize a special root object (strangely enough > called > > "IUnknown" <g>). Deriving from this, instead of from Object, means you > wind > > up with a COM style vtbl[], and it also sets the function calling conventions to stdcall. This has some effects like you can't do a > .classinfo > > on a COM object (no rtti). COM objects are also reference counted, and are > > not on the garbage collected heap. > > It's pretty okay. > > > It will be possible to write DLLs in D, I just haven't written the > necessary > > library support for it yet. > > ...which is pretty possible to do ourselves, right? Isn't is as simple as providing our own version of dmain2.d? Yeah, that's about it. |
January 19, 2002 Re: vtable | ||||
---|---|---|---|---|
| ||||
Posted in reply to Pavel Minayev | "Pavel Minayev" <evilone@omen.ru> wrote in message news:a2aik2$4l7$1@digitaldaemon.com... > Or even: > > enum vtable > { > foo, > // bar, > // bar, > // bar, > baz = foo + 4 > } > > So no pointers for overloaded functions. > Who needs them anyhow? =) I suppose this would be rather iky? enum vtable { foo_v, bar_i, bar_icda, bar_f, baz } // i = int, c = char, da = dynamic array, f = float or better yet thing.classinfo.method{"int bar(int)"]; thing.classinfo.method{"int bar(char[])"]; Walter, are functions in D overloadable on return type? |
January 19, 2002 Re: vtable | ||||
---|---|---|---|---|
| ||||
Posted in reply to Patrick Down | "Patrick Down" <pdown@austin.rr.com> wrote in message news:a2b3lv$f6a$1@digitaldaemon.com... > I suppose this would be rather iky? > > enum vtable > { > foo_v, > bar_i, > bar_icda, > bar_f, > baz > } // i = int, c = char, da = dynamic array, f = float Yep, because imagine a user trying to build the name of the function out of its arguments (because he doesn't see that compiler-generated enum). I must say that, having worked with Delphi for a long time, I don't remember any program that took a function pointer to an overloaded function. This is something that can be sacrificed, IMO. > thing.classinfo.method{"int bar(int)"]; > thing.classinfo.method{"int bar(char[])"]; This moves most of the code to run-time (since with enum we already have positions in vtable, and here it has to find a key in an associative array). |
January 19, 2002 Re: vtable | ||||
---|---|---|---|---|
| ||||
Posted in reply to Pavel Minayev | Okay, so it turned out to be not that simple... Since extern(D) - the default - doesn't specify order of arguments strictly, it cannot be used in low-level, so methods we want to get pointers to have to be extern(C). The problem is, such methods don't reside in the vtable - they are called directly! So, once again, the only way to get a pointer to it is some special operator, or something... |
January 19, 2002 Re: no vtable? - not so fast... | ||||
---|---|---|---|---|
| ||||
Posted in reply to Pavel Minayev | I should have thought twice before posting... =) Now, I came to the working solution, which seems perferctly portable. The idea is to define a base class for all classes that want pointers to their functions (most frequently it's class itself who uses pointers to its methods anyhow), and let it contain a dummy entry in the vtable - just an empty function - which then gets substituted by whatever pointer we have. So: class Component: Object { // should be the very first void _event_callback(void* ptr) { } } Component obj; ... // put pointer to our callback method into the vtable... obj.classinfo.vtable[Object.classinfo.vtable.length] = our_function_pointer; // ...and call it! obj._event_callback(pointer_to_some_data); Unfortunately D doesn't allow class.classinfo (only object.classinfo) - btw a feature request, Walter! =) - but nothing stops us from creating a temporary Object in static constructor and getting it's vtable.length... So if we get the method-list enumeration, method pointers can be considered there. |
January 19, 2002 Re: vtable | ||||
---|---|---|---|---|
| ||||
Posted in reply to Russell Borogove | "Russell Borogove" <kaleja@estarcion.com> wrote in message news:3C48E52C.10801@estarcion.com... > Walter wrote: > > > The solution is to recognize a special root object (strangely enough called > > "IUnknown" <g>). [details omitted] > > > > It sounds wartier than it actually is. > > > Actually, from the outside it sounds pretty elegant, even if it's warty on the inside. > > -RB Indeed, it does sound pretty elegant! Is the IUnknown root object part of the standard D libraries? Très Cool! I was delving into COM just before I learned of D, and I like both of them a lot, but I had I concern I couldn't mix coding with the two, so that would have been a shame. It is great to hear that not only is it supported, but that it is actually cleaner to do than in C++! -- Stijn OddesE_XYZ@hotmail.com http://OddesE.cjb.net __________________________________________ Remove _XYZ from my address when replying by mail |
Copyright © 1999-2021 by the D Language Foundation