【1.1】进程与线程

一、进程

  1. 进程的定义:进程是资源(CPU、内存等)分配的基本单位。处于执行期的程序。包括可执行程序代码,打开的文件,挂起的信号,内和内部的数据,处理器状态,具有内存映射的内存地址及多个执行线程。进程就是正在执行程序的实时结果。由三部分组成:PCB(进程控制块)、程序段和相关数据段。

  2. 进程的状态:在linux内核中,通常调用fork()系统的结果,通过复制一个现有进程来创建一个全新的进程。调用fork()的进程称为父进程,产生的进程为子进程(fork()系统调用从内核返回两次:一次回到父进程(子进程的PID),另一次回到新产生的子进程(返回0),fork()使用写时拷贝,不需要马上复制资源,使用vfork不拷贝页表项,先保证子进程先执行,一般直接调用exec函数)。接着调用exec()这组函数就可以创建新的地址空间,并把新的程序载入其中(新的程序从main函数开始执行)(进程创建:https://www.cnblogs.com/jacklu/p/5317406.html)。此时进程状态为TASK_RUNNIG(处于等待或者正在运行),当进程被抢占,仍处于TASK_RUNNIG状态,处于等待运行。当进程进入睡眠或者挂起 ,进程变为TASK_INTERRUPTIBEL(可唤醒)或TASK_UNINTERRUPTIBEL(深度睡眠)状态。当进程收到SIGSTOP或SIGTSTP信号进入TASK_STOPPED状态。程序通过exit()系统调用退出执行或者最后的线程调用pthread_exit(),这个函数会终结进程并将其占用的资源释放掉,此时进程进入EXIT_ZOMBIE僵尸态(ps -ef|grep defunc 找出僵尸进程)。进程还未真正的死亡,其“返回值”保存在该进程的进程控制模块中,等待父进程读取。父进程调用wait()(阻塞)或waitpid()(标志位选项)获取“死亡信息”,子进程状态为EXIT_DEAD死亡态,应及时调用,防止系统产生过多的僵尸进程。
  3. 孤儿进程:一个父进程退出,而它的一个或多个子进程还在运行,那么那些子进程将成为孤儿进程。孤儿进程将被 init 进程(进程号为 1)所收养,并由 init 进程对它们完成状态收集工作。
  4. 守护进程:它独立于控制终端并且周期性的执行某种任务或等待处理某些发生的事件。守护进程的创建:1、创建子进程,父进程退出。2、调用setsid创建新会话,成为新会话的首进程。3、改变当前目录为根目录,保证工作的文件目录不被删除;chdir(“/”)。4、重设文件权限掩码,给子进程更大的权限;umask(0)。5、关闭不用的文件描述符,因为会消耗资源;fdtablesize = getdtablesize();for (fd = 0; fd < fdtablesize; fd++){close(fd);}
  5. 进程上下文:当一个程序执行了系统调用或者触发了某个异常,它就陷入了内核空间。此时,我们称内核代表进程执行并处于上下文中。在进程上下文中,内核可以休眠并且可以被抢占。(相比中断上下文:1、不能睡眠或者放弃 CPU,2、不能尝试获得信号量,3、不能执行耗时的任务,4、不能访问用户空间的虚拟地址)。

二、线程

  1. 线程的定义线程是程序执行时的最小单位,它是进程的一个执行流,是 CPU 调度和分派的基本单位。线程间共享进程的所有资源,每个线程有自己的堆栈和局部变量。进程有自己的地址空间,线程共享地址空间
  2. 线程的创建:线程和进程的创建类似,只不过调用clone()的时候需要传递一些参数来指明需要共享的资源。(嵌入式有内核线程)。调用kthread_creat(),只是单独创建一个内核线程,需要调用wake_up_precess()唤醒通过kthread_run()可以实现创建并运行。直到调用do_exit()退出,或者其他部分调用khread_stop();

三、线程与进程区别

多线程的优点:

  • 无需跨进程边界;
  • 程序逻辑和控制方式简单; 
  • 所有线程可以直接共享内存和变量等;
  • 线程方式消耗的总资源比进程方式好;

多线程缺点

  • 每个线程与主程序共用地址空间,受限于 2GB 地址空间;
  • 线程之间的同步和加锁控制比较麻烦;
  • 一个线程的崩溃可能影响到整个程序的稳定性;
  • 到达一定的线程数程度后,即使再增加 CPU 也无法提高性能,例如Windows Server 2003,大约是 1500 个左右的线程数就快到极限了(线程堆栈设定为 1M),如果设定线程堆栈为 2M,还达不到 1500 个线程总数;线程能够提高的总性能有限,而且线程多了之后,线程本身的调度也是一个麻烦事儿,需要消耗较多的 CPU

进程优点:

  • 每个进程互相独立,不影响主程序的稳定性,子进程崩溃没关系;
  • 通过增加 CPU,就可以容易扩充性能;
  • 可以尽量减少线程加锁/解锁的影响,极大提高性能,就算是线程运行的模块算法效率低也没关系;
  • 每个子进程都有 2GB 地址空间和相关资源,总体能够达到的性能上限非常大

多进程缺点:

  • 逻辑控制复杂,需要和主程序交互;
  • 需要跨进程边界,如果有大数据量传送,就不太好,适合小数据量传送、
  • 密集运算
  • 多进程调度开销比较大;

 什么时候用进程什么时候用线程

进程与线程的选择取决以下几点:

  1. 需要频繁创建销毁的优先使用线程;因为对进程来说创建和销毁一个进程代价是很大的。
  2. 线程的切换速度快,所以在需要大量计算,切换频繁时用线程,还有耗时的操作使用线程可提高应用程序的响应。
  3. 因为对 CPU 系统的效率使用上线程更占优,所以可能要发展到多机分布的用进程,多核分布用线程。
  4. 并行操作时使用线程,如 C/S 架构的服务器端并发线程响应用户的请求。
  5. 需要更稳定安全时,适合选择进程;需要速度时,选择线程更好
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值