77范文网 - 专业文章范例文档资料分享平台

xv6操作系统整体报告(4)

来源:网络收集 时间:2020-03-27 下载这篇文档 手机版
说明:文章内容仅供预览,部分内容可能不全,需要完整文档或者需要复制内容,请下载word后使用。下载word有问题请添加微信号:或QQ: 处理(尽可能给您提供完整文档),感谢您的支持与谅解。点击这里给我发消息

? ? ? ? cwd是进程运行时所处的当前目录;

context是切换进程需要维护的硬件寄存器内容;

tf是中断进程后,需要恢复进程继续执行所保存的寄存器内容; name保存了进程的名字(用于调试)。

进程在内存中的布局如下:

expandable heap (堆) fixed-size stack(栈) original data and bss(数据) Text (代码)

proc[NPROC]数组(在proc.c文件的11行)定义了xv6所能够支持的进程所需的相关数据,NPROC表示了xv6可支持进程个数。

cpu结构是记录计算机中所有CPU的相关信息:

struct cpu {

uchar apicid; // Local APIC ID

struct proc *curproc; // Process currently running. struct context context; // Switch here to enter scheduler struct taskstate ts; // Used by x86 to find stack for interrupt

struct segdesc gdt[NSEGS]; // x86 global descriptor table volatile uint booted; // Has the CPU started? int ncli; // Depth of pushcli nesting.

int intena; // Were interrupts enabled before pushcli? };

其中:

? apicid 代表此CPU的id编号;

? curproc是当前正在此CPU上运行的进程控制块; ? context[???];

? ts是Task state segment,用于在中断时找到栈[???]; ? gdt是此CPU的全局描述符表(GDT); ? booted表示是否此CPU已经启动了; ? ncli表示执行pushcli函数的次数; ? intena表示[???];

全局变量

进程数组

proc[NPROC]数组就是进程池。

进程池访问锁

proc_table_lock是一个spinlock是用来保护对进程池的临界区访问。

当前运行进程

curproc则是记录每个cpu当前运行的进程。

第一个进程

initproc是记录第一个创立的进程。这个进程十分特殊,它将托管所有没有父进程的进程(也就是父进程先于子进程结束)。

下一进程号

nextid是用来产生进程号的,在系统启动后会一直保持递增。

处理过程

与进程相关的处理函数集中在proc.c中,下面将依次介绍相关处理过程。

进程管理初始化

pinit过程仅仅是初始化proc_table_lock锁。

初始化用户进程init

userinit是初始化第一个用户进程init。其处理过程如下所示:

1. 156行调用copyproc函数创建一个新的进程,注意这里调用copyproc函数的参数是0,

这表示是第一个用户进程。由于是第一个进程,因此在copyproc中没有进行内存等相关结构的初始化;

2. 因 此156~173是对相关结构(包括内存、当前目录cwd、trapframe)进行初始化。注

意的是,161~162行将进程的段加上了用户态权限而不 是内核态权限;p->tf->eip = 0表示起始执行的地址为0地址。p->tf->esp = p->sz的含义是???

3. 174~176行是将第一个用户进程的代码(initcode.S)拷贝到新进程的内存中,然后把

进程名字指定为“initcode”,设置进程状态为RUNNABLE; 4. 178行把刚初始化好的进程控制块p赋值全局变量initproc。

创建子进程

在xv6中,可以通过sys_fork来复制父进程内容并创建一个新的子进程。其处理过程如下所示:

1. 11行调用copyproc函数创建一个新的进程,注意这里调用copyproc函数的参数是p,

这表示要复制父进程p的相关内容来创建子进程;

2. 把新创建的子进程状态设置为RUNNABLE,返回子进程的pid。注意这也是fork返回

后,确定是父进程还是子进程返回的一个标志。

复制进程

函数copyproc是对进程进行复制,用户进程通过sys_fork函数来调用copyproc函数,完成对父进程的进程控制块的复制;而userinit函数调用copyproc函数,完成对第一个用户态进程的创建。其处理过程如下所示: 1. 108~109行是分配出一个进程结构用于接下来的PCB复制; 2. 112~115行是给新的进程np开辟内核栈空间; 3. 116行是将其trapframe所占的空间放在内核栈栈顶,大小位sizeof(struct trapframe),但指针np->tf指向栈顶-sizeof(struct trapframe)的位置; 4. 如果p(即父进程)非空,119~121行将np的parent指向p,且把p中的状态复制到np中的栈结构中新分配的trapframe中; 5. 如果p(即父进程)非空,124行根据p的sz(进程空间大小)分配np的mem内存空间; 6. 如果p(即父进程)非空,131行把p的内存空间mem复制到np的内存空间mem; 7. 如果p(即父进程)非空,133~135行调用filedup函数复制父进程打开的文件给子进程np; 8. 如果p(即父进程)非空,136行调用idup函数复制父进程的当前目录给子进程np; 9. 139~142行是对新的进程的上下文进行设置。这个上下文就是其被第一次sheduler()运行的状态。为什么会将eip指向forkret呢?因为需要把scheduler中加上的锁给释放。同样新的进程是运行在自己的内核栈中,因此esp指向新分配的栈地址; 10. 144~145行是设置从系统调用返回的值,由于是运行fork产生的,因此其作为子进程的返回值应该为0。 进程结构的空间分配 allocproc是进行进程分配,也就是在进程池中找出一个状态为UNUSED的进程返回。选出来的进程状态变成EMBRYO。注意,在访问进程池时,都会加上proc_table_lock。 增加进程的地址空间 growproc是增加一个进程的内存,用户进程通过sbrk调用。xv6的内存管理十分简单。当要增大内存空间n时, 假设原内存空间为sz,xv6将首先尝试开辟一个为sz+n的空间(55~57行)。如果成功,则将原内存中的内容拷贝到新的内存空间中,然后把新空间清 零,最后释放原空间。(58~63行)。 设置内核空间和用户空间段描述符 setupsegs是对一个进程进行段描述符和task state进行设置。当传入的进程地址p为0时,这个进程是一个IDLE进程,只运行在内核态,并且是在初始化生成的。因此对于这个进程不需要用户段,而 TS中的esp0都是置成0xffffffff。 其中81~85是为当前CPU设置段描述符,包含内核段和TSS段。而87~88为用户端,段的基址和大小由当前进程决定。设置完成后,调用lgdt和 ltr进行加载。

调度进程

scheduler对每个CPU进行进程调度。CPU到没有运行用户进程时,就会进入这个过程中。这个过程不停的从进程中选出一个RUNNABLE的进程,然后运行这个进程(通过swtch.S中的swtch函数进行)。

[TODO]

sched是放弃当前的用户进程,进入scheduler()。只需用通过swtch进行上下文切换即可。

放弃CPU

yield是用户进程用来主动放弃当前CPU,进入scheduler()。因为进入scheduler需要加锁所以把proc_table_lock加上。

设置用户进程返回

forkret是用于新fork的进程进行返回地址用的。由于调用sys_fork创建的新进程是通过shceduler()调用的,因此运行之前需要把proc_table_lock锁释放。

睡眠进程

sleep功能是让进程休眠。首先获得proc_table_lock,然后将记录chan,也就是说只有相关的chan才能把其唤起。然后调用sched()。当期被唤醒是,将继续运行,此时将chan等记录清空,并且将proc_table_lock锁释放,而获得lk锁。

唤醒进程

wakeup功能是唤醒进程。先获取proc_table_lock,然后调用函数wakeup1,然后释放proc_table_lock。

wakeup1是将由于chan休眠的进程都唤醒,即把进程的状态由SLEEPING改成RUNNABLE。

杀死进程

kill的作用是杀死某个进程。只需要从进程池中找到拥有相应进程ID的进程,将其killed状态置1即可。如果目标进程出于sleeping状态则将其设置成RUNNABLE使其尽早被杀掉。

退出进程

exit的是用于用户进程退出。在退出之前,用户进程需要关闭打开的文件(351~356行),将打开的文件夹关闭(358~359)。同时唤醒父进程,因为其可能出于wait状态。并将其子进程托管于init。然后改变其状态为ZOMBIE(等待父进程进行回收)。最后调用sched放弃CPU。

等待进程结束

wait是用于父进程等待子进程结束只用的。做法是不断的循环知道找到一个子进程变成ZOMBIE状态,则释放ZOMBIE子进程(回收其资源),然后结束循环返回其子进程的进程ID。在循环的时候需要判断是否被外部进程Kill,或有无活跃子进程,如果被杀死或无活跃子进程,则推出循环。

进程上下文切换

在操作系统中通常也把上下文切换称为进程切换(process switch)。当操作系统决定运行另外的进程时,它需要保存当前正在运行进程的当前上下文(Context,也可称“运行状态信息”),即CPU寄存器中的全部内容。这些内容保存在进程的堆栈空间或特定的上下文保存区。完成保存工作后,操作系统就可以把下一个将要运行进程的当前上下文从该进程的栈或上下文保存区中恢复到CPU的寄存器中,这样就可以继续下一个进程的运行。这个过程叫做进程切换。一般有两种情况的上下文切换:

? 高优先级的进程因为需要某种临界资源,主动请求阻塞,让出处理器,此时将调度就

绪状态的低优先级进程获得执行。这种切换称为进程级的上下文切换。

进程因为时钟中断或其它中断到来而被打断,在中断服务例程处理完毕后,内核发现有更高优先级进程处于就绪态,则在中断处理结束后直接切换到高优先级进程执行。这种调度也称为中断级的上下文切换。

swtch.S

这个程序是进行上下文切换。9行获取指向old context的指针,然后11~18行将当前的

context存入。注意:eip是保留函数返回的下一个地址。接着取出new context的指针,将所有寄存器复原,然后将要运行的eip压入栈,利用ret切换到新的进程。注意,在切换回去后,新的进程仍处于内核态。

?

第六章 中断处理和系统调用 (trap & system call)

1.概述

本章将给出xv6中断处理和系统调用实现的概貌。读者将学习以下一些内容:

? 什么是中断? ? 什么是系统调用?

? 中断与系统调用有何关系? ? xv6如何处理中断?

? xv6的时钟中断处理有何特别的作用? ? 应用程序如何访问xv6的各种实现功能? ? xv6如何处理系统调用?

操作系统需要对计算机系统中的各种外设进行管理,这就需要CPU和外设能够相互通信才行。一般外设的速度远慢于CPU的速度。如果让操作系统通过CPU“主动关心”外设的事件,即采用通常的轮询(polling)机制,则太浪费CPU资源了。所以需要操作系统和CPU能够一起提供某种机制,让外设在需要操作系统处理外设相关事件的时候,能够“主动通知”操作系统,即打断操作系统和应用的正常执行,让操作系统完成外设的相关处理,然后在恢复操作系统和应用的正常执行。在操作系统中,这种机制称为中断机制。中断机制给操作系统提供了处理意外情况的能力,同时它也是实现进程/线程抢占式调度的一个重要基石。

在操作系统中,把三种特殊的中断事件。由CPU外部设备引起的外部事件如I/O中断、时钟中断、控制台中断等是异步产生的,与CPU的执行无关,我们称之为异步中断(asynchronous interrupt)也称外部中断,简称中断(interrupt)。而把在CPU执行指令期间检测到不正常的或非法的条件(如除零错、地址访问越界)所引起的内部事件称作同步中断(synchronous interrupt),也称内部中断,简称异常(exception)。把在程序中使用请求系统服务的系统调用而引发的事件,称作陷入中断(trap interrupt),也称软中断(soft interrupt),系统调用(system call)简称trap。在后面的叙述中,如果没有特别指出,我们将用简称中断、异常、陷入来表示这三种特殊的中断事件。

中断处理是xv6操作系统十分重要的一部分。系统调用是用户程序和内核通讯的途径。xv6处理了一些重要的硬件中断,包括时钟中断、硬盘中断和键盘中断。同时,xv6也提供了丰富的系统调用。

2.源码分析

trap.c

这个文件包含了xv6对不同的中断的处理过程以及中断表的初始化。

中断初始化

tvinit过程中主要是对idt表进行初始化。其中vectors中存放的是每个中断处理程序的入口地址。vectors的定义是在vectors.S中, 由一个perl程序vectors.pl生成。从22行到23可以看到,

百度搜索“77cn”或“免费范文网”即可找到本站免费阅读全部范文。收藏本站方便下次阅读,免费范文网,提供经典小说教育文库xv6操作系统整体报告(4)在线全文阅读。

xv6操作系统整体报告(4).doc 将本文的Word文档下载到电脑,方便复制、编辑、收藏和打印 下载失败或者文档不完整,请联系客服人员解决!
本文链接:https://www.77cn.com.cn/wenku/jiaoyu/894191.html(转载请注明文章来源)
Copyright © 2008-2022 免费范文网 版权所有
声明 :本网站尊重并保护知识产权,根据《信息网络传播权保护条例》,如果我们转载的作品侵犯了您的权利,请在一个月内通知我们,我们会及时删除。
客服QQ: 邮箱:tiandhx2@hotmail.com
苏ICP备16052595号-18
× 注册会员免费下载(下载后可以自由复制和排版)
注册会员下载
全站内容免费自由复制
注册会员下载
全站内容免费自由复制
注:下载文档有可能“只有目录或者内容不全”等情况,请下载之前注意辨别,如果您已付费且无法下载或内容有问题,请联系我们协助你处理。
微信: QQ: