0

同期のために POSIX セマフォ (初期値 = 1 のミューテックスとして使用) を使用するスレッドセーフ ライブラリを作成する必要があります。非同期信号を正しく管理するための問題がいくつか見つかりました。この静的ライブラリにリンクするアプリケーションがあり、アプリケーション (マルチスレッド) がライブラリの関数を呼び出します。一部の内部構造へのアクセスは、posix セマフォによって制御されます (ライブラリの内部です)。

void library_func1(lib_handler *h)
{
   sem_wait(sem);
   /* do some stuff with global data */
   sem_post(sem);
}

void library_func2(lib_handler *h)
{
   sem_wait(sem);
   /* do some stuff with global data */
   sem_post(sem);
}

void library_close(lib_handler *h)
{
   ...
}

SIGINT1 つのスレッドがセマフォをロックしているときに非同期シグナル (たとえば ) が発生した場合、どのような追加が必要ですか? アプリケーションを再起動すると、セマフォが存在し、その値が であるため、デッドロックが発生します0。非同期シグナルが発生したときにセマフォを解放できる機能がありますが、library_closeこれを実行して確認する最良の方法はどれですか (その機能は、後に続く場合にのみシグナルセーフになると思いますexit)? マルチスレッド アプリケーションでは、通常、すべてのシグナルに対して 1 つのスレッド マネージャーを使用することをお勧めします。

皆さん、ありがとうございました。

4

2 に答える 2

0

Linux futex にも同じ問題がありました。完全に解決できるわけではありませんが、できることは、同じ共有メモリ領域のどこかにセマフォをロックしているプロセスの pid を書き込むことです。別のプロセスがセマフォをロックしようとして時間がかかりすぎる場合 ('too long' の値の場合)、共有メモリから pid を読み取ることによって、セマフォがロックされているプロセスを見つけます。そのプロセスが存在しなくなった場合は、デッドロックに陥っていることがわかります (ライブラリの内部データが一貫性のない状態にある可能性があるため、おそらく死ぬべきです)。

ロックを取得したプロセスは、ロックした直後に pid を書き込む前に終了する可能性があるため、これにはまだ小さな競合があります。私の知る限り、セマフォを使用してこれを回避する方法はありません。(取得時に pid がアトミックにロック変数に書き込まれるロック実装がある場合は機能する可能性がありますが、おそらくこれを自分で記述する必要があります。)

于 2013-01-12T14:28:35.283 に答える
-1

静的ライブラリの状態は、アプリの異なる実行間で引き継がれず、それを使用する他のアプリと共有されません。それを使用しているアプリケーションの状態の一部です。したがって、セマフォが不安定な状態になることはありません。

于 2012-09-05T20:25:46.647 に答える