【Linux】进程中的替换函数(exec)

摘要:本文主要讲述如何在进程中运行新代码,以及exec系列函数的基本使用方法.

在进程中运行新代码

    用函数fork创建子进程后,如果希望在当前子进程中运行新的程序,可以调用exec函数执行另一个程序.当进程调用exec函数时,该进程用户空间资源(正文、数据、堆和栈)完全由新程序替代,新程序则从main函数开始执行.因为调用exec函数并没有创建新的进程,所以前后的进程ID并没有改变,也即内核信息基本不做修改.
    exec系列函数共有7函数可供使用,这些函数的区别在于:指示新程序的位置是使用路径还是文件名,如果是使用文件名,则在系统的PATH环境变量所描述的路径中搜索该程序;在使用参数时使用参数列表的方式还是使用argv[]数组的方式.

1.exec系列函数

函数定义:
    #include <unistd.h>
    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, char *const envp[] */ );
    int execve(const char *pathname, char *const argv[], char *const envp[]);
    int execlp(const char *filename, const char *arg0, ... /* (char *)0 */ );
    int execvp(const char *filename, char *const argv[]);
    int fexecve(int fd, char *const argv[], char *const envp[]);

返回值:如果执行成功将不返回,否则返回-1,失败代码存储在errno中.
    前4个函数取路径名作为参数,后两个是取文件名作为参数,最后一个是以一个文件描述符作为参数.

规律:

l(list):表示参数采用列表

v(vector):参数采用数组

p(path):有p自动搜索环境变量PATH

e(env):表示自己维护环境变量

 

2.函数具体分析

    当指定filename作为参数时:
1)如果filename中包含/,则将其视为路径名.
2)否则就按PATH环境变量,在它所指的各目录搜寻可执行文件.

2.1 execl()函数

int execl(const char *pathname, const char *arg0, ... /* (char *)0 */ );
    execl()函数用来执行参数path字符串所指向的程序,第二个及以后的参数代表执行文件时传递的参数列表,最后一个参数必须是空指针以标志参数列表为空.
例子1:演示exec()函数的基本使用.


#include <unistd.h>

#include <stdio.h>

#include <sys/types.h>

#include <stdlib.h>

int main()

{

        pid_t pid;

        pid = fork();

        if(pid<0)

        {

                printf("error fork:%m\n");

                exit(-1);

        }

        else if(pid==0)

        {

                //

                execl("/bin/ls","ls","-l","/etc",(char *)0);

        }

        else

        {

                printf("parent process\n");

        }

        return 0;

}

2.2 execle()函数

int execle(const char *pathname, const char *arg0, .../* (char *)0, char *const envp[] */ );
    execle()函数用来执行参数path字符串所指向的程序,第二个及以后的参数代表执行文件时传递的参数列表,最后一个参数必须指向一个新的环境变量数组,即新执行程序的环境变量.
例子2:


#include <unistd.h>

int main(int argc, char *argv[], char *env[])

{

        execle("/bin/ls","ls","-l", "/etc",(char *)0,env);

        return 0;

}

2.3 execlp()函数

int execlp(const char *filename, const char *arg0, ... /* (char *)0 */ );
    execlp()函数会从PATH环境变量所指的目录中查找文件名为第一个参数指示的字符串,找到后执行该文件,第二个及以后的参数代表执行文件时传递的参数列表,最后一个参数必须是空指针.
例子3:


#include <unistd.h>

 

int main()

{

        execlp("ls", "ls", "-l", "/etc", (char *)0);

        return 0;

}

2.4 execv()函数

int execv(const char *path, char *const argv[]);
    execv()函数函数用来执行参数path字符串所指向的程序,第二个为数组指针维护的程序参数列表,该数组的最后一个成员必须是空指针.
例子4:


#include <unistd.h>

 

int main()

{

        char *argv[] = {"ls", "-l", "/etc", (char *)0};

        execv("/bin/ls", argv);

        return 0;

}

2.5 execvp()函数

int execvp(const char *file, char *const argv[]);
   execvp()函数会从PATH环境变量所指的目录中查找文件名为第一个参数指示的字符串,找到后执行该文件,第二个及以后的参数代表执行文件时传递的参数列表,最后一个成员必须是空指针.
例子5:


#include <unistd.h>

 

int main()

{

        char *argv[] = {"ls", "-l", "/etc", (char *)0};

        execvp("ls", argv);

        return 0;

}

 

事实上上边的这五个函数最终调用的还是execve()函数。

他们的关系如下图所示:

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值