进程与多进程实现

进程的简单介绍

程序是什么,进程是什么,二者的区别又是什么——

        程序是存放在磁盘的可执行文件——也就是一系列的指令集合,而进程可以说是被加载到内存的程序,是程序的一次执行过程——同一程序可能会有多个进程执行。也就是说程序是静态的,进程是动态的。

进程的组成——

        进程是由内核数据结构和进程对应的磁盘代码组成的。在Windows下,这个内核数据结构是PCB(Process Control Block);在Linux下,这个内核数据结构是task_struct,本文围绕Linux讨论。当进程被创建时,操作系统会为该进程分配一个唯一的,不重复的ID号——PID(Process ID).

进程的状态

        在操作系统中,一个CPU有且仅有一个运行队列——本质上是将该进程的内核数据结构放入运行队列中,进程状态的本质是进程内部的属性——内核数据结构的数据(如:1代表R,2代表T)。

下面是Linux中的具体状态STAT:

R:running,但并不是一个进程正在运行才是运行态,而是这个进程处于运行队列。

S:sleeping,浅度睡眠,当一个进程没有在等待IO操作,而是在等待某种条件满足(如信号或锁),这种状态下的进程是可以被信号中断的,在系统调度器看来,处于该状态下的进程一旦等待条件满足,就可以被唤醒并重新调度执行。

D:disk sleep也可以称为uninterruptible sleep;深度睡眠状态或不可中断睡眠状态;该进程通常是在等待某些无法被中断的系统调用完成(如等待IO操作),也就是说处于该状态下的进程无法被中断——甚至是系统级别的中断(以避免可能导致的系统不一致状态),只能通过断电或者是该进程醒来自己中断。

T:stopped或者是traced stop,意味着进程要为收到某些停止信号而停止运行,要么就是该进程正在被调试工具追踪(tracing);在该状态下的进程完全暂停,不消耗CPU时间,等待外部干预使其恢复到可运行状态。不同于S状态的是,T状态是完全冻结——只有特定的信号才能使其恢复(如SIGCONT,属于SIGKILL的kill指令无法中断);S状态更像是在等待某些条件达成,且允许进程在等待过程中被外界信号唤醒。

Z:zombie,僵尸进程——defunct;当前进程结束后会进入该状态——直到其父进程或操作系统(init进程,PID为1)读取到该进程状态信息对其进行释放。一般情况下是父进程对其进行回收,但如果父进程先于子进程中断,该子进程的父进程就会被替换成1,且这个子进程会变为后台进程(后面会详细介绍)。值得一提的是——该状态下的进程无法响应任何信号,因为它已经defunct。

X:dead,该进程已经中断且资源被回收,这个应该不用赘述了。

不可见的挂起态:如果一个进程处于等待队列(内核数据结构仍处于内存),但处于内存压力,其代码和数据放在内存

注:Linux下,内存压力非常大时——挂起也无法解决(此时操作系统已经处于崩溃边缘),系统会自动kill部分进程。

前台进程与后台进程:一个进程在运行时,shell无法再获取命令,但这个进程可以被Ctrl c 中断,那么这个进程就是前台进程(STAT后面带加号+的进程);与之相反,shell可以获取指令,且Ctrl c无法关闭,不带加号+的进程自然就是后台进程了。

相应指令:ps ajx——查看所有进程

                  ps ajx | head - 1——显示第一行,也就是相应数据的名称(多为缩写)

有了以上指令,我们就可以利用管道提前并查看相应进程的信息了——

ps ajx | head - 1 && ps ajx | grep "process name"

kill -l  ——查看所有信号

kill -9 PID ——中断相应进程

kill -19 PID——暂停相应进程

多进程

介绍一个库函数fork,头文件为unistd.h,具体作用是创建一个子进程,详细介绍我就直接把Linux Programer's Manual 中重要的返回值部分拷过来了:

  On  success,  the  PID  of the child process is returned in the parent, and 0 is returned in the
       child.  On failure, -1 is returned in the parent, no child process is created, and errno is  set
       appropriately.

利用这个返回值,我们便能简单实现一个多进程程序

#include <stdio.h>
#include <unistd.h>
#include <sys/types.h> // Include this for pid_t

int main() 
{
    pid_t re = fork();

    if (re > 0) 
    { // Parent process
        while (1) 
        {
            printf("I am a parent process\n");
            sleep(5);
        }
    } 
    else if (re == 0) 
    { // Child process
        while (1) 
        {
            printf("I am a child process\n");
            sleep(5);
        }
    } 
    else 
        {
            return 1;
        }

    return 0;
}


 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值