user2597781
user2597781

Reputation: 9

Marshal C++ to C# structs with unions of structs

I'm not an expert in COM or C++/C# marshaling and could use some help with this scenario:

Native Code:

typedef struct _Foo {
    FooType a; // enum
    WCHAR b[16];
    WCHAR c[16];
    BOOL d;
    ULONG size;
} Foo;

typedef struct _Bar {
    GUID a;
    WCHAR b[16];
    WCHAR c[16];
    BOOL d;
} Bar;

typedef struct _Baz {
    FILETIME a;
    FILETIME b;
    ULONG c;
    ULONG d;
    GUID e;
} Baz;

typedef struct _FooBarBaz
{
    SomeType type; // enum

    [switch_is(type)] union
    {
        [case(SomeType.A)]
        Foo a;

        [case(SomeType.B)]
        Bar b;

        [case(SomeType.C)]
        Baz b;
    } data;
} FooBarBaz;

Managed Code:

[StructLayout(LayoutKind.Sequential)]
internal struct Foo
{
    public FooType a;

    [MarshalAs(UnmanagedType.ByValArray, SizeConst = 16)]
    public char[] b;

    [MarshalAs(UnmanagedType.ByValArray, SizeConst = 16)]
    public char[] c;

    [MarshalAs(UnmanagedType.Bool)]
    public bool d;

    [MarshalAs(UnmanagedType.U4)]
    public uint e;
}

[StructLayout(LayoutKind.Sequential)]
internal struct Bar
{
    public Guid a;

    [MarshalAs(UnmanagedType.ByValArray, SizeConst = 16)]
    public char[] b;

    [MarshalAs(UnmanagedType.ByValArray, SizeConst = 16)]
    public char[] c;

    [MarshalAs(UnmanagedType.Bool)]
    public bool d;
}

[StructLayout(LayoutKind.Sequential)]
internal struct Baz
{
    public ComTypes.FILETIME a;

    public ComTypes.FILETIME b;

    [MarshalAs(UnmanagedType.U4)]
    public uint c;

    [MarshalAs(UnmanagedType.U4)]
    public uint d;

    public Guid e;
}

internal struct FooBarBaz
{
    public SomeType Type;

    // ??????
}

I'm not sure how to convert / marshal the native struct FooBarBaz to managed code. Any tips would be appreciated here.

Upvotes: 0

Views: 1031

Answers (1)

Geod24
Geod24

Reputation: 893

A precious ressource about translation can be found here IMO, reading it worth every single page :)

About FooBarZ, you are looking for [FieldOffset(NBR)], which is the way to translate union.

Look at the translation in pinvoke of the STRRET struct for an example on how to use it.

Upvotes: 2

Related Questions