历史上的今天
今天是:2024年12月19日(星期四)
2019年12月19日 | 痞子衡嵌入式:ARM Cortex-M文件那些事(6)- 可执行文件(.out/.e
2019-12-19 来源:eefocus
第四、五节课里,痞子衡已经给大家介绍了2种output文件,本文继续给大家讲project生成的另一种output文件-executable文件,也是特别重要的output文件。
文件关系:链接文件(.icf) + 工程文件(.ewp) + 可重定向文件(.o/.a) -> 可执行文件(.out/.elf)
仔细看过痞子衡之前课程的朋友肯定知道,痞子衡在第四节课可重定向文件(.o/.a)里介绍的object文件在格式上其实跟本文要讲的elf文件是类似的,它们都属于ELF文件分支。只不是relocatable文件只是中间过渡文件,而本文要讲的elf却是标准的output文件,这个文件几乎包含了工程的所有信息,有了这个文件我们既可以在线调试工程,也可以将elf文件转换成image文件,直接下载image文件数据进芯片中脱机运行。今天痞子衡就为大家仔细分析elf文件。
一、elf文件基础
ELF全称Executable and Linkable Format,可执行连接格式,ELF格式的文件最早用于存储Linux程序,后演变到ARM系统上存储ARM程序。ELF文件(目标文件)格式主要三种:
可重定向文件:用来和其他的目标文件一起来创建一个可执行文件或者共享目标文件(也称object文件或者静态库文件,通常后缀为.o和.a的文件)。这个文件是用于编译和链接阶段。
可执行文件:用于生成应用image,载入存储器执行(后缀通常为.out或者.elf)。这个文件是用于加载执行阶段。
共享目标文件:用于和其他共享目标文件或者object文件一起生成可执行文件,或者和可执行文件一起创建应用image。(也称共享库文件,后缀为.so的文件)。这个文件既可用于编译和链接阶段,也可用于加载执行阶段。
我们在ARM开发中更多接触的是前两种格式,第一种格式前面系列文章可重定向文件(.o/.a)已经介绍过,本文的主角是第二种格式-可执行文件。不管是哪种格式的ELF文件,其都可能包含如下三种基本索引表:
file header:一般在文件的开始,描述了ELF文件的整体组织情况。
program header:告诉系统如何创建image,可执行文件必须具有program header,而可重定向文件则不需要。
section header:包含了描述文件section的信息,每个section都有一个header,每一个header给出诸如section名称、section大小等信息。可重定向文件必须包含section header。
既然知道了存在三种索引表,那么表的结构定义在哪里呢?github上的linux仓库里有具体定义,在elf.h头文件里。
Linux仓库:https://github.com/torvalds/linux.git
elf.h路径:linuxincludeuapilinuxelf.h
打开elf.h文件便可找到三个表的原型定义,鉴于目前的ARM Cortex-M都是32bit,所以此处仅列出32bit下的表的原型:Elf32_Ehdr、Elf32_Phdr、Elf32_Shdr。
// file header#define EI_NIDENT 16typedef struct elf32_hdr{
unsigned char e_ident[EI_NIDENT]; /* Magic number and other info */
Elf32_Half e_type; /* Object file type */
Elf32_Half e_machine; /* Architecture */
Elf32_Word e_version; /* Object file version */
Elf32_Addr e_entry; /* Entry point virtual address */
Elf32_Off e_phoff; /* Program header table file offset */
Elf32_Off e_shoff; /* Section header table file offset */
Elf32_Word e_flags; /* Processor-specific flags */
Elf32_Half e_ehsize; /* ELF header size in bytes */
Elf32_Half e_phentsize; /* Program header table entry size */
Elf32_Half e_phnum; /* Program header table entry count */
Elf32_Half e_shentsize; /* Section header table entry size */
Elf32_Half e_shnum; /* Section header table entry count */
Elf32_Half e_shstrndx; /* Section header string table index */ } Elf32_Ehdr;// program headertypedef struct elf32_phdr{
Elf32_Word p_type; /* Segment type */
Elf32_Off p_offset; /* Segment file offset */
Elf32_Addr p_vaddr; /* Segment virtual address */
Elf32_Addr p_paddr; /* Segment physical address */
Elf32_Word p_filesz; /* Segment size in file */
Elf32_Word p_memsz; /* Segment size in memory */
Elf32_Word p_flags; /* Segment flags */
Elf32_Word p_align; /* Segment alignment, file & memory */} Elf32_Phdr;// section headertypedef struct elf32_shdr {
Elf32_Word sh_name; /* Section name, index in string tbl */
Elf32_Word sh_type; /* Type of section */
Elf32_Word sh_flags; /* Miscellaneous section attributes */
Elf32_Addr sh_addr; /* Section virtual addr at execution */
Elf32_Off sh_offset; /* Section file offset */
Elf32_Word sh_size; /* Size of section in bytes */
Elf32_Word sh_link; /* Index of another section */
Elf32_Word sh_info; /* Additional section information */
Elf32_Word sh_addralign; /* Section alignment */
Elf32_Word sh_entsize; /* Entry size if section holds table */} Elf32_Shdr;二、解析elf文件
所谓工欲善其事,必先利其器,在开始解析elf文件之前,我们必须先找到一款合适的解析工具,readelf就是GNU/Linux官方推出的专用解析工具。有了这个解析工具,我们便可以逐步分析elf文件。
2.1 解析工具readelf
既然elf文件是Linux系统下常用的可执行文件格式,那么Linux社区一定会有配套的工具去解析它,是的,这个工具就叫readelf,在GNU工具集binutils里。
2.1.1 GNU工具集(binutils)
GNU是“GNU's Not Unix”的递归缩写,又称为GNU计划,很多著名的开源软件及工具都是GNU开发的(比如大名鼎鼎的C语言编译器GCC)。binutils是GNU一系列binary小工具的集合,大家从下面的链接里找到官方binutils包。
主页:http://www.gnu.org/software/binutils/
仓库:git://sourceware.org/git/binutils-gdb.git
下载:http://ftp.gnu.org/gnu/binutils/
文档:https://sourceware.org/binutils/docs-2.29/binutils/index.html
但是使用上述包里的readelf会有一个问题,上述工具是在Linux系统下使用的,而大家平常做ARM Cortex-M开发很多都是在windows平台下,那么怎么在windows下使用readelf工具呢?别急,cygwin给了我们帮助。
2.1.2 cygwin(windows下使用GNU)
Cygwin是一个在windows平台上运行的类UNIX模拟环境,是cygnus solutions公司(已被Redhat收购)开发的自由软件。它对于学习UNIX/Linux操作环境,或者从UNIX到Windows的应用程序移植,尤其是使用GNU工具集在Windows上进行嵌入式系统开发,非常有用。
Installer:http://cygwin.com/install.html
Package:https://cygwin.com/packages/package_list.html
// 相关工具包 binutils - GNU assembler, linker, and similar utilities cygwin32-binutils - Binutils for Cygwin 32bit toolchain mingw64-x86_64-binutils - Binutils for MinGW-w64 Win64 toolchain mingw64-i686-binutils - Binutils for MinGW-w64 Win32 toolchain
下载安装好cygwin包后,便可在安装目录下cygwin64bin找到x86_64-w64-mingw32-readelf.exe工具(痞子衡选择的是mingw64-x86_64-binutils包)。
2.1.3 readelf.exe用法
readelf.exe遵循标准的windows命令行用法,使用--help可以列出所有命令option及其简介,下面仅列出比较常用的option。
C:cygwin64bin>x86_64-w64-mingw32-readelf.exe --help Usage: readelf
2.2 逐步分析elf文件
万事俱备了,开始分析elf文件,以第三节课工程文件(.ewp)里demo工程为例。编译链接该工程可在D:myProjectbspbuildsdemoReleaseExe路径下得到demo.elf文件。该文件大小32612 bytes,显然这么精简的一个小工程image size不可能这么大,说明elf文件里的记录信息数据占比非常大。
史海拾趣
|
请问各位:基于PID算法的有刷直流电机PWM调速系统中对有刷直流电机调速用到的算法是模拟 PID控制原理还是增量式PID控制或者别的PID控制原理?能否将PID算法式子告诉我?谢谢各位了!!QQ:286410824… 查看全部问答> |
|
本人在使用该芯片过程中遇到一些问题,想请有经验的朋友指教一下。 本人用720极的圆感应同步器作为角度传感器,想利用AD2S80来解码。 激磁信号使用的是5Khz的正弦波,AD2S80设置的分辨率为12位,该芯片的外围电路完全按照芯片手册上的针对5KHZ/12 ...… 查看全部问答> |
|
自己写的服务端和客户端,头文件包含是winsock2.h, 库使用的是Ws2.lib。 客户端发送消息是正常的,服务端也能收到消息,但是接收不到客户端发送的具体消息内容(一个字符串)。 同样的代码在windows下可以正常使用(用的库是ws2_32.lib)。 急 ...… 查看全部问答> |
|
我是MSP430小白,正处于入门阶段。 由于要做课题是关于MSP430平台下的存储,存储介质一般都是sd卡吧,所以我想找一本关于sd卡存储的数据组织、分区分簇(我不知道有没有这个概念,类似硬盘下单扇区之类的),主要介绍它的硬件特性和功能,有没有这 ...… 查看全部问答> |
|
TPS2393A集成电路是一款专为-48V系统优化的热插拔控制器。TPS2393A广泛用于许多应用中,它拥有如下强大功能:. 宽泛的输入电源范围. 可编程电流限制. UV/OV保护.&nbs ...… 查看全部问答> |
|
晒WEBENCH设计的过程+利用易电源设计工具进行一款USB充电器的设计 SIMPLE SWITCHER中文名字叫易电源,顾名思义它是一个非常容易控制的电源芯片。过去分离式方案相比,SIMPLE SWITCHER现在新推出的方案是一种更为集成的解决方案,它把MOS管和电感都集成在芯片内部,这样它就具有了明显的优势:把外部的元器件减少, ...… 查看全部问答> |




