当前位置: 首页 > news >正文

实用指南:Linux操作系统之进程控制(1)

实用指南:Linux操作系统之进程控制(1)

1、进程创建

复习fork函数,fork函数的返回值

fork函数是创建一个子进程,也就是当前的父进程创建一个新的子进程

整理一下就是:新的进程是子进程,原来的进程是父进程

#include 
#include 
int main()
{printf("I am a process:%d\n",getpid());pid_t id=fork();if(id<0){//进程创建失败!printf("fail fork!\n");return 1;}else if(id==0){//childprintf("I am a child:%d\n",getpid());}else{//parentprintf("I am a parent:%d,my son pid:%d\n",getpid(),id);}return 0;
}

fork调用进程,那么进程在内核中做了什么?

1、开辟新的内存块和内核数据结构给子进程

2、将父进程部分内核数据数据拷贝到子进程

3、将父进程的PCB、地址空间、页表相关内容也都复制拷贝到子进程中,但是只有pid不是复制

4、将子进程添加到系统进程列表中

5、fork返回,开始调度器调度

为什么fork有两个返回值?

  1. 你举手(调用fork()系统调用)

  2. 监考老师(操作系统)过来

    • 记下你的当前答题进度

    • 叫来一个新考生(创建子进程)

    • 给新考生一份空白的答题卡,但题目册和你共用一本

    • 悄悄告诉你:"他的考号是1001"

    • 悄悄告诉他:"你的考号是0"

  3. 你们继续考试

    • 你看你的题册,他看他的题册(同一本物理书

    • 你在你的答题卡写:助手考号=1001

    • 他在他的答题卡写:我的考号=0

  4. 当你想在题册上做标记时

    • 监考老师立刻复印该页,给你新的一页

    • 你在新页上做标记

    • 他如果也想标记,老师会复印原页给他新的一页

同理,

1、fork进入内核

2、fork函数的实现进行申请内存构建数据结构PCB,虚拟内存,页表,最后将当前新进程设置为R状态,放置进调度列表中

3、此时进程已经创建成功了,父子进程共享代码,fork函数的最后一个代码是返回一个值,return ret这个代码父子进程都会执行一次

所以会有两个返回值 在返回时,将函数的返回值返回给变量,发生了写时拷贝,一个变量名但是内容是不同的,本质父子页表映射数据到了不同的内存区域

写时拷贝

例如

父亲账户是一千元

儿子想在父亲账户取两百块钱!

银行说:不行,你不能在你爸爸账户上拿,请你立刻开一个账户,把你爸爸的一千元复制过去

儿子在新账户上操作,取了两百,余额800

父亲的账户没有变

结果:父亲的是一千(原账户),儿子的是八百(新账户)

#include 
#include 
int main()
{int data=1000;pid_t id = fork();if(id==0){//儿子开始取钱,取完剩下800printf("儿子:我看到:%d\n",data);data=800;printf("儿子:我要取钱了,还剩下:%d\n",data);}else{//父亲检查sleep(1);//儿子先拿printf("父亲:儿子拿完之后,我的钱剩下:%d\n",data);}return 0;
}

操作系统上的解释:

物理内存变化:初始(fork后):
父子都指向同一物理页,页面标记为"只读"儿子写操作时:
1. CPU:"哦,这个页面是只读的"
2. 触发缺页异常 → 进入内核
3. 内核:"这是COW页面,要复制"
4. 分配新物理页,复制内容
5. 修改儿子页表:指向新页面,设为可写
6. 儿子继续写操作结果:
父亲页表 → 原物理页(内容未变)
儿子页表 → 新物理页(修改后的内容)

进程调用失败的原因

系统有太多进程

实际用户的进程超出了限制

总结:本质是以父进程为模板创建了子进程,不是所有的子进程都复制父进程,例如PID就不是一样的

2、进程终止

进程共有三种退出场景

1、代码跑完了,结果是对的

2、代码跑完了,结果是不对的

3、代码没跑完,程序退出了(代码异常终止)

情况1和2退出的时候会有退出标志,而情况3是发生了异常会有退出的原因

进程常见退出码

int main()
{return ?;
}

return 后面跟着的数字就是进程的退出码

echo $?是可以查看最近一次的进程退出码

查看进程码的信息

#include
#include
int main()
{for(int i = 0;i<200;i++){printf("%d:%s\n",i,strerror(i));}return 0;
}

exit和return的区别

exit:终止整个进程,任何地方调用,都会终止

return:终止函数,如果main函数return,代表终止整个进程

站在OS角度,如何理解进程终止?

进程终止的本质

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

1. 释放进程管理数据结构

不是真的销毁数据结构对象,而是将它们标记为“空闲”状态,放回对应的数据结构对象池中。这样后续创建新进程时可以直接复用这些已分配的内存块,避免频繁的内存分配开销。

2. 释放程序代码和数据占用的内存空间

不是把内存内容清空,而是将相关内存页标记为“无效”,从进程的页表中移除映射关系。这些物理页面可以被其他进程重用。

3. 取消进程间的链接关系

解除进程与父进程、子进程、进程组等之间的关联关系,更新相关的内核数据结构。

http://www.jsqmd.com/news/340844/

相关文章:

  • 无需编码!零基础技术小白怎么搭建社区论坛小程序源码系统
  • 杭州德能暖通价格多少,靠谱吗? - myqiye
  • 提供一下获取的NTP时间中的月和周的枚举
  • windbg符号设置
  • 键盘改键神器,小巧实用
  • 盘点聚氨酯筛板优质加工厂,广东地区哪家值得选 - 工业品牌热点
  • 2026年正规的干湿联合闭式冷却塔/逆流冷却塔最新TOP厂家排名 - 品牌宣传支持者
  • 主流消息队列(MQ)的核心架构、底层原理
  • GaussDB Balanced 状态与重平衡完全指南
  • 基于龙伯格观测器的永磁同步电机无感FOC技术:反电势提取与转子位置速度信息获取
  • 2026年口碑好的GEO公司推荐,讯灵AI+Agent智能体实现精准触达 - mypinpai
  • Mamba:SSM、理论及在 Keras 和 TensorFlow 中的实现
  • 2026年不锈钢全屋定制衣柜厂家权威推荐榜:全屋不锈钢定制家居/厨房不锈钢全屋定制/本地不锈钢全屋定制/本地不锈钢定制家居/选择指南 - 优质品牌商家
  • 《质数与因数》小学知识点
  • 2026年食品级碳酸氢铵生产企业厂家权威推荐榜:农用级碳铵、工业碳酸氢铵生产企业、工业碳铵生产企业、工业级碳酸氢铵生产企业选择指南 - 优质品牌商家
  • C语言初阶——手把手教零基础/新手入门(万字心得笔记)
  • 无人机视角地理要素田地道路森林水体电力线识别分割数据集labelme格式1536张6类别
  • 2025年 Java 面试八股文
  • 一次关于角色的调研:寰夏华商联合会与 Sopra Steria Group 的巴黎对话
  • 供应商全景:从国内铝合金锭厂家排名看优质品牌选择 - 品牌推荐大师1
  • SpringBoot静态资源管理:从默认配置到自定义与WebJars
  • 如何做谷歌seo搜索优化?实战派老鸟的干货分享
  • 跟我学C++中级篇—静态变量的生命周期控制
  • glb格式3d模型压缩
  • 2026必备!10个降AI率平台推荐,千笔·专业降AI率智能体解决降AIGC难题
  • 嵌入式之C/C++(四)预处理
  • 我的 AI 销售学了甄嬛传,谈单张口就是本宫认为
  • 2026年热门的钢结构维护材料销售/钢结构原材料销售厂家推荐及采购参考 - 品牌宣传支持者
  • AI 软件的开发流程
  • 手机APP扫码上传图片到PC网站端实现方案