zoukankan      html  css  js  c++  java
  • DLL类库的加载和调用

    动态加载动态连接库能更加有效地使用内存,这在大型项目中是非常有用的一项技术。DLL中的函数可以很容易的实现动态加载调用,网上也有很多相关的介绍,但DLL中类库怎样实现动态加载调用呢?
    这是我在实际项目中遇到的一个问题,可以采用类工厂方法,把对象的指针导出来的方法解决这个问题,如果需要对跨平台的支持还可以使用QT中的QLibrary代替LoadLibrary等函数。

    1)与动态库调用有关的函数包括: 
    (1)LoadLibrary(或MFC 的AfxLoadLibrary),装载动态库。 
    (2)GetProcAddress,获取要引入的函数,将符号名或标识号转换为DLL内部地址。 
    (3)FreeLibrary(或MFC的AfxFreeLibrary),释放动态链接库。
    2)unix上与动态库调用有关的函数包括:
    (1)_打开动态链接库:dlopen,函数原型void *dlopen (const char *filename, int flag); 
    dlopen用于打开指定名字(filename)的动态链接库,并返回操作句柄。 
    (2)取函数执行地址:dlsym,函数原型为: void *dlsym(void *handle, char *symbol); 
    dlsym根据动态链接库操作句柄(handle)与符号(symbol),返回符号对应的函数的执行代码地址。 
    (3)关闭动态链接库:dlclose,函数原型为: int dlclose (void *handle); 
    dlclose用于关闭指定句柄的动态链接库,只有当此动态链接库的使用计数为0时,才会真正被系统卸载。 
    (4)动态库错误函数:dlerror,函数原型为: const char *dlerror(void); 当动态链接库操作函数执行失败时,dlerror可以返回出错信息,返回值为NULL时表示操作函数执行成功。 
    3)QT对动态库调用的封装函数
    QLibrary ( const QString & filename ) 
    void * resolve ( const char * symb ) //获取要引入的函数地址

    4)DLL中类库动态加载调用的实例
    //动态库DLL_PUBLICCallback.dll的代码
    //IPUBLICCallback.h 接口文件

    typedef long HRESULT;
    class IPUBLICCallback
    {
    public:
            virtual HRESULT Release( void )=0;
      virtual HRESULT Fun(int x)=0; 
    };
    extern "C" __declspec(dllexport) HRESULT CreatePUBLICCallback(IPUBLICCallback ** pp_obj);
     
     //CPUBLICCallback.h
    class CIPUBLICCallback : public IIPUBLICCallback
    {
    public:
    CIPUBLICCallback();
    virtual ~CIPUBLICCallback();
    HRESULT Fun(int x);
    HRESULT Release(){delete this;};
    };

    //CPUBLICCallback.cpp
    CPUBLICCallback::CPUBLICCallback()
    {
    }
    CPUBLICCallback::~CPUBLICCallback()
    {

    HRESULT CPUBLICCallback::Fun(int x)
    {
     ...

    HRESULT CreatePUBLICCallback(IPUBLICCallback ** pp_obj)
    {
    *pp_obj = new CPUBLICCallback;
    return TRUE;
    }

    //////////////
    //应用程序的代码
    //test.exe
    //test.cpp
    int main( int argc, char** argv )
    {
     IPUBLICCallback* m_pPUBLICCallback;
     typedef HRESULT (*MyCreatePUBLICCallback)(IPUBLICCallback **pp_obj);
     HINSTANCE hInst = LoadLibrary("DLL_PUBLICCallback.dll");
     //QLibrary hInst( "DLL_PUBLICCallback.dll" );
     if(hInst)
     {
      MyCreatePUBLICCallback _CreatePUBLICCallback = (MyCreatePUBLICCallback) GetProcAddress(hInst, "CreatePUBLICCallback" );
      //MyCreatePUBLICCallback _CreatePUBLICCallback = (MyCreatePUBLICCallback)hInst.resolve( "CreatePUBLICCallback" );

      if ( _CreatePUBLICCallback ) 
      {
       _CreatePUBLICCallback(&m_pPUBLICCallback);
       m_pPUBLICCallback->Fun(66);
        m_pPUBLICCallback->Release();
      }
      FreeLibrary(hInst);
     }
     return 0;
    }

    本文来自CSDN博客,转载请标明出处:http://blog.csdn.net/caih2000/archive/2007/01/20/1488598.aspx

  • 相关阅读:
    java数据类型
    如何判断数组
    git 常用命令
    如何配置 ESLint 工作流
    Lambda表达式和函数式接口
    面向对象(多态与内部类)
    面向对象(封装与继承)
    面相对像(基础)
    break;怎么跳出外部循环
    面向对象(类与对象)
  • 原文地址:https://www.cnblogs.com/minggoddess/p/1907177.html
Copyright © 2011-2022 走看看