10

シリアル通信に使用されるマルチスレッド Linux プログラムで、別のスレッドからのブロッキング read() 呼び出しを終了することは可能ですか (そして何が最善のアプローチでしょうか)?

すべてを可能な限り反応的に保ち、ポーリングを繰り返してタイムアウトを使用しないようにしたいと考えています。

この質問の背景は、JNI を使用して Linux 用の Scala シリアル通信ライブラリを作成しようとしているということです。私はネイティブ側をできるだけシンプルに保ち、特に read() と close() 関数を提供しようとしています。Scala 側では、1 つのスレッドが read() を呼び出し、シリアル ポートからのデータが利用可能になるまでブロックします。ただし、シリアルポートは他の方法で閉じることができ、その結果、close() が呼び出されます。ここで、ブロックされたスレッドを解放するには、システムの読み取り呼び出しをキャンセルする必要があります。

4

3 に答える 3

17

かなり一般的なトリックの 1 つ: read() でブロックする代わりに、シリアル ソケットとパイプの両方で select() でブロックします。次に、別のスレッドがスレッドをウェイクアップしたい場合は、そのパイプのもう一方の端にバイトを書き込むことでウェイクアップできます。そのバイトにより select() が返され、スレッドはクリーンアップして終了するか、必要なことは何でもできるようになります。(これを 100% 確実に機能させるには、シリアル ソケットをノンブロッキングに設定して、スレッドが select() でのみブロックし、read() では決してブロックしないようにする必要があることに注意してください)

于 2013-05-19T19:54:49.407 に答える
4

AFAIK シグナルは、スレッドをブロックしているシステム コールから抜け出す唯一の方法です。

pthread_kill()USR1 信号でスレッドに狙いを定めて使用します。

于 2013-05-19T17:22:46.320 に答える