exec函数和system函数
- exec系列函数
- system函数
exec系列函数
首先讲一下exec,exec系列的函数主要是在代码中去执行可执行程序,类似android中的shellUtils,也就是去执行脚本语言或者执行程序
在用fork函数创建子进程后,子进程往往要调用一种exec函数以执行另一个程序
当进程调用一种exec函数时,该进程完全由新程序代换,替换原有进程的正文,而新程序则从其main函数开始执行,因为调用exec并不创建新进程,所以前后的进程ID其实并未改变,exec只是用另一个新程序替换了当前进程的正文,数据,堆和栈段(用新程序的这些存储数据替换掉原来的存储数据)
exec系列相关函数(代码替换函数),所以一般是在子进程中去调用exec系列函数
函数:
int execl(const char *pathname,const char *arg0,.../*(char*)0*/);
int execv(const char *pathname,char *const argv[]);
int execle(const char *pathname,const char *arg0,.../*(char*)0, *const envp[]*/);
int execve(const char *pathname,char *const argv[],char *const envp[]);
int execlp(const char *pathname,const char *arg0,.../*(char(0)*/);
int execvp(const char *pathname,char *const argv[]);
返回:
出错返回-1,成功不返回
exec系列函数的注意点:
execve函数是系统调用,其余为库函数,**执行execve函数成功以后后面的代码不会执行,不会返回到原来的子进程中去了**
execlp和execvp函数中的pathname,相对路径和绝对路径都可以,其余的必须是绝对路径,相对路径需要在环境变量中注册
argv参数为新程序执行的main函数中传递的argv参数,最后一个为NULL
envp为进程的环境表
规律:exec+”替换字符串”,l(list)代表的是参数列表,第二位开始是参数列表,v代表argv,是传递给主函数的参数列表(指针数组形式),e代表的是环境变量,环境表。p第一个元素是pathname(可以是相对路径,也可以是绝对路径),不带p的路径必须是绝对路径
如果执行出错,那就直接中断程序的执行
l---->库函数
v---->库函数
le
ve--------->系统调用
lp
vp
简单实例代码如下
char *cmd1 = "cat";
char *cmd2 = "/bin/cat";
char *argv1 = "/etc/passwd";
char *argv2 = "/etc/bin";
execl(cmd2,cmd2,argv1,argv2,NULL);
wait(NULL);//等待执行结束
char * argv[4] = {cmd1,argv1,argv2,NULL};
execvp(cmd,argv);
来段简单的小Demo
#include<stdio.h>
#include<stdlib.h>
#include<unistd.h>
#include<sys/types.h>
#include<wait.h>
char * cmd1 = "cat";//相对路径
char * cmd2 = "/bin/cat"; //绝对路径
char * argv1 = "/etc/passwd";
char * argv2 = "/etc/group";
int main(int argc,char *argv[]){
pid_t pid = fork();
if(pid <0 ){
perror("fork error");
exit(EXIT_FAILURE);
}else if(pid > 0){
wait(0);//通过wait来防止僵尸进程
}else {
int result = execl(cmd2,cmd2,argv1,argv2,NULL);
//char *argv[4] = {cmd2,argv1,argv2,NULL};
//int result = execvp(cmd2,argv);
if(result == -1){
perror("exec error\n");
}
}
return 0;
}
system函数:
#include<stdlib.h>
int system(const char *command);
简化exec函数的使用
**system函数内部构建一个子进程,由子进程调用exec函数**
等同于/bin/bash -c "cmd"或者 exec("bash","-c","cmd");
system中传递的可以是相对路径也可以是绝对路径
如简单的实例:
char *cmd1 = "date";
system(cmd1);
来段简单的小demo
#include<stdio.h>
#include<stdlib.h>
#include<sys/types.h>
#include<unistd.h>
#include<wait.h>
char * cmd1 = "date > a.txt";
int main(int agrc,char * argv[]){
//system函数会自己在内部创建一个子进程,调用exec系列函数,来执行;
// system(cmd1);
system("ls -al");
return 0;
}
相比较前面的函数来说,这exec系列的函数和system函数都是非常简单的。就是可以直接能够使用函数来执行命令的,在程序执行的过程中,给我们提供了一些便利性,其实需要注意的是,在执行的时候尽量我们使用的是绝对路径。
谢谢观看
qq群号为324652573