Заполнение неуправляемого массива в управляемом коде - PullRequest
0 голосов
/ 19 сентября 2011

У меня есть управляемая программа, которая взаимодействует с неуправляемой библиотекой DLL.

Библиотека создает объект, который просит (с помощью функции обратного вызова, преобразованной в делегат) управляемый хост заполнить неуправляемый массив.Сам массив передается через указатель (IntPtr) вместе с информацией о его размере.Тип известен обеим сторонам.Дело в том, как можно безопасно заполнить неуправляемый массив данными в управляемом коде?Применяются два ограничения: небезопасный код и, предпочтительно, дополнительные массивы не создаются.Массив может быть передан другим способом, если таковой существует.

Пусть обратный вызов имеет следующий прототип:

typedef void (__stdcall * FillData)(double * array, int count);

Пусть делегат имеет следующий прототип:

protected delegate void FillData(IntPtr array, int count);

Ответы [ 2 ]

2 голосов
/ 19 сентября 2011

Если вы не хотите небезопасного кода, вам придется позволить маршаллеру pinvoke скопировать массив. Объявите тип делегата следующим образом:

private delegate MyUnmanagedCallback(
     [MarshalAs(UnmanagedType.LPArray, SizeParamIndex=1)] double[] array,
     int count);

Обязательно сохраните объект делегата, чтобы его нельзя было собрать мусором.

0 голосов
/ 19 сентября 2011

Запись управляемого обратного вызова в соответствии с вашим прототипом FillData.Создайте из него указатель неуправляемой функции с помощью метода Marshal.GetFunctionPointerForDelegate.Передайте его неуправляемому коду в качестве указателя на функцию обратного вызова.

...