PInvoke и char ** - PullRequest
       27

PInvoke и char **

3 голосов
/ 12 мая 2011

Я получил эту сборку от кого-то, кого я хотел бы использовать в моем приложении на c #.

Заголовок выглядит так:

int __declspec(dllimport) s2o(WCHAR* filename, char** out, int* len);

Мне удалось заставить его работать частично,используя:

[DllImport("s2o.dll", EntryPoint = "?skn2obj@@YAHPA_WPAPADPAH@Z", CallingConvention = CallingConvention.Cdecl)]
public static extern int s2o(
    [MarshalAs(UnmanagedType.LPWStr)]
    string filename,
    ref char[] @out,
    ref int len
);

И затем вызывая его так:

char[] result = null;
int length = 0;
s2o("filepath", ref result, ref length);

Кажется, что это работает частично, потому что «длина» фактически получает значение.К сожалению, «результат» остается нулевым.

Что я должен сделать, чтобы это работало?

Редактировать:

Хорошо, мне удалось добраться дозамените char [] на IntPtr, а затем вызовите Marshal.PtrToStringAnsi, как предложил Ник:

string result = Marshal.PtrToStringAnsi(ptr);

Однако из-за комментариев в том же ответе я немного беспокоюсь об использовании памяти,В сборке нет других методов, так как я могу все прояснить?

Ответы [ 2 ]

6 голосов
/ 12 мая 2011

О вашем последнем вопросе:

  • char - это один символ.
  • char* - указатель на символ.Если это интерпретируется как строка, все данные в памяти, которые следуют за этим адресом памяти, будут рассматриваться как принадлежащие этой строке, пока не встретится значение с 0x0.Передача char* в метод означает, что этот метод может изменять содержимое строки, но не ее длину.
  • char** - указатель на указатель на символ.Передача этого метода означает, что метод может создать новую строку и вернуть новый адрес вызывающей стороне.
3 голосов
/ 12 мая 2011

Взгляните на Marshal.PtrToStringAnsi Метод.

Или, как говорит Centro в комментарии к вашему вопросу, PtrToStringAuto может быть более подходящим.

Копирует все символы до первого нулевой символ из неуправляемого ANSI строка в управляемую строку и расширяется каждый символ ANSI в Unicode.

Также обратите внимание, что вы можете нести ответственность за освобождение памяти, возвращаемой этой функцией.

...