ELF符号延迟绑定(动态符号的加载)

Posted by Rohex on 2020-01-03
Words 522 and Reading Time 1 Minutes
Viewed Times

过程总结

首次调用会跳到动态符号的.plt表项的首条指令;该指令会跳转到该符号的.got表项地址,初始时该处存放的是.plt表项的第二条指令;.plt第二条指令会压入该符号的表项号,然后跳入.plt首地址;.plt首地址将got表中的第二项压入栈中(即本模块对应的ID),然后跳转到got表项的第三项执行( _dl_runtime_resolve函数); _dl_runtime_resolve函数执行完后,对应的.got表项里就有符号的真实地址;再次调用就可以通过.plt表项的首条指令直接跳到符号真实地址(.got表中解析后的结果)。

调试

  1. 首次调用libc.so的函数,会跳到对应的plt表项的首条指令

  2. plt首条指令是跳转到.got表里对应的表项

  3. got表中有6项,第四项为read
  4. 查看此时 read表项值,其对应着read plt表项中的第二条指令
    • got表中第一项对应代码的_DYNAMIC节,这个节里保存着动态链接器所需要的信息:比如依赖于哪些共享库、动态符号表位置、初始化代码位置等。
    • 第二项对应本模块的ID
    • 第三项对应,动态链接库的 _dl_runtime_resolve函数
  5. 再回头看看plt表项中的第二条指令,它会压入 read函数对应的got表项序号(去掉前3项),然后跳转到plt表的首段0x080482F0
  6. plt首地址的代码 将got表中的第二项压入栈中(即本模块对应的ID),然后跳转到got表项的第三项执行( _dl_runtime_resolve函数)
  7. 经过 _dl_runtime_resolve函数解析完,got表中就添入了read函数真实地址

  8. 查看该地址处符号,为read

  9. 反汇编该处指令

作者声明

本文版权归作者(rohex)所有,旨在技术交流使用。未经作者同意禁止转载,转载后需在文章页面明显位置给出原文连接,否则相关责任自行承担。

This is copyright.