Linux —— 进程控制

目录

一,进程创建

写时拷贝

二,进程终止

三,进程等待

获取子进程status


一,进程创建

  • 命令行启动命令(程序、指令等);
  • 通过程序自身fork创建;
#include<unistd.h>
//子进程返回0,父进程返回子进程的ID,出错返回-1
pid_t fork(void);

进程调用fork,当控制转移到内核中的fork代码后,内核将会:

  • 分配新的内存块和内核数据结构给子进程;
  • 拷贝父进程部分数据结构内容给子进程;
  • 添加子进程到系统进程列表中;
  • fork返回,开始调度器调度;

#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>int main()
{pid_t pid;printf("Before: pid is %d\n", getpid());pid = fork();if(pid == -1){perror("fork");exit(-1);}printf("After: pid is %d, fork return %d\n", getpid(), pid);sleep(1);return 0;                                                                 
}
[wz@192 Desktop]$ ./target 
Before: pid is 21739
After: pid is 21739, fork return 21740
After: pid is 21740, fork return 0
  • fork前,父进程独立执行;
  • fork后,父子进程分流执行;父子谁先执行完全由调度器决定;

写时拷贝

        通常父子代码共享,数据也共享(父子在不写入时);当有任意一方写入时,便以写实拷贝的方式各自一份副本,从而保证父子进程的独立性;

二,进程终止

  • 代码运行结束,结果正确,退出码为0;
  • 代码运行结束,结果不正确,退出码非0;
  • 代码异常终止;
#include <stdio.h>
#include <unistd.h>
#include <string.h>
int main()
{int i=0;for(i;i<200;i++){printf("%d:%s\n",i,strerror(i));}return 0;                                                               
}
[wz@192 Desktop]$ ./target 
0:Success
1:Operation not permitted
2:No such file or directory
3:No such process
4:Interrupted system call
5:Input/output error
6:No such device or address
7:Argument list too long
8:Exec format error
9:Bad file descriptor
10:No child processes
11:Resource temporarily unavailable
12:Cannot allocate memory
13:Permission denied
14:Bad address
15:Block device required
16:Device or resource busy
17:File exists
18:Invalid cross-device link
19:No such device
20:Not a directory
21:Is a directory
22:Invalid argument
23:Too many open files in system
24:Too many open files
25:Inappropriate ioctl for device
26:Text file busy
27:File too large
28:No space left on device
29:Illegal seek
30:Read-only file system
31:Too many links
32:Broken pipe
33:Numerical argument out of domain
34:Numerical result out of range
35:Resource deadlock avoided
36:File name too long
37:No locks available
38:Function not implemented
39:Directory not empty
40:Too many levels of symbolic links
41:Unknown error 41
42:No message of desired type
43:Identifier removed
44:Channel number out of range
45:Level 2 not synchronized
46:Level 3 halted
47:Level 3 reset
48:Link number out of range
49:Protocol driver not attached
50:No CSI structure available
51:Level 2 halted
52:Invalid exchange
53:Invalid request descriptor
54:Exchange full
55:No anode
56:Invalid request code
57:Invalid slot
58:Unknown error 58
59:Bad font file format
60:Device not a stream
61:No data available
62:Timer expired
63:Out of streams resources
64:Machine is not on the network
65:Package not installed
66:Object is remote
67:Link has been severed
68:Advertise error
69:Srmount error
70:Communication error on send
71:Protocol error
72:Multihop attempted
73:RFS specific error
74:Bad message
75:Value too large for defined data type
76:Name not unique on network
77:File descriptor in bad state
78:Remote address changed
79:Can not access a needed shared library
80:Accessing a corrupted shared library
81:.lib section in a.out corrupted
82:Attempting to link in too many shared libraries
83:Cannot exec a shared library directly
84:Invalid or incomplete multibyte or wide character
85:Interrupted system call should be restarted
86:Streams pipe error
87:Too many users
88:Socket operation on non-socket
89:Destination address required
90:Message too long
91:Protocol wrong type for socket
92:Protocol not available
93:Protocol not supported
94:Socket type not supported
95:Operation not supported
96:Protocol family not supported
97:Address family not supported by protocol
98:Address already in use
99:Cannot assign requested address
100:Network is down
101:Network is unreachable
102:Network dropped connection on reset
103:Software caused connection abort
104:Connection reset by peer
105:No buffer space available
106:Transport endpoint is already connected
107:Transport endpoint is not connected
108:Cannot send after transport endpoint shutdown
109:Too many references: cannot splice
110:Connection timed out
111:Connection refused
112:Host is down
113:No route to host
114:Operation already in progress
115:Operation now in progress
116:Stale file handle
117:Structure needs cleaning
118:Not a XENIX named type file
119:No XENIX semaphores available
120:Is a named type file
121:Remote I/O error
122:Disk quota exceeded
123:No medium found
124:Wrong medium type
125:Operation canceled
126:Required key not available
127:Key has expired
128:Key has been revoked
129:Key was rejected by service
130:Owner died
131:State not recoverable
132:Operation not possible due to RF-kill
133:Memory page has hardware error
134:Unknown error 134
135:Unknown error 135
136:Unknown error 136
137:Unknown error 137
138:Unknown error 138

进程常见退出方法:

  • 正常终止,可通过 echo $? 查看最近一次执行程序退出码;
    • main返回,return 0代表进程退出,0退出码表示成功;给系统查看,以确认进程是否正确;非main函数的return不受终止进程,是结束函数;
    • exit,任意位置调用此函数,都会直接终止进程;
    • _exit,与exit类型,但此函数不会刷新缓冲区等处理工作,直接终止进程;
  • 异常退出;
    • ctrl + C,信号终止;

退出码可自定义,也可使用系统错误码;

#include <unistd.h>
void exit(int status);
#include <unistd.h>
void _exit(int status);
//status 定义了进程终止状态,父进程通过wait来获取该值;
//虽然status为int,但仅低8位可被父进程使用,_exit(-1)执行echo $?结果为255;

 

#include <stdio.h>
#include <stdlib.h>
int main()
{printf("hello");exit(0);                                                                  return 0;
}
[wz@192 Desktop]$ ./target 
hello[wz@192 Desktop]$ 
#include <stdio.h>
#include <stdlib.h>
int main()
{printf("hello");_exit(0);                                                                  return 0;
}
[wz@192 Desktop]$ ./target 
[wz@192 Desktop]$ 

return退出

        一种常见的退出进程方法,执行return n等同于执行exit(n),因为调用main的运行时函数会将main的返回值当作exit的参数;

进程终止的核心思想,就是归还资源;

  • 释放曾经为管理进程所维护的所有数据结构对象;
    • 不是真的把数据结构对象销毁,而是设置为不用状态,保存起来,“数据结构池”;
  • 释放程序代码和数据所占的内存空间;
    • 不是将代码和数据清空,把内存设置为无效即可;
  • 取消曾经该进程的链接关系;

三,进程等待

进程等待的必要性

  • 子进程退出,父进程如不管不顾,就可能造成僵死进程,进而造成内存泄露;
  • 进程进入僵死状态,将无能为力,即使是kill -9,因为无法杀死一个已经死亡的进程;
  • 父进程交派给子进程的任务完成状况需知道,如子进程运行完,其结果对错与否,是否正常退出;
  • 父进程通过进程等待的方式,回收子进程资源,获取子进程退出信息;

pid_t wait(int*status)

  • 返回值,成功,返回被等待进程pid;失败,返回-1;
  • 参数,获取子进程退出状态,不关心可设置为NULL;
#include<sys/types.h>
#include<sys/wait.h>pid_t wait(int*status);

pid_ t waitpid(pid_t pid, int *status, int options)

  • 返回值
    • 正常返回的时候,waitpid返回收集到的子进程的进程PID;
    • 如设置了选项WNOHANG,而调用中waitpid方向没有已退出的子进程可收集,返回0;
    • 如调用中出错,则返回-1,这时errno会被设置成相应的值以指示错误所在;
  • 参数
    • pid,-1等待任一个子进程,与wait等效;>0等待其进程ID与pid相等的子进程;
    • status
      • WIFEXITED(status),若为正常终止子进程进程返回的状态,则为真;
      • WEXITSTATUS(status),若WIFEXITED非零,提取子进程退出码;
    • options,WNOHANG,若pid指定的子进程没有结束,则waitpid()函数返回0,不予以等待;若正常结束,则返回该子进程的ID;
#include<sys/types.h>
#include<sys/wait.h>pid_ t waitpid(pid_t pid, int *status, int options);
  • 若子进程已退出,调用wait/waitpid时,wait/waitpid会立即返回,并释放资源,获得子进程退出信息;
  • 如在任意时刻调用wait/waitpid,子进程存在且正常运行,则进程可能阻塞;
  • 如不存在该子进程,则立即出错返回;

获取子进程status

  • wait/waitpid都有一个status参数,此参数为输出型参数,由操作系统填充;
  • 如传递NULL,表示不关心子进程的退出状态信息;否则,操作系统会根据该参数,将子进程发退出信息反馈给父进程;
  • status不能简单的当作整型看待,可当作位图;

 

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

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

相关文章

Spring Boot参数校验实现自定义响应类优雅处理

&#x1f60a; 作者&#xff1a; 一恍过去 &#x1f496; 主页&#xff1a; https://blog.csdn.net/zhuocailing3390 &#x1f38a; 社区&#xff1a; Java技术栈交流 &#x1f389; 主题&#xff1a; Spring Boot参数校验实现自定义响应类优雅处理 ⏱️ 创作时间&#xf…

AnimateDiff论文解读-基于Stable Diffusion文生图模型生成动画

文章目录 1. 摘要2. 引言3. 算法3.1 Preliminaries3.2. Personalized Animation3.3 Motion Modeling Module 4. 实验5.限制6. 结论 论文&#xff1a; 《AnimateDiff: Animate Your Personalized Text-to-Image Diffusion Models without Specific Tuning》 github: https://g…

数据分析 VS 数据可视化:决战时刻

数据分析和数据可视化是数据科学领域中两个重要的组成部分&#xff0c;很多人不明白两者之间的关系&#xff0c;会误认为是一个东西&#xff0c;其实不然。本文就带大家简单了解一下它们的区别与联系吧&#xff01; 数据分析是指通过收集、处理和解释数据来获取有关特定问题或…

无涯教程-Lua - 嵌套if语句函数

在Lua编程中&#xff0c;您可以在另一个if or else if语句中使用一个if or else if语句。 nested if statements - 语法 嵌套if 语句的语法如下- if( boolean_expression 1) then--[ Executes when the boolean expression 1 is true --]if(boolean_expression 2)then--[ Ex…

ConCurrentHashMap常见面试题

1. JDK1.7和JDK1.8中ConCurrentHashMap的实现有什么不同&#xff1f; JDK1.7中的实现可以认为是大数组套小数组&#xff0c;大数组是Segment数组&#xff0c;小数组是HashEntry数组&#xff0c;锁是锁在大数组的元素上&#xff08;Segment&#xff09;&#xff0c;力度比较大&…

【BASH】回顾与知识点梳理(一)

【BASH】回顾与知识点梳理 一 前言一. 认识与学习 BASH1.1 硬件、核心与 Shell1.2 为何要学文字接口的 shell&#xff1f;1.3 系统的合法 shell 与 /etc/shells 功能1.4 Bash shell 的功能1.5 查询指令是否为 Bash shell 的内建命令&#xff1a; type1.6 指令的下达与快速编辑按…

VS+QT+VTK treeView树型结构模型加载隐藏实例

程序示例精选 VSQTVTK treeView树型结构模型加载隐藏实例 如需安装运行环境或远程调试&#xff0c;见文章底部个人QQ名片&#xff0c;由专业技术人员远程协助&#xff01; 前言 这篇博客针对<<VSQTVTK treeView树型结构模型加载隐藏实例>>编写代码&#xff0c;代码…

Chrome 75不支持保存成mhtml的解决方法

在Chrome 75之前&#xff0c;可以设置chrome://flags -> save as mhtml来保存网页为mhtml。 升级新版&#xff0c;发现无法另存为/保存网页为MHTML了。 在网上搜索无果后&#xff0c;只得从chromium项目的commits中查找&#xff0c;原来chrome搞了个"Chrome Flag Owner…

Android 创建 Gradle Task 自动打包并上传至蒲公英

前言 Android 项目日常开发过程中&#xff0c;经常需要打包给到非开发人员验收或调试&#xff0c;例如测试阶段&#xff0c;就要经常基于测试服务器地址&#xff0c;打包安装包&#xff0c;给到组内测试人员进行测试&#xff0c;并且 BUG 修复完成之后也需要再次打包给到测试人…

差分隐私 MP-SPDZ框架安装

ubuntu虚拟机安装MP-SPDZ框架 1.下载安装包到虚拟机内 https://github.com/data61/MP-SPDZ/releases 安装git 报错Waiting for cache lock: Could not get lock /var/lib/dpkg/lock-frontend. It is held by process 4402(unattended-upgr) 解决方案 #杀死进程 sudo k…

JAVA 反编译工具

Releases deathmarine/Luyten GitHub 安装exe 打开拖入文件即可

Express接口

1.创建基本的服务器 // 导入express模块 const express require(express); const send require(send);// 创建express的 服务器实例 const app express()// 启动服务器 app.listen(80, () > {console.log(express server running at );})2.创建API路由接口 // 导入expr…

「网络编程」传输层协议_ TCP协议学习_及原理深入理解(二 - 完结)[万字详解]

「前言」文章内容大致是传输层协议&#xff0c;TCP协议讲解的第二篇&#xff0c;续上篇TCP。 「归属专栏」网络编程 「主页链接」个人主页 「笔者」枫叶先生(fy) 目录 二、TCP协议2.9 TCP连接管理机制2.9.1 三次握手2.9.2 四次挥手2.9.3 演示查看TIME_WAIT和CLOSE_WAIT状态2.9.…

MySQL 远程操作mysql

可以让别人在他们的电脑上操作我电脑上的数据库 create user admin identified with mysql_native_password by admin; //设置账号密码都为admingrant all on *.* to admin; //给admin账号授权 授权完成

使用elementplus实现文本框的粘贴复制

需求&#xff1a; 文本框仅用于显示展示数据并且用户可以进行复制&#xff0c;并不会进行修改和编辑&#xff0c; 注意点&#xff1a; 1.首先且文本为多行。所以不能使用普通的el-input&#xff0c;这种一行超出就会隐藏了&#xff0c;如果多行超出行数也会隐藏&#xff08;…

用blender做一层石墨烯

文章目录 1 创建正六边形2 复制正六边形3 阵列4 球棍模型 1 创建正六边形 ShiftA->网格->圆环->左下角出现添加圆环菜单&#xff0c;将顶点设为6&#xff0c;得到一个正六边形。按下tab键进入编辑模式->快捷键F填充&#xff0c;得到下图 2 复制正六边形 首先将轴…

Django的FBV和CBV

Django的FBV和CBV 基于django开发项目时&#xff0c;对于视图可以使用 FBV 和 CBV 两种模式编写。 FBV&#xff0c;function base views&#xff0c;其实就是编写函数来处理业务请求。 from django.contrib import admin from django.urls import path from app01 import view…

Redis主从复制、哨兵机制、集群分片

一.主从复制 1.概述 主从复制&#xff0c;是指将一台Redis服务器的数据&#xff0c;复制到其他的Redis服务器。前者称为主节点(master)&#xff0c;后者称为从节点(slave)。 数据的复制是单向的&#xff0c;只能由主节点到从节点默认情况下&#xff0c;每台Redis服务器都是主节…

机器学习深度学习——权重衰减

&#x1f468;‍&#x1f393;作者简介&#xff1a;一位即将上大四&#xff0c;正专攻机器学习的保研er &#x1f30c;上期文章&#xff1a;机器学习&&深度学习——模型选择、欠拟合和过拟合 &#x1f4da;订阅专栏&#xff1a;机器学习&&深度学习 希望文章对你…