Linux——进程控制2|进程程序替换|替换原理|替换函数|替换函数创建子进程|其余替换函数介绍|使用替换致函执行其它文件程序|使用替换致函执行其它语言文件|execlp |上

简介: 笔记

进程程序替换


替换原理

用fork创建子进程后执行的是和父进程相同的程序(但有可能执行不同的代码分支),子进程往往要调用一种exec函数以执行另一个程序。


当进程调用一种exec函数时,该进程的用户空间代码和数据完全被新程序替换,从新程序的启动例程开始执行。


调用exec并不创建新进程,所以调用exec前后该进程的id并未改变

1.png



程序替换就是通过特定的接口,加载磁盘上的一个全新的程序(数据和代码)。加载到调用进程的上下文中(地址空间中),重新改一下页表和物理内存的关系就行,进程替换并没有创建新的子进程

2.png



替换函数

其实有六种以exec开头的函数,统称exec函数,本质就是加载程序的函数(从磁盘加载到内存):


#include <unistd.h>`
int execl(const char *path, const char *arg, ...);
int execlp(const char *file, const char *arg, ...);
int execle(const char *path, const char *arg, ...,char *const envp[]);
int execv(const char *path, char *const argv[]);
int execvp(const char *file, char *const argv[]);
int execve(const char *path, char *const argv[], char *const envp[]);

int execl(const char *path,const char *arg,...);


path:路径+目标文件名


…:可变参数列表


函数里可传入多个参数,最后一个参数,必须是NULL,表示参数传递完毕


演示:


注意这里ls的路径


这段程序正常运行


3.png4.png

加上execl,注意第一个参数和最后一个参数之间的参数,是我们在命令行上如何使用,就在这里如何书写

5.png6.png

在调用excel之后打印出来的内容跟直接调用ls一模一样

7.png8.png


execl运行成功以后,原程序的内容便不再执行,我们原始代码里还有一个printf没打印出来


execl是程序替换,调用该函数成功之后,会将当前进程的所有代码和数据进行替换,包括已经执行的和没执行的


所以,一旦调用成功,后续所有代码都不会再执行


故意写一个错代码

0.png

execl调用失败9.png

execl函数出错的时候才有返回值,返回值是-1,成功时没有返回值

10.png

我们一般这样写,如果执行了exit,则一定调用失败了


替换函数创建子进程

#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <sys/wait.h>
int main()
{
        pid_t id = fork();
        if(id == 0)
        {
           //子进程
            printf("子进程开始运行, pid: %d\n", getpid());
            execl("/usr/bin/ls","ls","-a","-l",NULL);
            sleep(3);
        }
        else 
        {
            //父进程
            printf("父进程开始运行, pid: %d\n", getpid());
            int status = 0;
            pid_t id = waitpid(-1, &status, 0); //阻塞等待, 一定是子进程先运行完毕,然后父进程获取之后,才退出!
            if(id > 0)
            {
                printf("wait success, exit code: %d\n", WEXITSTATUS(status));
            }
        }
    return 0;
}


11.png

阻塞等待, 一定是子进程先运行完毕,然后父进程获取之后,才退出!


创建子进程原因:如果不创建,替换的就是父进程,如果创建了,替换子进程,就不会影响父进程。


当子进程加载新程序,子进程和父进程代码会分离,也就是子进程会写时拷贝


其余替换函数介绍

exec系列函数的功能其实iu是加载器的底层接口


int execv(const char *path,char *const argv[])

path:文件路径+文件名


argv:指针数组,最后要以NULL结尾


execv中的v可看作vector方便记忆。

12.png13.png14.png

int execlp(const char *file,const char *arg,...);

file:文件名(要执行谁),execlp,p代表会在path环境中查找


arg:命令行模式下使用格式,命令行参数必须以NULL结尾

15.png16.png

int execvp(const char *file,char *const argv[]);

file:文件名(你要执行谁)


argv:指针数组


17.png18.png

还有execv系列

19.png



函数名带


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

v(vector) : 参数用数组

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

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

20.png

系统直接调用的是execve,上面的这些函数最终调用的都是excve这个接口,

21.png

相关文章
|
4天前
|
网络协议 Linux
linux系统重要文件目录
本文介绍了Linux系统中的重要目录及其历史背景,包括根目录、/usr、/etc、/var/log和/proc等目录的结构和功能。其中,/etc目录下包含了许多关键配置文件,如网卡配置、DNS解析、主机名设置等。文章还详细解释了各目录和文件的作用,帮助读者更好地理解和管理Linux系统。
19 2
|
4天前
|
缓存 监控 Linux
|
7天前
|
Linux Shell 数据库
文件查找是Linux用户日常工作的重要技能介绍了几种不常见的文件查找方法
文件查找是Linux用户日常工作的重要技能。本文介绍了几种不常见的文件查找方法,包括使用`find`和`column`组合、`locate`和`mlocate`快速查找、编写Shell脚本、使用现代工具`fd`、结合`grep`搜索文件内容,以及图形界面工具如`Gnome Search Tool`和`Albert`。这些方法能显著提升文件查找的效率和准确性。
27 2
|
10天前
|
Linux 数据库
linux 全局搜索文件
在 Linux 系统中,全局搜索文件常用 `find`、`locate` 和 `grep` 命令。`find` 根据文件名、类型、大小、时间戳等条件搜索;`locate` 通过预构建的数据库快速查找文件;`grep` 在文件中搜索特定文本,常与 `find` 结合使用。选择合适的命令取决于具体需求。
|
13天前
|
运维 安全 Linux
Linux文件清空的五种方法总结分享
每种方法各有优势,选择最合适的一种或几种,可以极大提高您的工作效率。更多有关Linux系统管理的技巧与资源,欢迎访问,持续提升您的运维技能。
59 1
|
6月前
|
Linux
百度搜索:蓝易云【Linux中如何对文件进行压缩和解压缩?】
这些是在Linux中进行文件压缩和解压缩的常见方法。根据您的需求和具体情况,可能会使用其他压缩工具和选项。您可以通过查阅相应命令的帮助文档来获取更多详细信息。
87 1
|
6月前
|
NoSQL Java Linux
Linux常用命令(文件目录操作、拷贝移动、打包压缩、文本编辑、查找)
Linux常用命令(文件目录操作、拷贝移动、打包压缩、文本编辑、查找)
|
6月前
|
算法 Java Linux
Linux下文件增删改查定位压缩操作与权限所属用户
Linux下文件增删改查定位压缩操作与权限所属用户
71 0
26Linux - 文件管理(文件压缩解压:bzip2)
26Linux - 文件管理(文件压缩解压:bzip2)
60 0
|
6月前
|
Java Shell Linux
Linux【脚本 01】简单Shell脚本实现定时备份文件、压缩、删除超时文件操作(showDoc文件备份脚本举例)
Linux【脚本 01】简单Shell脚本实现定时备份文件、压缩、删除超时文件操作(showDoc文件备份脚本举例)
325 0