Я пытаюсь создать обертку C++/CLI для некоторых родных DLL. Есть семь из этих DLL и больше в будущем, поэтому мне нужно загрузить их динамически. Все они имеют один и тот же набор функций. LoadLibrary и GetProcAddress отлично работали в приложении для загрузки этих функций.Wrapper для собственных функций
Всякий раз, когда я загружаю DLL и вызываю Initialize, я получаю AccessViolationException. Im тестирование с помощью приложения C# Console с выбранной платформой x86.
ОБНОВЛЕНИЕ: Не знаете, почему я проголосовал. На этот вопрос не ответил ни один из моих поисковых запросов. Я искал полчаса, прежде чем даже спросил. Все вопросы здесь примерно то же самое, используя другой метод. MSDN говорит, что AccessViolations в собственном взаимодействии являются признаком серьезных ошибок программирования. Я не вижу, что я делаю неправильно. Я сортирую свои строки и проверяю nullptrs перед вызовом. Функции загрузки, похоже, работают. Если я использую известные имена неправильных функций или неверный путь к DLL, он говорит мне, что загрузка не удалась. Если я ввожу правильные имена путей/функций, в нем говорится, что все сработало, но затем сбой, когда я пытаюсь его вызвать. Функция TSInit для DLL, которую я тестирую, фактически ничего не делает в этой конкретной DLL, однако она может сделать некоторую фактическую работу для других DLL с тем же интерфейсом.
Update 2:
Я думаю, этот вопрос без ответа. Как я уже сказал, есть несколько DLL с одним и тем же интерфейсом. Теперь я обнаружил, что некоторые из них работают, а некоторые нет. Я проверил все их с помощью dumpbin, чтобы подтвердить, что все они составлены x86, и они есть. Я не уверен, что не так с DLL, которые не работают. В родных приложениях C++ все они работают так, как ожидалось.
typedef long (WINAPI *TSRINIT)(long lType, HWND hParent, RECT *pRect);
namespace Imagery
{
public ref class Recongizer
{
public:
Recongizer(String^ DllPath) { LoadRecongizer(DllPath); }
~Recongizer() { UnloadLibrary(); }
bool LoadRecongizer(String^ DllPath)
{
HInstance = ::LoadLibrary(msclr::interop::marshal_as<std::wstring>(DllPath).c_str());
if (HInstance == nullptr) return false;
if (!LoadFunctions()) return false;
return true;
}
long Initalize(long lType)
{
if (HInstance == nullptr || TSInit == nullptr) return 0;
return TSInit(0, nullptr, nullptr);
}
private:
void UnloadLibrary()
{
if (HInstance != nullptr) ::FreeLibrary(HInstance);
}
bool LoadFunctions()
{
TSInit = (TSRINIT)::GetProcAddress(HInstance, "TSRInit");
if (TSInit == nullptr)
{
ErrorMessage = "TSRInit could not be loaded.";
return false;
}
return true;
}
property String^ ErrorMessage;
private:
HINSTANCE HInstance{ nullptr };
TSRINIT TSInit{ nullptr };
};
}
Вы не можете получить диагностику для такого неопределенного вопроса. Начните с * not * с помощью LoadLibrary(), нет никакого смысла в этом. Просто свяжите библиотеки импорта этих DLL и #include соответствующие файлы .h. Три режима отказа. –
Нарушения доступа не являются волшебными. Например, у вас есть трассировка стека. – MSalters