stdin / stdout / stderrのクロスプラットフォーム(linux / Win32)ノンブロッキングC ++ IO
-
10-07-2019 - |
質問
次の特性を備えたstdin / stdoutを使用して、ノンブロッキングIOに最適なソリューションを見つけようとしています。
- 十分なデータがある限り、 n サイズのチャンクで読み取ります。
- 十分なデータがない場合は、部分的なチャンクで読み取ります。
- 利用可能なデータがない場合は、( n より小さい可能性がある場合でも)何らかのデータがあるまでブロックします。
目標は、「制御」コードをすぐに処理しながら、大規模なデータセットを効率的に転送できるようにすることです(部分的に満たされたバッファーのどこかにそれらを残すのではなく)。
私は、スレッドとistream :: get()ループを使用するか、プラットフォーム固有のコードをたくさん書くことでこれを達成できることを知っています(Windowsのファイルハンドルでselect()できないため)... ((有望と思われるistream :: readsome()もありますが、Googleで見つけることができる唯一の結果は、実際にはうまく機能しないと言っている人だけでした。))
これらのAPIを使用したコーディングはあまり行っていないので、おそらくもっと良い方法があるでしょう。
解決
多分 boost :: asio はあなたのために役立ちますか?
他のヒント
スレッドとプラットフォーム固有のコードを使用しました。 別の質問への回答をご覧ください。 OS固有のものをinputAvailable()に入れることができました(Linuxはselectを使用し、Windowsはtrueを返すだけです)。次に、Windowsでタイムアウトを指定してWaitForSingleObject()を使用してスレッドを完了させ、TerminateThread()を使用してそれを強制終了します。非常にいですが、チームはこのちょっとしたブーストを使いたくありませんでした。
jwhitlockと似たようなことをしました...適切なOS固有の実装(*)をラップするStdinDataIOクラスになり、StdinDataIOが提供するファイル記述子で残りのプログラムがselect()できるようになりました。 stdinに関するWindowsの制限を至福の無知。 こちらとこちら必要に応じて、コードはすべてオープンソース/ BSDライセンスです。
(*)実装はLinux / MacOSXの単純なパススルーであり、Windowsではstdinから読み取り、受信したデータをソケット経由でメインに戻すための子スレッドをセットアップするかなり複雑なプロセスです。スレッド...あまりエレガントではありませんが、動作します。