额外的符号和汇编代码是什么意思?
what does extra symbol and assembly code mean?
我有一个简单的c文件:
// filename: test.c
void fun() {}
然后我使用命令将 test.c
编译为 libtest.so
:
gcc -shared -fPIC -Wl,--gc-sections -ffunction-sections -fdata-sections -o libtest.so test.c
strip -s ./libtest.so
然后使用readelf打印符号及其大小:
readelf -sW ./libtest.so
我得到了:
Symbol table '.dynsym' contains 11 entries:
Num: Value Size Type Bind Vis Ndx Name
0: 0000000000000000 0 NOTYPE LOCAL DEFAULT UND
1: 0000000000000420 0 SECTION LOCAL DEFAULT 9
2: 0000000000000000 0 NOTYPE WEAK DEFAULT UND __gmon_start__
3: 0000000000000000 0 NOTYPE WEAK DEFAULT UND _Jv_RegisterClasses
4: 0000000000000000 0 FUNC WEAK DEFAULT UND __cxa_finalize@GLIBC_2.2.5 (2)
5: 00000000002007c8 0 NOTYPE GLOBAL DEFAULT ABS _end
6: 00000000002007b8 0 NOTYPE GLOBAL DEFAULT ABS _edata
7: 00000000002007b8 0 NOTYPE GLOBAL DEFAULT ABS __bss_start
8: 0000000000000420 0 FUNC GLOBAL DEFAULT 9 _init
9: 000000000000052a 6 FUNC GLOBAL DEFAULT 11 fun
10: 0000000000000568 0 FUNC GLOBAL DEFAULT 12 _fini
然后使用objdump反汇编libtest.so的.text
部分:
objdump -S -d -j .text ./libtest.so
我得到了:
./libtest.so: file format elf64-x86-64
Disassembly of section .text:
0000000000000460 <fun-0xca>:
460: 48 83 ec 08 sub [=15=]x8,%rsp
464: 48 8b 05 15 03 20 00 mov 0x200315(%rip),%rax # 200780 <_fini+0x200218>
46b: 48 85 c0 test %rax,%rax
46e: 74 02 je 472 <__cxa_finalize@plt+0x2a>
470: ff d0 callq *%rax
472: 48 83 c4 08 add [=15=]x8,%rsp
476: c3 retq
477: 90 nop
478: 90 nop
479: 90 nop
47a: 90 nop
47b: 90 nop
47c: 90 nop
47d: 90 nop
47e: 90 nop
47f: 90 nop
480: 55 push %rbp
481: 80 3d 30 03 20 00 00 cmpb [=15=]x0,0x200330(%rip) # 2007b8 <__bss_start>
488: 48 89 e5 mov %rsp,%rbp
48b: 41 54 push %r12
48d: 53 push %rbx
48e: 75 62 jne 4f2 <__cxa_finalize@plt+0xaa>
490: 48 83 3d f8 02 20 00 cmpq [=15=]x0,0x2002f8(%rip) # 200790 <_fini+0x200228>
497: 00
498: 74 0c je 4a6 <__cxa_finalize@plt+0x5e>
49a: 48 8d 3d 57 01 20 00 lea 0x200157(%rip),%rdi # 2005f8 <_fini+0x200090>
4a1: e8 a2 ff ff ff callq 448 <__cxa_finalize@plt>
4a6: 48 8d 1d 3b 01 20 00 lea 0x20013b(%rip),%rbx # 2005e8 <_fini+0x200080>
4ad: 4c 8d 25 2c 01 20 00 lea 0x20012c(%rip),%r12 # 2005e0 <_fini+0x200078>
4b4: 48 8b 05 05 03 20 00 mov 0x200305(%rip),%rax # 2007c0 <__bss_start+0x8>
4bb: 4c 29 e3 sub %r12,%rbx
4be: 48 c1 fb 03 sar [=15=]x3,%rbx
4c2: 48 83 eb 01 sub [=15=]x1,%rbx
4c6: 48 39 d8 cmp %rbx,%rax
4c9: 73 20 jae 4eb <__cxa_finalize@plt+0xa3>
4cb: 0f 1f 44 00 00 nopl 0x0(%rax,%rax,1)
4d0: 48 83 c0 01 add [=15=]x1,%rax
4d4: 48 89 05 e5 02 20 00 mov %rax,0x2002e5(%rip) # 2007c0 <__bss_start+0x8>
4db: 41 ff 14 c4 callq *(%r12,%rax,8)
4df: 48 8b 05 da 02 20 00 mov 0x2002da(%rip),%rax # 2007c0 <__bss_start+0x8>
4e6: 48 39 d8 cmp %rbx,%rax
4e9: 72 e5 jb 4d0 <__cxa_finalize@plt+0x88>
4eb: c6 05 c6 02 20 00 01 movb [=15=]x1,0x2002c6(%rip) # 2007b8 <__bss_start>
4f2: 5b pop %rbx
4f3: 41 5c pop %r12
4f5: c9 leaveq
4f6: c3 retq
4f7: 66 0f 1f 84 00 00 00 nopw 0x0(%rax,%rax,1)
4fe: 00 00
500: 48 83 3d e8 00 20 00 cmpq [=15=]x0,0x2000e8(%rip) # 2005f0 <_fini+0x200088>
507: 00
508: 55 push %rbp
509: 48 89 e5 mov %rsp,%rbp
50c: 74 1a je 528 <__cxa_finalize@plt+0xe0>
50e: 48 8b 05 73 02 20 00 mov 0x200273(%rip),%rax # 200788 <_fini+0x200220>
515: 48 85 c0 test %rax,%rax
518: 74 0e je 528 <__cxa_finalize@plt+0xe0>
51a: 48 8d 3d cf 00 20 00 lea 0x2000cf(%rip),%rdi # 2005f0 <_fini+0x200088>
521: c9 leaveq
522: ff e0 jmpq *%rax
524: 0f 1f 40 00 nopl 0x0(%rax)
528: c9 leaveq
529: c3 retq
000000000000052a <fun>:
52a: 55 push %rbp
52b: 48 89 e5 mov %rsp,%rbp
52e: c9 leaveq
52f: c3 retq
530: 55 push %rbp
531: 48 89 e5 mov %rsp,%rbp
534: 53 push %rbx
535: 48 83 ec 08 sub [=15=]x8,%rsp
539: 48 8b 05 90 00 20 00 mov 0x200090(%rip),%rax # 2005d0 <_fini+0x200068>
540: 48 83 f8 ff cmp [=15=]xffffffffffffffff,%rax
544: 74 19 je 55f <fun+0x35>
546: 48 8d 1d 83 00 20 00 lea 0x200083(%rip),%rbx # 2005d0 <_fini+0x200068>
54d: 0f 1f 00 nopl (%rax)
550: 48 83 eb 08 sub [=15=]x8,%rbx
554: ff d0 callq *%rax
556: 48 8b 03 mov (%rbx),%rax
559: 48 83 f8 ff cmp [=15=]xffffffffffffffff,%rax
55d: 75 f1 jne 550 <fun+0x26>
55f: 48 83 c4 08 add [=15=]x8,%rsp
563: 5b pop %rbx
564: c9 leaveq
565: c3 retq
可以看出符号fun
的大小为6,对应虚拟地址0x52a~0x52f。
我有两个问题:
符号fun-0xca
有什么作用?
符号fun
中0x530到0x565的汇编代码是做什么用的?
省略strip -s ./libtest.so
。
在GCC创建的libtest.so
中,每个单独的函数在符号table中都有一个符号。 objdump -drwC -Mintel libtest.so
将显示每个名称,例如 _init
、deregister_tm_clones
、register_tm_clones
和 __do_global_dtors_aux
。我认为这些来自 CRT 启动代码;在链接时使用 gcc -v
以查看它传递给 ld
.
的任何额外 .o
文件
剥离符号会删除该信息,在文本部分留下没有符号名称的机器代码。唯一留给 objdump
引用的符号是 fun
,因此它将第一个代码块标记为 fun-0xca
.
我有一个简单的c文件:
// filename: test.c
void fun() {}
然后我使用命令将 test.c
编译为 libtest.so
:
gcc -shared -fPIC -Wl,--gc-sections -ffunction-sections -fdata-sections -o libtest.so test.c
strip -s ./libtest.so
然后使用readelf打印符号及其大小:
readelf -sW ./libtest.so
我得到了:
Symbol table '.dynsym' contains 11 entries:
Num: Value Size Type Bind Vis Ndx Name
0: 0000000000000000 0 NOTYPE LOCAL DEFAULT UND
1: 0000000000000420 0 SECTION LOCAL DEFAULT 9
2: 0000000000000000 0 NOTYPE WEAK DEFAULT UND __gmon_start__
3: 0000000000000000 0 NOTYPE WEAK DEFAULT UND _Jv_RegisterClasses
4: 0000000000000000 0 FUNC WEAK DEFAULT UND __cxa_finalize@GLIBC_2.2.5 (2)
5: 00000000002007c8 0 NOTYPE GLOBAL DEFAULT ABS _end
6: 00000000002007b8 0 NOTYPE GLOBAL DEFAULT ABS _edata
7: 00000000002007b8 0 NOTYPE GLOBAL DEFAULT ABS __bss_start
8: 0000000000000420 0 FUNC GLOBAL DEFAULT 9 _init
9: 000000000000052a 6 FUNC GLOBAL DEFAULT 11 fun
10: 0000000000000568 0 FUNC GLOBAL DEFAULT 12 _fini
然后使用objdump反汇编libtest.so的.text
部分:
objdump -S -d -j .text ./libtest.so
我得到了:
./libtest.so: file format elf64-x86-64
Disassembly of section .text:
0000000000000460 <fun-0xca>:
460: 48 83 ec 08 sub [=15=]x8,%rsp
464: 48 8b 05 15 03 20 00 mov 0x200315(%rip),%rax # 200780 <_fini+0x200218>
46b: 48 85 c0 test %rax,%rax
46e: 74 02 je 472 <__cxa_finalize@plt+0x2a>
470: ff d0 callq *%rax
472: 48 83 c4 08 add [=15=]x8,%rsp
476: c3 retq
477: 90 nop
478: 90 nop
479: 90 nop
47a: 90 nop
47b: 90 nop
47c: 90 nop
47d: 90 nop
47e: 90 nop
47f: 90 nop
480: 55 push %rbp
481: 80 3d 30 03 20 00 00 cmpb [=15=]x0,0x200330(%rip) # 2007b8 <__bss_start>
488: 48 89 e5 mov %rsp,%rbp
48b: 41 54 push %r12
48d: 53 push %rbx
48e: 75 62 jne 4f2 <__cxa_finalize@plt+0xaa>
490: 48 83 3d f8 02 20 00 cmpq [=15=]x0,0x2002f8(%rip) # 200790 <_fini+0x200228>
497: 00
498: 74 0c je 4a6 <__cxa_finalize@plt+0x5e>
49a: 48 8d 3d 57 01 20 00 lea 0x200157(%rip),%rdi # 2005f8 <_fini+0x200090>
4a1: e8 a2 ff ff ff callq 448 <__cxa_finalize@plt>
4a6: 48 8d 1d 3b 01 20 00 lea 0x20013b(%rip),%rbx # 2005e8 <_fini+0x200080>
4ad: 4c 8d 25 2c 01 20 00 lea 0x20012c(%rip),%r12 # 2005e0 <_fini+0x200078>
4b4: 48 8b 05 05 03 20 00 mov 0x200305(%rip),%rax # 2007c0 <__bss_start+0x8>
4bb: 4c 29 e3 sub %r12,%rbx
4be: 48 c1 fb 03 sar [=15=]x3,%rbx
4c2: 48 83 eb 01 sub [=15=]x1,%rbx
4c6: 48 39 d8 cmp %rbx,%rax
4c9: 73 20 jae 4eb <__cxa_finalize@plt+0xa3>
4cb: 0f 1f 44 00 00 nopl 0x0(%rax,%rax,1)
4d0: 48 83 c0 01 add [=15=]x1,%rax
4d4: 48 89 05 e5 02 20 00 mov %rax,0x2002e5(%rip) # 2007c0 <__bss_start+0x8>
4db: 41 ff 14 c4 callq *(%r12,%rax,8)
4df: 48 8b 05 da 02 20 00 mov 0x2002da(%rip),%rax # 2007c0 <__bss_start+0x8>
4e6: 48 39 d8 cmp %rbx,%rax
4e9: 72 e5 jb 4d0 <__cxa_finalize@plt+0x88>
4eb: c6 05 c6 02 20 00 01 movb [=15=]x1,0x2002c6(%rip) # 2007b8 <__bss_start>
4f2: 5b pop %rbx
4f3: 41 5c pop %r12
4f5: c9 leaveq
4f6: c3 retq
4f7: 66 0f 1f 84 00 00 00 nopw 0x0(%rax,%rax,1)
4fe: 00 00
500: 48 83 3d e8 00 20 00 cmpq [=15=]x0,0x2000e8(%rip) # 2005f0 <_fini+0x200088>
507: 00
508: 55 push %rbp
509: 48 89 e5 mov %rsp,%rbp
50c: 74 1a je 528 <__cxa_finalize@plt+0xe0>
50e: 48 8b 05 73 02 20 00 mov 0x200273(%rip),%rax # 200788 <_fini+0x200220>
515: 48 85 c0 test %rax,%rax
518: 74 0e je 528 <__cxa_finalize@plt+0xe0>
51a: 48 8d 3d cf 00 20 00 lea 0x2000cf(%rip),%rdi # 2005f0 <_fini+0x200088>
521: c9 leaveq
522: ff e0 jmpq *%rax
524: 0f 1f 40 00 nopl 0x0(%rax)
528: c9 leaveq
529: c3 retq
000000000000052a <fun>:
52a: 55 push %rbp
52b: 48 89 e5 mov %rsp,%rbp
52e: c9 leaveq
52f: c3 retq
530: 55 push %rbp
531: 48 89 e5 mov %rsp,%rbp
534: 53 push %rbx
535: 48 83 ec 08 sub [=15=]x8,%rsp
539: 48 8b 05 90 00 20 00 mov 0x200090(%rip),%rax # 2005d0 <_fini+0x200068>
540: 48 83 f8 ff cmp [=15=]xffffffffffffffff,%rax
544: 74 19 je 55f <fun+0x35>
546: 48 8d 1d 83 00 20 00 lea 0x200083(%rip),%rbx # 2005d0 <_fini+0x200068>
54d: 0f 1f 00 nopl (%rax)
550: 48 83 eb 08 sub [=15=]x8,%rbx
554: ff d0 callq *%rax
556: 48 8b 03 mov (%rbx),%rax
559: 48 83 f8 ff cmp [=15=]xffffffffffffffff,%rax
55d: 75 f1 jne 550 <fun+0x26>
55f: 48 83 c4 08 add [=15=]x8,%rsp
563: 5b pop %rbx
564: c9 leaveq
565: c3 retq
可以看出符号fun
的大小为6,对应虚拟地址0x52a~0x52f。
我有两个问题:
符号
fun-0xca
有什么作用?符号
fun
中0x530到0x565的汇编代码是做什么用的?
省略strip -s ./libtest.so
。
在GCC创建的libtest.so
中,每个单独的函数在符号table中都有一个符号。 objdump -drwC -Mintel libtest.so
将显示每个名称,例如 _init
、deregister_tm_clones
、register_tm_clones
和 __do_global_dtors_aux
。我认为这些来自 CRT 启动代码;在链接时使用 gcc -v
以查看它传递给 ld
.
.o
文件
剥离符号会删除该信息,在文本部分留下没有符号名称的机器代码。唯一留给 objdump
引用的符号是 fun
,因此它将第一个代码块标记为 fun-0xca
.