Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/spring-boot/5.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 为什么Exeve不启动流程?_C_Process_Fork - Fatal编程技术网

C 为什么Exeve不启动流程?

C 为什么Exeve不启动流程?,c,process,fork,C,Process,Fork,我为uni写了一个方法,它应该启动一个程序。我必须使用execve。但它不起作用。例如,当我使用execvp而不是execve时,它会工作并启动程序 #include <stddef.h> #include <unistd.h> #include <stdio.h> #include <sys/wait.h> pid_t run_command(char **argv, int no_fork){ extern char **enviro

我为uni写了一个方法,它应该启动一个程序。我必须使用execve。但它不起作用。例如,当我使用execvp而不是execve时,它会工作并启动程序

#include <stddef.h>
#include <unistd.h>
#include <stdio.h>
#include <sys/wait.h>

pid_t run_command(char **argv, int no_fork){
    extern char **environ;
    pid_t pid;


    if(no_fork != 0){
        execve(*argv, argv, environ);
        return 0;
    }
    else{
        if((pid = fork()) < 0){
            printf("Error: fork!\n");
            return -1;
        }
        else if(pid == 0){

            argv++;

            printf("execve(%s)\n", *argv);
            execve(*argv, argv, environ);

        }
        else {                                  
            wait(NULL);
        }
    }
    return pid;
}

/*
int run_cmdline(char ** argv){
    return 0;
}*/

int main(int argc, char* argv[]){
    run_command(argv, 0);

    return 0;
}
#包括
#包括
#包括
#包括
pid\u t运行\u命令(字符**argv,int no\u fork){
外部字符**环境;
pid_t pid;
如果(无叉子!=0){
execve(*argv,argv,environ);
返回0;
}
否则{
如果((pid=fork())<0){
printf(“错误:fork!\n”);
返回-1;
}
否则如果(pid==0){
argv++;
printf(“execve(%s)\n”,*argv);
execve(*argv,argv,environ);
}
否则{
等待(空);
}
}
返回pid;
}
/*
int run\u cmdline(字符**argv){
返回0;
}*/
int main(int argc,char*argv[]){
运行_命令(argv,0);
返回0;
}
汇编:

主壳体的叮当声

例如,执行:

/主firefox

应该启动firefox。使用execvp和不使用environ都可以工作,但不使用execve


Thx获取任何帮助:)

您正在使用
main
的参数列表调用
run\u命令。由于要运行的程序及其参数在
argv[1]
之后,因此需要检查
argc
是否至少为2,然后调用
run\u命令(argv+1,0)

编辑

似乎
run_命令
本身会增加
argv
,但由于某种原因,只能在调用
execve
的两个代码路径之一中增加。这两个代码路径应该一致地处理参数列表。我个人认为,调用方最好安排
run_命令
s
argv[0]
引用它应该运行的程序


如果您坚持在
run\u命令
本身中递增
argv
,使其
*argv
引用要运行的程序,那么在递增
argv
之前,您需要检查
argv[0]
argv[1]
是否均为非空。如果调用方负责使
run\u命令
s
*argv
引用要运行的程序,那么最好检查
*argv
是否为非空。

您正在使用
主参数列表调用
run\u命令。由于要运行的程序及其参数在
argv[1]
之后,因此需要检查
argc
是否至少为2,然后调用
run\u命令(argv+1,0)

编辑

似乎
run_命令
本身会增加
argv
,但由于某种原因,只能在调用
execve
的两个代码路径之一中增加。这两个代码路径应该一致地处理参数列表。我个人认为,调用方最好安排
run_命令
s
argv[0]
引用它应该运行的程序

如果您坚持在
run\u命令
本身中递增
argv
,使其
*argv
引用要运行的程序,那么在递增
argv
之前,您需要检查
argv[0]
argv[1]
是否均为非空。如果调用方负责使
run\u命令
s
*argv
引用要运行的程序,那么最好检查
*argv
是否为非空

execve(*argv,argv,environ)

/主firefox

execve
不搜索路径。您必须提供可执行文件的完整路径或自己解析路径。这种行为的参考文献在中,但我发现它很难阅读,对我来说更容易

比如:

./main /usr/bin/firefox
应该有效,甚至:

./main /usr/bin/sh -c firefox
或者只需使用
execvp
,它会神奇地自动获取“parent”
environ
并搜索路径。还有一个linux扩展名
execvpe
,它不在posix中,并且接受
environ

execve(*argv,argv,environ)

/主firefox

execve
不搜索路径。您必须提供可执行文件的完整路径或自己解析路径。这种行为的参考文献在中,但我发现它很难阅读,对我来说更容易

比如:

./main /usr/bin/firefox
应该有效,甚至:

./main /usr/bin/sh -c firefox

或者只需使用
execvp
,它会神奇地自动获取“parent”
environ
并搜索路径。还有一个linux扩展名
execvpe
,它不在posix中,并且确实需要
environ

如果
execve
失败,那么它将转到下一行,在那里您应该能够打印一条错误消息,指示发生了什么<代码>perror(“无法执行”)将是一个良好的开始。无法执行:错误的地址您的程序是否也需要搜索可执行文件的路径(仅当它不包含
/
字符时),或者程序用户是否有责任提供有效的路径名?如果
execve
失败,然后转到下一行,您应该能够打印一条错误消息,指示发生了什么<代码>perror(“无法执行”)将是一个良好的开始。无法执行:错误的地址您的程序是否也需要搜索可执行文件的路径(仅当它不包含
/
字符时),或者程序用户是否有责任提供有效的路径名?但我会在else if条件下使用argv++。所以我想这不是错误。@JanWolfram我从来没有发现过。为什么它对“fork”和“no fork”路径的参数列表有不同的处理?您仍然需要检查
argc
。我没有完成no,但它也应该是argv++。如果没有fork,我想启动新的childprocess0@JanWolfram另一件事是
execve
不搜索路径(您需要调用
execvpe
),因此除非