- 我無法完全訪問DLL源,只有標題。
- 在我的實際代碼的參數的名稱是更具描述性的
嗨,我試圖讓一個非託管的DLL,它接受所有字符通話*變量,其中兩個作爲「返回」值。 in1-8是輸入,in9和10是長度爲512的char *,並且是空的。通話完成後,應該填寫結果數據。如何傳遞和接收來自C#的char *到非託管C++ DLL的數據
下面是我試圖一起工作的樣本定義:
[DllImport("mydll.dll")]
public static extern IntPtr foo(
IntPtr in1,
IntPtr in2,
IntPtr in3,
IntPtr in4,
IntPtr in5,
IntPtr in6,
IntPtr in7,
IntPtr in8,
ref IntPtr result1,
ref IntPtr result2);
這裏是我的電話:
IntPtr param1 = Marshal.StringToHGlobalUni("testdata");
IntPtr param2 = Marshal.StringToHGlobalUni("testdata");
IntPtr param3 = Marshal.StringToHGlobalUni("testdata");
IntPtr param4 = Marshal.StringToHGlobalUni("testdata");
IntPtr param5 = Marshal.StringToHGlobalUni("testdata");
IntPtr param6 = Marshal.StringToHGlobalUni("testdata");
IntPtr param7 = Marshal.StringToHGlobalUni("testdata");
IntPtr param8 = Marshal.StringToHGlobalUni("testdata");
IntPtr param9 = IntPtr.Zero;
IntPtr param10 = IntPtr.Zero;
foo(param1, param2, param3, param4, param5, param6, param7, param8, ref param9, ref param10);
要打印一個IntPtr,我這樣做:
string str = Marshal.PtrToStringUni(param9);
Console.WriteLine(str);
在給我的「示例」中,C++調用如下所示:
char result1[512]="";
char result2[512]="";
foo("testdata", "testdata", "testdata", "testdata", "testdata", "testdata", "testdata", "testdata", result1, result2);
printf("%s,%s\n",result1,result2);
問題:在我試過的每種方法中,包括char [512]轉換爲byte [],StringBuilder大小512,IntPtr等等。param9和param10值在每個返回時都是空的。任何人都可以幫我解決這個問題嗎?提前致謝。
編輯 經過下面的一些有用的評論和更多的谷歌搜索後,我修補了我亂碼的工作。這裏的編輯:
[DllImport("mydll.dll")]
public static extern IntPtr foo(
IntPtr in1,
IntPtr in2,
IntPtr in3,
IntPtr in4,
IntPtr in5,
IntPtr in6,
IntPtr in7,
IntPtr in8,
IntPtr result1,
IntPtr result2);
我擺脫了兩個結果字符數組的ref。
IntPtr param1 = Marshal.StringToHGlobalAnsi("testdata");
IntPtr param2 = Marshal.StringToHGlobalAnsi("testdata");
IntPtr param3 = Marshal.StringToHGlobalAnsi("testdata");
IntPtr param4 = Marshal.StringToHGlobalAnsi("testdata");
IntPtr param5 = Marshal.StringToHGlobalAnsi("testdata");
IntPtr param6 = Marshal.StringToHGlobalAnsi("testdata");
IntPtr param7 = Marshal.StringToHGlobalAnsi("testdata");
IntPtr param8 = Marshal.StringToHGlobalAnsi("testdata");
IntPtr param9 = Marshal.AllocHGlobal(512 * sizeof(int));
IntPtr param10 = Marshal.AllocHGlobal(512 * sizeof(int));
foo(param1, param2, param3, param4, param5, param6, param7, param8, param9, param10);
上面我分配param9和10,而不是IntPtr.Zero
//printing..
string str = Marshal.PtrToStringAnsi(param9);
而且使用字符串,由於下面的答案一個更簡單的方法:
[DllImport("mydll.dll")]
public static extern IntPtr foo(
string in1,
string in2,
string in3,
string in4,
string in5,
string in6,
string in7,
string in8,
StringBuilder result1,
StringBuilder result2);
則:
StringBuilder resultA = new StringBuilder(512);
StringBuilder resultB = new StringBuilder(512);
foo("test", "test", "test", "test", "test", "test", "test", "test", resultA, resultB);
印刷:
Console.WriteLine(resultA.ToString());
現在看起來好多了,實際上現在的工作,謝謝你們!很容易混淆打開50個谷歌搜索標籤。
可能的重複http://stackoverflow.com/questions/803488/marshalling-c-dll-code-into-c-sharp – slfan
您是否嘗試過沒有ref參數的StringBuilder?我認爲這應該工作。 – slfan
@slfan,我已經嘗試過沒有在StringBuilder上的參考,它仍然是空的。感謝您的建議! – ayjis