Linux基础之进程-进程状态

news2024/11/18 11:20:13

目录

一、进程状态

1.1 什么是进程状态

1.2 运行状态

1.2 阻塞状态

1.3 挂起状态

二、Linux操作系统上具体的进程状态

2.1 状态

2.2 R 和 S 状态的查看

2.3 后台进程和前台进程

2.4 休眠状态和深度休眠状态


一、进程状态

1.1 什么是进程状态

       首先我们知道我们的操作系统是通过我们的PCB来管理我们的进程的,那么我们的状态这个属性一定在我们的PCB这个结构体里(其在PCB中是一个整形字段)。用简单的话来说,用宏定义(也可能是其他方式)了几个值,用这几个值来代表我们不同的状态。

#define NEW 1
#define RUNNING 2
#define BLOCK 3

struct PCB
{
   ...//其他属性
   int status;//状态
}//通过改变status的值来代表改变进程的状态

根据一些教材上的描述,进程大概会有以下的一些状态。

(图片来源于网络)。
       接下来我就来给大家好好介绍一下这些状态(其中创建状态、就绪状态和运行状态我统一归结为运行状态)。

1.2 运行状态

       在上文回答第四个问题的时候,我有提到过一个运行队列的概念,它提供了一种有序执行任务的机制,使得任务的执行顺序可控,并能够有效地利用系统资源。所以我们的OS会维护一个运行队列去存放我们的进程,而我们的CPU则会去执行该队列PCB所指的代码。

由此,我们的出一个概念:

不管一个进程是否在被处理,只要其PCB加入了运行队列,我们就称其处在运行状态。

1.2 阻塞状态

       我们的代码一定会或多或少的会访问系统中的某些资源,比方说:键盘、硬盘等等,在比方说我们的scanf()和cin>> ,本质上都是从我们的键盘上读取数据,那要是我们一直不输入怎么办,那是不是我们的程序会一直卡在那,不动了。为什么会不动呢,因为需要的数据没有就绪,也就是我们进程要访问的资源没有就绪,条件不具备,我们的代码就没办法往下执行。
       我们的OS要管理我们的进程,也同样会去管理我们的硬件资源,也就是说我们设备的资源充不充足,有没有就绪,OS是知道的,怎么知道的呢,通过维护我们的硬件资源的dev_list。但这个
list多个一个属性:PCB* wait_queue。也就是说,当我们的设备资源不充足时,我们对应的PCB就会加入到该设备的这个等待队列中,而我们把在设备的等待队列中的PCB的状态叫做阻塞状态

通过这部分的讲解,我们可以得到一个结论:

进程状态变化的本质:

1.更改PCB 对应的status变量的值

2.将PCB链入到我们不同的队列当中

1.3 挂起状态

       如果一个进程当前被阻塞了,那就注定了这个进程在其所需要的资源没有就绪之前是不会被调度的。那么如果这个时候我们的操作系统内的内存资源严重不足了该怎么办?
       我们的操作系统在我们的磁盘中划分了一个叫做swap的分区,其作用就是在我们OS的内存资源不足的时候,换取一些资源回来。怎么换呢?换谁呢?就换我们处于阻塞状态的进程。
 
       将我们的PCB的数据(是数据置换了,留出空间,而不是这个进程没有了)置换到我们的swap分区,置换之后我们的进程所处状态就叫挂起状态。
       这个时候可能有人会问,OS不是非常注重效率的吗,其主动去访问我们的磁盘,不会降低我们OS的效率吗?确实会影响我们OS的效率,但是这个时候OS都快挂掉了,所以优先考虑的问题是让OS运行下去。
       当之后我们的资源空闲出来,我们的进程被重新调度时,曾经被置换出去的数据和代码,又会被重新置换回来。

二、Linux操作系统上具体的进程状态

2.1 状态


先来看看再kernal内核里的代码

/*
* The task state array is a strange "bitmap" of
* reasons to sleep. Thus "running" is zero, and
* you can test for combinations of others with
* simple bit tests.
*/
static const char * const task_state_array[] = {
"R (running)", /* 0 */
"S (sleeping)", /* 1 */
"D (disk sleep)", /* 2 */
"T (stopped)", /* 4 */
"t (tracing stop)", /* 8 */
"X (dead)", /* 16 */
"Z (zombie)", /* 32 */
}
  • R运行状态(running): 并不意味着进程一定在运行中,它表明进程要么是在运行中要么在运行队列里。
  • S睡眠状态(sleeping): 意味着进程在等待事件完成(这里的睡眠有时候也叫做可中断睡眠(interruptible sleep))。
  • D磁盘休眠状态(Disk sleep)有时候也叫不可中断睡眠状态(uninterruptible sleep),在这个状态的进程通常会等待IO的结束。
  • T停止状态(stopped): 可以通过发送 SIGSTOP 信号给进程来停止(T)进程。这个被暂停的进程可以通过发送 SIGCONT 信号让进程继续运行。
  • X死亡状态(dead):这个状态只是一个返回状态,你不会在任务列表里看到这个状态。

2.2 R 和 S 状态的查看

我们可以通过我们的代码和我们的指令来查看我们的进程状态,先写一段代码。

可以看到我们的状态如下
      其中STAT(status)就代表我们的状态栏,可以看到我们的程序,一直明明在跑,却处于我们的S(即阻塞状态)状态,这是为什么呢?其实我们的CPU速度是很快的,程序其实已经走完了,但是我们的printf语句是需要访问我们的外设的(显示器),访问外设又是一个比较慢的过程,所以该进程的大部分时间都处于S状态。那如果我们不输出呢?

可以看到我们的进程状态就可以被观测到处于我们的R状态(运行状态)。至于这个+号是什么意思,我们马上就能知道了。

2.3 后台进程和前台进程

有+号代表是前台进程,没有的代表是后台进程。
首先这两个概念是什么意思呢?

前台进程:进程在被执行时,无法使用其他的指令,且其可以被ctrl + C 强行终止掉

后台进程:进程在被执行时,可以使用其他的指令,但是不能被ctrl + C 强行终止掉,所以需要kill将其杀掉。

那怎么将我们的进程变成一个后台进程呢?

在执行我们的程序时,在其后面加上一个 &
类似于: ./mybin &

给大家演示一下:

      可以看到我们在边执行程序的时候还可以使用我们的指令(如果要终止这个进程使用指令 kill -9 + 该进程的PID)。

2.4 休眠状态和深度休眠状态

       对于这个状态给大家举个例子就能理解了,假设我们有一个进程正在向磁盘中存放数据(数据量有点大),由于访问我们的硬件速度很慢,我们的进程就会进入我们的S状态(即阻塞状态),如果这个时候我内存资源已经不够,swap分区也不够用了,需要干掉一些进程来存活,那恰好就把这个还在等待磁盘返回结果的进程干掉了,其数据全都释放了。那此时,如果我们的磁盘存储失败了,那我们的这部分数据就丢失了,那是不是很容易造成很严重的影响。所以就有了我们深度睡眠状态D,不可被中断。

D磁盘休眠状态(Disk sleep)有时候也叫不可中断睡眠状态(uninterruptible sleep),在这个状态的进程通常会等待IO的结束。

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

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

相关文章

未来互联网:Web3的技术革新之路

引言 随着技术的不断发展和社会的日益数字化,互联网作为信息交流和社交媒介的重要平台已经成为我们生活中不可或缺的一部分。然而,传统的互联网架构在数据安全、隐私保护和去中心化等方面存在着诸多挑战。为了解决这些问题,Web3技术应运而生…

【js】获取媒体流实现拍照功能,摄像头切换

<script setup>import {onMounted,reactive,ref} from vueconst videoConstraints reactive({width: 500,height: 300});let picArr reactive([])let videoNode ref(null)let show ref(true)let stream reactive({})onMounted(async () > {// 获取视频流&#xf…

C++语法|深入理解 new 、delete

在开发过程中&#xff0c;非常重要的语法就有我们new和delete&#xff0c;周所周知在C中最为强大的能力就是对内存的控制&#xff0c;所以我们再怎么强调new和delete都不为过 文章目录 1.new和delete基本语法new和malloc的区别是什么&#xff1f;(1)开辟单个元素的内存差别(2)开…

Python专题:十三、日期和时间(2)

datetime 模块 today()函数 date类型 year month day

摊还分析

一、摊还分析 概念&#xff1a;是求数据结构中一个操作序列执行所有操作的平均时间&#xff0c;与平均复杂度不同&#xff0c;它不涉及输入概率&#xff0c;能够保证在最坏情况下操作的平均性能。 适用场景&#xff1a;用含 n 个操作的序列&#xff08;o1&#xff0c;o2&#x…

互联网轻量级框架整合之HibernateMyBatis

持久层框架 Hibernate 假设有个数据表&#xff0c;它有3个字段分别是id、rolename、note, 首先用IDEA构建一个maven项目Archetype选择org.apache.maven.archetypes:maven-archetype-quickstart即可&#xff0c;配置如下pom <project xmlns"http://maven.apache.org/…

ERROR: tensorboard 1.14.0 has requirement setuptools>=41.0.0(问题解决)

问题描述&#xff1a; ERROR: tensorboard 1.14.0 has requirement setuptools>41.0.0, but youll have setuptools 39.2.0 which is incompatible. 问题原因&#xff1a; setuptools 版本太低 解决方法&#xff1a;升级setuptools版本 pip install --upgrade setuptools…

Notepad8.1.9汉化中文版

下载地址&#xff1a;Notepad8.1.9.zip 一款优秀免费的源代码编辑器&#xff0c;支持语法高亮的开源纯文本编辑器&#xff0c;并且可以替代系统自带的记事本的功能。

40V/300mA快速瞬态低压差线性稳压器替代ADP7142

概述(替代ADP7142/LT1962/LT1521/LT3060) PCD4900 是一款 CMOS、低压差&#xff08;LDO&#xff09;线性稳压器&#xff0c;采用 1.9V 至 40V 电源供电&#xff0c;最大输出电流为 300 mA。这款高输入电压 LDO 适用于调节 36V 至 1.2V 供电的高性能模拟和混合信号电路。该器件…

iOS copy的正确姿势

参考文章 知识准备&#xff08;理解堆栈&#xff09; 堆区&#xff1a; 程序员管理 若程序员不释放&#xff0c;由os释放不同于数据结构中的堆&#xff0c;堆区的结构类似于数据结构中的链表栈区&#xff1a; 由编译器来管理 存放函数参数值&#xff0c;局部变量的值等结构类似…

C语言(指针)7

Hi~&#xff01;这里是奋斗的小羊&#xff0c;很荣幸各位能阅读我的文章&#xff0c;诚请评论指点&#xff0c;关注收藏&#xff0c;欢迎欢迎~~ &#x1f4a5;个人主页&#xff1a;小羊在奋斗 &#x1f4a5;所属专栏&#xff1a;C语言 本系列文章为个人学习笔记&#x…

nestjs封装一个响应体

封装一个DTO // response.dto.tsimport {CallHandler,ExecutionContext,Injectable,NestInterceptor, } from "nestjs/common"; import { FastifyReply } from "fastify"; import { Observable } from "rxjs"; import { map } from "rxjs/…

苹果macOS无法给App麦克风授权解决办法

好久没有在电脑上录制课程了&#xff0c;有些东西还是录下来记忆深刻&#xff0c;却意外发现MAC系统升级后无法授权给第三方的App使用摄像头和麦克风&#xff0c;而录屏软件是需要开启麦克风和摄像头才能录制屏幕上的操作和声音&#xff0c;官方提示在第三方APP若有使用摄像头和…

echarts切换tab,图表设置宽度100%结果为100px

当外层div盒子设置宽度为100%时&#xff0c;可echarts渲染出来宽度只有100px&#xff0c;这种情况大多数echarts所在的div设置了display:none&#xff0c;获取不到外部盒子的宽度。 这里可以通过echarts源码获取宽度的行为来解释 究其原因就是出现在了图表设置了display:none…

【从零开始实现stm32无刷电机foc】【理论】【1/6 电机旋转本质】

目录 电机旋转需要什么样的力&#xff1f;怎么产生力矢量&#xff1f;怎么产生任意的线圈磁矢量&#xff1f; 电机旋转需要什么样的力&#xff1f; 电机切向存在受力&#xff0c;电机就会旋转。 进一步查看电机结构&#xff0c;分为转子和定子&#xff0c;大部分情况下&#…

超级简单的地图操作工具开发可疑应急,地图画点,画线,画区域,获取地图经纬度等

使用echars的地图画点,画线,画区域,获取地图经纬度等 解压密码:10086007 地图也是用临时的bmap.js和china.js纯离线二选一 一共就这么多文件 画点,画线,画区域 点击地图获取经纬度-打印到控制台,这样就能渲染航迹,多变形,结合其他算法算圆等等操作 下载资源:https://download…

ROS2 conda 环境下报 No module named ‘catkin_pkg‘

这里使用的环境是&#xff1a;Ubuntu 22.04, ROS2, Conda python 虚拟环境是3.10 ~/.bashrc 里注释掉 conda&#xff0c;并添加 export PYTHONPATH$PYTHONPATH:/usr/lib/python3/dist-packages sudo gedit ~/.bashrc source ~/.bashrc

使用Remix部署智能合约到币安链(Remix的操作介绍 币安链合约的部署) 点赞收藏哦

大家好&#xff0c;我是程序员大猩猩呀。 据我所知&#xff0c;很多人进入币圈之后&#xff0c;想要通过炒币一夜暴富&#xff01;另一部分人呢他们希望自己能创建一个项目&#xff0c;然后发行自己的数字货币然后暴富。 不管是什么方式吧&#xff0c;只要不违法&#xff0c;…

Spring框架中常见注解

Spring&#xff1a; SpringMVC&#xff1a; RequestMapping用在类上表示所有该类下方法的父路径 RequestParam 做映射&#xff0c;前端请求的参数映射到控制器Controller的处理方法上的参数上。 【当参数需要设置默认值&#xff08;前端没有发送这个参数&#xff09;、参数名…

面对.halo勒索病毒,如何有效防范与应对?

导言&#xff1a; 随着网络技术的不断发展&#xff0c;网络安全问题也日益凸显。其中&#xff0c;勒索病毒作为一种极具破坏性的网络攻击手段&#xff0c;近年来在全球范围内频发。其中&#xff0c;.halo勒索病毒作为勒索病毒家族中的一员&#xff0c;其危害性和传播性不容忽视…