readelfが関数サイズを計算する方法

readelfが関数サイズを計算する方法

readelfユーティリティが関数サイズを計算する方法を理解しようとしています。簡単なプログラムを書いてみました

#include <stdio.h>

int main() {
    printf("Test!\n");
}

今私が使用した関数のサイズを確認するには:

readelf -sw a.out|sort -n -k 3,3|grep FUNC

生産する:

 1: 0000000000000000     0 FUNC    GLOBAL DEFAULT  UND puts@GLIBC_2.2.5 (2)
 2: 0000000000000000     0 FUNC    GLOBAL DEFAULT  UND __libc_start_main@GLIBC_2.2.5 (2)
29: 0000000000400470     0 FUNC    LOCAL  DEFAULT   13 deregister_tm_clones
30: 00000000004004a0     0 FUNC    LOCAL  DEFAULT   13 register_tm_clones
31: 00000000004004e0     0 FUNC    LOCAL  DEFAULT   13 __do_global_dtors_aux
34: 0000000000400500     0 FUNC    LOCAL  DEFAULT   13 frame_dummy
48: 0000000000000000     0 FUNC    GLOBAL DEFAULT  UND puts@@GLIBC_2.2.5
50: 00000000004005b4     0 FUNC    GLOBAL DEFAULT   14 _fini
51: 0000000000000000     0 FUNC    GLOBAL DEFAULT  UND __libc_start_main@@GLIBC_
58: 0000000000400440     0 FUNC    GLOBAL DEFAULT   13 _start
64: 00000000004003e0     0 FUNC    GLOBAL DEFAULT   11 _init
45: 00000000004005b0     2 FUNC    GLOBAL DEFAULT   13 __libc_csu_fini
60: 000000000040052d    16 FUNC    GLOBAL DEFAULT   13 main
56: 0000000000400540   101 FUNC    GLOBAL DEFAULT   13 __libc_csu_init

さて、メイン関数のサイズを確認してみると16と出てきますね。この値にどのように到達しますか?これはスタックサイズですか?

コンパイラはgccバージョン4.8.5(Ubuntu 4.8.5-2ubuntu1〜14.04.1)を使用します。

GNU readelf(Ubuntu用GNU Binutils)2.24

答え1

与えられたサイズは、のreadelfバイナリオブジェクトのサイズであり、mainこれは機能を実装する機械命令の順序です。私のシステムでは

57: 00000000004004d7    21 FUNC    GLOBAL DEFAULT   13 main

fromは、またはに示すreadelfように、コンパイルされたコードとよく一致します。gcc -Sobjdump -d

0000000000000000 <main>:
   0:   55                      push   %rbp
   1:   48 89 e5                mov    %rsp,%rbp
   4:   bf 00 00 00 00          mov    $0x0,%edi
   9:   e8 00 00 00 00          callq  e <main+0xe>
   e:   b8 00 00 00 00          mov    $0x0,%eax
  13:   5d                      pop    %rbp
  14:   c3                      retq   

21バイトはbytes55などです4889e5

関連情報