标签:
进程管理是所有操作系统的心脏所在。
1.进程就是处于执行期的程序以及它所包含的资源的总称。
2.线程是在进程中活动的对象。
3.进程提供两种虚拟机制:虚拟处理器和虚拟内存。
4.内核调度的对象是线程,而不是进程。
内核把进程的列表存放在叫做任务队列的双向循环链表中。链表中的每一项都是类型为task_struct的进程描述符结构,该结构定义在<linux/sched.h>文件中。
Linux通过slab分配器分配task_struct结构——能达到对象复用和缓存着色的目的。
用slab分配器动态生成task_struct,只需在栈底或者栈顶创建一个新的结构struct thread_info。
内核通过一个唯一的进程标识值PID来标识每个进程。PID是一个数,表示为pid_t隐含类型,实际上就是一个int类型,最大值默认设置为32768。
进程描述符中的state域是用来描述进程当前状态。
调整某个进程的状态,最好用set_task_state(task,state)函数。
功能:该函数将指定的的进程设置为指定的状态。
等价于
task -> state = state
陷入内核空间:从一个可执行文件载入到进程的地址空间执行。
进程只有通过接口才能陷入内核执行。
所有的进程都是PID为1的init进程的后代。
系统中的每一个进程必有一个父进程,可以拥有零个或多个子进程,拥有同一个父进程的进程叫做兄弟。
获得父进程的进程描述符: struct task_struct *my_parent = current->parent; 依次访问子进程: struct task_struct *task; struct list_head *list; list_for_each(list, ¤t->children) { task = list_entry(list, struct task_struct, sibling); /* task指向当前某个子进程*/ }
init进程的进程描述符是作为init_task静态分配的。
获取链表中的下一个进程: list_entry(task->tasks.next, struct task_struct, tasks) 获取链表中的前一个进程: list_entry(task->tasks.prev, struct task_struct, tasks) for_each_process(task)宏提供了依次访问整个任务队列的能力, struct task_struct *task; for_each_process(task) { /* 它打印出每个任务名称和PID*/ printk("%s[%d]\n", task->comm, task->pid); }
fork()通过拷贝当前进程创建一个子进程。
(子进程与父进程的区别仅在于PID,PPID和某些资源和统计量)
exec()负责读取可执行文件并将其载入地址空间开始运行。
写时拷贝是一种可以推迟甚至免除拷贝数据的技术,内核不复制整个进程地址空间,而是让父进程和子进程共享一个拷贝。
资源的复制只有在需要写入时才会进行,在此之前以只读方式共享。
do_fork定义在kernel/fork.c文件中,调用copy_process
创建进程的大概步骤: 1.fork()、vfork()、__clone()都根据各自需要的参数标志调用clone()。 2.由clone()去调用do_fork()。 3.do_fork()调用copy_process()函数,然后让进程开始运行。 4.返回do_fork()函数,如果copy_process()函数成功返回,新创建的子进程被唤醒并让其投入运行。
与fork()功能基本相同。
优点:
不拷贝父进程的页表项
vfork()系统调用的实现是通过向clone()传递一个特殊标志来进行的。
Linux把所有的线程都当做进程来实现。
clone(CLONE_VM | CLONE_FS | CLONE_SIGHAND, 0);
新建的进程和它的父进程就是线程。
clone(SIGHAND, 0);
vfork()的实现。
clone(CLONE_VFORK | CLONE_VM | SIGHAND, 0);
clone()参数标志决定新创建进程的行为方式和父子进程之间共享的资源种类。
内核线程没有独立的地址空间,只在内核空间进行。内核线程也只能由其他线程创建。
内核线程启动后就一直运行直到调用do_exit
进程终结时,内核必须释放它所占有的资源并告知父进程。
原因:
一般是来自自身,发生在调用exit()系统调用时。
释放进程描述符时,需要调用release_task()。
如果父进程在子进程之前退出,必须有机制来保证子进程能找到一个新的父亲,否则这些成为孤儿的进程就会在退出时永远处于僵死状态。
解决方法:
标签:
原文地址:http://www.cnblogs.com/bonjourvivi/p/5340542.html