zoukankan      html  css  js  c++  java
  • Qt加载动态链接库

    先制作个简单的动态链接库,再在Qt里面加载它。

    【制作动态链接库】

    先编写一个hello.c

    1 #include <stdio.h>
    2 int hello()
    3 {
    4     printf("hello world!\n");
    5 }

    在Linux下编译,生成hello.o:

    gcc -c hello.c

    编译成动态链接库libhello.so(注意:Linux下的动态链接库以lib开始命名):

    gcc -shared -o libhello.so hello.o

     

    【加载动态链接库】

    在Qt中加载libhello.so,先创建一个空的Qt工程,添加新文件main.c,内容如下:

     1  #include <stdio.h>
     2  #include <QLibrary>
     3 
     4  int main(int argc, char *argv[])
     5  {
     6      QLibrary *hello_lib = NULL;
     7      //写清楚库的路径,如果放在当前工程的目录下,路径为./libhello.so
     8      hello_lib = new QLibrary("/home/libhello.so");
     9  
    10      //加载动态库
    11      hello_lib->load();
    12      if (!hello_lib->isLoaded()) 
    13      {
    14          printf("load libhello.so failed!\n");
    15          return 0; 
    16      }
    17  
    18      //定义函数指针
    19      typedef void (*Fun)();
    20  
    21      //resolve得到库中函数地址
    22      Fun hello = (Fun)hello_lib->resolve("hello");
    23      if (hello)
    24      {
    25           hello();
    26      }
    27  
    28      //卸载库
    29      hello_lib->unload();
    30      return 0;
    31  }

    运行后输出:hello world!

     

    还有一种方法:主程序在编译的时候加上-L. -llibxxx.so

     

    【QLibrary的文档】

    The QLibrary class loads shared libraries at runtime.

    An instance of a QLibrary object operates on a single shared object file (which we call a "library", but is also known as a "DLL"). A QLibrary provides access to the functionality in the library in a platform independent way. You can either pass a file name in the constructor, or set it explicitly with setFileName(). When loading the library, QLibrary searches in all the system-specific library locations (e.g. LD_LIBRARY_PATH on Unix), unless the file name has an absolute path. If the file cannot be found, QLibrary tries the name with different platform-specific file suffixes, like ".so" on Unix, ".dylib" on the Mac, or ".dll" on Windows and Symbian. This makes it possible to specify shared libraries that are only identified by their basename (i.e. without their suffix), so the same code will work on different operating systems.

    The most important functions are load() to dynamically load the library file, isLoaded() to check whether loading was successful, and resolve() to resolve a symbol in the library. The resolve() function implicitly tries to load the library if it has not been loaded yet. Multiple instances of QLibrary can be used to access the same physical library. Once loaded, libraries remain in memory until the application terminates. You can attempt to unload a library using unload(), but if other instances of QLibrary are using the same library, the call will fail, and unloading will only happen when every instance has called unload().

    A typical use of QLibrary is to resolve an exported symbol in a library, and to call the C function that this symbol represents. This is called "explicit linking" in contrast to "implicit linking", which is done by the link step in the build process when linking an executable against a library.

    Note: In Symbian resolving symbols using their names is supported only if the library is built as STDDLL. Otherwise ordinals must be used. Also, in Symbian the path of the library is ignored and system default library location is always used.

    The following code snippet loads a library, resolves the symbol "mysymbol", and calls the function if everything succeeded. If something goes wrong, e.g. the library file does not exist or the symbol is not defined, the function pointer will be 0 and won't be called.

    QLibrary myLib("mylib");
    typedef void (*MyPrototype)();
    MyPrototype myFunction = (MyPrototype) myLib.resolve("mysymbol");
    if (myFunction)
        myFunction();

    The symbol must be exported as a C function from the library for resolve() to work. This means that the function must be wrapped in an extern "C" block if the library is compiled with a C++ compiler. On Windows, this also requires the use of a dllexport macro; see resolve() for the details of how this is done. For convenience, there is a static resolve() function which you can use if you just want to call a function in a library without explicitly loading the library first:

    typedef void (*MyPrototype)();
    MyPrototype myFunction = (MyPrototype) QLibrary::resolve("mylib", "mysymbol");
    if (myFunction)
        myFunction();

    【参考文献】

    http://blog.csdn.net/wanglin754/art9969icle/details/704

  • 相关阅读:
    Android view显示在软键盘上方
    ListView子项点击无反应的解决办法
    adb for mac
    Android文件的流操作工具类
    Linux之间配置SSH互信(SSH免密码登录)
    最简单的Linux虚拟机磁盘扩容方法
    Grunt + Bower—前端构建利器
    Microsoft Office 2016 简体中文 Vol 版镜像下载(Pro Plus、Visio、Project 下载)
    如何在windows下安装GIT
    如何在Crystal框架项目中内置启动MetaQ服务?
  • 原文地址:https://www.cnblogs.com/qyddbear/p/2682119.html
Copyright © 2011-2022 走看看