0

以下のコードでCPUがunsafe_variableを2回フェッチできるかどうかを確認したいのですが?揮発性および_ReadWriteBarrier(VS上)のために、コンパイラーがコードを並べ替えたり最適化したりしないと仮定しましょう。ここではMutexを使用できません。私は、潜在的なダブルフェッチの場合のみを気にします。

私はCPU設計の専門家ではありませんが、潜在的なダブルフェッチに関して懸念しているのは、投機的実行(分岐予測とプリフェッチ手法を含むパフォーマンス最適化手法)、レジスタとメモリ位置の名前変更、およびリオーダーバッファの使用です。 1つまたは2つのCPU内にバッファを保存しますか?ここでのダブルフェッチが可能かどうか教えてください。

int function(void* Data) {
    size_t _varSize = ((volatile DATA *)Data)->unsafe_variable;
    // unsafe_variable is in some kind of shared memory and can change at any time
    _ReadWriteBarrier();
    // this does not prevent against CPU optimisations (MemoryBarrier would)
    if (_varSize > x * y) { return FALSE;}
    size_t size = _varSize - t * q;
    function_xy(size);
    return TRUE;
}
4

2 に答える 2

1

揮発性メモリの場所へのアクセスは、C標準C11 5.1.2.3/2の副作用としてカウントされます。

「揮発性オブジェクトへのアクセス、オブジェクトの変更、ファイルの変更、またはこれらの操作のいずれかを実行する関数の呼び出しは、すべて副作用です。」

また、コンパイラは、追加の副作用を引き起こすコードを生成することを許可されていません。揮発性変数への追加アクセスを引き起こすコードを生成することは明示的に許可されていません(C115.1.2.3 / 6)。

しかし、あなたはVC ++を使用しているので、すべての賭けはオフになっています。それはほとんどどの基準にも従いません。可能であれば、代わりに厳密に準拠したCコンパイラを使用することをお勧めします。

于 2012-06-11T06:27:29.073 に答える
0

C言語では、このレベルでのメモリシステムの動作やスレッドに関することは何も指定されていないため、特定の答えはありません。

確実にするには、CPU、OS、およびコンパイラの正確な詳細が必要になります。

ただし、計算が中断されない限り、最新のアーキテクチャがメモリから2回フェッチして、前述の目的のいずれかを実行することはないと思います。最初の参照の後の参照は、キャッシュすることです。

unsafe_variableただし、フェッチの開始後、使用可能になる前にコンテキストスイッチがある_varSize場合、このスレッドが続行するとフェッチが再開される可能性があります。

于 2012-06-11T05:58:11.227 に答える