• ベストアンサー

Linuxでのスレッド間メッセージについて

Linuxでスレッドを複数生成し、スレッド間でメッセージのやり取りをしたいと思っています。 ネットで色々検索したのですが、欲しい情報にめぐり合えていません。 # WindowsのPostThreadMessage()みたいなものを探しています。 #「プロセス間通信」というものは発見しましたが・・・ 何か方法はありますでしょうか? スレッド間のメッセージのやり取りの方法がない場合は代替案も教えて頂きたいです。 # セマフォを用いて共有メモリアクセスかな?と思っています。

質問者が選んだベストアンサー

  • ベストアンサー
  • guccii
  • ベストアンサー率31% (14/44)
回答No.1

pthreadでは、排他や条件セマフォ等はありますが、メッセージ交換のAPIはありません。おそらく多くの人はプロセス間通信を用いているのではないでしょうか? ただし、posixのメッセージキューは、実装により1プロセスがオープンできる数が著しく(32個とか)制限されていますし、SystemVのメッセージもOSの初期設定値が著しく低い値が設定されていたりして、現代的なマルチスレッドの設計には向いていないかもしれません。また、UNIXは所有者プロセスがいなくなってもリソースが残ってしまいますので、正直使いづらいです。 プロセス内でのみのメッセージ交換なら、pthreadとSTLなどを組み合わせてキューをつくることも考えられます。軽量で高速なキューの実装が可能です。とりあえず実装することは難しくないのですが、デッドロック等に十分に注意して実装してください。共有メモリにおけば、プロセス間通信も可能でしょう。 もうひとつは、パイプもしくはソケットを用いる方法が考えられます。UNIXではこれが一般的だろうと思われます。UNIXドメインのソケットを用いればポートをバインドする必要もありません。ソケットをラップして、キューライクなインターフェースにすることも可能でしょう。ただし、UNIXドメインのソケットがWindowsにないので、ポーティング・ソース共有が少し面度くさくなります。 あとは、メッセージキューイング製品を用いることも選択肢としてはあります。コスト的に許されればの話ですが。オープンソースもなくはないですが、試してみたことはないです。 といったところでしょうか。 ちなみにWindowsもプロセス間/スレッド間で用いるメッセージキューがありませんね。代わりにウインドウメッセージキューを用いることもありますが、信頼性が低い(Win3.1のころは最悪でした)。ウインドウを持たないスレッドに必ずウインドウメッセージキューを作成するあたりも少し不満が残ります。名前付きでオープンできないですし。代わりにmailslotをラップしてキューを実装してりしていました。最近はMSMQという選択肢もありますが。javaでもconcurrentパッケージがJDKに入ったのは最近ですし、こっちはプロセス間通信ができません。 世の中ではメッセージ交換方式のプログラミングがなかなか普及しないみたいで、各プラットフォームでいつも悩まされます。

ITomo
質問者

お礼

詳しいご説明ありがとうございます。 今回、初めてLinuxを使用して開発することになりまして。。。 pthreadで色々検索したのですが、API一覧が載っているHPはなかなかありませんでした。 # 本日、一件発見しました。 今回作成したものはWindows上でも動かしたいと思っていますので、 キューを作成しようと思います。 >ちなみにWindowsもプロセス間/スレッド間で用いるメッセージキューがありませんね。 PostThreadMessage()はスレッドのメッセージキューにメッセージをポストすると思っているのですが、 私は何か勘違いをしていますでしょうか?

その他の回答 (4)

  • galluda
  • ベストアンサー率35% (440/1242)
回答No.5

がるです。 まず > 他のプロセスとのやり取りはありません。 了解です。 以下、これを前提にしたお話を。 前述しましたが、プロセスは「常にメモリ空間が個々に独立」していて、一方でスレッドは「同一メモリ空間内に複数存在する」ものになります。 一応念のため。「メモリ空間が独立しているスレッド」は存在しません(逆はありえまして。Linuxの場合、スレッドは"同一メモリ空間を共有する複数のプロセス"として実装されているので、ある見方によっては"メモリ空間を共有するプロセスがある"といえなくもないです。かなり余談ですが)。 プロセスは「メモリ空間が独立している」ために、通常プロセス間での情報のやり取りは「無理」で、ゆえに、どうしてもやむを得ず「プロセス間通信」なるものを使わざるを得ない、という事情があります。 一方で、スレッドの場合「メモリ空間を共有」しているので、たとえば「グローバル変数」とかが「各スレッドで共有しているブツ」になるので、特になにかを用意しなくても基本的な通信は行えてしまいます。 # ってか、たとえばpthreadで実装する場合、pthread_mutexとかちゃんと使わないと「共有したくないのに共有しちゃう」、いわゆる thread unsafeなブツになります。 このあたりが「何かしらの仕組みが」ない、理由になります。 あとは…単純なやり取りなら「通信用のglobalな変数」を設定するか、もうちょっと複雑にやりとりをするなら、「通信用のglobalな変数」を基点に、#3さんのおっしゃってるようなリングバッファの実装とかそのあたりをなさるとよろしいのかなぁとおもいます。 ちと蛇足的な部分もあり恐縮ですが。何かの参考にでもなれば幸いです。

ITomo
質問者

お礼

すぐにお礼ができず、申し訳ありませんでした。 細かいご説明ありがとうございます。 基本的な事の再確認ができました。 # 曖昧な部分もありました。 ご参考にさせて頂き、実装してみようと思います。

  • guccii
  • ベストアンサー率31% (14/44)
回答No.4

>>ちなみにWindowsもプロセス間/スレッド間で用>いるメッセージキューがありませんね。 >PostThreadMessage()はスレッドのメッセージキューにメッセージをポストすると思っているのですが、 >私は何か勘違いをしていますでしょうか? 説明不足でしたね。PostThreadMessageはウインドウメッセージキューを使用します。ウインドウメッセージキューは以前は信頼性が低く、メッセージ数が制限されていたことと、WM_TIMERなどのメッセージをOSがまとめたりもしますので、個人的になんとなく信頼がもてないということです。失っても構わないような通知レベルのメッセージならともかく、応答を必要とするデータを渡すのにウインドウメッセージキューを使用するのにはなんとなく抵抗があります。最近の環境ではおそらく問題ないとは思いますが、とはいえ、"post"は暗にメッセージロストすることを示唆しています。また、送信を確実に行おうとするためSendMessageをすると送信側にもウインドウメッセージキューが作られますから、スレッド数が多い場合には意識しないところで無駄なリソースを使ってしまっている可能性もあります。GUIの描画処理をマルチスレッド化する用途なら十分有用なのですが... また、GUI処理のウインドウメッセージと混ざってキューイングされることや、ほかのセマフォやイベントと複数待機できないのも少し不満です。 余談ですがOS/2にはメッセージキューがあったんですけどねぇ。

ITomo
質問者

お礼

すぐにお礼ができず、申し訳ありませんでした。 Windowsの詳しい説明までして頂き、大変参考になりました。 プログラミングしていましたが、中身をちゃんと理解して使用していませんでした。 基本的な事柄をもっと勉強して、開発をして行きたいと思います。 # 既存ソースを真似して作成したりすることが多かったです・・・ # 何かあったときに原因不明になってしまうかもしれませんね。 ありがとうございました。

  • moritan2
  • ベストアンサー率25% (168/670)
回答No.3

linuxの場合メモリを共有しないスレッドもあるのですが、メモリを共有するスレッドなら、リングバッファーでキューを作ってやるのが一番高速です。キュー2個で双方向の通信が出来ます。特別なAPIを使うわけではないので Windows でも linux でもなんでも動くし、セマフォとかクリティカルセクションのようなものも必要ありません。単純なだけに高速なので私はいつもこれを使っていますね。

ITomo
質問者

お礼

ご回答ありがとうございます。 スレッド間のやり取りは多くの人がやっていると思っていますので、 何かしらの仕組みが既にある(使える)かと思っていました。 自分で作るのはなんとかできるとは思いますが、 あるものを作ってもしょうがないですので・・・ キューは今まで作る機会がありませんでしたので、 勉強も兼ねて作ってみようと思います。

  • galluda
  • ベストアンサー率35% (440/1242)
回答No.2

がると申します。 一応念のため。「プロセスではなくてスレッド」ですよね? スレッドであると仮定すると。次に出てくるのは ・常に「同一プロセス内の各スレッド間での通信」 でしょうか?それとも ・「異なるプロセスの可能性のある各スレッド間での通信」 でしょうか? ここでまた回答が異なってきます。 大変に失礼ながら、ではあるのですが。たぶん、スレッドについてきちんと把握されていないのだろうと推測いたします。 スレッドとプロセスの違いを、特に「メモリ空間」の観点から一度調べてみると、色々と見えてくるのではないかと思います。 プロセスは「それぞれが独立している」事がメリットでもありデメリットでもあり。 スレッドは「同一メモリ空間内に共存している」事がメリットでもありデメリットでもあります。

ITomo
質問者

補足

「プロセスではなくてスレッド」です。 読みが深いですね。言葉が足らずすいません。 Linuxでスレッド間通信について調べていたら、 なぜか「プロセス間通信で・・・」という書き込みを見かけたもので、 質問に >#「プロセス間通信」というものは発見しましたが・・・ を書いたしだいです。 今回は1プロセスで5スレッドを生成し、この生成したスレッド間でメッセージのやり取りをしたいと思っていました。 他のプロセスとのやり取りはありません。

関連するQ&A