0

次のような一連のプログラムがあります。

C++ プログラム「A」は、bash スクリプトを起動する別の C++ プログラム「B」を起動します。

bash スクリプトを起動するために、以下を使用しています。

int returnVal = system("pathToScript/myScript.sh");

ログ ファイルでスクリプトの出力を確認できるので、確実に実行されています。

問題は、スクリプトが何を返しても returnVal が常に -1 であることです。スクリプトに「exit 3」をハードコーディングしましたが、システム コールを介して起動すると、依然として -1 の returnVal が返されます。

ターミナルでスクリプトをスタンドアロンで実行し、「$?」をエコーし​​ます。予想どおり、戻り値 3 が表示されます。

では、C++ プログラムのチェーンを実行すると、終了コードが壊れるのはなぜですか? これを回避する方法はありますか?

編集- perror を使用すると、「子プロセスがありません」というエラー メッセージが表示されます。

編集- 別の方法として、fork/exec/wait を使用してスクリプトを実行しようとしていますが、182、56、163、62、51 などのランダムな終了コードを取得しています...以下のコード:

pid_t pid = vfork();

switch (pid)
{
  case -1:
     cout << "Failed to fork." << endl;

  case 0: // Child process
     cout << "Child process launched!" << endl;
     execl("/pathToScript/myScript.sh", "/pathToScript/myScript.sh", "someArgument", NULL);
     cout << "execl call failed." << endl;
     exit(0);

  default:
     int status;

     cout << "Waiting for process to complete..." << endl;

     waitpid(pid, &status, 0); // Wait for the process to complete.

     cout << "Process exited with status: " << WEXITSTATUS(status) << endl;
}

ここでランダムな終了ステータスが表示されるのはなぜですか?

アドバイスをいただければ幸いです。ありがとう!

4

1 に答える 1

2

コメントで述べたように、あなたの問題は ignorigSIGCHLDです。無視SIGCHLDすると、ゾンビの作成を防ぐことができます。したがって、その性質をデフォルトに設定することで、何かを壊すことができます。

ここで例:

signal (SIGCHLD, SIG_DFL);
system ("some_program");
signal (SIGCHLD, SIG_IGN);

1 行目と 3 行目の実行の間に子プロセス ( の子プロセスではないsystem) が終了すると、ゾンビになります。

このリソース リークを正しく解決したい場合は、別の方法 (doubleforkまたはwait) を使用してゾンビの問題を解決する必要があります。


ここでランダムな終了ステータスが表示されるのはなぜですか?

waitpid通話に失敗したため。出力すると戻り値はwaitpidになります-1。ほとんどの場合の値は にerrnoなりますECHILDSIGCHLDの処理をに設定すると、とSIG_IGNが壊れます。あなたの例では、変数に何も書き込みません(またはゴミを書き込みます)。waitwaitpidwaitpidstatus

182、56、163、62、51など

この数値は、初期化されていない整数変数 (またはゴミ) の値です。

別の方法として、 fork/exec/wait を使用してスクリプトを実行しようとしています

それは良い代替手段ではありません。代替ソリューションは、プログラムのすべての部分に対しての配置SIGCHLDを設定します。SIG_DFLそして、他の部分でゾンビを処理する戦略を変更します。

于 2013-08-06T07:04:30.200 に答える