Chinaunix首页 | 论坛 | 博客
  • 博客访问: 1339429
  • 博文数量: 92
  • 博客积分: 10389
  • 博客等级: 上将
  • 技术积分: 1918
  • 用 户 组: 普通用户
  • 注册时间: 2006-08-10 16:13
文章存档

2014年(1)

2012年(15)

2009年(6)

2008年(37)

2007年(72)

2006年(54)

我的朋友

分类: LINUX

2008-01-28 15:14:09

=================== String Table 字符串表=========================


String table sections 保存着以NULL终止的一系列字符,一般我们称为字
符串。object文件使用这些字符串来描绘符号和section名。一个字符串的
参考是一个string table section的索引。第一个字节,即索引0,被定义保
存着一个NULL字符。同样的,一个string table的最后一个字节保存着一个
NULL字符,所有的字符串都是以NULL终止。索引0的字符串是没有名字或者说
是NULL,它的解释依靠上下文。一个空的string table section是允许的;
它的section header的成员sh_size将为0。对空的string table来说,非0的
索引是没有用的。

一个 settion 头的 sh_name 成员保存了一个对应于该 setion 头字符表部分
的索引(就象ELF头的 e_shstrndx 成员所特指的那样。下表列出了一个有 25 字节
的字符串表(这些字符串和不同的索引相关联):


       Index   +0   +1   +2   +3   +4   +5   +6   +7   +8   +9
       =====   ==   ==   ==   ==   ==   ==   ==   ==   ==   ==
          0    \0   n    a    m    e    .    \0   V    a    r    
         10    i    a    b    l    e    \0   a    b    l    e
         20    \0   \0   x    x    \0


+ Figure 1-15: String Table Indexes

  Index   String
  =====   ======
      0   none
      1   "name."
      7   "Variable"
     11   "able"
     16   "able"
     24   null string


如上所示,一个字符串表可能涉及该 section 中的任意字节。一个字符串可能
引用不止一次;引用子串的情况是可能存在的;一个字符串也可能被引用若干次;而
不被引用的字符串也是允许存在的。

   ==================== Symbol Table 符号表=========================


一个object文件的符号表保存了一个程序在定位和重定位时需要的定义和引用的信息。
一个符号表索引是相应的下标。0表项特指了该表的第一个入口,就象未定义的符号
索引一样。初始入口的内容在该 section 的后续部分被指定。

                             Name       Value
                             ====       =====
     STN_UNDEF      0

一个符号表入口有如下的格式:

+ Figure 1-16: Symbol Table Entry

  typedef struct {
      Elf32_Word st_name;
      Elf32_Addr st_value;
      Elf32_Word st_size;
      unsigned char st_info;
      unsigned char st_other;
      Elf32_Half st_shndx;
  } Elf32_Sym;

* st_name

  该成员保存了进入该object文件的符号字符串表入口的索引(保留了符号名的表达字符)。 
  如果该值不为 0 ,则它代表了给出符号名的字符串表索引。否则,该符号无名。

注意:External C 符号和object文件的符号表有相同的名称。

* st_value

  该成员给出了相应的符号值。它可能是绝对值或地址等等(依赖于上下文);
  细节如下所述。

* st_size

  许多符号和大小相关。比如,一个数据对象的大小是该对象所包含的字节数目。
  如果该符号的大小未知或没有大小则这个成员为 0 。

* st_info

  成员指出了符号的类型和相应的属性。相应的列表如下所示。下面的代码说明了
  如何操作该值。

    #define ELF32_ST_BIND(i) ((i)>>4)
    #define ELF32_ST_TYPE(i) ((i)&0xf)
    #define ELF32_ST_INFO(b, t) (((b)<<4)+((t)&0xf))

* st_other

  该成员目前为 0 ,没有含义。

* st_shndx

  每一个符号表的入口都定义为和某些 section 相关;该成员保存了相关的 section
  头索引。就象 Figure 1-8 {*}和相关的文字所描述的那样,某些 section 索引
  指出了特殊的含义。

一个符号的属性决定了可链接性能和行为。

+ Figure 1-17: Symbol Binding, ELF32_ST_BIND

  Name        Value
  ====        =====
  STB_LOCAL       0
  STB_GLOBAL      1
  STB_WEAK        2
  STB_LOPROC     13
  STB_HIPROC     15

* STB_LOCAL

  在包含了其定义的object文件之外的局部符号是不可见的。不同文件中的具有相同
  名称的局部符号并不相互妨碍。

* STB_GLOBAL

  全局符号是对所有的object目标文件可见的。一个文件中的全局符号的定义可以
  满足另一个文件中对(该文件中)未定义的全局符号的引用。 

* STB_WEAK

  弱符号相似于全局符号,但是他们定义的优先级比较低一些。

* STB_LOPROC through STB_HIPROC

  其所包含范围中的值由相应的处理器语义所保留。

全局符号和弱符号的区别主要在两个方面。

* 当链接器链接几个可重定位的目标文件时,它不允许 STB_GLOBAL 符号的同名
多重定义。另一方面,如果一个全局符号的定义存在则具有相同名称的弱符号名不会
引起错误。链接器将认可全局符号的定义而忽略弱符号的定义。与此相似,如果有一个
普通符号(比如,一个符号的 st_shndx 域包含 SHN_COMMON),则一个同名的弱符号
不会引起错误。链接器同样认可普通符号的定义而忽略弱符号。

* 当链接器搜索档案库的时候,它选出包含了未定义的全局符号的存档成员。该成员
的定义或者是全局的或者是一个弱符号。链接器不会为了解决一个未定义的弱符号
选出存档成员。未定义的弱符号具有 0 值。

在每一个符号表中,所有具有 STB_LOCAL 约束的符号优先于弱符号和全局符号。
就象上面 "sections" 中描述的那样,一个符号表部分的 sh_info 头中的成员
保留了第一个非局部符号的符号表索引。

符号的类型提供了一个为相关入口的普遍分类。

+ Figure 1-18: Symbol Types, ELF32_ST_TYPE

  Name         Value
  ====         =====
  STT_NOTYPE       0
  STT_OBJECT       1
  STT_FUNC         2
  STT_SECTION      3
  STT_FILE         4
  STT_LOPROC      13
  STT_HIPROC      15

* STT_NOTYPE

  该符号的类型没有指定。

* STT_OBJECT

  该符号和一个数据对象相关,比如一个变量、一个数组等。

* STT_FUNC

  该符号和一个函数或其他可执行代码相关。

* STT_SECTION

  该符号和一个 section 相关。这种类型的符号表入口主要是为了重定位,一般的
  具有 STB_LOCAL 约束。


* STT_FILE

  按惯例而言,该符号给出了和目标文件相关的源文件名称。一个具有 STB_LOCAL
  约束的文件符号,其 section 索引为 SHN_ABS ,并且它优先于当前对应该文件的
  其他 STB_LOCAL 符号。

* STT_LOPROC through STT_HIPROC

  该范围中的值是为处理器语义保留的。

共享文件中的函数符号(具有 STT_FUNC 类型)有特殊的意义。当其他的目标文件
从一个共享文件中引用一个函数时,链接器自动的为引用符号创建一个链接表。除了
STT_FUNC 之外,共享的目标符号将不会自动的通过链接表引用。


如果一个符号涉及到一个 section 的特定定位,则其 section 索引成员 st_shndx
将保留一个到该 section 头的索引。当该 section 在重定位过程中不断
移动一样,符号的值也相应变化,而该符号的引用在程序中指向同样的定位。某些
特殊的 section 索引有其他的语义。


* SHN_ABS

  该符号有一个不会随重定位变化的绝对值。

* SHN_COMMON

  该符号标识了一个没有被分配的普通块。该符号的值给出了相应的系统参数,就象
  一个 section 的 sh_addralign 成员。也就是说,链接器将分配一个地址给
  该符号,地址的值是 st_value 的倍数。该符号的大小指出了需要的字节数。
 

* SHN_UNDEF

  该 section 表索引表明该符号是未定义的。当链接器将该目标文件和另一个定义
  该符号的文件相装配的时候,该文件内对该符号的引用将链接到当前实际的定义。

如上所述,符号表的 0 索引(STN_UNDEF)是保留的,它包含了如下内容:

+ Figure 1-19: Symbol Table Entry: Index 0

  Name        Value    Note
  ====        =====    ====
  st_name       0      No name
  st_value      0      Zero value
  st_size       0      No size
  st_info       0      No type, local binding
  st_other      0
  st_shndx  SHN_UNDEF  No section


    Symbol Values(符号值)

符号表入口对于不同的目标文件而言对 st_value 成员有一些不同的解释。

* 在可重定位文件中, st_value 保存了 section 索引为 SHN_COMMON 符号
的强制对齐值。

* 在可重定位文件中, st_value 保存了一个符号的 section 偏移。也就是说,
st_value 是从 st_shndx 定义的 section 开头的偏移量。

* 在可执行的和可共享的目标文件中, st_value 保存了一个虚拟地址。为了使
这些文件符号对于动态链接器更为有效,文件层面上的 section 偏移让位于内存
层面上的虚拟地址( section 编号无关的)。


尽管符号表值对于不同的目标文件有相似的含义,相应的程序还是可以有效地访问数据
阅读(2479) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~