静态库调用静态库&静态库加载静态库------谈谈undefined reference to和linker input file unused because linking not done
2017-06-16 21:57
489 查看
静态库可以调用静态库吗? 静态库可以加载静态库吗? 搞清这些东西, 对于linux开发很重要, 本文我们来探讨这些问题。
先看程序:
business.h:
main.cpp
我们来编译运行看下:
一切正常。
我们再看看:
basic.h
business.h:
main.cpp内容为:
来看看结果:
main.cpp -L. -lbusiness -lbasic, 这就带来了一个问题: libbusiness.a/business.h并不能独立地对外提供能力, 略蛋疼。
怎么办呢? 这里可以考虑两种方法:
a. 把libbasic.a库和libbusiness.a库合成新的libbusiness.a库, 但我个人不建议这么做。
b. 专门为libbusiness.a搞一个宏, 使得每次链接libbusiness.a的时候, 自动也链接到libbasic.a, 这对于使用libbusiness.a的人来说, 是透明的, 不可见的, 不需要管的, 比较爽。
综上所述:
1. 静态库 .a文件(这里更准确的说法应该是.o文件)不能加载其他静态库, 因为只涉及到编译,不涉及到链接。
2. 静态库 .a文件(这里更准确的说法应该是.o文件)可以调用其他静态库(调用其中的函数), 此时并不会链接, 也不需要链接, 也链接不了。
很多时候, 当我们的business模块要调用新的basic模块的静态库时, 要特别特别小心, 否则就会坑后面的同学, 后面同学在编译main的时候(或者其他so需要依赖于business静态库的时候), 肯定会undefined reference to xxx, 不好意思, 我曾经坑过两位同学
其实, “加载”和“链接”的意思是差不多的。 好了, 本文先说道这里, 又有进步啦。
先看程序:
business.h:
#include <iostream> using namespace std; void business();business.cpp:
#include <iostream> #include "business.h" using namespace std; void business() { printf("business code\n"); }
main.cpp
#include <iostream> #include "business.h" using namespace std; int main() { business(); printf("main code\n"); }
我们来编译运行看下:
xxxxxx:~/liblearn> g++ -c business.cpp xxxxxx:~/liblearn> ar rcs libbusiness.a business.o xxxxxx:~/liblearn> ls business.cpp business.h business.o libbusiness.a main.cpp xxxxxx:~/liblearn> g++ main.cpp -L. -lbusiness xxxxxx:~/liblearn> ls a.out business.cpp business.h business.o libbusiness.a main.cpp xxxxxx:~/liblearn> ./a.out business code main code xxxxxx:~/liblearn>
一切正常。
我们再看看:
basic.h
#include <iostream> using namespace std; void basic();basic.cpp
#include <iostream> #include "basic.h" using namespace std; void basic() { printf("basic code\n"); }
business.h:
#include <iostream> using namespace std; void business();business.cpp:
#include <iostream> #include "basic.h" #include "business.h" using namespace std; void business() { basic(); printf("business code\n"); }
main.cpp内容为:
#include <iostream> #include "business.h" using namespace std; int main() { business(); printf("main code\n"); return 0; }
来看看结果:
xxxxxx:~/liblearn> ls basic.cpp basic.h business.cpp business.h main.cpp xxxxxx:~/liblearn> g++ -c basic.cpp xxxxxx:~/liblearn> g++ -c business.cpp xxxxxx:~/liblearn> strings business.o | grep "basic code" xxxxxx:~/liblearn> xxxxxx:~/liblearn> xxxxxx:~/liblearn> ar rcs libbasic.a basic.o xxxxxx:~/liblearn> g++ -c business.cpp -L. -lbasic g++: -lbasic: linker input file unused because linking not done xxxxxx:~/liblearn> strings business.o | grep "basic code" xxxxxx:~/liblearn> xxxxxx:~/liblearn> xxxxxx:~/liblearn> ar rcs libbusiness.a business.o xxxxxx:~/liblearn> g++ main.cpp -L. -lbusiness ./libbusiness.a(business.o): In function `business()': business.cpp:(.text+0x79): undefined reference to `basic()' collect2: ld returned 1 exit status xxxxxx:~/liblearn> xxxxxx:~/liblearn> xxxxxx:~/liblearn> g++ main.cpp -L. -lbusiness -lbasic xxxxxx:~/liblearn> xxxxxx:~/liblearn> xxxxxx:~/liblearn> ./a.out basic code business code main code xxxxxx:~/liblearn> strings a.out | grep "basic code" basic code xxxxxx:~/liblearn>分析一下, 我们看到, 在编译business.cpp后, strings命令的结果没有basic code信息, 也就是business没有加载basic模块的任何东西, 因为这里只是编译, 没有链接. 即使主动链接一下, 也没有鸟用, 还会有warning提示linker input file unused because linking not done, 所以, 很自然地, g++ main.cpp -L. -lbusiness找不到basic, 很自然地需要g++
main.cpp -L. -lbusiness -lbasic, 这就带来了一个问题: libbusiness.a/business.h并不能独立地对外提供能力, 略蛋疼。
怎么办呢? 这里可以考虑两种方法:
a. 把libbasic.a库和libbusiness.a库合成新的libbusiness.a库, 但我个人不建议这么做。
b. 专门为libbusiness.a搞一个宏, 使得每次链接libbusiness.a的时候, 自动也链接到libbasic.a, 这对于使用libbusiness.a的人来说, 是透明的, 不可见的, 不需要管的, 比较爽。
综上所述:
1. 静态库 .a文件(这里更准确的说法应该是.o文件)不能加载其他静态库, 因为只涉及到编译,不涉及到链接。
2. 静态库 .a文件(这里更准确的说法应该是.o文件)可以调用其他静态库(调用其中的函数), 此时并不会链接, 也不需要链接, 也链接不了。
很多时候, 当我们的business模块要调用新的basic模块的静态库时, 要特别特别小心, 否则就会坑后面的同学, 后面同学在编译main的时候(或者其他so需要依赖于business静态库的时候), 肯定会undefined reference to xxx, 不好意思, 我曾经坑过两位同学
其实, “加载”和“链接”的意思是差不多的。 好了, 本文先说道这里, 又有进步啦。
相关文章推荐
- 问题linker input file unused because linking not done
- g++: -l[some]: linker input file unused because linking not done
- g++: -l[some]: linker input file unused because linking not done
- 编译mjpg-streamer input_uvc 错误 linker input file unused because linking not done
- 关于makefile报错:linker input file unused because linking not done
- linker input file unused because linking not done
- [Linux-C++] linker input file unused because linking not done 提示 编译与链接的知识
- 在调用静态库,一直提示undefined reference to 问题解决
- C++调用C静态库,出现undefined reference to “” 的问题
- undefined reference to `av_close_input_file' 原因分析
- 关于[Linker error] undefined reference to `WSAStartup@8'的解决办法作者:chenxusukhoi
- [linker error] undefined reference to vtable for **
- Dev C++中的错误的解决[Linker error] undefined reference to `__cpu_features_init' -chu
- C++调用C的库函数 undefined reference to
- 安装MiniSAP,DAEMON加载CD1,显示“Unable to mount image.File not accessible”
- Eclipse c++ 中[Linker error] undefined reference to `WSAStartup@8'的解决办法
- eclipse里调用接口库时出现了错误 Undefined reference to
- 奇葩问题:This file could not be checked in because the original version of the file on the server was moved or deleted. A new version of this file has been saved to the server, but your check-in comments were not saved
- gcc链接.cpp和.c文件生成的.o库文件的时候,Linking error "undefined reference to `__gxx_personality_v0'"
- [常见问题]Linker error: undefined reference to WSASend