[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[FDclone-users:00153] Re: {FreeBSD,OpenBSD}/sparc64, IA64(AIX 対応その後)
- Subject: [FDclone-users:00153] Re: {FreeBSD,OpenBSD}/sparc64, IA64(AIX 対応その後)
- From: SHIOTA Shoichi <Shoichi.Shiota@lightwell.co.jp>
- Date: Fri, 02 May 2003 11:50:40 +0900
潮田@徹夜あけです。
やっぱり長文です。
> > IBM との保守契約はどうなっています?
> BP(ビジネス・パートナー)向けのリース契約で、ハードに関しては
> 細かく書いてありますが、ソフトに関しては特に書いてないみたい
> です。
> 購入した担当者に確認してみます。
これは、購入時の IBM 側営業マンにメールを投げたので、
結果は後日ということで。
(門前払いの可能性が大ですが)
で、寝付けず Web 上をさまよっていたら
[FDclone-users:00148] で私の書きました
> 私自身、 AIX 上で同じこと(SIGCHLD のハンドラ中で再度 SIGCHLD の
> ハンドラのセット)をしているプログラムを書いていて、それが今も
> 某所で動いています。
> もっと雑なつくりで、どんな signal を捕らえても、すべてのハンドラを
> 再度セットするようなやつですが。
> うーん、なぞ。
の、からくりが少しわかりました。
小島さんのセキュリティホール memo で、 OpenSSH portable の
version があがったネタを発見。
ふーん、 AIX 名指しなんだとか独り言をいいながらソースを wget 。
で、いつもなら絶対しないのに、これの SIGCHLD のハンドラーはと、
ソースをながめてみました。
> static void
> main_sigchld_handler(int sig)
> {
> int save_errno = errno;
> pid_t pid;
> int status;
>
> while ((pid = waitpid(-1, &status, WNOHANG)) > 0 ||
> (pid < 0 && errno == EINTR))
> ;
>
> signal(SIGCHLD, main_sigchld_handler);
> errno = save_errno;
> }
「うーん、やっぱりハンドラー関数の中で自分を再度セットしてるよな。
しかも、 signal() で。
その上には waitpid() のループしかないしなー・・・・・
waitpid() のループ!!!」
某所のソースを確認。
う、やっぱり。
[FDclone-users:00150] で私の書きました
> void ExitChild(int iSignal)
> {
> pid_t iPid = 0;
>
> (省略)
>
> /* シグナルの再セット */
> SetSignalFunc();
>
> return;
> }
の省略部分は大雑把に書くと、
--- ここから ---
do {
/* 終了した子プロセスを取得 */
iPid = waitpid((pid_t)0, &iStatus, WNOHANG);
if (iPid < 1) {
break;
}
/* 自分の子供のリストから iPid の検索 */
/* みつかった pid の終了時間を今の時刻に */
} while (1);
--- ここまで ---
と、同様に waitpid() のループでした。
ではと、[FDclone-users:00150] で書きました、かの暴走プログラムの
main() にいる wait() をコメントにし、CatchSIGCHLD() の頭に
waitpid() のループを入れたら見事に暴走がとまりました。
(あのソースぐらいだとループにしなくても大丈夫でしたが)
signal() でも sigaction() でも同じように動くようです。
waitpid() の man をみても特に記述は見られないのでただの観測結果
なのですが、自分の備忘録をかねてお知らせいたします。
http://www16.boulder.ibm.com/doc_link/en_US/a_doc_lib/libs/basetrf2/wait_waitpid_wait3_wait364.htm
# ちなみに、上記の URL (自体)をみて初めて waitpid() の man の
# 呼び出し方がわかりました
# $ man 1 wait
# は、日本語でその manual が表示されるのですが、
# $ man 2 wait
# wait に対するエントリがセクション 2 にありません。
# とでるので、 wait() の manual が存在していないとばかり
# 思っていましたが、
# $ man 2 wait_waitpid_wait3_wait364
# でやっと英語の manual が出てきました。
# AIX install program が symlink を作ってくれなかっただけらしい。