This table shows how the data types used in the Win32 API, should be expressed in Managed C++ (VC7) and Managed VB (VB7) in order for PInvoke to correctly marshal your data.
wtypes.h | Unmanaged C | VC7 | VB7 | Additional Info |
---|---|---|---|---|
HANDLE | void* | void* | Long | |
BYTE | unsigned char | unsigned char | Byte | |
SHORT | short | short | Integer | 2 bytes |
WORD | unsigned short | unsigned short | Integer | 2 bytes |
INT | int | int | Long | 4 bytes |
UINT | unsigned int | unsigned int | Long | 4 bytes |
LONG | long | int | Long | 4 bytes |
BOOL | long | int | Long | 4 bytes |
DWORD | unsigned long | unsigned int | Long | 4 bytes |
ULONG | unsigned long | unsigned int | Long | 4 bytes |
CHAR | char | char | Char | |
LPSTR | char* | String for in, StringBuilder* for inout | String | decorate with ansi |
LPCSTR | const char* | String | String | decorate with ansi |
LPWSTR | wchar_t* | String for in, StringBuilder* for inout | String | decorate with unicode |
LPCWSTR | const wchar_t* | String | String | decorate with unicode |
FLOAT | float | float | Single | 4 bytes |
DOUBLE | double | double | Double | 8 bytes |
For simple number types, PInvoke simply copies the bits, without any conversion. This includes the NGWS runtime data types for 1, 2, 4, and 8 byte integers; 1, 2, 4, and 8 byte unsigned integers; and 4 and 8 byte real numbers.
The NGWS runtime also supports data types for agnostic-sized integers and reals.
PInvoke copies string arguments, converting from the NGWS runtime format (Unicode) to the platform unmanaged format. Strings are treated as immutable, so they are not copied back from unmanaged to managed space when the function returns.
On the other hand, PInvoke does copy back any argument of type StringBuilder, since this is a mutable string. Notice that this simulates "by-reference" semantics by using copy-in/copy-out.
These are not permitted to be pointers to garbage-collected (managed) memory. They are copied directly, providing a mechanism for passing references to (unmanaged) data.
PInvoke handles arguments that are specified as Object (the root of the VOS class hierarchy) as a special case. Specifying an argument as Object indicates that the data type isn't known at compile or link time, but can be determined at runtime. The value being passed must be a managed object (this will be enforced by static type checking) and must be one of the following types (which are then handled as described separately):
Platform Invocation Services handles arguments that are marked as an NGWS runtime interface type by extracting the "classic COM" interface pointer and passing it to the unmanaged code. Interfaces are immutable and are therefore not copied back out.