Linux进程状态


1. 进程状态

在 操作系统中,进程状态是操作系统对进程生命周期的抽象描述,反映了进程当前的运行状态和资源使用情况。
在这里插入图片描述

1.1 运行

在正式理解各种进程状态之前,我们要知道一个CPU有一个调度队列,当一个进程持有cpu资源,就叫运行状态。广义的来说,一个进程只要在调度队列中就是运行状态。

进程要么正在 CPU 上执行,要么处于就绪队列中,等待 CPU 调度(具备运行条件,只需获得 CPU 时间片即可执行)。
特点:是进程的 “活跃” 状态,可能随时被调度执行。

1.2 阻塞

含义:进程等待某种设备或资源就绪。
从运行状态到阻塞状态的本质实际上是,将一个进程从运行队列取下,链入到一个等待队列中。而操作系统对软硬件资源管理,管理的方式是先描述再组织。组织硬件为一个类似pcb的东西,所以会存在运行队列,等待队列。
由阻塞状态再回到运行状态的本质就是从等待队列链回到运行队列。
进程状态的变化,表现之一,就是要在不同的队列中进行流动,本质都是数据结构的增删查改。

在操作系统中,阻塞状态(Blocked State) 是进程的一种常见状态,指进程因等待某个不可立即满足的资源或事件(如 I/O 操作、信号、锁等)而暂时无法继续执行,主动放弃 CPU 使用权,进入暂停状态。
核心特点
非运行状态:处于阻塞状态的进程不占用 CPU 时间片,即使 CPU 空闲也无法执行。
等待条件:进程必须等待某个特定事件完成(如磁盘读写结束、用户输入、信号到达等)才能恢复运行。
被动唤醒:阻塞状态的进程不能主动退出该状态,只能由外部事件(如等待的资源就绪)触发唤醒,进入就绪状态(等待 CPU 调度)。

1.3 挂起

在磁盘中存在swap交换分区,当cpu资源严重不足,操作系统将阻塞状态的进程的代码和数据交换到磁盘中,只留下pcb,称为阻塞挂起。交换的过程叫唤入唤出操作。
如果cpu资源还是不足,操作系统会将运行队列中的进程唤出到磁盘中,称为运行挂起。

在操作系统中,挂起状态(Suspended State) 是指进程被暂时从内存中换出到外存(如磁盘的交换区),暂时不参与 CPU 调度的一种状态。其核心目的是为了缓解内存资源紧张,通过将暂时不用的进程 “移至后台”,释放内存供活跃进程使用。
挂起状态的核心特征
不在内存中:挂起的进程其代码和数据会被交换到外存(如 swap 分区),仅在内存中保留少量进程控制块(PCB)信息(用于标识进程)。
无法直接调度:由于不在内存,即使 CPU 空闲,挂起进程也不能立即执行,必须先被换回内存(“激活”)才能进入就绪状态。
主动 / 被动触发:通常由操作系统根据内存使用情况自动触发(如内存不足时),也可能通过特定命令手动挂起(如某些实时系统中)。

2. 理解内核链表

// 内核链表节点(仅包含指针,无数据)
struct list_head {
    struct list_head *next;  // 下一个节点
    struct list_head *prev;  // 上一个节点
};

同一个数据结构可以同时属于多个链表(通过嵌入多个 list_head 节点),且链表操作与具体数据类型无关,通用性极强。pcb在内核中只存在一份,但是!可以属于多种数据结构。就是通过内核链表来实现。

3. Linux内核源码进程状态

以上是操作系统的知识,下面看具体的Linux操作系统对各种状态的表现。

3.1 运行状态(R,Running/Runnable)

含义:进程要么正在 CPU 上执行,要么处于就绪队列中,等待 CPU 调度(具备运行条件,只需获得 CPU 时间片即可执行)。
特点:是进程的 “活跃” 状态,可能随时被调度执行。

  1 #include <stdio.h>
  2 #include <sys/types.h>
  3 #include <unistd.h>
  4 
  5 int main()
  6 {
  7      printf("我是一个进程, pid: %d\n", getpid());
  8 
  9     int x;
 10     scanf("%d", &x);
 11     while(1)
 12     {
 13         printf("hello linux\n");
 14     }
 15     return 0;
 16 }

在这里插入图片描述

./test & # 表示放在后台运行

R+表示放在后台运行,要通过kill命令杀死进程。

3.2 睡眠状态(S,Interruptible Sleep)

S状态,也叫休眠状态是可中断休眠的浅度睡眠,可以被kill掉。

含义:进程因等待某个事件(如 I/O 完成、信号、定时器等)而暂时停止运行,进入阻塞状态。
特点:可被信号唤醒(如被中断或收到 kill 信号),唤醒后进入就绪状态(R)等待调度。
示例:进程调用 sleep(10) 或等待键盘输入时,会进入 S 状态。

在这里插入图片描述

3.3 深度睡眠状态(D,Uninterruptible Sleep)

含义:进程因等待关键系统资源(如磁盘 I/O 操作)而阻塞,此时不响应任何信号(包括 kill 信号)。
特点:确保进程在完成关键操作前不被中断,避免资源不一致。只有当等待的事件完成后,才能自动唤醒。
风险:若等待的资源永久不可用(如硬件故障),进程可能长期处于 D 状态,只能通过重启系统解决。

深度睡眠状态也叫不可中断休眠 。场景:某x进程任务是向磁盘写入文件,将数据交给磁盘后,进程处于s状态(阻塞状态),但此时系统资源严重不足,操作系统杀死该进程,导致磁盘无法将结果返回给x进程,进而导致数据丢失,由此产生D状态。D状态下,进程不对任何kill命令相应,避免数据丢失,总结,D状态也是阻塞状态的一种。

3.4 停止状态(T,Stopped)

含义:进程被暂停执行,通常由外部信号触发(如 SIGSTOP 信号)。
特点:可通过 SIGCONT 信号恢复运行(进入 R 状态)。
示例:在终端中按下 Ctrl+Z 会发送 SIGTSTP 信号,使前台进程进入 T 状态。

t状态也叫暂停状态/追踪状态。
场景:当文件被debug时,设置断点,进程即被暂停,进入t暂停状态。
T暂停状态:用户通过键盘暂停ctrl+z,进程会进入T暂停状态。

3.5 僵尸状态(Z,Zombie)

含义:进程已经终止(代码执行完毕或被信号终止),但内核仍保留其进程控制块(PCB)中的信息(如退出状态、资源使用统计),等待父进程通过 wait() 或 waitpid() 回收。
特点:进程已无实际运行代码,不占用 CPU 和内存资源,但仍有一个 PID 存在(直到被回收)。
危害:若父进程未及时回收僵尸进程,会导致 PID 资源泄露(系统 PID 数量有限)。

Z状态也叫僵尸状态,目的是为了使父进程获取退出信息。
场景:进程是为了执行某种任务,执行结果等相关的信息要让父进程知道,所以子进程结束后不能马上转为x状态,而是要转为z状态。此时可以释放代码和数据,因为子进程不会再被调度但是要维持进程退出的基本信息让父进程知道。
如果父进程一直不管,不回收子进程的退出结果,那么子进程的pcb会一直存在,导致引发内存泄漏。

3.6 死亡状态(X,Dead)

含义:进程已完全终止,所有资源(包括 PCB)被内核释放,是进程生命周期的终点。
特点:在进程列表中无法看到(瞬时状态),仅作为状态转换的中间标记。

X状态,进程结束状态。

3.7 孤儿进程

场景:父进程先挂,只剩下子进程。如果在父子进程关系中,父进程先退出,子进程要被1号进程领养,一号进程就是操作系统。
为什么要领养?如果不领养,没有人回收子进程的退出状态,而一直处于僵尸状态,造成内存泄漏。被系统领养后子进程变为后台进程,只能用kill命令杀死子进程。


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值