linux应用开发基础(一)GCC编译器、动态库、静态库使用
2017-07-29 16:44
267 查看
2017.7.29,开始巩固Linux应用开发的一些基础内容
编译过程:
把一个.c文件编程一个可执行文件,其实就是这四个步骤:
预处理->编译->汇编->连接
再具体说明这几个过程的作用:
预处理阶段:
在该阶段,对包含的头文件(#include)和宏定义(#define、#ifdef等)进行处理 (替换)。预编译程序所完成的基本上是对源程序的“替代”工作。经过此种替代,生成一个没有宏定义、没有条件编译指令、没有特殊符号的输出文件。可以使用gcc的选项“-E” 让gcc在预处理结束后停止编译过程,如下!
编译阶段:
接下来进行的是编译阶段,在这个阶段中,gcc首先要检查代码的规范性、是否有语法错误等,以确定代码的实际要做的工作,在检查无误后,gcc把代码翻译成汇编语言。用户可以使用“-S”选项来进行查看,该选项只进行编译而不进行汇编,生成汇编代码。
汇编阶段:
该阶段就是把编译阶段生成的目标“.s”文件生成目标文件
链接阶段:
链接是把.s汇编文件链接生成.o的目标文件,链接的作用把你使用的函数实现链接起来,比如你的程序使用了printf()函数,而“stdio.h”中也只有该函数的声明,而没有该该函数的实现,那么就需要也就是链接到libc.so.6库函数中去,这样就能够调用函数“printf”了,而这也是链接的作用。其命令如下:
其实gcc命令顺序可以变,但是大家一定要记住!-o后面一定是生成得目标文件
平时如果想把.c文件编译成可执行文件,直接如下就行
为了方便理解,这是gcc所支持后缀名解释:
静态库是一系列的目标文件(.o文件)的归档文件(文件名格式为libxxx.a),如果在编译某个程序时链接静态库,则链接器将会搜索静态库,从中提取出它所需要的目标文件并直接拷贝到该程序的可执行二进制文件(ELF格式文件)之中;静态库只在程序链接时起作用,最终的执行程序脱离静态库运行。
动态库
动态库(文件名格式为libxxx.so)在程序编译时并不会被链接到目标代码中,而是在程序运行时才被载入。
hello.c
hello.h
main.c
首先把hello.c生成.o目标文件
把hello.o生成静态库.a
libmy_lib.a就是我们的静态库,静态库的命名规则:lib库名.a
这个时候你可以把库libmy_lib.a和头文件hello.h、给其他人使用了
然后main.c就可以使用这个库生成可执行文件
注意:-L./是指链接库的位置,即当前目录下
那如果我的头文件hello.h是在./include目录下呢
gcc 里关于库的一些选项:
还是上面的hello.c hello.h main.c
创建libmy_lib.so:
动态库的命名规则:lib库名.so
生成可执行文件main
运行时候
发现执行错误,原因是动态库libmy_lib.so路径没找到,动态库不是在当前目录下吗?怎么又找不到!!因为运行文件用到函数的动态库,系统默认是在/lib或者/usr/lib/目录下,由/etc/ld.so.conf设置。
解决方法:
第一种方法:将libmy_lib.so复制到/lib或者/usr/lib/目录中
第二种方法:将库路径添加到环境变量LD_LIBRARY_PATH中去使用export指令
第三种方法:配置文件/etc/ld.so.conf中指定的动态库搜索路径
第四种方法:编译目标代码时指定的动态库搜索路径
一:gcc编译器
GNU CC(简称为gcc)是GNU项目中符合ANSI C标准的编译系统,能够编译用C、C++和Object C等语言编写的程序。gcc不仅功能强大,而且可以编译如C、C++、Object C、Java、Fortran、Pascal、Modula-3和Ada等多种语言,而且gcc又是一个交叉平台编译器,适合在多种架构中开发程序!!编译过程:
把一个.c文件编程一个可执行文件,其实就是这四个步骤:
预处理->编译->汇编->连接
再具体说明这几个过程的作用:
预处理阶段:
在该阶段,对包含的头文件(#include)和宏定义(#define、#ifdef等)进行处理 (替换)。预编译程序所完成的基本上是对源程序的“替代”工作。经过此种替代,生成一个没有宏定义、没有条件编译指令、没有特殊符号的输出文件。可以使用gcc的选项“-E” 让gcc在预处理结束后停止编译过程,如下!
gcc –E hello.c –o hello.i
编译阶段:
接下来进行的是编译阶段,在这个阶段中,gcc首先要检查代码的规范性、是否有语法错误等,以确定代码的实际要做的工作,在检查无误后,gcc把代码翻译成汇编语言。用户可以使用“-S”选项来进行查看,该选项只进行编译而不进行汇编,生成汇编代码。
gcc –S hello.i –o hello.s
汇编阶段:
该阶段就是把编译阶段生成的目标“.s”文件生成目标文件
gcc –c hello.s -o hello.o
链接阶段:
链接是把.s汇编文件链接生成.o的目标文件,链接的作用把你使用的函数实现链接起来,比如你的程序使用了printf()函数,而“stdio.h”中也只有该函数的声明,而没有该该函数的实现,那么就需要也就是链接到libc.so.6库函数中去,这样就能够调用函数“printf”了,而这也是链接的作用。其命令如下:
gcc hello.o –o hello
其实gcc命令顺序可以变,但是大家一定要记住!-o后面一定是生成得目标文件
平时如果想把.c文件编译成可执行文件,直接如下就行
gcc hello.c -o hello
为了方便理解,这是gcc所支持后缀名解释:
二:动静态库
静态库:静态库是一系列的目标文件(.o文件)的归档文件(文件名格式为libxxx.a),如果在编译某个程序时链接静态库,则链接器将会搜索静态库,从中提取出它所需要的目标文件并直接拷贝到该程序的可执行二进制文件(ELF格式文件)之中;静态库只在程序链接时起作用,最终的执行程序脱离静态库运行。
动态库
动态库(文件名格式为libxxx.so)在程序编译时并不会被链接到目标代码中,而是在程序运行时才被载入。
实践是最好的说明:
静态库例子:hello.c
#include<stdio.h> void hello() { printf("hello world\n"); }
hello.h
void hello();
main.c
#include <stdio.h> #include "hello.h" int main() { hello(); return 0; }
首先把hello.c生成.o目标文件
gcc –c hello.c -o hello.o
把hello.o生成静态库.a
ar rcsv libmy_lib.a hello.o
libmy_lib.a就是我们的静态库,静态库的命名规则:lib库名.a
这个时候你可以把库libmy_lib.a和头文件hello.h、给其他人使用了
然后main.c就可以使用这个库生成可执行文件
gcc main.c -o main -L./ -lmy_lib
注意:-L./是指链接库的位置,即当前目录下
那如果我的头文件hello.h是在./include目录下呢
gcc main.c -o main -I./include -L./ -lmy_lib
gcc 里关于库的一些选项:
标题
动态库:还是上面的hello.c hello.h main.c
创建libmy_lib.so:
gcc -shared -fpic hello.c -o libmy_lib.so
动态库的命名规则:lib库名.so
gcc main.c -o main -L./ -lmy_lib
生成可执行文件main
运行时候
./main
发现执行错误,原因是动态库libmy_lib.so路径没找到,动态库不是在当前目录下吗?怎么又找不到!!因为运行文件用到函数的动态库,系统默认是在/lib或者/usr/lib/目录下,由/etc/ld.so.conf设置。
解决方法:
第一种方法:将libmy_lib.so复制到/lib或者/usr/lib/目录中
第二种方法:将库路径添加到环境变量LD_LIBRARY_PATH中去使用export指令
第三种方法:配置文件/etc/ld.so.conf中指定的动态库搜索路径
第四种方法:编译目标代码时指定的动态库搜索路径
相关文章推荐
- 【C/C++开发】C++静态库与动态库以及在Linux和Windows上的创建使用
- Linux中静态库和动态库的创建和使用
- Linux下静态库和动态库(共享库)的制作与使用
- linux 下动态库、静态库嵌套使用
- 一步一步教你使用AgileEAS.NET基础类库进行应用开发-基础篇-类库介绍
- linux下静态库、动态库的编译和使用
- 用Java快速开发Linux GUI应用-Java基础-Java-编程开发
- 一步一步教你使用AgileEAS.NET基础类库进行应用开发-基础篇-UDA中的委托与应用
- 一步一步教你使用AgileEAS.NET基础类库进行应用开发-基础篇-演示ORM中的查询
- Linux动态库和静态库的建立及使用方法
- 使用Eclipse和AJDT开发AspectJ应用(1)- 基础篇
- 一步一步教你使用AgileEAS.NET基础类库进行应用开发-基础篇-UDA中处理事务
- 一步一步教你使用AgileEAS.NET基础类库进行应用开发-基础篇-UDA应用中使用IOC解偶数据连接环境
- 学习使用J2EE Web应用的事件功能-Java基础-Java-编程开发
- linux下c/c++编译器和调试器以及静态库、动态库使用汇总
- 一步一步教你使用AgileEAS.NET基础类库进行应用开发-基础篇-演示ORM的基本操作
- 一步一步教你使用AgileEAS.NET基础类库进行应用开发-基础篇-涉及的数据定义
- 使用 Java 进行 MySQL 开发 (摘自:MySQL for Linux on POWER,第 2 部分: 开发应用)
- 一步一步教你使用AgileEAS.NET基础类库进行应用开发-系列目录
- 使用Eclipse和AJDT开发AspectJ应用(1)- 基础篇