首页 > 其他分享 >lab3实验报告

lab3实验报告

时间:2023-03-14 16:47:05浏览次数:45  
标签:v0 sp sw t0 lab3 lw TF 实验报告

lab3实验报告

一、实验思考题

Thinking3.1

为了保证在envs中顺序与在Env块的顺序相同。

Thinking3.2

  • 低10位表示Env在envs中的位置,高位表示调用分配函数的次数。
  • 如果只有低位,

Thinking3.3

操作系统采用的布局没有真正的内核进程,用户可以通过临时变成内核态来获得内核空间的管理权限。所以保存boot_pgdir可以实现访问相应内核区域。

  • UTOP是用户可以使用空间的最高地址
  • ULIM往上是内核空间,是用户空间的最高地址,用户不能修改这之间的内存空间。

env_cr3存储进程页目录的物理地址,通过这条语句可以实现页目录自映射。

虚拟地址可以让各进程更加安全地运行在自己的空间,只关注于逻辑的地址,而不必考虑复杂的物理地址转换。物理地址是真实连续的内存空间地址。

Thinking3.4

user_data参数传递了信息

struct Env *env = (struct Env *)user_data;

如果没有这个参数就得不到页目录的信息,无法加载二进制镜像文件。

Thinking3.5

  • 内容不能完全填充满一页bin_size < BY2PG-offset
  • 内容填充满整个页面,但是结尾处不是整页,即 % BY2PG != 0
    bin_size >= BY2PG && (bin_size - BY2PG + offset) % BY2PG != 0
  • 内容填充满整个页面,且结尾处是BY2PG的整数倍。bin_size >= BY2PG && (bin_size - BY2PG + offset) % BY2PG == 0

segment size大于bin_size时需要自动填充.bss段。

Thinking3.6

虚拟空间,虚拟地址中指令可以认为是连续存放的,所以可以按照顺序执行指令,但如果是物理地址,则有可能是分散在内存空间中的。

每一个进程从elf文件中读取的entry_point相同,但储存的物理地址不同,从而能保护进程的内存空间。

Thinking3.7

设为epc的值,在处理程序运行完毕之后,需要返回中断异常发生的现场,正是epc所保存的位置。

Thinking3.8

TIMESTACK是发生时钟中断异常时,内核中保存保存现场所用的栈指针。

#include <asm/regdef.h>
#include <asm/cp0regdef.h>
#include <asm/asm.h>
#include <trap.h>

.macro STI
        mfc0    t0,     CP0_STATUS
        li      t1, (STATUS_CU0 | 0x1)
        or      t0, t1
        mtc0    t0, CP0_STATUS

.endm


.macro CLI
        mfc0    t0, CP0_STATUS
        li      t1, (STATUS_CU0 | 0x1)
        or      t0, t1
        xor     t0, 0x1
        mtc0    t0, CP0_STATUS
.endm

.macro SAVE_ALL

                mfc0    k0,CP0_STATUS
                sll             k0,3      /* extract cu0 bit */
                bltz    k0,1f
                nop
                /*
                 * Called from user mode, new stack
                 */
                //lui   k1,%hi(kernelsp)
                //lw    k1,%lo(kernelsp)(k1)  //not clear right now

1:
                move    k0,sp
                get_sp
                move    k1,sp
                subu    sp,k1,TF_SIZE
                sw      k0,TF_REG29(sp)
                sw      $2,TF_REG2(sp)
                mfc0    v0,CP0_STATUS
                sw      v0,TF_STATUS(sp)
                mfc0    v0,CP0_CAUSE
                sw      v0,TF_CAUSE(sp)
                mfc0    v0,CP0_EPC
                sw      v0,TF_EPC(sp)
                mfc0    v0, CP0_BADVADDR
                sw      v0, TF_BADVADDR(sp)
                mfhi    v0
                sw      v0,TF_HI(sp)
                mflo    v0
                sw      v0,TF_LO(sp)
                sw      $0,TF_REG0(sp)
                sw      $1,TF_REG1(sp)
                //sw    $2,TF_REG2(sp)
                sw      $3,TF_REG3(sp)
                sw      $4,TF_REG4(sp)
                sw      $5,TF_REG5(sp)
                sw      $6,TF_REG6(sp)
                sw      $7,TF_REG7(sp)
                sw      $8,TF_REG8(sp)
                sw      $9,TF_REG9(sp)
                sw      $10,TF_REG10(sp)
                sw      $11,TF_REG11(sp)
                sw      $12,TF_REG12(sp)
                sw      $13,TF_REG13(sp)
                sw      $14,TF_REG14(sp)
                sw      $15,TF_REG15(sp)
                sw      $16,TF_REG16(sp)
                sw      $17,TF_REG17(sp)
                sw      $18,TF_REG18(sp)
                sw      $19,TF_REG19(sp)
                sw      $20,TF_REG20(sp)
                sw      $21,TF_REG21(sp)
                sw      $22,TF_REG22(sp)
                sw      $23,TF_REG23(sp)
                sw      $24,TF_REG24(sp)
                sw      $25,TF_REG25(sp)
                sw      $26,TF_REG26(sp)
                sw      $27,TF_REG27(sp)
                sw      $28,TF_REG28(sp)
                sw      $30,TF_REG30(sp)
                sw      $31,TF_REG31(sp)
.endm
/*
 * Note that we restore the IE flags from stack. This means
 * that a modified IE mask will be nullified.
 */
.macro RESTORE_SOME
                .set    mips1
                mfc0    t0,CP0_STATUS
                ori     t0,0x3
                xori    t0,0x3
                mtc0    t0,CP0_STATUS
                lw      v0,TF_STATUS(sp)
                li      v1, 0xff00
                and     t0, v1
                nor     v1, $0, v1
                and     v0, v1
                or      v0, t0
                mtc0    v0,CP0_STATUS
                lw      v1,TF_LO(sp)
                mtlo    v1
                lw      v0,TF_HI(sp)
                lw      v1,TF_EPC(sp)
                mthi    v0
                mtc0    v1,CP0_EPC
                lw      $31,TF_REG31(sp)
                lw      $30,TF_REG30(sp)
                lw      $28,TF_REG28(sp)
                lw      $25,TF_REG25(sp)
                lw      $24,TF_REG24(sp)
                lw      $23,TF_REG23(sp)
                lw      $22,TF_REG22(sp)
                lw      $21,TF_REG21(sp)
                lw      $20,TF_REG20(sp)
                lw      $19,TF_REG19(sp)
                lw      $18,TF_REG18(sp)
                lw      $17,TF_REG17(sp)
                lw      $16,TF_REG16(sp)
                lw      $15,TF_REG15(sp)
                lw      $14,TF_REG14(sp)
                lw      $13,TF_REG13(sp)
                lw      $12,TF_REG12(sp)
                lw      $11,TF_REG11(sp)
                lw      $10,TF_REG10(sp)
                lw      $9,TF_REG9(sp)
                lw      $8,TF_REG8(sp)
                lw      $7,TF_REG7(sp)
                lw      $6,TF_REG6(sp)
                lw      $5,TF_REG5(sp)
                lw      $4,TF_REG4(sp)
                lw      $3,TF_REG3(sp)
                lw      $2,TF_REG2(sp)
                lw      $1,TF_REG1(sp)
.endm

.macro RESTORE_ALL
                RESTORE_SOME
                lw      sp,TF_REG29(sp)  /* Deallocate stack */
.endm

.set    noreorder
.macro RESTORE_ALL_AND_RET
                RESTORE_SOME
                lw      k0,TF_EPC(sp)
                lw      sp,TF_REG29(sp)  /* Deallocate stack */
                jr      k0
                rfe
.endm


.macro get_sp
        mfc0    k1, CP0_CAUSE
        andi    k1, 0x107C
        xori    k1, 0x1000
        bnez    k1, 1f
        nop
        li      sp, 0x82000000
        j       2f
        nop
1:
        bltz    sp, 2f
        nop
        lw      sp, KERNEL_SP
        nop

2:      nop


.endm

在这段代码中,.macro get_sp段中,先从CP0中读取信息,如果读到原因是4号中断,就把TIMESTACK的值存到sp中,保存上下文。与KERNEL_SP不同在于TIMESTACK栈指针保存了时钟产生的中断异常,而KERNEL_SP栈指针是非时钟中断异常时使用。

Thinking3.9

li t0, 0x01		// 把1存入$t0
sb t0, 0xb5000100	// 在0xb5000100地址中写入0x01
sw sp, KERNEL_SP	// 栈指针设置为KERNEL_SP
setup_c0_status STATUS_CU0|0x1001 0		// 调用宏函数设置CP0_STATUS的值
jr ra	// 返回

nop

Thinking3.10

设置进程就绪队列,每一个进程中添加一个时间片,从而起到计时的功能。当时间片用完后,该进程执行时钟中断操作,这个进程会被移动到就绪队列的队尾,并且复位时间片。之后让就绪队列的队首进程继续执行相应的时间片。循环此过程,做到了时钟周期切换进程。

二、实验难点图示

加载二进制镜像

  • load_icode,进行内存的分配,然后将二进制代码加载至已经分配好的内存中,这一步会调用load_elf
  • load_elf,首先解析ELF的结构,然后将ELF的内容复制到内存中,这一步会调用load_icode_mapper
  • load_icode_mapper,进行复制,需要将load_elf中返回的entry_point设置为正确的PC

中断

start.S中分发异常,开启时钟中断。

进程调度通过

  1. 设置两个队列
  2. 判断当前所在队列的队首进程的状态
    1. ENV_FREE,则移除
    2. ENV_NOT_RUNNABLE,加入另一个队列的尾部
    3. ENV_RUNNABLE,如果时间片用完,则复原时间片后插入另一个队列的尾部
  3. 如果当前队列为空,转到另一个队列。

进程地址空间

  • UTOP以下可操作
  • UVPT与用户进程页目录相关,需要用自映射机制进行单独处理。

三、体会与感想

本lab实验总体上内容比较多,课堂上有很多进程调度相关的算法,在这次lab中也实现了一个简单的时间片算法,首次深入体会操作系统如何管理进程。

遇到比较大的困难在于代码的理解和debug方面,要阅读相关的代码并且进行补充实现。在要实现的代码部分一般有比较详细的注释说明了核心用法、前置条件和后置条件,有些还有提示。但是自己在实现时可能还是有一些细节没有考虑足够,所以在实现时出现了bug。但由于调试手段相对匮乏,通过多个带标记的printf才将bug定位出来,最终成功修复bug。

  • 输出there is xxx定位代码运行位置
  • 输出关键的变量值

进程调度的算法是第二部分比较核心的内容,这部分相关的汇编代码理解比较重要,需要理解如何分发异常和处理中断。另外在很多函数中调用了lab2中的内存相关的函数,对于复杂的函数,应该尽量考虑全面,操作系统各个部分联系在一起,所以如果漏掉某种情况,就很可能在其他部分出现一些错误,给debug的工作带来一定困难。

标签:v0,sp,sw,t0,lab3,lw,TF,实验报告
From: https://www.cnblogs.com/ddl789/p/17215428.html

相关文章

  • lab4实验报告
    lab4实验报告一、实验思考题Thinking4.1保存现场过程中改写非通用的寄存器,SAVE_ALL将所有通用寄存器的值存入栈中。一些其他的寄存器,如k0存储sp的值,k1存储帮助sp更新值,v......
  • lab6实验报告
    lab6实验报告一、实验思考题Thinking6.11#include<stdlib.h>2#include<unistd.h>34intfildes[2];5/*bufsizeis100*/6charbuf[100];7intstatus;8......
  • lab5实验报告
    lab5实验报告一、实验思考题Thinking5.1/proc是一种由软件创建的特殊的伪文件系统,通过特殊的接口来访问内核。每一个文件对应于内核中的函数,其中大部分文件时只读的,但可......
  • python学习-第三方库综合程序设计实验报告
    目录实验四: Python综合程序设计实验名称:Python综合程序设计              指导教师:      实验日期:2022年 12 月 5 日......
  • Lab3
    Lab3主要是实现一个容错的KV数据库,并用Lab2的Raft服务,在每台运行Raft的peer上构建一个状态机.3A跟着课程提示一步步走,补全client.go中的sendRPC和server.go中的处理......
  • 实验报告
    一.实验目的解析SSM框架?2.SpringBoot框架功能特性?3.SpringBoot工作生命周期?4.SSM框架和SpringBoot框架的对比?5.Maven框架的jar管理方式? 二.......
  • NEMU PA 4 实验报告
    一、实验目的在前面的PA123中,我们分别实现了基本的运算单元,实现了各种指令和程序的装载,实现了存储器的层次结构。而在PA4中,为了让NEMU可以处理异常情况以及和外设交互,我们......
  • NEMU PA 3-3 实验报告
    一、实验目的在上一章PA3-2中,我们实现了分段机制,将48位的虚拟地址vaddr转换成了laddr。为什么不是paddr呢?这就要说到这一章要完成的东西:**分页机制**。从80386开始,计算......
  • NEMU PA 3-2 实验报告
    一、实验目的在上一章节我们完成了Cache的实现,但是这只是在速度上提高了取指和存取操作数的效率,而在访问的安全性上没有得到有效提升。在PA3-2中我们要完成的,就是在NEMU......
  • NEMU PA 3-1 实验报告
    一、实验目的在前面的PA1中,我们实现了CPU和FPU,在PA2中我们实现了对指令的解码和对ELF的装载,以及进一步完善了CLI调试器。那么在整个PA3中,我们将要着力于内存的相关处理,如C......