2017-09-21 8 views
-1
obj.CurrSize -= size; 
0x00000000003ad2d7 <+183>: mov eax,0x0  
0x00000000003ad2dc <+188>: test rax,rax 
0x00000000003ad2df <+191>: je 0x3ad2e6 <+198> 
0x00000000003ad2e1 <+193>: call 0x0 
0x00000000003ad2e6 <+198>: mov rax, 0xffffffffffffff60 
0x00000000003ad2ed <+205>: sub rbx,r15 
0x00000000003ad2f0 <+208>: add QWORD PTR fs:[rax],rbx` 

ゼロをテストし、ゼロの場合は1つの命令をジャンプしますが、それ以外の場合は同じですか?このasmコードの意味は何ですか?

+0

そのビットを削除して、違いがあるかどうかを確認してください。 –

+0

@MadPhysicist? – vladon

+0

@PeterCordesそれは-O2とclangです。見て、eaxはゼロですが、レックスはテストしました。 – vladon

答えて

2

無関係な質問exposes a pattern that looked similar to yoursを読んで、私はあなたの奇妙なコードの起源を発見したと思います。

おそらくこのコードはpthreadライブラリが実際にリンクされていたかどうかを確認するため__gthread_active_p()を使用して、特定のもので、スレッド関連のC++ 11の機能の拡張に由来しています。潜在的ににあり

ほとんどのコードにlibstdcにおけるスレッドの問題との契約++(しかし、何のスレッドのサポートが必要とされないときのための合理的なフォールバックを持っている)は、シンボル__pthread_key_createがある場合は順番に、一般的にチェックするまで沸騰する

if(__gthread_active_p()) 

が散らばっていますNULLとは異なるものに定義されています。ここでのトリックは、__attribute__ ((weak))と宣言されているため、定義がない場合(つまり、pthreadライブラリがリンクされていない場合)、リンカはNULLへの参照を解決します。

コンパイラがスレッド関連の処理を行うために残したチェック(つまり、共有リソースを保護するためのミューテックスの取得など)は、コードに表示されます。あなたはNULLポインタに解決すべて__pthreadシンボルを参照してください

mov eax,__pthread_key_create 
    test rax,rax 
    jz .skip_mutex_init 
    call __pthread_init_some_mutex 
.skip_mutex_init: 
    mov rax, 0xffffffffffffff60 
    sub rbx,r15 
    add QWORD PTR fs:[rax],rbx` 

:事前にリンクのコードは、おそらくのようなものです。コンパイラは、-lpthreadでリンカが呼び出されるかどうかを知ることができず、リンカはダム置換を実行するだけです(LTOが有効になっていない限り、再度オプティマイザを実行するには遅すぎます)。全く異なるゲーム)。

あなた自身同様のパターンplaying with the compiler explorerを見ることができます:完全なバイナリ(11010キャプションと右のボタン)を結ぶ有効/無効にしてみてください、とコマンドラインで-pthreadを追加/削除。

さて、私は正確にあなたの結果を再現するために管理していませんでしたが、おそらくそれが使用されている、または別のスレッド対応のコンポーネントは、あなたのコード内で使用されているlibstdc++の異なるバージョンから来ている(私はちょうどstd::mutexstd::shared_ptrてみました) 。

+0

いいえ、 '0x0コール'単にNULLポインタではなく、次の命令を呼び出しています。すでに静的にリンクされたプログラム(gdb disasmの出力)の災害です。 – vladon

+0

私は確信していませんが、IIRCは通常gdbをダンプして 'call 0x3ad2e6 <+0>'と呼びます。それでも、逆コンパイラなどを止めるための手書きコードのように見える場合は、ファンクション自体の内部に偽の呼び出しを挿入すると、ヒューリスティックに混乱が生じ、関数のエントリポイント/ブロックが再構築されます。 –

+0

ああ、これはNULLポインタのロードであり、 'mov eax、imm32'ではありませんでした。私はGDBのIntel構文のバージョンに慣れていない。 'objdump'は' DWORD PTR:0'を出力します。 (@vladon) –

関連する問題