The Win32 HANDLE type under D2

Stewart Gordon smjg_1998 at yahoo.com
Sun Feb 5 08:13:14 PST 2012


On 04/02/2012 19:40, Yao Gomez wrote:
<snip>
> Just use the Win32 API way when STRICT is defined:
>
> ---
> struct HANDLE__{ int unused; }
> alias HANDLE__* HANDLE;
<snip>

Looking through MinGW, this is the code:

#ifdef STRICT
typedef void *HANDLE;
#define DECLARE_HANDLE(n) typedef struct n##__{int i;}*n
#else
typedef PVOID HANDLE;
#define DECLARE_HANDLE(n) typedef HANDLE n
#endif

so a HANDLE is just a void*, but DECLARE_HANDLE creates a struct as you describe.

This seems to be a hack to create a strong typedef in C, which works as long as the base 
type is void*.  Unfortunately, types (such as HGDIOBJ) can't by this means be made 
subtypes of HANDLE and then have subtypes of their own (such as HBRUSH, HPEN, HBITMAP). 
So HGDIOBJ has just been made a void*.

But is its being void* in the first place because it's actually a pointer, or is it a hack 
to accommodate subtypes in this way?  (I've a recollection of a handle being just an 
integer in Win16.)

FWIW I've just been experimenting with this idea
-----
struct HANDLE {
     void* h;
     alias h this;
}

template DECLARE_HANDLE(string name, base = HANDLE) {
     mixin ("struct " ~ name ~ " {
         " ~ base.stringof ~ " h;
         alias h this;
     }");
}

mixin DECLARE_HANDLE!("HWND");
mixin DECLARE_HANDLE!("HGDIOBJ");
mixin DECLARE_HANDLE!("HPEN", HGDIOBJ);
-----
but found that it allows implicit conversions between all handle types, not just up the 
hierarchy.  Is this a bug?

Stewart.


More information about the Digitalmars-d mailing list