GNU ld链接脚本lds简单教程

Andrew Haung  [email protected]
 
   所有创建可执行文件的最后一步就是链接。它是由ld或者是用gcc间接调用ld来完成的。它主要任务和把外部库和应用程序的目标代码放到text段正确位置。以及创建程序中其它段(如data/bss段)。
   标准C程序的链接是一般是固定的。它是ld调用一个缺省的链接脚本来完成的。因此对于一般的应用开发者,几乎感觉不到ld以及链接脚本的存在。
   但是如果在一些特殊情况下,主要是底层非操作系统程序。里面很多代码,特别是汇编代码。必须要链接到指定的位置。而且这个时候的程序入口不一定也不是main了。这种情况在bootloader,Linux内核以及裸机程序(非操作系统的程序,bootloader可以看成这类程序一个特例)。这时,你就要手工编写lds文件了。
 
  一.lds格式
---------------------------------------------------------------
  lds的格式非常复杂,但是常用就是那几句。因此我们可以用下面一个比较通用的模板来解释.
OUTPUT_FORMAT("elf32-littlearm", "elf32-bigarm", "elf32-littlearm")
OUTPUT_ARCH("arm")
ENTRY(_start)
SECTIONS
{
 . = 0x30000000;
 .text : { *(.text)}
 . = ALIGN(2);
 .data : { *(.data)}
}
 
OUTPUT_FORMAT表示输出格式。其中有三个参数,第一个是指默认的输出格式。第二是指ld命令行参数使用-EB'输出的格式。第三个是指使用-EL时输出的格式
 
elf32-littlearm 表示ELF可执行文件格式,小端字节序和ARM体系结构.
 
OUTPUT_ARCH 表示输出的体系结构,这里是ARM
ENTRY(_start) 表示执行的入口符号。它可以是汇编的代码段标签,或者C语言的函数,这里表示使用函数_start作为入口。
 
SECTIONS 是表示各段的分布描述.
  . = 0x30000000; 表示程序起始地址
  .text : { *(.text)}
    .text:表示代码段的描述,{}中。 *(.text)总是最后一句表示.text缺省的描述.
 另一个.text实例
    .text :         {
          cpu/arm920t/start.(.text) ; 代码的第一个代码部分
          *(.text) ;其它代码部分
        }

     
  . = ALIGN(2); 表示接下来部分采用2对齐
   .data : { *(.data)} 数据库缺省描述
    
类似还有 .bss .got 和.rodata  段。
   
 
 
对lds的详细解翻译可以参见
   GNU-ld链接脚本浅析  http://www.cublog.cn/u/13991/showart_177822.html
 
二.lds的使用
-------------------------------------------------
 
用-T参数可以把lds脚本传给ld
 
ld -T your.lds -o elf_name
上句表根据your.lds来链接出elf可执行文件 elf_name
 
在底层开发里,下载到内存或Nand Flash的,还得多得用objcopy一步格式转换,以ARM为例.它需要用arm-linux-objcopy来转换
 
arm-linux-objcopy elf_name  -I elf32-littlearm -O binary -o bin_name
表示把elf格式的elf_name变成二进制的bin_name

你可能感兴趣的:(GNU ld链接脚本lds简单教程)