甕星

Microsoft MVP for Visual Basic...

ホーム 連絡をする 同期する ( RSS 2.0 ) Login
投稿数  251  : 記事  0  : コメント  247  : トラックバック  527

ニュース


MCP - C# Application




FORMAT OBグループに参加する


Archives

Post Category

Image Gallery

Community

Hobby

MSKK blogs

Other MVP's

Other Sites

棒MLでvolatileが話題に上がっていました。実は今までvolatileが何のためにあって、何に使うのが分かっていませんでした。ぶっちゃけ存在すら記憶のかなたに忘れていました。殆どのアプリケーションはvolatileの存在を忘れていても、運良く動いてしまいますから・・・。でも運に頼っていたなんて、プロ失格です。orz

以下のようなコードを記述した場合、volatileで宣言していないとThreadBで値を変更してもThreadAはループから脱出できない場合があります。コンパイラがコードを最適化した結果、メモリ上の値を取得するのではなく、CPUレジスタに退避されている値を参照する可能性があるためです。あるいは逆にThreadBで行っている代入はCPUレジスタにだけ反映され、メモリには書き込まれないかもしれません。このような場合2つのスレッドは同じ変数を参照しているにもかかわらず、同じ値を参照していないと言う状態が発生します。

voltileで宣言した場合、必ず変数への参照は最適化されずに、必ずメモリの値を取得するようになります。それによって上記のような現象を避けることが出来ます。本来、複数のThreadから参照する可能性のある変数は全てvolatile宣言する必要があります。


    volatile int abort = 0;
    UINT ThreadA(LPVOID)
    {
        while(!abort)
        {
            ...
        }
    }
    UINT ThreadB(LPVOID)
    {
        ....
        abort = 1;
    }

もちろん代償もあります。volatile宣言を行った場合、コードは最適化されないので、実行速度の低下をもたらします。したがって複数のThreadから参照する可能性のある変数は、必要最小限にしなくてはなりません。

このvolatile宣言、あらためて確認していたらC#にもあるのですね。C#の場合にはC++と同じように変数宣言時にvolatileを指定します。また言語に限らずShared(public static)に宣言された変数はvolatile宣言した変数と同じように扱うそうです。

C++ならコンパイル時に幸運に恵まれればvolatileを忘れてもアプリケーションは問題なく動きました。一度コンパイルされたコードが実行中に最適化され、メモリからデータを取得しなくなる可能性はありませんでしたから。でも.Netではそうは行きません。実行時最適化機能によってコードが最適化される可能性があるため、volatileを忘れると何時おかしな動作をしだすか予想できません。volatile宣言を忘れないように気をつけましょう。:-)

投稿日時 : Thursday, February 03, 2005 10:17 PM

コメント

No comments posted yet.

コメントをお寄せください。

タイトル
名前
Url:
コメント 
   
Protected by Clearscreen.SharpHIPこの絵に表示されている文字列を入力してください (半角で6文字です):