嵌入式Linux编程基础.ppt_第1页
嵌入式Linux编程基础.ppt_第2页
嵌入式Linux编程基础.ppt_第3页
嵌入式Linux编程基础.ppt_第4页
嵌入式Linux编程基础.ppt_第5页
已阅读5页,还剩138页未读 继续免费阅读

下载本文档

版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领

文档简介

1、嵌入式Linux编程基础,南京邮电大学信息安全系,大纲,C文件到二进制文件 嵌入式交叉编译环境构建 嵌入式编译工具使用 基础工具gcc/as/ldd/ar/gdb等使用 高级工具objcopy/strip/readelf/ldd等使用 Make工具及Makefile文件使用 嵌入式可执行文件格式解析,PART ONE,C文件到二进制文件之旅,面向嵌入式系统的软件开发环境(传统的开发环境),编译器,汇编器,liber,连接器,编辑 环境,软件设计,交叉开发环境IDE,Debugger (调试,跟踪),转换程序,仿真器(ICE),目 标 板,烧结程序,串口,并口,以太网,USB,项目 管理,编译器

2、和汇编器的作用,编译器将C文件转换成为汇编文件 汇编器将汇编文件转换成为二进制指令流*.o文件(目标文件) 每个目标文件是独立编址的,也就是说每个目标文件的第一条指令都从相同的地址开始存放,目标文件的结构,TEXT (CODE),DATA,执行代码,有初值的全局变量 或静态变量,无初值的全局变量 或静态变量,RO,RW,ZI,低地址,高地址,ARM CPU,连接器的作用,将多个目标文件或库文件按照各文件中段进行统一编址 生成一个完整的统一的地址印象 嵌入式系统中一般生成一个绝对地址印象(非PIC) 在有MMU的系统中可以为每个任务单独分配一个地址空间,连接器的作用,ROM Based,RAM

3、Base,RO1,ZI 1,RO2,RW2,ZI2,RO3,RW3,ZI3,RO1,RO2,RO3,RW1,RW2,RW3,ZI1,ZI2,ZI3,file1.o,file2.o,file3.o,Link,file.out,RW1,PART TWO,嵌入式交叉编译环境构建,开发环境,交叉编译环境,随着硬件平台和操作系统的多样化,软件向不同平台移植的工作变得越来越繁复。交叉编译技术的引入为软件的不同平台移植创造了便利条件。在交叉编译技术中有两种比较典型的实现: Java模式,即Java的字节码编译技术; GNU GCC 模式,即通常所讲的Cross GCC 技术。,嵌入式交叉编译环境,嵌入式交叉

4、编译环境就是在PC机上建立基于开发板的程序编译环境,它有两个非常显著的特点 第一,整套交叉编译环境建立在PC机上,它和PC机的编译环境共存; 第二,利用交叉编译环境编译出来的可执行程序只能在嵌入式开发板上运行。,(cont.),在linux终端下用vi建立程序exam6-1.c 基于嵌入式开发板进行编译 #arm-linux-gcc o exam6-1-2 exam6-1.c 基于PC机上进行编译: # gcc o exam6-1-1 exam6-1.c 在PC机上执行 # ./exam6-1-1 如果在PC机上执行 ./exam6-1-2 bash: ./exam6-1-2: cannot

5、execute binary file,(cont.),# objdump d exam6-1-1 # arm-linux-objdump d exam6-1-2 可以看出这两个可执行程序的汇编码并不完全相同,Host与Target,是一个基于x86架构的计算机(Pentium4处理器、Athlon处理器等),即i386平台。,Target是目标平台,比如ARM、MIPS、SuperH、PowerPC等。,GNU GCC 模式,计算机源程序(c , java),文本编辑器,计算机系统,目标平台,目标代码,计算机系统,GCC交叉编译器,PART II 嵌入式交叉编译环境, 工具链构成,嵌入式交叉

6、编译环境构建,利用已有的工具链建立,步骤,从网上下载交叉编译工具链压缩包 目前网络上主要流行下列两种类型的压缩包 :cross-2.95.3.tar.bz2 cross-3.3.2.tar.bz2 建立目录 #cd /usr/loal #mkdir arm 将cross-2.95.3.tar.bz2拷贝到/usr/local/arm目录下 解压缩包 #tar xjvf cross-2.95.3.tar.bz2 修改/etc/bashrc文件 编辑/etc/bashrc 文件, 在最后增加路径 export PATH=/usr/local/arm/2.95.3/bin:$PATH,嵌入式交叉编译

7、环境,手动创建新的工具链,Linux 下的GCC 交叉编译器,GNU Binutils GNU Binutils 的主要工具有两个,一个是连接程序ld,另外一个是汇编程序as。其主要目的是为GNU 系统,提供汇编和连接工具。 GNU GCC GNU GCC 就是上面提到的GCC,GCC 主要是为GNU 系统提供C 编译器。现在支持多种语言,这其中包括C/C+、Fortran、Java、Objective-C、甚至还有Ada。 GNU GLibc 用于定义系统调用和其它一些基本的函数调用。,GCC 交叉编译器生成,第一步,取得Binutils、GCC、Glibc 的源码。 第二步,配置并编译Bi

8、nutils 取得我们所需要的汇编和连接程序。 第三步,配置并编译GCC 源码生成GCC 编译器。一般是C 编译器首先生成,然后以这个为基础在结合下一步要生成的Glibc 的C 函数库,再编译生成其它编译器。 第四步,配置Glibc 并编译生成Glibc 的C 函数库。 第五步,再次配置和编译GCC 源码,生成其它语言的编译器,如C+编译器等。,生成的Toolchain,Binutils工具包介绍,addr2line :把程序地址转换为文件名和行号。在命令行中给它一个地址和一个可执行文件名,它就会使用这个可执行文件的调试信息指出在给出的地址上是哪个文件以及行号。 ar:建立、修改、提取归档文件

9、。归档文件是包含多个文件内容的一个大文件,其结构保证了可以恢复原始文件内容。,Binutils工具包介绍,as :主要用来编译GNU C编译器gcc输出的汇编文件,产生的目标文件由连接器ld连接。 c+filt :连接器使用它来过滤C+ 和Java 符号,防止重载函数冲突。 gprof :显示程序调用段的各种数据。 nm :列出目标文件中的符号。,Binutils工具包介绍,objcopy :把一种目标文件中的内容复制到另一种类型的目标文件中。 objdump :显示一个或者更多目标文件的信息。显示一个或者更多目标文件的信息。使用选项来控制其显示的信息。它所显示的信息通常只有编写编译工具的人才

10、感兴趣。,Binutils工具包介绍,ld :连接器。它把一些目标和归档文件结合在一起,重定位数据,并链接符号引用。通常,建立一个新编译程序的最后一步就是调用ld。 ranlib :产生归档文件索引,并将其保存到这个归档文件中。在索引中列出了归档文件各成员所定义的可重分配目标文件。,Binutils工具包介绍,readelf :显示ebf格式可执行文件的信息。 size :列出目标文件每一段的大小以及总体的大小。默认情况下,对于每个目标文件或者一个归档文件中的每个模块只产生一行输出。 strip :丢弃目标文件中的全部或者特定符号。,Binutils工具包介绍,strings :打印某个文件的

11、可打印字符串,这些字符串最少4个字符长,也可以使用选项-n设置字符串的最小长度。默认情况下,它只打印目标文件初始化和可加载段中的可打印字符;对于其它类型的文件它打印整个文件的可打印字符,这个程序对于了解非文本文件的内容很有帮助。,gcc编译器介绍,cpp: C预处理器。 g+:C+ 编译器。 gcc :C编译器。 gccbug :创建bug报告的shell脚本。 libgcc* :gcc的运行库。 libstdc+:标准C+ 库,包含许多常用的函数。 libsupc+:提供支持C+语言的库函数。,glibc库介绍,catchsegv :当程序发生segmentation fault的时候,用来

12、建立一个堆栈跟踪。 gencat :建立消息列表。 getconf :针对文件系统的指定变量显示其系统设置值。 getent :从系统管理数据库获取一个条目。,glibc库介绍,glibcbug :建立glibc的bug报告并且email到bug报告的邮件地址。 iconv :转化字符集。 iconvconfig :建立快速读取的iconv模块所使用的设置文件。 ldconfig :设置动态链接库的实时绑定。 ldd :列出每个程序或者命令需要的共享库。,glibc库介绍,lddlibc4 :辅助ldd操作目标文件。 locale :可以告诉编译器打开或关闭内建的locale支持的Perl程序

13、。 localedef :编译locale标准。 nscd :提供对常用名称设备调用的缓存的守护进程。 nscd_nischeck:检查在进行NIS+侦查时是否需要安全模式。,glibc库介绍,pcprofiledump :打印PC profiling产生的信息。 pt_chown:帮助grantpt设置子虚拟终端的属主,用户组和读写权限。 rpcgen :产生实现RPC协议的C代码。 rpcinfo :对RPC服务器产生一个RPC呼叫。,PART THREE 交叉编译工具使用, arm-linux-gcc使用,编译器编译生成目标代码任务步骤,预处理,把预处理命令扫描处理完毕; 编译,把预处理

14、后的结果编译成汇编或者目标模块; 汇编,把编译出来的结果汇编成具体CPU上的目标代码模块; 连接,把多个目标代码模块连接生成一个大的目标模块;,预编译,编译器是怎么知道 deck_t 类型是什么的呢?因为在预编译期间,它实际上把deck.h文件复制到了game.c文件中。源代码中的预编译指示以#为前缀。你可以通过在gcc后加上 -E 选项来调用预编译器 gcc -E -o game_precompile.txt game.c,预编译过程通过完成三个主要任务给了代码很大的灵活性。 把include的文件拷贝到要编译的源文件中。 用实际值替代define的文本,在调用宏的地方进行宏替换。 条件编译

15、,编译,作为一个中间步骤,gcc把你的代码翻译成汇编语言。它一定要这样做,它必须通过分析你的代码搞清楚你究竟想要做什么。如果你犯了语法错误,它就会告诉你,这样编译就失败了。人们有时会把这一步误解为整个过程。但是,实际上还有许多工作要gcc去做呢。,汇编,as 把汇编语言代码转换为目标代码。事实上目标代码并不能在CPU上运行,但它离完成已经很近了。编译器选项 -c 把 .c 文件转换为以 .o 为扩展名的目标文件。 如果我们运行 gcc -c game.c我们就自动创建了一个名为game.o的文件。,连接,连接器ld,使用下面的命令,接受前面由 as 创建的目标文件并把它转换为可执行文件 gcc

16、 -o game main.o game.o 这将把两个目标文件组合起来并创建可执行文件 game 连接器从game.o目标文件中找到 playgame函数,并把它包括进可执行文件。,虽然我们并没有编写前面作为调试语句调用的 printf 函数,连接器却能从我们用 #include 语句包含的文件中找到它的声明,并把存储在C库(/lib/libc.so.6)中的目标代码连接进来。这种方式使我们可以使用已能正确工作的其他人的函数,只关心我们所要解决的问题。这就是为什么头文件中一般只含有数据和函数声明,而没有函数体。一般,你可以为连接器创建目标文件或函数库,以便连接进可执行文件。我们的代码可能产生

17、问题,因为在头文件中我们没有放入任何函数声明。,arm-linux-*重点工具介绍,C/C+编译器arm-linux-gcc arm-linux -gcc主要功能是将源程序编译成汇编代码,它有十分丰富的命令选项,可以控制编译的各个阶段。 汇编器arm-linux as 汇编器arm-linux -as将arm-linux -gcc编译的汇编代码转换为目标代码 连接器arm-linux -ld 在编写一个大的程序时,经常把它分成许多独立的模块,这时需要连接器所有的模块组合起来,并结合c函数库和初始化代码,产生最后可执行的文件。 库管理器arm-linux ar 可以使用ar程序建立静态库,把几个

18、小文件合并成一个大文件。建立静态库时,必须把几个.O文件合并成一个单独的.a文件。,GCC编译过程,交叉编译器arm-linux-gcc,概述 arm-linux-gcc是嵌入式Linux系统平台下的gcc,是GNU推出的功能强大、性能优越的多平台编译器,是GNU的代表作品之一。arm-linux-gcc可以在多种硬体平台上编译出可执行程序的超级编译器,其执行效率与一般的编译器相比平均效率要高20%30%。,交叉编译器arm-linux-gcc,arm-linux-gcc语法形式 arm-linux-gcc option | filename . 通常情况下,产生一个新的程序需要经过四个阶段:

19、预处理、编译、汇编,链接 当然我们可以通过参数决定该编译操作执行到何步结束,arm-linux-gcc常用命令选项,参数繁多,在Linux环境下寻求帮助 man arm-linux -gcc -S 只对文件进行编译,但是并不进行汇编和链接。 例: arm-linux -gcc-S main.c 上例中就会产生一个汇编文件main.S,arm-linux -gcc常用命令选项,-E 只对文件进行预处理,但不需要进行编译、汇编和链接。 例: arm-linux -gcc-E main.c-o main1.c 用vi看看main1.c vi main1.c,arm-linux -gcc常用命令选项,

20、-c 只对文件进行编译和汇编,但是并不进行链接,也就是说只把程序做成obj文件。 例: arm-linux -gcc-c main.c 将生成.o的obj文件 生成main.o文件,arm-linux -gcc常用命令选项,-o 指定目标名称,缺省的时候,gcc编译出来的文件是a.out 例: arm-linux -gcc main.c arm-linux -gcc-o main.exe main.c arm-linux -gcc-o main.asm-S main.c 生成的目标文件名分别为a.out、 main.exe、 main.asm文件,arm-linux -gcc常用命令选项,-i

21、ncludefile 包含某个代码,简单来说,就是编译某个文件时需要另一个文件的时候,就可以用它设定,功能就相当于在代码中使用#include。 例: arm-linux -gccmain1.c-include type.h,arm-linux -gcc常用命令选项,-I dir 如果使用#include“file”的时候,gcc/g+会先在当前目录查找你所指定的头文件,如果没有找到,编译器会到缺省的头文件目录找; 如果使用-I指定了目录, 编译器会先到你所指定的目录查找,然后再按常规的顺序去找。 例: arm-linux -gcc -o main -I . main3.c -I 就是取消前一

22、个参数的功能,所以一般在-Idir之后使用,arm-linux -gcc常用命令选项,-iprefixprefix和-iwithprefixdir 这两个参数一般一起使用,当-I的目录查找失败,会到prefix+dir下查找 -llibrary 指定编译的时候使用的库 例: arm-linux -gcc-lcurseshello.c,arm-linux -gcc常用命令选项,-Ldir 指定编译的时候,搜索库的路径。比如自己的库,就可以用它指定到你的库所在的目录,不然编译器将只在标准库的目录找。这个dir就是目录的名称。 -O0 O1 O2 -O3 编译器的优化选项的4个级别, -O0:表示没

23、有优化; -O1:为缺省值: -O3优化级别最高,arm-linux -gcc常用命令选项,-g 编译器在编译的时候产生调试信息。 例: arm-linux gcc o main -gmain1.c,PART THREE 交叉编译工具使用,其它工具的使用,C预处理器cpp,语法格式 cpp options file.,#define number (23) #include main( ) printf(“%d”, number *4); #cpp example6-3.c -o temp.c 或 #arm-linux-gcc -E -o temp.c example6-3.c,arm-lin

24、ux-as:嵌入式汇编器,arm-linux-as语法格式 arm-elf-as OPTION 汇编文件,arm-linux-ld :嵌入式linux链接器,语法格式: arm-linux-ld option file ,链接脚本文件的编写,连接脚本文件描述了如何将多个目标码文件连接到一起,读者可以使用下列命令来察看: #arm-linux-ld verbose 当然此时使用到的连接脚本文件为内部脚本文件,读者可以自己编写连接脚本文件,rootlichao kkk# vi section.lmds OUTPUT_ARCH(arm) SECTIONS . = 0 x100000; .text :

25、 *(.text) . = 0 x8000000; .data : *(.data) .bss : *(.bss) arm-linux-ld -o exp2 hello.o main.o -T section.lmds -Map map.txt -lc,命令脚本定义,ENTRY(SYMBOL) : 将符号SYMBOL的值设置成入口地址 入口地址(entry point): 进程执行的第一条用户空间的指令在进程地址空间的地址) ld有多种方法设置进程入口地址, 按一下顺序: (编号越前, 优先级越高)1, ld命令行的-e选项2, 连接脚本的ENTRY(SYMBOL)命令3, 如果定义了star

26、t符号, 使用start符号值4, 如果存在。text section, 使用。text section的第一字节的位置值5, 使用值0,INCLUDE filename : 包含其他名为filename的链接脚本 INPUT(files): 将括号内的文件做为链接过程的输入文件 OUTPUT(FILENAME) : 定义输出文件的名字 STARTUP(filename) : 指定filename为第一个输入文 件 OUTPUT_FORMAT(BFDNAME) : 设置输出文件使用的BFD格,arm-linux-objdump,该工具显示一个或者更多目标文件的信息,即以一种可阅读的格式让程序员

27、更多地了解二进制文件可能带有的附加信息。对于一般只想让自己程序跑起来的程序员,这个命令没有更多意义,对于想进一步了解系统的程序员,应该掌握这种工具。它所显示的信息通常只有编写编译工具的人才感兴趣。 语法格式: arm-linux-objdump option 可执行文件名 -a 显示档案库的成员信息 -D 反汇编所有段 -h 显示目标文件各个section的头部摘要信息。 -help 简短的帮助信息 -d 反汇编代码段,arm-linux-ldd,语法格式: ldd -version -v|-verbose -d|-data-relocs -r|-function-relocs -help F

28、ILE. -version : 此选项用于打印出ldd的版本号。 -v 或 -verbose : 此选项指示ldd输出关于所依赖的动态链接库的尽可能详细的信息。 -d 或 -data-relocs : 此选项执行重定位,并且显示不存在的函数。 -r 或 -function-relocs : 此选项执行数据对象与函数的重定位,同时报告不存在的对象。 help: 此选项用于打印出ldd的帮助信息,例:查看可执行文件需要的库,# ldd -v dd libc.so.6 = /lib/tls/libc.so.6 (0 x42000000) /lib/ld-linux.so.2 = /lib/ld-li

29、nux.so.2 (0 x40000000) Version information: ./dd: libc.so.6 (GLIBC_2.1.3) = /lib/tls/libc.so.6 libc.so.6 (GLIBC_2.1) = /lib/tls /libc.so.6 libc.so.6 (GLIBC_2.3) = /lib/tls /libc.so.6 libc.so.6 (GLIBC_2.0) = /lib/tls /libc.so.6 libc.so.6 (GLIBC_2.2) = /lib/tls /libc.so.6 /lib/tls /libc.so.6: ld-linux

30、.so.2 (GLIBC_2.3) = /lib/ld-linux.so.2 ld-linux.so.2 (GLIBC_2.1) = /lib/ld-linux.so.2 ld-linux.so.2 (GLIBC_2.0) = /lib/ld-linux.so.2 ld-linux.so.2 (GLIBC_PRIVATE) = /lib/ld-linux.so.2,命令选项功能描述-archive-headers-a 显示档案库的成员信息,与 ar tv 类似-disassemble-all-D与 -d 类似,但反汇编所有段-section-headers-headers-h 显示目标文件各个

31、section的头部摘要信息。-help 简短的帮助信息。,arm-linux-strip,strip经常用来去除目标文件中的一些符号表、调试符号表等信息,以减小程序的大小。strip的默认选项会去除.symbol节的内容以及.debug节的内容,因此尽量只对可执行文件执行strip而不要对静态库或动态库等目标文件strip。 arm-linux-strip 选项 objfile.,使用举例,(1)移除所有的符号信息 armlocalhost gcc#cp hello hello1 armlocalhost gcc#arm-linux-strip stripall hello stripall

32、: 移除所有符号信息 armlocalhost gcc#ls -l rwxrxrx 1 arm root 2856 7月 3 15:14 hello rwxrxrx 1 arm root 13682 7月 3 15:13 hello1 被strip后的hello程序比原来的hello1程序要小很多。 (2)移除调试符号信息 armlocalhost gcc#arm-linux-strip g hello armlocalhost gcc#ls -l rwxrxrx 1 arm root 4501 7月 3 15:17 hello rwxrxrx 1 arm root 13682 7月 3 15

33、:13 hello1,arm-linux-readelf,readelf用来显示ELF格式目标文件的信息,可通过参数选项来控制显示哪些特定信息(注意: readelf不支持显示archive文档, 也不支持64位的ELF文件) readelf 选项 elffile.,ELF格式,Executable and linking format(ELF)文件是x86 Linux系统下的一种常用目标文件(object file)格式,有三种主要类型: 适于连接的可重定位文件(relocatable file),可与其它目标文件一起创建可执行文件和共享目标文件。 适于执行的可执行文件(executable

34、 file),用于提供程序的进程映像,加载的内存执行。 共享目标文件(shared object file),连接器可将它与其它可重定位文件和共享目标文件连接成其它的目标文件,动态连接器又可将它与可执行文件和其它共享目标文件结合起来创建一个进程映像。,文件格式,ELF header在文件开始处描述了整个文件的组织,Section提供了目标文件的各项信息(如指令、数据、符号表、重定位信息等) Program header table指出怎样创建进程映像,含有每个program header的入口 Section header table包含每一个section的入口,给出名字、大小等信息。,in

35、t addfun(int x,int y) int z; z=x+y; return z; int sum; int a=10; void main() int b=20; addfun(a,b); ,ELF Header: Magic: 7f 45 4c 46 01 01 01 00 00 00 00 00 00 00 00 00 Class: ELF32 Data: 2s complement, little endian Version: 1 (current) OS/ABI: UNIX - System V ABI Version: 0 Type: EXEC (Executable f

36、ile) Machine: Intel 80386 Version: 0 x1 Entry point address: 0 x8048244 Start of program headers: 52 (bytes into file) Start of section headers: 1432 (bytes into file) Flags: 0 x0 Size of this header: 52 (bytes) Size of program headers: 32 (bytes) Number of program headers: 6 Size of section headers

37、: 40 (bytes) Number of section headers: 23 Section header string table index: 22,rootlichao elf-exam# readelf -a hello ELF Header: Magic: 7f 45 4c 46 01 01 01 00 00 00 00 00 00 00 00 00 Class: ELF32 Data: 2s complement, little endian Version: 1 (current) OS/ABI: UNIX - System V ABI Version: 0 Type:

38、EXEC (Executable file) Machine: Intel 80386 Version: 0 x1 Entry point address: 0 x8048244 Start of program headers: 52 (bytes into file) Start of section headers: 1432 (bytes into file) Flags: 0 x0 Size of this header: 52 (bytes) Size of program headers: 32 (bytes) Number of program headers: 6 Size

39、of section headers: 40 (bytes) Number of section headers: 23 Section header string table index: 22,Section Headers: Nr Name Type Addr Off Size ES Flg Lk Inf Al 0 NULL 00000000 000000 000000 00 0 0 0 1 .interp PROGBITS 080480f4 0000f4 000013 00 A 0 0 1 2 .note.ABI-tag NOTE 08048108 000108 000020 00 A

40、 0 0 4 3 .hash HASH 08048128 000128 000024 04 A 4 0 4 4 .dynsym DYNSYM 0804814c 00014c 000040 10 A 5 1 4 5 .dynstr STRTAB 0804818c 00018c 000045 00 A 0 0 1 6 .gnu.version VERSYM 080481d2 0001d2 000008 02 A 4 0 2 7 .gnu.version_r VERNEED 080481dc 0001dc 000020 00 A 5 1 4 8 .rel.dyn REL 080481fc 0001f

41、c 000008 08 A 4 0 4 9 .rel.plt REL 08048204 000204 000008 08 A 4 b 4 10 .init PROGBITS 0804820c 00020c 000017 00 AX 0 0 4 11 .plt PROGBITS 08048224 000224 000020 04 AX 0 0 4 12 .text PROGBITS 08048244 000244 00017c 00 AX 0 0 4 13 .fini PROGBITS 080483c0 0003c0 00001b 00 AX 0 0 4 14 .rodata PROGBITS

42、080483dc 0003dc 000008 00 A 0 0 4 15 .eh_frame PROGBITS 080483e4 0003e4 000004 00 A 0 0 4 16 .data PROGBITS 080493e8 0003e8 000010 00 WA 0 0 4 17 .dynamic DYNAMIC 080493f8 0003f8 0000c8 08 WA 5 0 4 18 .ctors PROGBITS 080494c0 0004c0 000008 00 WA 0 0 4 19 .dtors PROGBITS 080494c8 0004c8 000008 00 WA

43、0 0 4 20 .jcr PROGBITS 080494d0 0004d0 000004 00 WA 0 0 4 21 .got PROGBITS 080494d4 0004d4 000014 04 WA 0 0 4 22 .shstrtab STRTAB 00000000 0004e8 0000b0 00 0 0 1 Key to Flags: W (write), A (alloc), X (execute), M (merge), S (strings) I (info), L (link order), G (group), x (unknown) O (extra OS proce

44、ssing required) o (OS specific), p (processor specific),Program Headers: Type Offset VirtAddr PhysAddr FileSiz MemSiz Flg Align PHDR 0 x000034 0 x08048034 0 x08048034 0 x000c0 0 x000c0 R E 0 x4 INTERP 0 x0000f4 0 x080480f4 0 x080480f4 0 x00013 0 x00013 R 0 x1 Requesting program interpreter: /lib/ld-

45、linux.so.2 LOAD 0 x000000 0 x08048000 0 x08048000 0 x003e8 0 x003e8 R E 0 x1000 LOAD 0 x0003e8 0 x080493e8 0 x080493e8 0 x00100 0 x00100 RW 0 x1000 DYNAMIC 0 x0003f8 0 x080493f8 0 x080493f8 0 x000c8 0 x000c8 RW 0 x4 NOTE 0 x000108 0 x08048108 0 x08048108 0 x00020 0 x00020 R 0 x4 Section to Segment m

46、apping: Segment Sections. 00 01 .interp 02 .interp .note.ABI-tag .hash .dynsym .dynstr .gnu.version .gnu.version_r .rel.dyn .rel.plt .init .plt .text .fini .rodata .eh_frame 03 .data .dynamic .ctors .dtors .jcr .got 04 .dynamic 05 .note.ABI-tag,Dynamic segment at offset 0 x3f8 contains 20 entries: T

47、ag Type Name/Value 0 x00000001 (NEEDED) Shared library: libc.so.6 0 x0000000c (INIT) 0 x804820c 0 x0000000d (FINI) 0 x80483c0 0 x00000004 (HASH) 0 x8048128 0 x00000005 (STRTAB) 0 x804818c 0 x00000006 (SYMTAB) 0 x804814c 0 x0000000a (STRSZ) 69 (bytes) 0 x0000000b (SYMENT) 16 (bytes) 0 x00000015 (DEBU

48、G) 0 x0 0 x00000003 (PLTGOT) 0 x80494d4 0 x00000002 (PLTRELSZ) 8 (bytes) 0 x00000014 (PLTREL) REL 0 x00000017 (JMPREL) 0 x8048204 0 x00000011 (REL) 0 x80481fc 0 x00000012 (RELSZ) 8 (bytes) 0 x00000013 (RELENT) 8 (bytes) 0 x6ffffffe (VERNEED) 0 x80481dc 0 x6fffffff (VERNEEDNUM) 1 0 x6ffffff0 (VERSYM)

49、 0 x80481d2 0 x00000000 (NULL) 0 x0,Relocation section .rel.dyn at offset 0 x1fc contains 1 entries: Offset Info Type Sym.Value Sym. Name 080494e4 00000306 R_386_GLOB_DAT 00000000 _gmon_start_ Relocation section .rel.plt at offset 0 x204 contains 1 entries: Offset Info Type Sym.Value Sym. Name 08049

50、4e0 00000107 R_386_JUMP_SLOT 08048234 _libc_start_main There are no unwind sections in this file. Symbol table .dynsym contains 4 entries: Num: Value Size Type Bind Vis Ndx Name 0: 00000000 0 NOTYPE LOCAL DEFAULT UND 1: 08048234 251 FUNC GLOBAL DEFAULT UND _libc_start_mainGLIBC_2.0 (2) 2: 080483e0 4

51、 OBJECT GLOBAL DEFAULT 14 _IO_stdin_used 3: 00000000 0 NOTYPE WEAK DEFAULT UND _gmon_start_,Histogram for bucket list length (total of 3 buckets): Length Number % of total Coverage 0 0 ( 0.0%) 1 3 (100.0%) 100.0% Version symbols section .gnu.version contains 4 entries: Addr: 00000000080481d2 Offset:

52、 0 x0001d2 Link: 4 (.dynsym) 000: 0 (*local*) 2 (GLIBC_2.0) 1 (*global*) 0 (*local*) Version needs section .gnu.version_r contains 1 entries: Addr: 0 x00000000080481dc Offset: 0 x0001dc Link to section: 5 (.dynstr) 000000: Version: 1 File: libc.so.6 Cnt: 1 0 x0010: Name: GLIBC_2.0 Flags: none Versio

53、n: 2,使用举例2,#vi hello.c #include void main() printf(“hello worldn”); #arm-linux-gcc o hello hello.c (1)读elf文件开始的文件头部 rootlichao gccexample# arm-linux-readelf -h hello ELF Header: Magic: 7f 45 4c 46 01 01 01 61 00 00 00 00 00 00 00 00 Class: ELF32 . (4). 显示使用的动态库 rootlichao gccexample# arm-linux-reade

54、lf -d hello Dynamic segment at offset 0 x468 contains 20 entries: Tag Type Name/Value 0 x00000001 (NEEDED) Shared library: libc.so.6 .,(2). 读elf文件中所有ELF 的头部: armlocalhost gcc# arm-linux-readelf e hello ELF Header: Magic: 7f 45 4c 46 01 01 01 61 00 00 00 00 00 00 00 00 Section Headers: Nr Name Type A

55、ddr Off Size ES Flg Lk Inf Al 0 NULL 00000000 000000 000000 00 0 0 0 Program Headers: Type Offset VirtAddr PhysAddr FileSiz MemSiz Flg Align PHDR 0 x000034 0 x00008034 0 x00008034 0 x000c0 0 x000c0 R E 0 x4 ,(3) 显示整个文件的符号表 rootlichao gccexample# arm-linux-readelf -s hello Symbol table .dynsym contai

56、ns 6 entries: Num: Value Size Type Bind Vis Ndx Name 0: 00000000 0 NOTYPE LOCAL DEFAULT UND 1: 00008284 492 FUNC GLOBAL DEFAULT UND abortGLIBC_2.0 (2) 2: 00008294 264 FUNC GLOBAL DEFAULT UND _libc_start_mainGLIBC_2.0 (2) 3: 000082a4 64 FUNC GLOBAL DEFAULT UND printfGLIBC_2.0 (2) 4: 0000841c 4 OBJECT

57、 GLOBAL DEFAULT 14 _IO_stdin_used 5: 00000000 0 NOTYPE WEAK DEFAULT UND _gmon_start_ Symbol table .symtab contains 94 entries: Num: Value Size Type Bind Vis Ndx Name 0: 00000000 0 NOTYPE LOCAL DEFAULT UND 1: 000080f4 0 SECTION LOCAL DEFAULT 1 2: 00008110 0 SECTION LOCAL DEFAULT 2,arm-linux-objcopy,工

58、具程序objcopy的作用是拷贝一个目标文件的内容到另一个目标文件中。Objcopy使用GNU BFD库去读或写目标文件。Objcopy可以使用不同于源目标文件的格式来写目的目标文件(也即是说可以将一种格式的目标文件转换成另一种格式的目标文件)。 bjcopy在进行目标文件的转换时,将生成一个临时文件,转换完成后就将这个临时文件删掉。 使用Objcopy生成S记录格式文件或者原始的二进制文件的过程中,-S选项和-R选项可能会比较有用。-S选项是用来删掉包含调试信息的部分,-R选项是用来删掉包含了二进制文件不需要的内容的那些部分。 arm-linux-objcopy 选项 infile outfile 例:objcopy有一个很重要的作用是把代码从elf文件中抽取出来,形成可执行的机器码: arm-elf-o

温馨提示

  • 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
  • 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
  • 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
  • 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
  • 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
  • 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
  • 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

最新文档

评论

0/150

提交评论