《深入理解计算机系统》第7章:重定位PC相对引用的理解

在第七章《链接》中的静态链接有对符号进行重定位PC相对引用的处理,书上对应的还有"公式",但不是很好理解。现做实验对"公式"进行理解("公式"内容如有兴趣可以参考原文)

我们的目的是根据.text节起点和目标函数地址(如下面的0x8048420),重新计算引用偏移量

现创建2个文件

//main.c
void swap();
int buf[2]={1,2};
int main()
{
        swap();
        return 0;
}

//swap.c 
extern int buf[];
int *bufp0 = &buf[0];
int *bufp1;
void swap()
{
        int temp;
        bufp1 = &buf[1];
        temp = *bufp0;
        *bufp0 = *bufp1;
        *bufp1 = temp;
}

 可以看到main.c引用了swap.c的函数,编译main.c为main.o,反汇编有如下结果

# objdump -d main.o

main.o:     file format elf32-i386
Disassembly of section .text:

00000000 <main>:
   0:   8d 4c 24 04        lea    0x4(%esp),%ecx
   4:   83 e4 f0          and    $0xfffffff0,%esp
   7:   ff 71 fc          pushl  -0x4(%ecx)
   a:   55              push   %ebp
   b:   89 e5            mov    %esp,%ebp
   d:   51              push   %ecx
   e:   83 ec 04                 sub    $0x4,%esp
  11:   e8 fc ff ff ff           call   12 <main+0x12>   --对swap引用的地址偏移量为12(call命令占一个字节)
  16:   b8 00 00 00 00       mov    $0x0,%eax
  1b:   83 c4 04          add    $0x4,%esp
  1e:   59              pop    %ecx
  1f:   5d              pop    %ebp
  20:   8d 61 fc           lea    -0x4(%ecx),%esp
  23:   c3              ret    

 将swap.o和main.o编译为可执行文件p,查看p的.text节信息(截取部分如下)

 [15] .text             PROGBITS        08048330 000330 0001bc 00  AX  0   0 16 --节起始地址为红色部分

反汇编p,(截取部分如下)

080483f0 <main>:
 80483f0:       8d 4c 24 04        lea    0x4(%esp),%ecx
 80483f4:       83 e4 f0          and    $0xfffffff0,%esp
 80483f7:       ff 71 fc          pushl  -0x4(%ecx)
 80483fa:       55              push   %ebp
 80483fb:       89 e5            mov    %esp,%ebp
 80483fd:       51              push   %ecx
 80483fe:       83 ec 04          sub    $0x4,%esp
 8048401:       e8 1a 00 00 00       call   8048420 <swap>
 8048406:       83 c4 04                 add    $0x4,%esp
 8048409:       31 c0                    xor    %eax,%eax
 804840b:       59                       pop    %ecx
 804840c:       5d                       pop    %ebp
 804840d:       8d 61 fc                 lea    -0x4(%ecx),%esp

 由于不知道swap相对与.text起始地址的偏移量,我们采用main函数的地址,它相对于main函数的偏移量为0x12。

那么新的引用量为0x8048420-(0x080483f0+0x12)-4 = 1A

实际上0x080483f0+0x12+4的地址就是PC的值,0x8048420-PC就是偏移值

可见"公式"害死人。。。

posted @ 2018-02-28 11:16  charlieroro  阅读(1452)  评论(3编辑  收藏  举报