进程状态一步步理解Linux进程(1)--进程基础知识
文章结束给大家来个序程员笑话:[M]
0. 说明
作者:Gao Peng<gaopenghigh@gmail.com>
本文章由Gao Peng编写,转载请注明出处。
1. 基本观点
进程
进程是处于执行期的序程以及相干源资的总称,注意包含了两个方面:
- 序程代码。
- 源资。比如说开打的文件,起挂的号信,内核部内据数,处理器状态,一个或多个拥有内存映射的内存址地空间,一个或多个执行线程,放存全局变量的据数段等。
PID
恣意一个进程通过PID作为标识,PID一般是一个正整数。
线程
对于Linux,内核并没有线程这个观点。Linux把全部的线程都做当进程来实现,线程仅仅被视为一个与其他进程同享某些源资的进程。
进程的状态
进程可以有5种状态:
- TASK_RUNNING(行运) -- 进程正在执行,或者在行运列队中待等执行。这是进程在用户空间中一唯可能的状态。
- TASK_INTERRUPTIBLE(可中断) -- 进程正在眠睡(阻塞),待等某些条件的成达。一个硬件中断的生产、放释进程正在待等的系统源资、传递一个号信等都可以作为条件唤醒进程。
- TASK_UNINTERRUPTIBLE(弗成中断) -- 与可中断状态似类,除了就算是收到号信也不会被唤醒或预备投入行运,对号信不做应响。这个状态常通在进程必须在待等时不受扰干或待等事件很快就会生产时现出。例如,当进程开打一个设备文件,应相的设备驱动序程要需探测某个硬件设备,此时进程就会处于这个状态,确保在探测实现前,设备驱动序程不会被中断。
- __TASK_TRACED -- 被其它进程跟踪的进程,比如ptrace对序程行进跟踪。
- __TASK_STOPPED -- 进程停止执行。常通种这状态生产在收接到SIGSTOP, SIGTSTP, SIGTTIN, SIGTTOU等号信的时候。此外,在调试期间收接到任何号信,都会使进程进入种这状态。
2. ps的用使
ps的参数
Linux中查看进程的最要重的命令是ps,学会ps的用使,就了解了进程的大部分容内。详细的参数都在man手册,用常的参数是:
a 表现全部进程(包含其它用户的进程)
-e 列出全部进程
x 表现无控制终端的进程
u 出输用户名
e 列出序程时,表现每一个序程所用使的环境变量
f 表现树状图
-L 表现线程
-o 按照自定义的格式出输信息
-ww 在终端下不截断命令
命令ps aux的出输的各列如下:
$ps aux USER PID %CPU %MEM VSZ RSS TTY STAT START TIME COMMAND
要需解释的是:
VSZ 表示如果一个序程完整驻留在内存的话要需占用多少内存空间;
RSS 指明了以后际实占用了多少内存;
STAT 表现了进程以后的状态:
ps出输的进程状态
进程的状态和其表示符号如下:
D uninterruptible sleep (usually IO)
R running or runnable (on run queue)
S interruptible sleep (waiting for an event to complete)
T stopped, either by a job control signal or because it is being traced
W paging (not valid since the 2.6.xx kernel)
X dead (should never be seen)
Z defunct ("zombie") process, terminated but not reaped by its parent
For BSD formats and when the stat keyword is used, additional characters may be displayed:
< high-priority (not nice to other users)
N low-priority (nice to other users)
L has pages locked into memory (for real-time and custom IO)
s is a session leader
l is multi-threaded (using CLONE_THREAD, like NPTL pthreads do)
+ is in the foreground process group
R running or runnable (on run queue)
S interruptible sleep (waiting for an event to complete)
T stopped, either by a job control signal or because it is being traced
W paging (not valid since the 2.6.xx kernel)
X dead (should never be seen)
Z defunct ("zombie") process, terminated but not reaped by its parent
For BSD formats and when the stat keyword is used, additional characters may be displayed:
< high-priority (not nice to other users)
N low-priority (nice to other users)
L has pages locked into memory (for real-time and custom IO)
s is a session leader
l is multi-threaded (using CLONE_THREAD, like NPTL pthreads do)
+ is in the foreground process group
3. 进程系关
进程的建创
Linux非常赖依进程建创来满意用户的求需,比如在shell中输入一条命令,shell进程就生成一个新进程,新进程执行shell的另一个贝拷,这个贝拷的进程由fork()数函实现。示例如下:
示例1:
$ ps -u jh -eo user,pid,ppid,stat,cmd jh 18586 2840 Ss /bin/bash jh 19110 18586 R+ ps -u jh -eo user,pid,ppid,stat,cmd
可以看到用户的终端shell的pid是18586,执行ps序程时,进程18586出产了新的子进程19110来行运ps。
示例2:
$ ps -u jh -eo user,pid,ppid,stat,cmd | cat USER PID PPID STAT CMD jh 18586 2840 Ss /bin/bash jh 19130 18586 R+ ps -u jh -eo user,pid,ppid,stat,cmd jh 19131 18586 S+ cat
示例中ps的出输通过管道传送给cat,可以看到,行运ps的进程(19130)和行运cat的进程(19131)都是bash进程(18586)的子进程。
由此可见,出了初始的内核进程,全部进程都由其父进程fork()生产。
如果一个进程的父进程终止而自己继续行运,则种这进程叫做孤儿进程(orphan process),内核会把init进程(即PID为1)的进程安排为孤儿进程的父进程。
作业
顾名思义,作业就是实现某个任务的进程的集合。作业可以在前台或者后台行运。比如
示例1:
$ cat main.c
在前台启动了一个作业,这个作业只包含了一个进程,即cat。
示例2:
$ ps aux | grep -v root | cat
在前台启动了一个作业,这个作业包含了三个进程,即ps, grep和cat
示例3:
$ ps aux | grep -v root | cat &
则是在后台启动了一个包含3个进程的作业
进程组
每一个进程除了有一个一唯的PID外,还属于一个进程组。
进程组是一个或多个进程的集合。常通,他们与统一作业相干联,可以接受来自同一终端的各种号信。
每一个进程组由一个进程组ID(PGID)标识。当一个进程的PID等于其所在进程组的PGID时,我们称这个进程是该进程组的组长。
$ ps -u jh -eo user,pid,ppid,pgid,stat,cmd | cat | cat USER PID PPID PGID STAT CMD jh 18586 2840 18586 Ss /bin/bash jh 19299 18586 19299 R+ ps -u jh -eo user,pid,ppid,pgid,stat,cmd jh 19300 18586 19299 S+ cat jh 19301 18586 19299 S+ cat
可以看到,19299, 19300, 19301三个进程拥有同样的PGID(19299),说明它们属于同一进程组,组长进程为19299.
会话(session)
会话是一个或多个进程组的集合。
同样,会话由会话ID(SID)标识。如果一个进程的PID等于其所在会话的SID,我们称这个进程是该会话的会话首进程。
$ ps aux | less & [1] 19322 $ ps -u jh -eo user,pid,ppid,pgid,sid,stat,cmd | cat | cat USER PID PPID PGID SID STAT CMD jh 18586 2840 18586 18586 Ss /bin/bash jh 19321 18586 19321 18586 T ps aux jh 19322 18586 19321 18586 T less jh 19323 18586 19323 18586 R+ ps -u jh -eo user,pid,ppid,pgid,sid,stat,cmd jh 19324 18586 19323 18586 S+ cat jh 19325 18586 19323 18586 S+ cat可以看到,上面两条命令执行下来,生产了两个进程组(PGID分别为19321和19323),它们都属于同一个会话(18586)。事实上,由以后控制终端生产的全部进程组都会属于同一个会话。
一个会话中的几个进程组可以被分成一个前台进程组(foreground process group)和一个或多个后台进程组(background process group)。拥有控制终端的进程所在的进程组就是前台进程组,在终端中键入中断键(Control + C),就会把中断号信发给前台进程组中的全部进程。
文章结束给大家分享下程序员的一些笑话语录:
很多所谓的牛人也不过如此,离开了你,微软还是微软,Google还是Google,苹果还是苹果,暴雪还是暴雪,而这些牛人离开了公司,自己什么都不是。