オペレーティングシステム実験は、上記の例のプログラムで同時プロセスを確立する方法を参照して、マルチプロセス同時実行プログラムを作成します.親プロセスは、まずlsコマンドを実行するサブプロセスを作成し、psコマンドを実行するサブプロセスを作成し、lsコマンドの前にpsコマンドが常に実行されるように制御します.
7867 ワード
実験一、プロセス制御実験1.1実験目的プロセス同時実行概念に対する理解を深める.同時プロセスの作成と制御方法を実践します.プロセスの動的特性を観察し、体験します.プロセスライフサイクル中にステータス変換を作成、変換、取り消しするプロセスをさらに理解します.プロセス制御の方法を把握し、親子プロセス間の制御と協力関係を理解する.Linuxシステムでプロセスが制御に関連するシステム呼び出しを作成するプログラミングとデバッグ技術を練習します.1.2実験説明1)プロセスの作成、実行に関するシステム呼び出し説明プロセスは、システム呼び出しfork()によりサブプロセスを作成し、そのサブプロセスと並行して実行することができる.サブプロセスの初期の実行イメージは親プロセスのコピーである.サブプロセスはexec()システム呼び出しファミリーを介して新しい実行プログラムをロードできます.親プロセスは、wait()またはwaitpid()システム呼び出しを使用して、サブプロセスの終了を待機し、サブプロセスの終了ステータスの収集とクリーンアップを担当します.fork()システム呼び出し構文:
forkがサブプロセスを正常に作成すると、サブプロセスのプロセス番号が返され、失敗すると-1が返されます.execシステム呼び出しには6つの関数のセットがあり、サンプル実験ではexecveシステム呼び出し構文を参照しています.
pathが読み込む新しい実行ファイルの絶対パス名文字列.Argv[]新しい実行プログラムに渡す完全なコマンドパラメータのリスト(空でもよい).Envp[]新しい実行プログラムに渡す完全な環境変数パラメータのリスト(空でもよい).Execが正常に実行されると、元のプロセスの代わりに新しいプログラムが使用されますが、プロセス番号は変更されず、呼び出しプロセスに戻ることはありません.exec呼び出しに失敗すると、-1が返されます.wait()システム呼び出し構文:
statusサブプロセスを保持するための終了状態pidは、−1全てのPGIDがPIDの絶対値に等しいのを待つサブプロセス1全てのサブプロセスを待つ0全てのPGIDが呼び出しプロセスに等しいサブプロセスを待つ
0待機PIDがpidに等しいサブプロセスoptionは、waitpidプロセスを呼び出す動作を規定します.WNOHANGがサブプロセスがない場合、WUNTRACEDがステータスを報告していないプロセスに戻ると、waitとwaitpidが成功すると終了するサブプロセスに戻るプロセス番号を返します.成功しない場合は-1を返します.getpid()システム呼び出し構文:
getpidは現在のプロセスのプロセス番号を返し、getppidは現在のプロセスの親プロセスのプロセス番号を返す2)プロセス制御に関連するシステム呼び出し説明は、プロセスの動作を制御するために信号を1つのプロセスに送信することができる.信号は、キーボード割り込み、タイマ割り込み、不正メモリリファレンスなど、割り込みまたは異常イベントによって発生します.信号の名前はSIGで始まり、例えばSIGTERM、SIGHUPである.kill-lコマンドを使用して、システムの現在の信号セットを表示できます.信号はいつでも発生します.受信信号のプロセスは、受信した信号に対して3つの処理措置の1つをとることができる:・この信号を無視する・システムのデフォルトの処理を実行する・この信号をキャプチャしてカスタマイズされた処理信号を生成する生成から処理されるまでのプロセス:生成(generate)->保留(pending)->配信(deliver)->配置(disposition)または無視(igore)信号セットがC言語のsigset_であるtデータ型のオブジェクト、sigset_tデータ型定義
Signumがキャプチャする信号handlerプロセスでカスタマイズした信号処理関数名signal呼び出しに成功すると、信号処理関数の戻り値が返され、-1が正常に返されず、システム変数errnoがSIG_に設定されます.ERR.
#include
pid_t fork(void);
forkがサブプロセスを正常に作成すると、サブプロセスのプロセス番号が返され、失敗すると-1が返されます.execシステム呼び出しには6つの関数のセットがあり、サンプル実験ではexecveシステム呼び出し構文を参照しています.
#include
int execve(const char *path, const char *argv[], const char * envp[]);
pathが読み込む新しい実行ファイルの絶対パス名文字列.Argv[]新しい実行プログラムに渡す完全なコマンドパラメータのリスト(空でもよい).Envp[]新しい実行プログラムに渡す完全な環境変数パラメータのリスト(空でもよい).Execが正常に実行されると、元のプロセスの代わりに新しいプログラムが使用されますが、プロセス番号は変更されず、呼び出しプロセスに戻ることはありません.exec呼び出しに失敗すると、-1が返されます.wait()システム呼び出し構文:
#include
#include
pid_t wait(int *status);
pid_t waitpid(pid_t pid,int *status,int option);
statusサブプロセスを保持するための終了状態pidは、−1全てのPGIDがPIDの絶対値に等しいのを待つサブプロセス1全てのサブプロセスを待つ0全てのPGIDが呼び出しプロセスに等しいサブプロセスを待つ
0待機PIDがpidに等しいサブプロセスoptionは、waitpidプロセスを呼び出す動作を規定します.WNOHANGがサブプロセスがない場合、WUNTRACEDがステータスを報告していないプロセスに戻ると、waitとwaitpidが成功すると終了するサブプロセスに戻るプロセス番号を返します.成功しない場合は-1を返します.getpid()システム呼び出し構文:
#include
#include
pid_t getpid(void);
pid_t getppid(void);
getpidは現在のプロセスのプロセス番号を返し、getppidは現在のプロセスの親プロセスのプロセス番号を返す2)プロセス制御に関連するシステム呼び出し説明は、プロセスの動作を制御するために信号を1つのプロセスに送信することができる.信号は、キーボード割り込み、タイマ割り込み、不正メモリリファレンスなど、割り込みまたは異常イベントによって発生します.信号の名前はSIGで始まり、例えばSIGTERM、SIGHUPである.kill-lコマンドを使用して、システムの現在の信号セットを表示できます.信号はいつでも発生します.受信信号のプロセスは、受信した信号に対して3つの処理措置の1つをとることができる:・この信号を無視する・システムのデフォルトの処理を実行する・この信号をキャプチャしてカスタマイズされた処理信号を生成する生成から処理されるまでのプロセス:生成(generate)->保留(pending)->配信(deliver)->配置(disposition)または無視(igore)信号セットがC言語のsigset_であるtデータ型のオブジェクト、sigset_tデータ型定義
#include
typedef void (*sighandler_t)(int);
sighandler_t signal(int signum, sighandler_t handler);
Signumがキャプチャする信号handlerプロセスでカスタマイズした信号処理関数名signal呼び出しに成功すると、信号処理関数の戻り値が返され、-1が正常に返されず、システム変数errnoがSIG_に設定されます.ERR.
私の実験コード:
#include
#include
#include
#include
#include
#include
typedef void(*sighandler_t)(int);
void sigcat(){//
printf("%d Process continue
",getpid());
}
int main(int argc,char*argv[])
{
int status_1,status_2;
signal(SIGINT,(sighandler_t)sigcat);//Registe a interrupt fuction
char *args1[]={"/bin/ls","-a",NULL};//
char *args2[]={"/bin/ps","-a",NULL};
int pid1=fork();
if(pid1<0)
{
printf("Create Process fail
");
}
if(pid1==0)
{
printf("ls -the child process starting%d
",getpid());
pause();//Wait for the interrupt
printf("ls the child process waking%d
",getpid());
status_1=execve(args1[0],args1,NULL);
exit(0);
}
else
{
//Father process
printf("
Father Process starting%d
",getpid());
int pid2=fork();
if(pid2>0)// pid2
{
printf("ps the childprocess over%d
",pid2);
printf("ls waking%d
",pid1);
waitpid(pid2,&status_2,0);
kill(pid1,SIGINT);// p1
waitpid(pid1,&status_1,0);
printf("ls over%d
",pid1);
printf("Father process over%d
",getpid());
exit(0);
}
if(pid2<0)
{
printf("Process 2fails
");
}
if(pid2==0)
{
printf("ps starting%d
",getpid());
status_2=execve(args2[0],args2,NULL);
}
}
return 0;
}