Member 13261094 Ответов: 2

Dll не загружается должным образом с помощью loadlibrary в VS 2019


Ниже приведен код DLL (скомпилированный в VS2019 v142, SDK 10,режим отладки), скомпилированный успешно. Загрузка этой библиотеки DLL с помощью LoadLibrary()в программе MFC(скомпилирована в VS2019 v142 , Sdk 10,режим отладки). Оба кода прекрасно работают в VS2010. Но не Уокинг в VS2017.

#include "stdafx.h"
#include "SiTempJCL.h"

#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif

BEGIN_MESSAGE_MAP(SiJCLTemplateDfltApp, CWinApp)
	
END_MESSAGE_MAP()


SiJCLTemplateDfltApp::SiJCLTemplateDfltApp()
{
	// TODO: add construction code here,
	// Place all significant initialization in InitInstance
}


SiJCLTemplateDfltApp theApp;

extern "C" __declspec( dllexport )

CSResult* FireRule(CObList& list)
{
	AFX_MAINTAIN_STATE2 *pState = new AFX_MAINTAIN_STATE2(AfxGetStaticModuleState());
	try 
	{
		
		CString *sJobTemplate;
		CString sDBUseCode="M";
		if((sDBUseCode == "M") || (sDBUseCode == "P")) {
			sJobTemplate = new CString("JOBM");
		}
		else {
			sJobTemplate = new CString("JOBC");
		}

		// Return JCL job template id
		CSResult *ruleRet = new CSResult();
		ruleRet->SetReturnObject((CObject *) sJobTemplate);

		delete pState;
		return ruleRet;
	}
	catch (...)
	{
		delete pState;
		throw;
	}
}


Что я уже пробовал:

Код для вызова вышеуказанной библиотеки DLL:
HINSTANCE         hModule;
hModule = LoadLibrary("SiJCLTemplate.dll");

SiLauncherApp* pSiBatchLauncherApp1 = (SiLauncherApp*)AfxGetApp();

Я проверил, что hModule не является нулевым, загрузив dll и вызвав функцию firerule.
но я думаю, что он не загружается должным образом. как и когда я проверяю
pSiBatchLauncherApp1
объект после loadlibrary, он показывает мне
{SiJCLTemplateDfltApp.dll!SiJCLTemplateDfltApp theApp<NULL>};
.


Я предполагаю, что есть какая-то проблема в коде DLL . возможно, потребуется небольшое изменение, которое не поддерживает MS2017.

Пожалуйста, проводите.

2 Ответов

Рейтинг:
0

Richard MacCutchan

Единственное, что я вижу, это то, что ваша dll не имеет своей функции DllMain, как описано в разделе Точка входа DllMain (Process.h) - Win32 apps | Microsoft Docs[^].


Shao Voon Wong

Действительно!

Richard MacCutchan

Хотя из дальнейших комментариев следует, что в этом нет необходимости. Может быть, он добавляется автоматически МФЦ.

Рейтинг:
0

Shao Voon Wong

CString не является производным от CObject таким образом, вы не можете привести его указатель к CObject*.

CString* p_str = new CString(L"Hello");
CObject* p_obj = p_str;

Я получил эту ошибку от VC++ 2019:
error C2440: 'initializing': cannot convert from 'CString *' to 'CObject *'

Весьма вероятный, CString используется для наследования от CObject в более старом VC++, но не сейчас.


Member 13261094

Не получая никаких ошибок компиляции. Он также загружает библиотеку и выполняет функцию dll. Единственное, что он портит объект pSiBatchLauncherApp1.

Shao Voon Wong

Это происходит потому, что Си-стиль приведения типов компилятор тишина. Нет ошибки компиляции для приведенного ниже кода. Вот почему актерский состав в стиле с не поощряется.

По CString* p_str = новая строка CString(л"Здравствуйте!");
Объект cobject* p_obj = (объект cobject*)p_str;

Но этот исходный код будет иметь ошибку компиляции.

По CString* p_str = новая строка CString(л"Здравствуйте!");
Объект cobject* p_obj = p_str;

Shao Voon Wong

Не забудьте сделать функцию и указатель функции одним и тем же соглашением о вызове, как упоминалось в предыдущем потоке вопросов.

https://en.wikipedia.org/wiki/X86_calling_conventions

Объявление функции должно быть

siRuleReturn* по WinAPI FireRule(содержащий coblist&усилитель; список);

И объявление указателя функции должно быть

siRuleReturn* (WINAPI* FIRERULE)(CObList& list);

Shao Voon Wong

Вы можете сделать устранение причины, закомментировав строки, начинающиеся снизу, пока сбой не произойдет. Тогда вы знаете, что недавняя закомментированная строка-это причина.