0

マルチコア プロセッサが登場する直前の時代に作成された非常に多くのプログラムは、rdtsc 命令を使用して正確なデータを取得します。

これは、競合する値で終了する可能性があるため、マルチスレッドのプログラムでは深刻な問題であり、これが原因で多くの完全なクラッシュが発生します (一部のシングルスレッド プログラムも、rtdsc の使用方法によってはクラッシュする可能性があります)。

少なくとも Windows では、「プロセッサ アフィニティ」を設定することを推奨するのが一般的ですが、残念ながらこれは、並列処理を使用するように (不適切に、明らかに) 設計された一部のプログラムを著しく不自由にします。

ソースコードがまったくなくても、クラッシュしたプログラムで rdtsc 呼び出しを探し出し、それを別のものに置き換えるのはどれほど難しいのでしょうか? (そして、それが何なのかはわかりません...)

4

1 に答える 1

3

原則として、誰かがマシン コード バイナリを渡した場合、どのバイトが命令で、どのバイトがコードであるかを判断するのに非常に (チューリング!) 苦労する可能性があります。それを正しく理解できない場合、パッチを適用する RDTSC の指示を見つけることさえできません。(さらに悪いことに、一部のプログラムはコードを生成します。現在、データ領域内のものはランタイムであり、一時的に RDTSC が含まれている可能性があります)。非常に特殊なプログラムでは、一部の命令が文字通り他の命令とオーバーラップする場合があり、一部の JMP は長い命令として識別されるものの途中に文字通り着陸します。(x86 命令の長さは 16 バイト程度です!)。

バイナリ リバース エンジニアリング担当者は、この問題を抱えています。一般的に、彼らがどのように成功するかはわかりません。ほとんどのプログラム オブジェクト コードは、何も隠そうとしないコンパイラによって生成されるためだと思います (隠そうとするコンパイラに遭遇した場合は注意してください)。

それらを見つけることができれば、提案された不整合の問題を回避するために、既知の定数をレジスタにロードするルーチンへの関数呼び出しによってそれらを置き換えると思います。それらの場所にパッチを当てるのはかなり厄介かもしれません。RDTSC は (私が思うに) 2 バイトであり、何らかの理由で移動できない他の 2 つの命令に挟まれている可能性があります。そのため、各 RDTSC でブレークポイント (1 バイト) だけを使用して RDTSC シミュレーターにトラップする必要がある場合があります。誰かがRDTSCを使用してタイミングループでナノ秒のクロックティックを読み取る場合、これによりパフォーマンスの問題が発生する可能性があります。

全体として、これは困難な道のように思えます。本当に古いプログラムをどれだけ実行したいですか? その理由は?

于 2016-01-27T07:20:53.920 に答える