2016-04-30 37 views
8

にコンパイルCでのプットとprintfの違いは、これはputs()を使用して、私のCプログラムでは何:アセンブリ言語

#include <stdio.h> 
int main(void){ 
puts("testing"); 
} 

gcc -S -o sample.s sample.cを使用した後のアセンブリにそれをコンパイルし、これは私が得たものである:

 .file "sample.c" 
     .section  .rodata 
.LC0: 
     .string "testing" 
     .text 
.globl main 
     .type main, @function 
main: 
     pushl %ebp 
     movl %esp, %ebp 
     andl $-16, %esp 
     subl $16, %esp 
     movl $.LC0, (%esp) 
     call puts 
     leave 
     ret 
     .size main, .-main 
     .ident "GCC: (GNU) 4.4.5 20110214 (Red Hat 4.4.5-6)" 
     .section  .note.GNU-stack,"",@progbits 

は、私が代わりにプットのprintf()を使用していたのと同じ方法、この時間を行なったし、これは私が得たものである:

.file "sample.c" 
     .section  .rodata 
.LC0: 
     .string "testing" 
     .text 
.globl main 
     .type main, @function 
main: 
     pushl %ebp 
     movl %esp, %ebp 
     andl $-16, %esp 
     subl $16, %esp 
     movl $.LC0, %eax  //this is the difference 
     movl %eax, (%esp) 
     call printf 
     leave 
     ret 
     .size main, .-main 
     .ident "GCC: (GNU) 4.4.5 20110214 (Red Hat 4.4.5-6)" 
     .section  .note.GNU-stack,"",@progbits 
ここ

printf()機能mov $.LC0は直接(%esp)からputs()機能mov %.LC0ながらmov %eax(%esp)に、%eaxに、私は理解していないものです。 私はなぜそれが分からないのですか?

+6

'printf'は可変引数関数であり、それらは異なった引数の固定数を持つ関数から呼び出されますので、それはおそらくです。 – Barmar

+1

興味深いことに、os xにclangを使用すると、両方のプログラムが同じアセンブリにコンパイルされます。 – Leandros

+0

GCCはlinux上で位置依存コードをコンパイルする理由は何ですか? – Leandros

答えて

4

アセンブリレベルでの2つの機能の大きな違いは、puts()関数は1つの引数(表示する文字列へのポインタ)をとり、printf()関数は1つの引数(フォーマットへのポインタ文字列)、次にスタック内の任意の数の引数(printf()は可変関数です)。

引数の数のチェックは絶対にありません。文字列には文字%が遭遇した回数だけ依存します。たとえば、この特殊性は、書式文字列形式のバグ利用方法で、プロセスのスタックの内容をインタラクティブに探索するために使用されます。

したがって、基本的には、puts()には引数が1つしかなく、printf()は可変関数です。

方が良い、この違いを理解したい場合は、コンパイルしようとは:

#include <stdio.h> 

int main(void) { 
    printf("testing %d", 10); 
} 
+1

また、 'puts'は' fputs'とは異なり暗黙的に '\ n'を追加します。コンパイラがprintfをputsに最適化する2つのケースと、そうでない2つのケース(https://godbolt.org/g/w2d2fI)も参照してください。そして、http://stackoverflow.com/questions/36343733/o2-optimizes-printfs-n-str-to-putsstr。 –

関連する問題