例とマニュアルページを見てみましたが、signalfdとsigwaitinfoの違いを理解することはできません。構文に加えて、両方とも同じことを行い、信号がいくつかの構造に詳細を保存するのを待っています。
マンページにこう書いてあります。これは信号の使用に代わるものです。 select(2)、poll(2)、および epoll(7) を介してファイル記述子を監視する利点があるハンドラまたは sigwaitinfo(2)。
これが正確に何を意味するのかを説明できる人はいますか?
答え1
select(2), poll(2) および epoll(7) システムコールは、単純にファイル記述子 (I/O チャネルを表す小さな整数) でイベントを待つ方法です。イベントには、「データの読み取り」、「書き込みの準備」などが含まれます。コードは最終的にイベントを生成するファイル記述子のセットを構成し、select()、poll()、または epoll() を呼び出してデータが到着し、カーネルが次を使用してソケットを別のホストに接続するまでプログラムを待機します。とにかく記述子は間違っていた。
signalfd(2) は新しいイベントを追加します。 シグナル到着。 unix/linux/*BSDでは、「信号」はやや非同期イベントです。 CPUが誤った命令を実行しようとし、I / Oが準備され、コードが0に分割され、モデムが停止します。 signalfd(2) を使用すると、信号が到着したときにイベントを生成する select()、poll()、epoll() で使用できるファイル記述子を生成できます。
過去には、信号が到着したときにカーネルが魔法のように呼び出すハンドラ関数を指定しました(「アップコール」とも呼ばれます)。 sigaction()システムコールを使用してカーネルにどの関数を呼び出すかを知らせると、sigwaitinfo()と同じ情報が得られます。
signalfd()の代わりにsignal()またはsigaction()を使用してハンドラ関数を設定することの違いは、ハンドラ関数をいつでも魔法のように呼び出すことができることです。コードの一部は再入可能でなければなりません(スレッドから安全であるだけでなく注意してください)。あなた)信号の「いつでも」特性を処理します。 signalfd()を使用すると、信号はコードのイベントループで処理される別のイベントにすぎません。コードは通常どおり実行されます。
sigwaitinfo() は、指定した信号が到着するまでコードを一時停止します。この信号が到着するまで、コードは何もしません。イベントループがなければ何もありません。 sigwaitinfo() も Linux カーネルのリアルタイム機能の一部であるようです。 sigwaitinfo()は呼び出す関数を指定するのではなく、信号が到着したときにカーネルが呼び出すコードの位置を指定すると考えることができます。
次に追加:
ちょうど見つけた「自己管理技術」に関するブログ投稿シグナルと選択ベースのI / Oを処理することは、コードの面で不便であるだけでなく、「不愉快な競争条件」にも苦しむ可能性があります。問題を解決しますが、問題はすべてユーザースペースにあり、より多くのコードが必要です。
答え2
簡単に言えば、sigwaitinfo()を使用すると信号だけを待つことができます。 poll / select / etcでsignalfd()を使用すると、ファイル記述子(ファイルIO、timerfd、eventfdなど)を介してアクセスできるすべてのイベントを待つことができます。