osiete03のプロフィール

@osiete03 osiete03
ありがとう数0
質問数1
回答数1
ベストアンサー数
1
ベストアンサー率
100%
お礼率
0%

  • 登録日2013/06/25
  • PINVOKEで構造体配列をマーシャルする方法

    Cで作ったdll内の関数を.NET(C#)のプログラムからPINVOKEを介して呼び出そうとしているのですが、構造体の配列を引数として渡すにはどうするべきかわかりません。データの流れる向きは、両方向 [In, Out] です。下記の方法を試してうまくいかないのですが、どこが悪いのでしょうか?下記サンプルはうまくいかないのですが、構造体の配列をメンバーに持った構造体を使ってデータを受け渡そうとしています。もしかして、IntPtrを使って自分でマーシャリングしないとできませんか? 助言いただきたく、おねがいいたします。 -- 呼び出し側 -- using System; using System.Runtime.InteropServices; using System.Text; namespace MarshalTest {   [StructLayout(LayoutKind.Sequential)]   class Data   {     private const int buffersize = 256;     [MarshalAs(UnmanagedType.I4)]     public int count;     [MarshalAs(UnmanagedType.ByValArray, ArraySubType = UnmanagedType.U1, SizeConst = buffersize)]     public Byte[] data;     public Data()     {       count = 0;       data = new Byte[buffersize];     }   }   [StructLayout(LayoutKind.Sequential)]   class DataBundle   {     private const int buffersize = 8;     [MarshalAs(UnmanagedType.I4)]     public int count;     [MarshalAs(UnmanagedType.ByValArray, ArraySubType = UnmanagedType.LPStruct, SizeConst = buffersize)]     public Data[] data;     public DataBundle()     {       count = 0;       data = new Data[buffersize];       for (int idx = 0; idx < buffersize; idx++)       {         data[idx] = new Data();       }     }   }   class Program   {     [DllImport("NativeDll.dll")]     private static extern void test1([Out] Data data);     [DllImport("NativeDll.dll")]     private static extern void test2([Out] DataBundle data);     static void Main(string[] args)     { #if false       // これはできます。       Data data = new Data();       test1(data);       System.Console.WriteLine(Encoding.ASCII.GetString(data.data, 0, data.count)); #else       // これができません。       DataBundle data = new DataBundle();       test2(data);       for (int idx = 0; idx < data.count; idx++)       {         System.Console.WriteLine(Encoding.ASCII.GetString(data.data[idx].data, 0, data.data[idx].count));       } #endif     }   } } -- 呼ばれ側 -- #include <Windows.h> extern "C" { #define MAX_DATA  256 #define MAX_BUNDLE  8   struct Data   {     int count;     char data[MAX_DATA];   };   struct DataBundle   {     int count;     Data data[MAX_BUNDLE];   };   __declspec(dllexport) void __stdcall test1(Data *data);   __declspec(dllexport) void __stdcall test2(DataBundle *data); }; void __stdcall test1(Data *data) {   const char *text = "osite !! goo !!";   data->count = strlen(text);   strcpy(data->data, text);   data->data[strlen(text)] = '\0'; } void __stdcall test2(DataBundle *data) {   const char *text = "osite !! goo !!";   for (int idx = 0; idx < MAX_BUNDLE; idx++)   {     strcpy(data->data[idx].data, text);     data->data[idx].data[strlen(text)] = '\0';   } } 以上です。