Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/linux/22.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 理解C+中的fork、exec和wait+;(Linux)_C++_Linux_Fork_Exec_Wait - Fatal编程技术网

C++ 理解C+中的fork、exec和wait+;(Linux)

C++ 理解C+中的fork、exec和wait+;(Linux),c++,linux,fork,exec,wait,C++,Linux,Fork,Exec,Wait,我对在linux中使用这些不同类型的系统调用非常陌生,这让我感到非常困惑。有了这个,我只要求朝正确的方向推进/开始,而不是完成。 使用fork、exec和wait,我已经阅读了它们,但这对我的处境仍然没有真正的帮助。 我要做的是: 打印promt并等待用户输入最多包含四个参数或选项的命令。“退出”将停止程序 一些示例,mkdir blah,创建目录,然后提示输入新命令,touch blah/this blah/that blah/there 我必须调用fork来创建一个子进程来执行输入的命令,然

我对在linux中使用这些不同类型的系统调用非常陌生,这让我感到非常困惑。有了这个,我只要求朝正确的方向推进/开始,而不是完成。 使用
fork
exec
wait
,我已经阅读了它们,但这对我的处境仍然没有真正的帮助。 我要做的是:

打印promt并等待用户输入最多包含四个参数或选项的命令。“退出”将停止程序

一些示例,
mkdir blah
,创建目录,然后提示输入新命令,
touch blah/this blah/that blah/there

我必须调用
fork
来创建一个子进程来执行输入的命令,然后在子进程中调用
exec
,使子进程成为要执行的程序(这一部分让我更加困惑),最后在父进程中调用
wait
,以便解释器在命令完成之前不会打印下一个提示

实现这一目标的最佳方式是什么?与中一样,读入命令/参数/选项然后执行它们的最佳方式是什么? 我认为这样做最好是
do..while
,而
while
条件是检查“退出”的条件

我知道,我做的很少,但也不多

int main()
{
char command[25];
pid_t  pid;
int rs;
cout << "Enter command: ";
cin >> command;

while(strcmp(command, "exit") != 0) {
    pid = fork();

    if (pid == 0) { //child process
    rs = execl("echo", command);
            }
 else { // parent process
    cout << "Enter a command: ";
    cin >> command; 
}

}



return 0;
}
intmain()
{
char命令[25];
pid_t pid;
int-rs;
cout>命令;
while(strcmp(命令,“退出”)!=0){
pid=fork();
如果(pid==0){//子进程
rs=execl(“echo”,命令);
}
else{//父进程
cout>命令;
}
}
返回0;
}

这些系统调用的功能的一般分解:

分叉:分叉当前进程。实际上,当调用fork时,执行在调用fork时暂停,整个程序被复制到一个新的进程空间中,该进程空间是原始进程的子进程空间。然后这两个进程在fork调用之后继续并行执行。您需要获取PID,以便判断当前正在执行的程序是子程序还是父程序

exec:暂停当前进程的执行,用指定的要运行的新程序擦除内存中的当前进程。然后它运行新程序

等待:暂停当前进程,直到至少一个子进程终止。它是waitpid()的包装器,允许您暂停当前进程的执行,并等待当前进程的子进程(可能是自身的克隆,也可能是exec插入的新程序)的状态发生变化

下面是我在大学上过的一门课中的一些代码演示,正在等待和分叉(但没有执行):

#include <stdio.h>
#include <stdlib.h>
#include <errno.h>
#include <semaphore.h>
#include <fcntl.h>
#include <unistd.h>
#include <sys/stat.h>
#include <sys/wait.h>
const int BUFFER_SIZE = 1000;

void copySegment(int i, int segmentSize, FILE * fin, FILE * fout) {
    // Does not need to be shown to prove point
}

int main(int argc, char * argv[]) {
    int i;
    sem_t * sem;
    pid_t pid;
    FILE * fin, * fout;
    struct stat sbuf;
    int fileSize, fileDescriptor, segmentSize;
    fin = fopen(argv[1], "r");
    fout = fopen("forkcopy.txt", "w");
    fileDescriptor = fileno(fin);
    fstat(fileDescriptor, &sbuf);
    fileSize = sbuf.st_size;
    segmentSize = fileSize / 4;
    sem = sem_open("sem", O_CREAT | O_EXCL, 0644, 4);
    sem_unlink("sem");
    for (i = 0; i < 4; i++) {
        pid = fork();
        if (pid < 0)
            printf("Fork error.\n");
        else if (pid == 0)
            break;
    }
    if (pid != 0) {
        while (pid = waitpid(-1, NULL, 0)) {
            if (errno == ECHILD)
                break;
        }
        sem_destroy(sem);
        fclose(fin);
        fclose(fout);
        exit(0);
    } else {
        sem_wait(sem);
        copySegment(i, segmentSize, fin, fout);
        sem_post(sem);
        exit(0);
    }
}
#包括
#包括
#包括
#包括
#包括
#包括
#包括
#包括
const int BUFFER_SIZE=1000;
无效复制段(int i,int segmentSize,文件*fin,文件*fout){
//不需要显示来证明这一点
}
int main(int argc,char*argv[]){
int i;
sem_t*sem;
pid_t pid;
文件*fin,*fout;
结构统计sbuf;
int fileSize、fileDescriptor、segmentSize;
fin=fopen(argv[1],“r”);
fout=fopen(“forkcopy.txt”,“w”);
fileDescriptor=fileno(fin);
fstat(文件描述符和sbuf);
fileSize=sbuf.st_size;
分段大小=文件大小/4;
sem=sem_open(“sem”,O|u CREAT | O|u EXCL,0644,4);
sem_取消链接(“sem”);
对于(i=0;i<4;i++){
pid=fork();
if(pid<0)
printf(“Fork错误。\n”);
否则如果(pid==0)
打破
}
如果(pid!=0){
while(pid=waitpid(-1,NULL,0)){
if(errno==ECHILD)
打破
}
扫描电镜(sem);
财务总监(财务);
fclose(fout);
出口(0);
}否则{
sem_wait(sem);
复制段(i、段大小、尾翼、尾翼);
sem_post(sem);
出口(0);
}
}

manfork
甚至还有代码示例。非常感谢您提供您的尝试。代码比您提出的关于最佳方法的问题更容易、更精确地提出改进建议。