メイン終了してもスレッドが終了しない


おじゃ  2012-05-22 16:33:50  No: 73393  IP: 192.*.*.*

VC2010
Win7です。
Win32プロジェクト

スレッドの終了の仕方わからないです。
以下簡単なコードです。

int APIENTRY _tWinMain
{
   HANDLE h=(HANDLE)_beginthreadex(NULL,0,Thr,NULL,0,NULL);

   while (GetMessage(&msg, NULL, 0, 0) > 0)
   {
        //省略
    }
   CloseHandle(h);  
   return (int) msg.wParam;
}

unsigned int __stdcall Thr(LPVOID pParam)
{
    while (true)
    {
        //省略
     }
}

このようになっています。
Thrのスレッドは無限ループになっています。
メインでreturn (int) msg.wParam;になった時点で終了すると思っていましたが、
Thrのループはまだ死なずに動いていました。
_endthreadex(0)をメインにいれましたが、とくに変わらず。
どうしたらThrの処理がreturn (int) msg.wParam;
のタイミングで抜けるようになるでしょうか?
よろしくお願いします。

編集 削除
瀬戸っぷ  2012-05-22 23:27:17  No: 73394  IP: 192.*.*.*

TerminateThread()で無理矢理殺すか、スレッド自身が自分で終了できるように作る。ということになるかと。

http://msdn.microsoft.com/ja-jp/library/cc429380.aspx
解説にあるとおり、「無理矢理」なのでリソースリークとか発生するかも知れませんし、場合によってはめでたくデッドロックしてリセットしか残されていない。なんてことになるかも知れません。
スレッド自身が、自分で使ったリソースなどの後始末をして終了できるように作っておく方が安全です。
どうやって終了する契機を通知するか…が問題になるかも知れませんが。
単純に変数を参照する。だと失敗する可能性もありますのでご注意を。
# 私ならEventオブジェクトとかで通知します。

編集 削除
おじゃ  2012-05-23 16:43:50  No: 73395  IP: 192.*.*.*

TerminateThread()止めることはできました。
ですが、あまり使用をおすすめできないやりかたみたいなので、使用するのもなあと思っています。

とにかくスレッドThr内でなにか受け取れればよいのですよね?
> # 私ならEventオブジェクトとかで通知します。
とありますが、これは
イベントを作成しておいて   CloseHandle(h);  
のタイミングなどでイベントをセットし、Thrでそれを確認する?
ってことでしょうか?

> 単純に変数を参照する。だと失敗する可能性もありますのでご注意を。
なぜ変数ではだめなんでしょうか?

編集 削除
瀬戸っぷ  2012-05-23 16:58:33  No: 73396  IP: 192.*.*.*

>イベントを作成しておいて   CloseHandle(h);  
>のタイミングなどでイベントをセットし、Thrでそれを確認する?
>ってことでしょうか?

そのように処理しています。

>なぜ変数ではだめなんでしょうか?

「スレッド 変数 最適化」あたりで検索して下さい。
対応を間違えなければ変数でも可能でしょう。

編集 削除