700字范文,内容丰富有趣,生活中的好帮手!
700字范文 > Linux C++编译及 静态/动态 链接库 笔记

Linux C++编译及 静态/动态 链接库 笔记

时间:2021-09-20 15:29:57

相关推荐

Linux C++编译及 静态/动态 链接库 笔记

[size=x-large][color=blue]1、C++文件的编译[/color][/size]

[color=blue]g++参数介绍(非常棒~)[/color]

[url]/lidan/archive//05/25/2239517.html[/url]

[color=blue]官方文档[/color]:[url]/onlinedocs/[/url]

[color=blue]官方参数大全(gcc5.3)[/color]:[url]/onlinedocs/gcc-5.3.0/gcc/Option-Summary.html#Option-Summary[/url]

-E [color=blue]预处理[/color], 将#include的文件展开等

-S 生成[color=blue]汇编[/color]文件

-c 生成[color=blue]object[/color]文件

gcc XX.o -o XX [color=blue]链接[/color],,输出文件名为XX

-O1, -O2, -O3 [color=blue]优化[/color]代码 ,-O3级别最高, -O1为默认

-g 及 -ggdb 等,,生成[color=blue]调试[/color]信息

-fPIC 及 -fpic , 生成[color=blue]动态链接库[/color]时使用,, 前者在多平台通用,但程序运行速度慢

-M , -MM, 输出 文件的[color=blue]依赖关系[/color](比如各种.h)文件(写makefile时可以使用)

-std=c++14(或-std=gnu++14) -std=c++11(或-std=gnu++11)启用 [color=blue]c++14[/color]/11的信息,其中使用gnu++14会启用gcc的扩展 :

/projects/cxx0x.html

/projects/cxx1y.html

一般直接用-c 生成object文件,再多个object文件链接一下即可

或者不指定参数,直接从 多个.cpp 文件生成可执行文件

-Wall 输出尽可能多的警告

-I [color=blue]头文件路径[/color]

-L [color=blue]库文件路径[/color](静态、动态)

-l 库文件(无需包含扩展名.so 或.a )[color=red](但是我自己在Ubuntu14.04.1中直接使用XX.so即可,而不是-lXX.so)[/color]

[size=x-large][color=blue]2、静态链接库、动态链接库的编译[/color][/size]

[color=blue]Program Library HOWTO:[/color][url]/program-library/[/url]

[color=blue]C++ dlopen mini HOWTO[/color][url]/HOWTO/C++-dlopen/[/url]

这篇文章中讲了由于C++的Name Mangling,,需要 extern "C"等封装才能正常使用fopen函数调用C++函数的问题

[color=red]很多网上的教程会用到 -l 选项指定库文件!!!但是我试的时候直接指定库文件全名就行!!!(具体见makefile内容)[/color]

[color=blue]nm[/color] 查看exe、.o、.so、 .a文件中的符号信息,比如C++函数名被编译器[color=blue]mangle之后的名称[/color]

nm XX.so | c++filt 可以查看函数的[color=blue]原始名称[/color]

关于mangling更多请参见[url]/chenxintao/article/details/7585483[/url]

关于库文件搜索路径的问题,没详细实验,在Ubuntu下貌似当前路径也可以~ 这个,用到再试了

只是简单记一下LD_LIBRARY_PATH 的修改方式:/view/1270749.htm

不多说了,上代码(完整代码见[color=red]附件[/color]):

[color=blue]库文件[/color]:

#pragma once

int plus(int a,int b);

#include "sharedLib.h"

int plus(int a,int b){

return a+b;

}

[color=blue]采用静态链接库[/color]:

#include "sharedLib.h"

#include <iostream>

int main(void){

std::cout<<"Running "<<__FILE__<<std::endl;

int p=plus(2,3);

std::cout<<"The sum is "<<p<<std::endl<<std::endl;

}

[color=blue]采用动态链接库[/color](源文件和采用静态链接库完全相同):

#include "sharedLib.h"

#include <iostream>

int main(void){

std::cout<<"Running "<<__FILE__<<std::endl;

int p=plus(2,3);

std::cout<<"The sum is "<<p<<std::endl<<std::endl;

}

[color=blue]采用动态加载.so文件(fopen)[/color]:

#include <iostream>

#include <dlfcn.h>

#include "sharedLib.h"

typedef int (*F)(int,int);

using FF=int (*)(int,int);

int checkDLLState(void* dp){

const char* dlsym_error= dlerror();

if (dlsym_error) {

std::cerr << "Cannot load symbol : " << dlsym_error <<std::endl;

dlclose(dp);

return 1;

}

return 0;

}

int main(void){

std::cout<<"Running "<<__FILE__<<std::endl;

const char* dllName="./sharedLib.so";

// reset errors

dlerror();

void* dp=dlopen(dllName, RTLD_LAZY);

if(checkDLLState(dp))return -1;

std::cout<<"dp = "<<(unsigned long long)(dp)<<std::endl;

F f;

f=(F)( dlsym(dp,"_Z4plusii")); // if do not want to use this name, add extern "C" before the function "plus"

if(checkDLLState(dp))return -1;

int sum=f(1,2);

std::cout<<"The sum is "<<sum<<std::endl<<std::endl;

dlclose(dp);

}

[color=blue]makefile[/color]:

看不懂的搜下 “跟我一起写makefile”,,我也是简单学了一下而已

终端内输入 make runall就可以执行程序了

all: main_link_a main_link_so main_dynamicLoad

runall: all

echo "now beggin running all executations"

./main_link_a

./main_link_so

./main_dynamicLoad

#use static library

main_link_a: main_link_a.cpp sharedLib.a

g++ -Wall -o main_link_a main_link_a.cpp ./sharedLib.a

sharedLib.a: sharedLib.cpp sharedLib.h

g++ -Wall -static -c -o sharedLib.o sharedLib.cpp

ar rcs sharedLib.a sharedLib.o

#use dynamic library

main_link_so: main_link_so.cpp sharedLib.so

g++ -Wall -o main_link_so main_link_so.cpp ./sharedLib.so -ldl

sharedLib.so: sharedLib.cpp sharedLib.h

g++ -Wall -shared -fPIC -o sharedLib.so sharedLib.cpp

#use fopen, dynamic load .so libarary, use function by name

main_dynamicLoad: main_dynamicLoad.cpp sharedLib.so

g++ -Wall -std=c++11 -o main_dynamicLoad main_dynamicLoad.cpp ./sharedLib.so -ldl #-ldl for dynamic link

#view mangled c++ function name in sharedLib.so

viewFuncName: sharedLib.so

echo viewing mangled function name

nm sharedLib.so #view mangled function name

echo

echo viewing demangled function name

nm sharedLib.so | c++filt #view demangled name

clean:

-rm *.so *.o *.a #the minus sign at the beginning means the commnand after this one will be executed even error occurs.

-rm main_link_a main_link_so main_dynamicLoad

-rm *~

[size=x-large][color=blue]3、设置可执行程序在当前路径下查找.so文件[/color][/size]

自己生成了个.so文件,,还得先加到库路径里才能用?

编译可执行文件时只需要添加[color=blue][b]-rpath=.[/b][/color]选项即可!!!!

完整代码为(-WI选项需不需要我没试):

gcc -o test test.c -I. -L. -la -Wl,-rpath=.

引用自:[url]/cjf_iceking/article/details/25219675[/url]

本内容不代表本网观点和政治立场,如有侵犯你的权益请联系我们处理。
网友评论
网友评论仅供其表达个人看法,并不表明网站立场。