Qt DLL 요약[2] - QT DLL 생성 및 호출
카탈로그
Qt DLL 요약[1] - Link Library 예비 지식
Qt DLL 요약[2] - QT DLL 생성 및 호출
Qt DLL 요약[3] - VS2008 + Qt QPluginLoader를 사용한 DLL 액세스
개발 환경: VS2008+Qt4.7.4
최근에 많은 Qt의 DLL 예를 보고 QT 동적 링크 라이브러리를 어떻게 만들고 호출하는지 정리했다.
먼저 다음과 같은 QT 동적 링크 라이브러리를 호출하는 방법에 대해 살펴보겠습니다.
1. 명시적으로 DLL을 연결하고 DLL의 전역 함수를 호출하며 Qt의 QLibrary 방법을 사용한다.
2. 링크 DLL을 표시하고 DLL의 클래스 객체, 구성원 함수를 호출합니다.(대상을 통해 클래스 구성원 함수 호출 가능)
① 허함수표를 사용하는 방법, 이것도COM이 사용하는 방법으로 Qt의 QLibrary 기술을 이용하여 호출한다.
②GetProcAddress를 사용하여 직접 호출합니다.
③ 생성된 DLL 플러그인 클래스를 Qt의 QPluginLoader 클래스로 직접 호출
3. 암시적 링크 DLL: Qt의 Qlibrary 방법
이런 세 가지 방법에 관하여 아래에 상세하게 서술한다
상세 분류 서술
전제: 두 개의 프로젝트 파일 디렉터리
1. TestDLL 프로젝트:testdllglobal.h,TestDll.h,TestDll.cpp
2. TestMain exe 응용 프로그램:main.cpp
testdll_global.h 파일 소스 코드는 변하지 않습니다
#ifndef TESTDLL_GLOBAL_H
#define TESTDLL_GLOBAL_H
#include <QtCore/qglobal.h>
#ifdef TESTDLL_LIB
# define TESTDLL_EXPORT Q_DECL_EXPORT
#else
# define TESTDLL_EXPORT Q_DECL_IMPORT
#endif
#endif // TESTDLL_GLOBAL_H
DLL의 명시적 링크는 어떤 때는 암시적 링크보다 유연성이 높습니다.예를 들어, 실행 중 DLL을 찾을 수 없는 것을 발견하면, 프로그램은 오류 정보를 표시하고 계속 실행할 수 있습니다.프로그램에 플러그인 서비스를 제공하고 싶을 때, 현식 링크도 매우 유용하다
1. 디스플레이 링크를 사용하여 DLL의 전역 함수를 호출하고 TestDLL 하나만 있으면 된다.dll.
일반적으로 Windows 다음 프로그램에서는 dll을 호출하는 절차를 세 가지 단계로 나눈다. LoadLibrary (), GetProcAdress (), FreeLibrary ()
여기서 LoadLibrary () 함수는 지정한 dll 파일을 불러와서 호출 프로그램의 메모리에 불러옵니다. (DLL에는 자신의 메모리가 없습니다!)
GetProcAddress() 함수는 호출을 위해 지정된 DLL(Dynamic Link Library)의 출력 라이브러리 함수 주소를 읽어들입니다.
FreeLibrary() dll이 차지하는 공간을 놓습니다.
QT의 QLibrary 클래스는 링크가 DLL을 호출하는 절차를 보여줍니다. load(), resolve(const char * symbol), unload()와 VC 절차가 유사합니다.
TestDll.dll 프로젝트의 TestDLLh소스 코드
#ifndef TESTDLL_H
#define TESTDLL_H
#include "testdll_global.h"
class TESTDLL_EXPORT TestDll
{
public:
TestDll();
~TestDll();
private:
};
extern "C" TESTDLL_EXPORT void helloWorld();
extern "C" TESTDLL_EXPORT int add(int a,int b);
#endif // TESTDLL_H
TestDll.dll 프로젝트의 TestDLLcpp 소스
#include <iostream>
#include "TestDll.h"
TestDll::TestDll()
{
}
TestDll::~TestDll()
{
}
void helloWorld()
{
std::cout << "hello,world!";
}
int add(int a,int b)
{
return a + b;
}
주: 1) DLL 프로젝트를 성공적으로 구축하면 VS 명령 프롬프트 줄에서 명령 "dumpbin -exports DllTest.dll"로 볼 수 있습니다. (VC 도구 패키지의 depends로 볼 수도 있습니다) 주: 2) extern "C"링크 표시를 사용해야 합니다. 그렇지 않으면 C++ 컴파일러가 수식된 함수 이름을 생성합니다. 이로써 함수의 이름은 더 이상 Helloworld가 아니라 "?helloWorld@TestDll@@UAEXXZ'라는 이름입니다.왜 이름이 Hello World가 아니죠?이는 C++가 함수의 재부팅을 지원하기 위해 컴파일할 때 함수의 매개 변수 유형 정보와 반환값 유형 정보를 함수 이름에 넣기 때문에 코드의 이름이 같은 재부팅 함수는 컴파일한 후에 서로 구분되고 호출할 때 함수 이름도 같은 처리를 거치면 대응하는 함수를 찾을 수 있기 때문이다.자세히 보면 이 문장동적 링크 라이브러리(Dynamic Link Library) 학습 노트
TestMain 프로젝트maincpp
#include <QtCore/QCoreApplication>
#include <iostream>
#include <QLibrary>
typedef int (*Fun)(int,int); // ,int add(int a,int b);
int main(int argc, char *argv[])
{
QCoreApplication a(argc, argv);
QLibrary mylib("TestDll.dll"); // dll
int result;
//
if (mylib.load())
{
std::cout << "DLL load is OK!"<<std::endl;
// add()
Fun add = (Fun)mylib.resolve("add");
// add()
if (add)
{
std::cout << "Link to add Function is OK!"<<std::endl;
// dll add()
result = add(5,6);
std::cout << result;
}
else
std::cout << "Link to add Function failed!!"<<std::endl;
}
//
else
std::cout << "DLL is not loaded!"<<std::endl;
return a.exec();
}
2. 디스플레이 링크를 사용하여 C++ 클래스의 클래스 대상, 구성원 함수를 호출합니다
C++ 클래스의 구성원 함수를 내보내고 현시적으로 연결하려면 어떻게 해야 합니까?여기에 두 가지 문제가 있다.첫째, C++ 구성원 함수 이름은 수식된 것이다(extern "C"표시를 지정해도 이렇다).둘째, C++에서는 구성원 함수에 대한 포인터를 다른 유형으로 변환할 수 없습니다.이 두 문제는 C++ 클래스의 현식 링크를 제한합니다.다음은 이 문제를 해결하기 위한 두 가지 방법을 소개한다.
① 허함수표를 사용하는 방법, 이것도COM이 사용하는 방법으로 Qt의 QLibrary 기술을 이용하여 호출한다.
②GetProcAddress를 사용하여 직접 호출합니다.
③ 생성된 DLL 플러그인 클래스를 Qt의 QPluginLoader 클래스로 직접 호출
① 허함수표의 방법, QLibrary 기술 호출
TestDll.h 코드
#ifndef TESTDLL_H
#define TESTDLL_H
#include "testdll_global.h"
class TESTDLL_EXPORT TestDll
{
public:
TestDll();
virtual~TestDll();
virtual void helloWorld(); //
private:
};
extern "C" TESTDLL_EXPORT TestDll* getTestDll(); // TestDll
#endif // TESTDLL_H
TestDll.cpp 소스
#include <iostream>
#include "TestDll.h"
TestDll::TestDll()
{
}
TestDll::~TestDll()
{
}
void TestDll::helloWorld()
{
std::cout << "hello,world!";
}
TestDll* getTestDll()
{
return new TestDll();
}
TestMain 프로젝트의 main.cpp 소스
#include <QtCore/QCoreApplication>
#include <iostream>
#include <QLibrary>
#include "../TestDll/TestDll.h" // , TestDll
typedef TestDll* (*GetTestDll)();// , TestDLL ;
int main(int argc, char *argv[])
{
QCoreApplication a(argc, argv);
QLibrary mylib("TestDll.dll"); // dll
int result;
//
if (mylib.load())
{
GetTestDll getTestDll = (GetTestDll)mylib.resolve("getTestDll");
if(getTestDll)
{
TestDll *testDll = getTestDll();
testDll->helloWorld();
delete testDll;
}
}
//
else
std::cout << "DLL is not loaded!"<<std::endl;
return a.exec();
}
이 방법은 사용자가 프로그램을 위해 쉽게 플러그인을 만들 수 있도록 사용된다.그것의 단점은 창설 대상의 메모리를 dll에 분배해야 한다는 것이다
②GetProcAddress를 사용하여 클래스 객체의 멤버 함수를 직접 호출합니다.
이 방법은 테스트를 하지 않았습니다. 저에게 큰 도움이 되지 않았습니다. 그리고 def로 DLL 함수를 내보내야 합니다. 관심 있으면 이 글을 참고하십시오.DLL의 클래스에 대한 명시적 링크
③ 생성된 DLL 플러그인 클래스를 Qt의 QPluginLoader 클래스로 직접 호출
이 방법은 제가 단독으로 총결산을 한 편 썼는데 QPluginLoader의 간단한 예를 보십시오VS2008+Qt에서 QPluginLoader를 사용하여 DLL에 액세스
3. 은밀한 링크 방법으로 QLibrary 클래스를 통해 DLL의 클래스 대상, 전역 함수에 대한 호출
TestDll.h
#ifndef TESTDLL_H
#define TESTDLL_H
#include "testdll_global.h"
class TESTDLL_EXPORT TestDll
{
public:
TestDll();
~TestDll();
void helloWorld(); //
private:
};
extern "C" TESTDLL_EXPORT int add(int a,int b); //
#endif // TESTDLL_H
TestDll.cpp 소스
#include <iostream>
#include "TestDll.h"
TestDll::TestDll()
{
}
TestDll::~TestDll()
{
}
void TestDll::helloWorld()
{
std::cout << "hello,world!";
}
int add(int a,int b)
{
return a + b;
}
TestMain 프로젝트의 main.cpp, 헤더 파일과lib 파일을 약간 설정해야 합니다
1. 프로젝트의 메인 프로그램에 TestDll을 도입한다.h 헤더 파일,
2. 프로젝트 속성 설정:TestDLL에 가입lib의 파일 디렉터리입니다. Linker/General/Additional Library Diretories에서TestDll을 선택하십시오.lib의 파일 디렉토리 D:\VSWorkSpace\Test\Debug
3. 프로젝트 속성 설정: TestDll에 가입.lib 파일, Linker/Input/Additional Dependencies에 TestDll을 추가합니다.lib
main.cpp 소스
#include <QtCore/QCoreApplication>
#include <iostream>
#include <QLibrary>
#include "../TestDll/TestDll.h"
// TestDll.lib , 2,3
//#pragma comment(lib, "../Debug/TestDll.lib")
int main(int argc, char *argv[])
{
QCoreApplication a(argc, argv);
int result = add(5,6);
std::cout << result;
TestDll dll;
dll.helloWorld();
return a.exec();
}
결과는 바로 컴파일에 성공할 수 있다
이 내용에 흥미가 있습니까?
현재 기사가 여러분의 문제를 해결하지 못하는 경우 AI 엔진은 머신러닝 분석(스마트 모델이 방금 만들어져 부정확한 경우가 있을 수 있음)을 통해 가장 유사한 기사를 추천합니다:
자바 파일, 폴 더 생 성 및 삭제QQ 그룹 에서 어떤 사람 이 폴 더 의 삭 제 를 묻 자 인터넷 으로 찾 아 보 았 습 니 다. 프로그램 을 만 들 었 습 니 다. 주의해 야 할 점 은 폴 더 안의 내용 이 파일 인지 하위 폴 더 인지 판단 해 ...
텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
CC BY-SA 2.5, CC BY-SA 3.0 및 CC BY-SA 4.0에 따라 라이센스가 부여됩니다.