2009-02-03 39 views
7

Với tuyên bố C API này, nó sẽ được nhập vào C# như thế nào?Làm cách nào để nhập const char * API thành C#?

const char* _stdcall z4LLkGetKeySTD(void); 

tôi đã có thể để có được điều này cho đến nay:

[DllImport("zip4_w32.dll", 
     CallingConvention = CallingConvention.StdCall, 
     EntryPoint = "z4LLkGetKeySTD", 
     ExactSpelling = false)] 
    private extern static const char* z4LLkGetKeySTD(); 

Trả lời

12

Hãy thử điều này

[DllImport("zip4_w32.dll", 
     CallingConvention = CallingConvention.StdCall, 
     EntryPoint = "z4LLkGetKeySTD", 
     ExactSpelling = false)] 
    private extern static IntPtr z4LLkGetKeySTD(); 

Sau đó bạn có thể chuyển đổi kết quả vào một String bằng cách sử dụng Marshal.PtrToStringAnsi(). Bạn vẫn cần phải giải phóng bộ nhớ cho IntPtr bằng cách sử dụng phương thức Marshal.Free * thích hợp.

+0

Làm cách nào để biết phương thức Marshal.Free * nào nên được sử dụng? –

+0

@thelaughingdm, nó phụ thuộc vào cách bộ nhớ được cấp phát. Marshal.FreeCoTaskMemAlloc giải phóng CoTaskMemAlloc gốc. Mỗi cái đều hoạt động với một phương thức riêng – JaredPar

2

Chỉ cần sử dụng 'string' thay vì 'const char *'.

Chỉnh sửa: Điều này là nguy hiểm vì lý do mà JaredPar giải thích. Nếu bạn không muốn sử dụng miễn phí, đừng sử dụng phương pháp này.

+0

Bạn lấy lời ra khỏi miệng của tôi! – leppie

+0

Chắc chắn không sử dụng String. Nếu sự trở lại của một hàm là một Chuỗi thì CLR sẽ cố gắng CoTaskMemFree con trỏ tự nhiên mà có khả năng không phải là những gì người dùng muốn ở đây – JaredPar

+1

http://msdn.microsoft.com/en-us/magazine/cc164193.aspx dưới cùng của paragrah theo hình 8 – JaredPar

4

Luôn sử dụng C++ const char * hoặc char * và không std :: string.

Cũng nên nhớ rằng char trong C++ là một sbyte trong C# và unsigned char là một byte trong C#.

Bạn nên sử dụng mã không an toàn khi giao dịch với DllImport.

[DllImport("zip4_w32.dll", 
    CallingConvention = CallingConvention.StdCall, 
    EntryPoint = "z4LLkGetKeySTD", 
    ExactSpelling = false)] 
private extern static sbyte* or byte* z4LLkGetKeySTD(); 

void foo() 
{ 
    string res = new string(z4LLkGetKeySTD()); 
} 
Các vấn đề liên quan