|
马上注册,结交更多好友,享用更多功能,让你轻松玩转社区。
您需要 登录 才可以下载或查看,没有帐号?立即注册
x
由于在linux中,用户权限很大,做任何事情都很自由,所以,你往往需要知道你做的每一步在干什么。
Linux下文件的范例是不依附于厥后缀名的,但一样平常来说:
.o,是方针文件,相称于windows中的.obj文件
.so为共享库,是sharedobject,用于静态毗连的,和dll差未几
.a为静态库,是很多多少个.o合在一同,用于静态毗连
.la为libtool主动天生的一些共享库,vi编纂检察,次要纪录了一些设置信息。能够用以下命令检察*.la文件的格局$file*.la
*.la:ASCIIEnglishtext
以是能够用vi来检察其内容。
@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
创立.a库文件和.o库文件:
[yufei@localhostperl_c2]$pwd
/home/yufei/perl_c2
[yufei@localhostperl_c2]$catmylib.c
#include<stdio.h>
#include<string.h>
voidhello(){
printf("successcallfromperltoclibrary
");
}
[yufei@localhostperl_c2]$catmylib.h
externvoidhello();
[yufei@localhostperl_c2]$gcc-cmylib.c
[yufei@localhostperl_c2]$dir
mylib.cmylib.hmylib.o
[yufei@localhostperl_c2]$ar-rmylib.amylib.o
ar:正在创立mylib.a
[yufei@localhostperl_c2]$dir
mylib.amylib.cmylib.hmylib.o
@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111
静态链接库*.so的编译与利用--
静态库*.so在Linux下用c和c++编程时常常会碰着,比来在网站找了几篇文章先容静态库的编译和链接,总算弄懂了这个之前一向不太懂得得东东,这里做个条记,也为别的正为静态库链接库而忧?的兄弟们供应一点匡助
1、静态库的编译
上面经由过程一个例子来先容怎样天生一个静态库。这里有一个头文件:so_test.h,三个.c文件:test_a.c、test_b.c、test_c.c,我们将这几个文件编译成一个静态库:libtest.so。
so_test.h:
#include<stdio.h>
#include<stdlib.h>
voidtest_a();
voidtest_b();
voidtest_c();
test_a.c:
#include"so_test.h"
voidtest_a()
{
printf("thisisintest_a...
");
}
test_b.c:
#include"so_test.h"
voidtest_b()
{
printf("thisisintest_b...
");
}
test_c.c:
#include"so_test.h"
voidtest_c()
{
printf("thisisintest_c...
");
}
将这几个文件编译成一个静态库:libtest.so
$gcctest_a.ctest_b.ctest_c.c-fPIC-shared-olibtest.so
2、静态库的链接
在1、中,我们已乐成天生了一个本人的静态链接库libtest.so,上面我们经由过程一个程序来挪用这个库里的函数。程序的源文件为:test.c。
test.c:
#include"so_test.h"
intmain()
{
test_a();
test_b();
test_c();
return0;
}
l将test.c与静态库libtest.so链接天生实行文件test:
$gcctest.c-L.-ltest-otest
l测试是不是静态毗连,假如列出libtest.so,那末应当是毗连一般了
$lddtest
l实行test,能够看到它是怎样挪用静态库中的函数的。
3、编译参数剖析
最次要的是GCC命令行的一个选项:
-shared该选项指定天生静态毗连库(让毗连器天生T范例的导出标记表,偶然候也天生弱毗连W范例的导出标记),不必该标记内部程序没法毗连。相称于一个可实行文件
l-fPIC:暗示编译为地位自力的代码,不必此选项的话编译后的代码是地位相干的以是静态载进时是经由过程代码拷贝的体例来满意分歧历程的必要,而不克不及到达真正代码段共享的目标。
l-L.:暗示要毗连的库在以后目次中
l-ltest:编译器查找静态毗连库时有隐含的定名划定规矩,即在给出的名字后面加上lib,前面加上.so来断定库的称号
lLD_LIBRARY_PATH:这个情况变量唆使静态毗连器能够装载静态库的路径。
l固然假如有root权限的话,能够修正/etc/ld.so.conf文件,然后挪用/sbin/ldconfig来到达一样的目标,不外假如没有root权限,那末只能接纳输入LD_LIBRARY_PATH的办法了。
4、注重
挪用静态库的时分有几个成绩会常常碰着,偶然,明显已将库的头文件地点目次经由过程“-I”include出去了,库地点文件经由过程“-L”参数引诱,并指定了“-l”的库名,但经由过程ldd命令观察时,就是逝世活找不到你指定链接的so文件,这时候你要作的就是经由过程修正LD_LIBRARY_PATH大概/etc/ld.so.conf文件来指定静态库的目次。一般如许做就能够办理库没法链接的成绩了。
makefile内里怎样准确的编译和毗连天生.so库文件,然后又是在其他程序的makefile内里怎样编译和毗连才干挪用这个库文件的函数????
答:
你必要告知静态链接器、加载器ld.so在那里才干找到这个共享库,能够设置情况变量把库的路径增加到库目次/lib和/usr/lib,LD_LIBRARY_PATH=$(pwd),这类办法接纳命令行办法不太便利,一种替换办法
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^正文^^^^^^^^^^^^^^^^^^^^^^^^^^^^
LD_LIBRARY_PATH能够在/etc/profile仍是~/.profile仍是./bash_profile里设置,大概.bashrc里,
改完后运转source/etc/profile或./etc/profile
更好的举措是添进/etc/ld.so.conf,然后实行/sbin/ldconfig
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^正文^^^^^^^^^^^^^^^^^^^^^^^^^^^^
是把库路径增加到/etc/ld.so.conf,然后以root身份运转ldconfig
也能够在毗连的时分指定文件路径和称号-I-L.
GCC=gcc
CFLAGS=-Wall-ggdb-fPIC
#CFLAGS=
all:libfunctest
libfunc:func.ofunc1.o
$(GCC)-shared-Wl,-soname,libfunc.so.1-olibfunc.so.1.1{GetProperty(Content)}lt;
ln-sflibfunc.so.1.1libfunc.so.1
ln-sflibfunc.so.1libfunc.so
***********************************************正文************************************************
ln-s是用来创立软链接,也就相称于windows中的快速体例,在以后目次中创立上一级目次中的文件ttt的定名为ttt2软链接的命令是ln-s../tttttt2,假如原文件也就是ttt文件删除的话,ttt2也酿成了空文件。
ln-d是用来创立硬链接,也就相称于windows中文件的正本,当原文件删除的时分,其实不影响“正本”的内容。
编译方针文件时利用gcc的-fPIC选项,发生与地位有关的代码并能被加载就任何地点:
gccCfPICCgCcliberr.cColiberr.o
利用gcc的-shared和-soname选项;
利用gcc的-Wl选项把参数传送给毗连器ld;
利用gcc的-l选项显现的毗连C库,以包管能够失掉所需的启动(startup)代码,从而制止程序在利用分歧的,大概不兼容版本的C库的体系上不克不及启动实行。
gccCgCsharedCWl,-soname,liberr.soColiberr.so.1.0.0liberr.oClc
创建响应的标记毗连:
lnCsliberr.so.1.0.0liberr.so.1;
lnCsliberr.so.1.0.0liberr.so;
在MAKEFILE中:
$@
暗示划定规矩中的方针文件集。在形式划定规矩中,假如有多个方针,那末,"$@"就是婚配于方针中形式界说的汇合。
$%
仅当方针是函数库文件中,暗示划定规矩中的方针成员名。比方,假如一个方针是"foo.a(bar.o)",那末,"$%"就是"bar.o","$@"就是"foo.a"。假如方针不是函数库文件(Unix下是[.a],Windows下是[.lib]),那末,其值为空。
{GetProperty(Content)}lt;
依附方针中的第一个方针名字。假如依附方针是以形式(即"%")界说的,那末"{GetProperty(Content)}lt;"将是切合形式的一系列的文件集。注重,其是一个一个掏出来的。
$?
一切比方针新的依附方针的汇合。以空格分开。
$^
一切的依附方针的汇合。以空格分开。假如在依附方针中有多个反复的,谁人这个变量会往除反复的依附方针,只保存一份。
*********************************************正文***********************************************************************
test:test.olibfunc
$(GCC)-otesttest.o-L.-lfunc
%.o:%.c
$(GCC)-c$(CFLAGS)-o$@{GetProperty(Content)}lt;
clean:
rm-fr*.o
rm-fr*.so*
rm-frtest
要天生.so文件,cc要带-shared参数;要挪用.so的文件,好比libfunc.so,能够在cc命令最初加上-lfunc,还要视情形加上-L/usr/xxx指出libfunc.so的路径;如许,在你要编译的源文件中就能够挪用libfunc.so这个库文件的函数.
后面的都说的差未几了,最初提示一下最好供应一个接行动文件
静态加载,用dlopen,dlclose,dlsym
</p>
vim除非你打算真正的学好linux,或者说打算长久时间学习他,而且肯花大量时间vim,否则,最好别碰 |
|