进程等待和进程程序替换

进程控制

  • 进程等待
  • 进程程序替换

进程等待

在这里插入图片描述

如果子进程没有退出
而父进程在进行执行waitpid进行等待,阻塞等待, 进程阻塞了
在等待某种条件发生(子进程退出)

进程程序替换

  1 #include <stdio.h>2 #include <unistd.h>3 4 int main()5 {6     printf("testexec ... begin\n");7 8     execl("/usr/bin/ls", "ls", "-l", "-a", NULL);                                                                                                        9 10     printf("testexec ... end!\n");11     return 0;12 }
[tt@kunkun testexec]$ ./testexec 
testexec ... begin
total 28
drwxrwxr-x 2 tt tt 4096 Feb 18 20:56 .
drwxrwxr-x 6 tt tt 4096 Feb 18 20:25 ..
-rw-rw-r-- 1 tt tt   70 Feb 18 20:29 Makefile
-rwxrwxr-x 1 tt tt 8408 Feb 18 20:56 testexec
-rw-rw-r-- 1 tt tt  192 Feb 18 20:56 testexec.c

exec*系列的函数,执行完毕之后,后续的代码不见了,因为被替换了
exec函数的返回值可以不关心了。只要替换成功,就不会向后继续运行,只要继续运行了,一定是替换失败了

多进程版
fork创建子进程,让子进程自己去替换 wait
int execl(const char *path, const char *arg, ...);

  1 #include <stdio.h>2 #include <unistd.h>3 #include <stdlib.h>4 #include <sys/types.h>5 #include <sys/wait.h>6 7 int main()8 {9     printf("testexec ... begin\n");10 11     pid_t id = fork();12     if(id == 0)13     {14         //child15         execl("/usr/bin/ls", "ls", "-l", "-a", NULL);16         exit(1);17     }18 19     //father20     int status = 0;21     pid_t rid = waitpid(id, &status, 0);                                                                                                                                                                     22     if(rid > 0)23     {24         printf("father wait sucess, child exit code: %d\n", WEXITSTATUS(status));25     }26 27     printf("testexec ... end!\n");28     return 0;29 }
[tt@kunkun testexec]$ ./testexec 
testexec ... begin
total 28
drwxrwxr-x 2 tt tt 4096 Feb 18 21:51 .
drwxrwxr-x 6 tt tt 4096 Feb 18 20:25 ..
-rw-rw-r-- 1 tt tt   70 Feb 18 20:29 Makefile
-rwxrwxr-x 1 tt tt 8616 Feb 18 21:51 testexec
-rw-rw-r-- 1 tt tt  530 Feb 18 21:51 testexec.c
father wait sucess, child exit code: 0
testexec ... end!

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

  1 #include <stdio.h>2 #include <unistd.h>3 #include <stdlib.h>4 #include <sys/types.h>5 #include <sys/wait.h>6 7 int main()8 {9     printf("testexec ... begin\n");10 11     pid_t id = fork();12     if(id == 0)13     {14         sleep(2);15         char *const argv[] =16         {17             (char*)"ls",18             (char*)"-l",19             (char*)"-a",20             (char*)"--color",21             NULL22         };23         //child24         execv("/usr/bin/ls", argv);25         exit(1);26     }                                                                                                                                                                                                                                                                    27 28     //father29     int status = 0;30     pid_t rid = waitpid(id, &status, 0);31     if(rid > 0)32     {33         printf("father wait sucess, child exit code: %d\n", WEXITSTATUS(status));34     }35 36     printf("testexec ... end!\n");37     return 0;38 }

int execvp(const char *file, char *const argv[]);
用户可以不传要执行的文件的路径(但是文件名要传),直接告诉exec* ,我要执行谁就行
p:查找这个程序,系统会在环境变量PATH中进行查找

int execvpe(const char *file, char *const argv[], char *const envp[]);
第三个参数整体替换所有环境变量
1、用全新的给子进程
2、用老的环境变量给子进程,environ
3、老的环境变量稍微修改,给子进程
Makefile

  1 .PHONY:all2 all:testexec mypragma3 4 testexec:testexec.c5   gcc -o $@ $^                                                                                    6 mypragma:mypragma.cc7   g++ -o $@ $^ -std=c++118 .PHONY:clean9 clean:10   rm -f testexec mypragma
  1 #include <iostream>  2 #include <unistd.h>                                                                               3                             4 using namespace std;  5             6 int main()  7 {                                                                 8     cout << "hello C++, I am a C++ pragma!" << getpid() << endl;  9     cout << "hello C++, I am a C++ pragma!" << getpid() << endl;  10     cout << "hello C++, I am a C++ pragma!" << getpid() << endl;  11     cout << "hello C++, I am a C++ pragma!" << getpid() << endl;  12                13     return 0;                                         14 }                                   
  1 #include <stdio.h>2 #include <unistd.h>3 #include <stdlib.h>4 #include <sys/types.h>5 #include <sys/wait.h>6 7 int main()8 {9     printf("testexec ... begin\n");10 11     pid_t id = fork();12     if(id == 0)13     {14         printf("child pid: %d\n", getpid());                                                      15         sleep(2);16         execl("./mypragma", "myprama", NULL);17         exit(1);18     }19 20     //father21     int status = 0;22     pid_t rid = waitpid(id, &status, 0);23     if(rid > 0)24     {25         printf("father wait sucess, child exit code: %d\n", WEXITSTATUS(status));26     }27 28     printf("testexec ... end!\n");29     return 0;30 }
[tt@kunkun testexec]$ ./testexec 
testexec ... begin
child pid: 30468
hello C++, I am a C++ pragma!30468
hello C++, I am a C++ pragma!30468
hello C++, I am a C++ pragma!30468
hello C++, I am a C++ pragma!30468
father wait sucess, child exit code: 0
testexec ... end!
[tt@kunkun testexec]$ python
Python 2.7.5 (default, Nov 14 2023, 16:14:06) 
[GCC 4.8.5 20150623 (Red Hat 4.8.5-44)] on linux2
Type "help", "copyright", "credits" or "license" for more information.
>>> quit();
[tt@kunkun testexec]$ python
Python 2.7.5 (default, Nov 14 2023, 16:14:06) 
[GCC 4.8.5 20150623 (Red Hat 4.8.5-44)] on linux2
Type "help", "copyright", "credits" or "license" for more information.
>>> quit()
[tt@kunkun testexec]$ touch test.py
[tt@kunkun testexec]$ vim test.py 
[tt@kunkun testexec]$ python3 test.py
hello python
hello python
hello python
hello python

shell脚本

  1 #!/usr/bin/bash2 3 cnt=04 while [ $cnt -le 10 ]5 do6     echo "hello shell, cnt: ${cnt}"7     let cnt++8 done            
[tt@kunkun testexec]$ bash test.sh
hello shell, cnt: 0
hello shell, cnt: 1
hello shell, cnt: 2
hello shell, cnt: 3
hello shell, cnt: 4
hello shell, cnt: 5
hello shell, cnt: 6
hello shell, cnt: 7
hello shell, cnt: 8
hello shell, cnt: 9
hello shell, cnt: 10
execl("/usr/bin/bash", "bash", "test.sh", NULL);
execl("/usr/bin/python", "python", "test.py", NULL);
[tt@kunkun testexec]$ chmod +x test.sh
[tt@kunkun testexec]$ chmod +x test.py
[tt@kunkun testexec]$ ll
total 44
-rw-rw-r-- 1 tt tt  159 Feb 20 15:49 Makefile
-rwxrwxr-x 1 tt tt 9128 Feb 20 16:00 mypragma
-rw-rw-r-- 1 tt tt  354 Feb 20 16:00 mypragma.cc
-rwxrwxr-x 1 tt tt 8720 Feb 20 16:00 testexec
-rw-rw-r-- 1 tt tt  569 Feb 20 16:01 testexec.c
-rwxrwxr-x 1 tt tt  107 Feb 20 16:05 test.py
-rwxrwxr-x 1 tt tt  103 Feb 20 16:29 test.sh
[tt@kunkun testexec]$ ./test.sh
hello shell, cnt: 0
hello shell, cnt: 1
hello shell, cnt: 2
hello shell, cnt: 3
hello shell, cnt: 4
hello shell, cnt: 5
hello shell, cnt: 6
hello shell, cnt: 7
hello shell, cnt: 8
hello shell, cnt: 9
hello shell, cnt: 10
[tt@kunkun testexec]$ ./test.py
hello python
hello python
hello python
hello python
    1 #include <stdio.h>2  #include <unistd.h>3  #include <stdlib.h>4  #include <sys/types.h>5  #include <sys/wait.h>6  7  int main()8  {9      printf("testexec ... begin\n");10  11      pid_t id = fork();12      if(id == 0)13      {14          //我的父进程本身就有一批环境变量!!!,从bash来15          char *const argv[] = 16          {17              (char*)"mypragma",18              (char*)"-a",19              (char*)"-b",20              NULL21          };22          char *const envp[] =23          {24              (char*)"HAHA=111111",25              (char*)"HEHE=222222",26              NULL27          };28          extern char**environ;                                                                  29          printf("child pid: %d\n", getpid());                                                         30          sleep(2);31          execvpe("./mypragma", argv, environ);32          //execvpe("./mypragma", argv, envp);33          exit(1);34      }35  36      //father37      int status = 0;38      pid_t rid = waitpid(id, &status, 0);39      if(rid > 0)40      {41          printf("father wait sucess, child exit code: %d\n", WEXITSTATUS(status));42      }43  44      printf("testexec ... end!\n");45      return 0;46  }
    1 #include <iostream>2 #include <unistd.h>3 4 using namespace std;5 6 int main(int argc, char *argv[], char *env[])7 {8     int i = 0;9     for(; argv[i]; i++)10     {11         printf("argv[%d] : %s\n", i, argv[i]);12     }13 14     printf("--------------------------------\n");15     for(i = 0; env[i]; i++)16     {17         printf("env[%d] : %s\n", i, env[i]);18     }19     printf("--------------------------------\n");                                               20     cout << "hello C++, I am a C++ pragma!" << getpid() << endl;21     cout << "hello C++, I am a C++ pragma!" << getpid() << endl;22     cout << "hello C++, I am a C++ pragma!" << getpid() << endl;23     cout << "hello C++, I am a C++ pragma!" << getpid() << endl;24 25     return 0;26 }

putenv添加环境变量
#include <unistd.h>

   int execve(const char *filename, char *const argv[], char *const envp[]);

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/21289.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

UEFI Spec 学习笔记---6 - Block Translation Table (BTT) Layout

6.1 Block Translation Table (BTT) Background 定义个一个连续地址的非易失性的namespace&#xff0c;就是将一整个namespace 拆分成一个个block&#xff0c;其中的地址保存至BBT&#xff08;块转换表&#xff09;&#xff0c;这样可以防止扇区撕裂&#xff08;由于电源问题导…

SAP 代码扫描工具

描述&#xff1a; ZSCANNER是一个先进的代码分析工具&#xff0c;旨在提供对程序和功能模块内部工作的全面见解。它揭示了代码的技术细节&#xff0c;包括正在创建、读取、更新或删除的数据表&#xff08;CRUD操作&#xff09;&#xff0c;以及正在调用的类、功能模块和BAPI&a…

c语言基础第12节《函数的调用》

c语言基础10 函数 函数的调用 调用方式 ①函数语句&#xff1a; test(); // 对于无返回值的函数&#xff0c;直接调用 int res max(2,4); // 对于有返回值的函数&#xff0c;一般需要再主调函数中接收被调函数的返回值。②函数表达式&#xff1a; 4 max(2,4) scanf(&qu…

C++:iterator迭代器失效

说明&#xff1a;这里拿 vector 举例。 原因一&#xff1a;扩容导致迭代器失效 // 迭代器失效 void insert(iterator pos, const T& x) {assert(pos > _start);assert(pos < _finish);// 满了就扩容if (_finish _end_of_storage){reserve(capacity() 0 ? 4 : ca…

QT之改变鼠标样式

QT改变鼠标图片 资源路径如下 代码实现 QPixmap customCursorPixmap(":/images/mouse.png");QCursor customCursor(customCursorPixmap);QWidget::setCursor(customCursor); // 可以设置为整个窗口或特定控件QWidget::setCursor(); // 设置为透明光标&#xff0c…

用DeepSeek零基础预测《哪吒之魔童闹海》票房——从数据爬取到模型实战

系列文章目录 1.元件基础 2.电路设计 3.PCB设计 4.元件焊接 5.板子调试 6.程序设计 7.算法学习 8.编写exe 9.检测标准 10.项目举例 11.职业规划 文章目录 **一、为什么要预测票房&#xff1f;****二、准备工作****三、实战步骤详解****Step 1&#xff1a;数据爬取与清洗&am…

高并发下秒杀系统的设计

文章目录 1 业界通用做法1.1 压力分摊1.2 RedisMySQL1.3 Inventory Hint1.4 压力分摊RedisMQ 2 Redis MQ 解决高并发下的秒杀场景2.1 Redis库存预扣减2.1.1 lua脚本执行流程&#xff1a;2.1.2 Lua脚本主要做了几件事&#xff1a; 2.2 MySQL库存扣减2.3 记录操作流水的原因 3 I…

双重差分学习笔记

双重差分适用的研究场景&#xff1a; 研究某项政策或者冲击造成的影响 例如&#xff0c;某某小学在2024.12.12日颁布了小红花激励措施&#xff0c;我们要研究这项措施对学生成绩的影响&#xff0c;此时&#xff0c;就可以使用双重差分模型。 双重差分适用的数据类型&#xf…

深入理解 C++17 中的 std::atomic<T>::is_always_lock_free

文章目录 原子操作与锁无关性&#xff08;Lock-Free&#xff09;锁无关性&#xff08;Lock-Free&#xff09;无锁&#xff08;Lock-Free&#xff09;与无阻塞&#xff08;Wait-Free&#xff09; std::atomic<T>::is_always_lock_free 是什么&#xff1f;truefalse与 is_l…

VSCode 中 Git 添加了多个远端,如何设置默认远端

VSCode 中 Git 添加了多个远端&#xff0c;如何设置默认远端 查看分支&#xff1a;设置默认远端手动指定远端 查看分支&#xff1a; * 表示当前默认远端 git branch -vv* master a1b2c3d [origin/main] Fix typo dev d4e5f6g [upstream/dev] Add feature设置默认远端 将本…

一文讲清 AIO BIO NIO的区别

引言 在 Java 编程中&#xff0c;BIO&#xff08;Blocking I/O&#xff09;、NIO&#xff08;Non-blocking I/O&#xff09;和 AIO&#xff08;Asynchronous I/O&#xff09;是三种不同的 I/O 模型&#xff0c;它们在处理输入输出操作时有着不同的机制和特点&#xff0c;但是市…

使用(xshell+xftp)将前端项目部署到服务器

一.以vue项目为例 将项目打包生成dist文件 二.下载载安装xshell和xftp 下载地址&#xff1a;家庭/学校免费 - NetSarang Website 三.连接服务器 在xshell新建会话&#xff08;需要用到服务器、用户名、密码、端口号&#xff09;正确输入后连接到服务器 使用命令连接&#x…

硬件岗位是否适合你?

在当今科技飞速发展的时代,硬件行业作为技术创新的基石,始终扮演着至关重要的角色。无论是智能手机、自动驾驶汽车,还是人工智能服务器,硬件都是这些技术的核心支撑。然而,硬件岗位是否适合你?作为一名硬件专家,我将从多个角度为你分析,帮助你判断自己是否适合从事硬件…

Linux基本指令(二)

文章目录 基本指令echocat&#xff08;输入重定向&#xff09;history日志moretail和headmv&#xff08;重要&#xff09;时间相关的指令查找的命令 知识点Linux下一切皆文件为什么计算机关机了&#xff0c;开机后还能准确地记录时间呢&#xff1f; 基本指令 echo 1. echo&…

【Blender】二、建模篇--05,阵列修改器与晶格形变

阵列修改器是bender里面一个比较常用的修改器,所以我们单独开口来讲,我们会先从几片树叶出发,然后我们用阵列修改器把这几片树叶变成这样的造型和这样的造型。这两个造型分别就代表着阵列修改器最常用的两种偏移方法,我们现在就开始我们先来做几个树叶。 1.树叶建模 首先…

fpga助教面试题

第一题 module sfp_pwm( input wire clk, //clk is 200M input wire rst_n, input wire clk_10M_i, input wire PPS_i, output reg pwm ) reg [6:0] cunt ;always (posedge clk ) beginif(!rst_n)cunt<0;else if(cunt19) //200M是10M的20倍cunt<0;elsecunt<cunt1;…

SpringAI系列 - ToolCalling篇(二) - 如何设置应用侧工具参数ToolContext(有坑)

目录 一、引言二、集成ToolContext示例步骤1: 在`@Tool`标注的工具方法中集成`ToolConext`参数步骤2:`ChatClient`运行时动态设置`ToolContext`参数三、填坑一、引言 在使用AI大模型的工具调用机制时,工具参数都是由大模型解析用户输入上下文获取的,由大模型提供参数给本地…

Jest单元测试

由于格式和图片解析问题&#xff0c;可前往 阅读原文 前端自动化测试在提高代码质量、减少错误、提高团队协作和加速交付流程方面发挥着重要作用。它是现代软件开发中不可或缺的一部分&#xff0c;可以帮助开发团队构建可靠、高质量的应用程序 单元测试&#xff08;Unit Testi…

pyside6学习专栏(二):程序图像资源的加载方式

pyside6中的QLabel控件可以加载图像和gif动画&#xff0c;可以直接从外部文件加载&#xff0c;也可以从QRC类型的文件(实际是一脚本文件)经编绎生成对应的资源.PY模块文件(就是将qrc文本中指定的资源文件的16制内容写入.py文件)来使用&#xff0c;本文对两种方式作了一简单的示…

Nginx--日志(介绍、配置、日志轮转)

前言&#xff1a;本博客仅作记录学习使用&#xff0c;部分图片出自网络&#xff0c;如有侵犯您的权益&#xff0c;请联系删除 一、Nginx日志介绍 nginx 有一个非常灵活的日志记录模式&#xff0c;每个级别的配置可以有各自独立的访问日志, 所需日志模块 ngx_http_log_module 的…