Я пытаюсь написать оболочку C ++ / CLI, используя VS2010, против API C ++, для которого у меня есть доступ только к заголовочным файлам и файлу dll / lib.
У меня возникла проблема с копированием резервной копии нативной ссылки из нативного кода в ссылку на отслеживание в коде C #. Я получаю SystemAccessViolation. Код выглядит следующим образом:
Неуправляемые собственные заголовки C ++ для собственных функций, которые возвращают ссылку на создание, а также на изменение пользовательского объекта:
class ManageCustomObject;
_declspec(dllimport) errorCode CreateCustomObject(CustomObject& customObject);
_declspec(dllimport) errorCode ModifyCustomObject(CustomObject& customObject);
Важно отметить, что CustomObject имеет только частные конструкторы:
CustomObject(const CustomObject&) { }
CustomObject& operator=(const CustomObject&) { return *this; }
Теперь мой метод уровня C ++ / CLI выглядит следующим образом:
public ref class WrapperManageCustomObject {
public:
errorCode WrapperCreateCustomObject(CustomObject% customObject)
{
return CreateCustomObject(customObject);
}
errorCode WrapperModifyCustomObject(CustomObject% customObject)
{
return ModifyCustomObject(customObject);
}
};
И оболочка для CustomObject выглядит следующим образом:
public class WrapperCustomObject : public CustomObject {
public:
WrapperCustomObject(const CustomObject&) {};
};
В C # код выглядит следующим образом:
WrapperCustomObject wrapperCustomObject;
WrapperManageCustomObject wrapperManageCustomObject = new WrapperManageCustomObject();
long result;
// this works great
result = wrapperManageCustomObject.CreateCustomObject(ref wrapperCustomObject);
// can utilize wrapperCustomObject here with other native functions no problem, so long as I don't try to modify it...
...
// this throws an AccessViolationException was unhandled message
// essentially I am modifying / returning a different native customObject (though I'm not 100% sure what it does as I do not have access to the code)
result = wrapperManageCustomObject.ModifyCustomObject(ref wrapperCustomObject);
Как вы можете видеть в моих комментариях, попытка изменить этот объект с помощью ссылки выдает «AccessViolationException не обработан: попытка чтения или записи защищенной памяти. Это часто указывает на то, что другая память повреждена».
Теперь, если я исключу из этого уравнения C # и ссылку на отслеживание и сделаю все это в C ++ или C ++ / CLI (если ссылка на отслеживание отсутствует), это работает нормально. Я предполагаю, что это как-то связано с собственным кодом, пытающимся получить доступ к обновлению ссылки, которая теперь находится в управляемой земле.
Есть ли способ обойти это, чтобы по существу заставить этот код "работать" изнутри C #? Нет способа передать нативную ссылку на C #, о которой я знаю.