进程控制块(PCB)结构

2019-07-14 06:17发布

一、进程控制块(PCB)结构 进程控制块(PCB)是系统为了管理进程设置的一个专门的数据结构。系统用它来记录进程的外部特征,描述进程的运动变化过程。同时,系统可以利用PCB来控制和管理进程,所以说,PCB(进程控制块)是系统感知进程存在的唯一标志。  Linux系统的PCB包括很多参数,每个PCB约占1KB多的内存空间。用于表示PCB的结构task_struct简要描述如下: 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 include/linux/sched.h struct task_struct {  volatile long state;  struct thread_info *thread_info;  atomic_t usage; unsigned long flags; unsigned long ptrace;    int lock_depth;    int prio, static_prio;  struct list_head run_list;  prio_array_t *array;    unsigned long sleep_avg;  long interactive_credit;  unsigned long long timestamp;  int activated;    unsigned long policy;  cpumask_t cpus_allowed;  unsigned int time_slice, first_time_slice;   struct list_head tasks;  struct list_head ptrace_children;  struct list_head ptrace_list;    struct mm_struct *mm, *active_mm; ...  struct linux_binfmt *binfmt;  int exit_code, exit_signal;  int pdeath_signal; ...  pid_t pid;  pid_t tgid; ... struct task_struct *real_parent; struct task_struct *parent; struct list_head children;  struct list_head sibling;  struct task_struct *group_leader; ...  struct pid_link pids[PIDTYPE_MAX];    wait_queue_head_t wait_chldexit;  struct completion *vfork_done;  int __user *set_child_tid;  int __user *clear_child_tid;    unsigned long rt_priority;  unsigned long it_real_value, it_prof_value, it_virt_value;  unsigned long it_real_incr, it_prof_incr, it_virt_incr;  struct timer_list real_timer;  unsigned long utime, stime, cutime, cstime;  unsigned long nvcsw, nivcsw, cnvcsw, cnivcsw;  u64 start_time; ...  uid_t uid,euid,suid,fsuid;   gid_t gid,egid,sgid,fsgid;  struct group_info *group_info;  kernel_cap_t cap_effective, cap_inheritable, cap_permitted;  int keep_capabilities:1;  struct user_struct *user; ...  struct rlimit rlim[RLIM_NLIMITS];  unsigned short used_math;  char comm[16]; ...  int link_count, total_link_count; ...  struct fs_struct *fs; ...  struct files_struct *files; ...  unsigned long ptrace_message;  siginfo_t *last_siginfo; ...  }; 调度数据成员: 1) vo latile long state
表示进程的当前状态。进程运行时, 它会根据具体情况改变状态。进程状态总共有TASK RUNN ING ( 可运行状态)、TASK INTERRUPT IBLE ( 可中断的等待状态)、TASK UNINTERRUPT IBLE(不可中断的等待状态)、TASK ZOMB IE( 僵死状态)、TASK STOPPED(暂停状态) 等5种。 2) long pr io rity进程优先级, prio rity 的值给出了进程每次获取CPU 后, 可使用的时间片长度( 单位是jiffies)。 3) unsigned long rt_priority rt_priority 的值给出了实时进程的优先级, rt_priority 
1000给出进程每次获取CPU 后, 可使用的时间片长度(单位是jiffies)。 4) long counter在轮转法调度时counter表示当前进程还可运行多久。在进程开始时被赋为priority的值, 以后每隔一个时钟中断递减1,减到0时引起新一轮调度。 5) unsigned long policy表示该进程的进程调度策略。调度策略有: SCH ED_OTHER 0, 非实时进程, 用基于优先权的轮转法。 SCH ED_FIFO 1, 实时进程, 用先进先出算法。
SCH ED_RR 2, 实时进程, 用基于优先权的轮转法   进程队列指针: 1) struc t task_struct* next_task, * prev_task
在Linux 中所有进程(以PCB 的形式)组成一个双向链表,
next_task和prev_task是链表的前后向指针。 2) struct task_struct* p_opptr, * p_pptr
struct task_struc t* p_cptr, * p_ysptr, * p_osptr
以上分别是指向该进程的原始父进程、父进程、子进程和新
老兄弟进程的指针。 3) struct task_struct* pidhash_next
struct task_struct** pidhash_pprev
用于链入进程hash表的前后指针。系统进程除了链入双
向链表外, 还被加到hash表中。   进程标识: uid_t uid  gid_t gid uid和gid分别是运行进程的用
户标识和用户组标识。 pid_t pid  pid_t pgrp pid和pgrp分别是运行进程的
进程标识号和进程组标识号 时间数据成员: long per_cpu_utime [ NR_CPUS ] per_cpu_stime
[ NR_CPUS]
per_cpu_utime 是用户态进程运行的时间, per_cpu_
stime是内核态进程运行的时间 进程创建时间unsigned long start_time
文件系统数据成员: struct fs_struct* fs
fs保存了进程本身与VFS( 虚拟文件系统)的关系信息。
struct fs_struct
{
 atom ic_t count;
 rw lock_t lock;
 int umask;
 struct dentry* root, * pwd, * altroot;
 struct vfsm ount* rootmnt, * pwdmnt, * altrootmnt;
}
其中root、rootm nt是根目录的dentry 和其mount点的vfsmount。
pwd、pwdmnt 是当前工作目录的dentry 和其mount 点的vfs..
mount。altroot、altrootmnt是保存根节点被替换之后原来根目标
的dentry和其mount点的vfsmount。   内存数据成员: 1) struct mm_struct* mm
在Linux 中, 采用按需分页的策略解决进程的内存需求。
task_struct的数据成员mm 指向关于存储管理的mm_truc t结
构。 2) struct mm_struct* active_mm
active_mm 指向活动地址空间。 3) mm_segm ent_t addr_ lim it
表示线程空间地址。
用户线程空间地址: 0..0xBFFFFFFF。
内核线程空间地址: 0..0xFFFFFFFF 4) spinlock_t alloc_ lock
用于申请空间时用的自旋锁。自旋锁的主要功能是临界区
保护。   页面管理: 1) int swappable: 1
进程占用的页面是否可换出。swappab le为1表示可换出。
2) unsigned long min_flt, maj_ flt
该进程累计minor缺页次数和major缺页次数。
3) unsigned long nswap
该进程累计换出页面数。
4) unsigned long swap_cnt
下一次循环最多可换出的页数。   二、makefile makefile定义了一系列的规则来指定,哪些文件需要先编译,哪些文件需要后编译,哪些文件需要重新编译,甚至于进行更复杂的功能操作,makefile带来的好处就是——“自动化编译”,一旦写好,只需要一个make命令,整个工程完全自动编译,极大的提高了软件开发的效率。make是一个命令工具,是一个解释makefile中指令的命令工具. Makefile来告诉make命令如何编译和链接这几个文件。规则是:
1)如果这个工程没有编译过,那么我们的所有C文件都要编译并被链接。
2)如果这个工程的某几个C文件被修改,那么我们只编译被修改的C文件,并链接目标程序。
3)如果这个工程的头文件被改变了,那么我们需要编译引用了这几个头文件的C文件,并链接目标程序。
下面举一个简单的例子:(进度条的实现) 1.vim proc.c写入(进度条的实现)  2、vim Makefile写入   第一行中并没有任何参数,只是在冒号(:)后列出编译中所需的文件,当第一行中的任何文件中更改时,make就知道需要重新编译了。 其中.PHONY意思表示clean是一个“伪目标”,清除 所有 .o文件 ,.o文件就是目标文件 3、执行make指令就可以编译proc.c这个程序