Linux下库文件学习(三)如何创建和使用库文件

       最近在Linux下使用第三方库Protobuf时,遇到一个问题:编译出的可执行程序在运行时总报错:“error while loading shared libraries: libprotobuf.so.7: cannot open shared object file: No such file or directory”。于是花时间弄清楚原因,找到解决方案,跟大家共享一下。

         库文件的创建和使用,通过具体的例子来介绍。

1.  准备源文件
      建立一个新目录libtest,在libtest下新建两个目录a和so,a和so目录下均有cacl.h cacl.C test_cacl.C三个文件,内容如下:
   

 ****************************************************************************************************************************************  

     cacl.h

   #ifndef CACL_H
   #define CACL_H
    
    int Add(int nLeft, int nRight);
    
   #endif

 **************************************************************************************************************************************** 

     cacl.C

    #include <stdio.h>
    
    int Add(int nLeft, int nRight)
    {
        return nLeft + nRight;
    }
 **************************************************************************************************************************************** 

   test_cacl.C

   #include "cacl.h"
   #include <stdio.h>
   
   int main()
   {
       int nA   = 100;
       int nB   = 200;
       int nRev = Add(nA, nB);
       printf("The sum is %d\n", nRev);
  
       return 0;
   }
 **************************************************************************************************************************************** 



2.  静态库的创建和使用
     (1)  在a目录下,编译生成cacl.o文件;
            g++ -c cacl.C

     (2)  在a目录下,使用ar命令封装生成静态库文件libcacl.a;
            ar crv libcacl.a cacl.o
            静态库文件名的命名规范是以lib为前缀,紧接着跟静态库名,扩展名为.a

     (3)  在a目录下,编译连接libcacl.a生成测试程序;
            g++ -o testcacl test_cacl.C -L. -lcacl

     (4)  在a目录下,可以正确运行testcacl,即使删除了libcacl.a文件(正是静态库的特点);

3.  动态库的创建和使用
     (1)  在so目录下,编译生成cacl.o文件;
            g++ -fPIC -c cacl.C
            P.S.此处编译参数 -fPIC 一定不能省略,否则下一步将会失败;因为g++默认生成的.o文件是不带-fPIC选项,即生成的是静态链接文件,故下一步封装   生成动态库时会失败。

     (2)  在so目录下,使用ar命令生成静态库文件libcacl.so;
            g++ -shared -fPIC -o libcacl.so cacl.o
            动态库文件名的命名规范是以lib为前缀,紧接着跟静态库名,扩展名为.so

     (3)  在so目录下,编译连接libcacl.a生成测试程序;

            g++ -o testcacl test_cacl.C -L. -lcacl


     (4)  在so目录下,可以正确运行testcacl;
            若在当前目录下删除了libcacl.so,将会报错“testcacl: error while loading shared libraries: libcacl.so: cannot open shared object file: No such file or directory”,具体原因在 Linux下库文件学习(二)如何设置库的路径中已经讲解地非常清楚,请大家自己去找解决方案;


4.  编译参数解析 
       

               -shared: 该选项指定生成动态连接库(让连接器生成T类型的导出符号表,有时候也生成弱连接W类型的导出符号),不用该标志外部程序无法连接。当于一个可执行文件;

                   -fPIC:表示编译为位置独立的代码,不用此选项的话编译后的代码是位置相关的所以动态载入时是通过代码拷贝的方式来满足不同进程的需要,而不能达到真正代码段共享的目的;

                      -L.: 表示要连接的库在当前目录中 ;

       -libcacl.a/so: 编译器查找动态连接库时有隐含的命名规则,即在给出的名字前面加上lib,后面加上.so来确定库的名称;

5.  优先级

      若同一个目录下既有静态库.a,又有动态库.so,则编译链接时优先使用动态库,可通过如下方法验证。

     (1)   先把cacl.h test_cacl.C这两个文件都拷贝到libtest目录下,然后将目录a中的libcacl.a和目录so中的libcacl.so拷贝到libtest目录下,使用命令“g++ -o testcacl test_cacl.C -L. -lcacl”编译链接生成可执行程序testcacl;
     (2)   运行testcacl,运行结果正确;
     (3)   删除libcacl.so之后,运行testcacl,会报错“testcacl: error while loading shared libraries: libcacl.so: cannot open shared object file: No such file or directory”。
  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值