我们知道,程序通过汇编、C等语言罪IDE中编写,然后通过编译器变成了CPU能够执行的格式来执行,这些编译好的数据需要被存储在磁盘上,然后我们可以通过系统调用告诉OS(操作系统),由OS来获取这些编译好的数据,并进行解析,将它们从磁盘加载到内存中,然后创建一个进程来代表这个程序,最后让CPU执行。在这个过程中,最重要的便是将这些编译好的数据时如何被存储的,以及它们的格式时什么。其格式意味着OS应如何正确的解释它们,并将其放在对应的内存地址上,本节了解下Linux上的文件格式ELF
一个程序的组成主要由:
栈区(stack):由编译器自动分配和释放,用于存储函数的参数值、局部变量的值等。
堆区(heap):由程序员进行分配和释放,若程序员不释放,则程序结束时由OS回收。
数据段:初始化的全局变量和静态变量罪同一块区域中,程序结束后由系统释放
BSS段:未初始化的全局变量和未初始化的静态变量所在区域。程序结束后由系统释放
代码段:存储程序的二进制代码和文字常量
了解了上述信息后,来看下ELF.众所周知,我们经常使用英文缩写来表示事物,这个很容易产生误解。所以我们先来看下ELF的全称 executable and linkable format(可执行链接的格式),这里的格式自然指的是程序格式又可以分为3类,如下:
可重定向文件:文件保存着代码和适当的数据,用来和其他的目标文件一起来创建一个可执行文件或者是一个共享目标文件(目标文件或者静态库文件,即Linux通常后缀为.a和.o的文件)
可执行文件:文件保存着一个用来执行的程序(如bash、gcc等)。
共享目标文件:共享库。文件保存着代码和合适的数据,用来被下链接编辑器和动态链接器链接(Linux中后缀为.so的文件)