views:

478

answers:

2

I am trying to call an unmanaged C++ function, that has a structure as an input parameter. The structure is defined in the header file like this:

struct MyStruct
{
int     siOrder;
char     aaszNames[6][25];
int     siId[6];
int     siTones[6];        
};

I tried to declare the managed struct as following:

[StructLayoutAttribute(LayoutKind.Sequential, CharSet=CharSet.Ansi)]
public struct MyStruct {

public int siOrder;

[MarshalAsAttribute(UnmanagedType.ByValTStr, SizeConst=150)]
public string aaszNames;

[MarshalAsAttribute(UnmanagedType.ByValArray, SizeConst=6, ArraySubType=UnmanagedType.I4)]
public int[] siId;

[MarshalAsAttribute(UnmanagedType.ByValArray, SizeConst=6, ArraySubType=UnmanagedType.I4)]
public int[] siTones;
}

But without any success. I am guessing that the marshaling fails, since the aaszNames is actually an array of six 25 long null-terminating strings. I tried declaring aaszNames as

 [MarshalAsAttribute(UnmanagedType.ByValArray, SizeConst=150)]
 public char[] aaszNames;

filling the array with nulls where necessary. But, again, nothing.

Is there something I am missing? What am I dong wrong? What is the best way to marshal this 2-D char array?

Any hints, please.

A: 
[MarshalAsAttribute(UnmanagedType.ByValArray, SizeConst=150)]
 public char[] aaszNames;

That marshalling type looks well. Probably issue in function call, or bad memory allocation/

necrostaz
The function I am calling, has one more structure as a parameter, with which I have no problem. What exactly do you mean with bad memory allocation?
TTheot
1. How you alloc a memory for your struct?2. Best way for marshal struct as input function parameter is pointer(IntPtr).Typical example:IntPtr strPtr = Marshal.AllocHGlobal(Marshal.SizeOf(typeof(StructType)));Marshal.StructureToPtr(struct,strPtr);Foo(strPtr);Marshal.FreeHGlobal(strPtr);
necrostaz
I really do not alloc memory manually. I am aware of that example, but since I manage to successfully pass the other (simpler) struct as input parameter in the same function, and in several others, I thought that leaving this to .NET would also work.
TTheot
A: 

I would write a small c-program to check the byte size of the C-structure.
Then I would go with the other suggestion to extract the data field by field.
From a C standpoint the /0 is treated as normal character included in the 6 bytes whereas C# would use a length of 5 and have the /0 hidden.

weismat