1

バックグラウンド

私はさまざまな本や記事を読んで、同時実行のコンテキストでのプロセッサキャッシュ、キャッシュの一貫性、およびメモリバリアについて学びました。しかし、これまでのところ、私の一般的なコーディング手法が厳密な意味で安全であるかどうかを判断することはできませんでした。

仮定

  1. 次の擬似コードは、2プロセッサマシンで実行されます。

    int sharedVar = 0;
    
    myThread()
    {
        print(sharedVar);
    }
    
    main()
    {
        sharedVar = 1;
        spawnThread(myThread);
        sleep(-1);
    }
    
  2. main()はプロセッサ1(P1)で実行され、myThread()はP2で実行されます。

  3. 最初、sharedVarはP1とP2の両方のキャッシュに存在し、初期値は0です(上記に示されていない「ウォームアップコード」のため)。

質問

厳密に言えば、できれば特定のタイプのCPUを想定せずに、myThread()は1を出力することが保証されていますか?

プロセッサキャッシュに関する私の新たな知識により、print()ステートメントの時点で、P2がmain()でのP1の割り当てによって引き起こされたsharedVarの無効化要求を受け取っていない可能性があります。したがって、myThread()が0を出力する可能性があるようです。

参考文献

これらは私が読んでいる関連記事と本です:

  1. 共有メモリ整合性モデル:チュートリアル
  2. メモリバリア:ソフトウェアハッカーのハードウェアビュー
  3. Linuxカーネルのメモリバリア
  4. コンピュータアーキテクチャ:定量的アプローチ
4

2 に答える 2

1

厳密に言えば、できれば特定のタイプのCPUを想定せずに、myThread()は1を出力することが保証されていますか?

理論的には、ストアはほとんどすべてのアーキテクチャでロード後に移動できるため、x86でも、またはの0いずれかを印刷できます。1

myThread()実際には、印刷するのは難しいでしょう0
スレッドの生成は、おそらく次のようになるため、暗黙的なストア/リリースメモリバリア
として機能する可能性があります。- 実行パスに沿ってメモリバリアをもたらす少なくとも1つの命令がある-インターロックされた命令、明示的なメモリバリア命令など
-または、新しいスレッドを設定すると多くの命令が実行されるため、ストアは呼び出されるまでにストアバッファから単純にリタイア/ドレインされます。その中には、多くのストアが含まれますmyThread()

于 2010-06-09T18:51:35.237 に答える
0

ここではJavaについてのみ説明します。Java言語仕様(セクション17.4.5)で定義されるmyThread()に発生するため、1を出力することが保証されています。

The write to sharedVar in main() happens before spawning the thread with function myThread() because the variable assignment comes first in program order. Next, spawning a thread happens before any actions in the thread being started. By the transitivity of the definition in Section 17.4.5 (hb(x, y) and hb(y, z) implies hb(x, z)), writing to the variable sharedVar happens before print() reads sharedVar in myThread().

You might also enjoy reading Brian Goetz's article Java theory and practice: Fixing the Java Memory Model, Part 2 covering this subject, as well as his book Java Concurrency in Practice.

于 2010-06-06T14:39:12.410 に答える