mit6.S081实验环境的配置

Posted by LemonWhale on June 19, 2024

1. Ubuntu虚拟机配置实验环境

mit6.S081官网链接
CSDN
CSDN

  • 使用Ubuntu20.04,别的版本有可能有问题
  • 环境配置大约需要9GiB的空间
    1.1 安装RISC-V交叉编译工具
    1. 克隆RISC-V交叉编译工具的仓库到本地
      $ git clone --recursive https://github.com/riscv/riscv-gnu-toolchain
      
    2. 下载编译所需的工具包

      注意:不是Ubuntu20.04下载可能会有问题

      $ sudo apt-get install autoconf automake autotools-dev curl libmpc-dev libmpfr-dev libgmp-dev gawk build-essential bison flex texinfo gperf libtool patchutils bc zlib1g-dev libexpat-dev
      
    3. 配置并编译工具链
      $ cd riscv-gnu-toolchain
      $ ./configure --prefix=/usr/local
      $ sudo make
      $ cd ..
      
      1.2 编译 QEMU 5.1.0
    4. 下载并且解压QEME 5.1.0资源包
      $ wget https://download.qemu.org/qemu-5.1.0.tar.xz
      $ tar xf qemu-5.1.0.tar.xz
      
    5. 为riscv64-softmmu编译QEMU
      $ cd qemu-5.1.0
      $ ./configure --disable-kvm --disable-werror --prefix=/usr/local --target-list="riscv64-softmmu"
      $ make
      $ sudo make install
      $ cd ..
      
      1.3 测试环境是否配置成功

      ```Shell

      测试riscv64交叉编译工具

      $ riscv64-unknown-elf-gcc –version riscv64-unknown-elf-gcc (GCC) 10.1.0 …

测试qemu工具

$ qemu-system-riscv64 –version QEMU emulator version 5.1.0


#### 2. 运行xv6操作系统
[mit6.S081官网链接](https://pdos.csail.mit.edu/6.S081/2020/labs/util.html)
##### 2.1 下载实验压缩包并切换到util分支
```Shell
$ git clone git://g.csail.mit.edu/xv6-labs-2020
Cloning into 'xv6-labs-2020'...
...
$ cd xv6-labs-2020
$ git checkout util
2.2 编译并且运行xv6
$ make qemu
riscv64-unknown-elf-gcc    -c -o kernel/entry.o kernel/entry.S
riscv64-unknown-elf-gcc -Wall -Werror -O -fno-omit-frame-pointer -ggdb -DSOL_UTIL -MD -mcmodel=medany -ffreestanding -fno-common -nostdlib -mno-relax -I. -fno-stack-protector -fno-pie -no-pie   -c -o kernel/start.o kernel/start.c
...  
riscv64-unknown-elf-ld -z max-page-size=4096 -N -e main -Ttext 0 -o user/_zombie user/zombie.o user/ulib.o user/usys.o user/printf.o user/umalloc.o
riscv64-unknown-elf-objdump -S user/_zombie > user/zombie.asm
riscv64-unknown-elf-objdump -t user/_zombie | sed '1,/SYMBOL TABLE/d; s/ .* / /; /^$/d' > user/zombie.sym
mkfs/mkfs fs.img README  user/xargstest.sh user/_cat user/_echo user/_forktest user/_grep user/_init user/_kill user/_ln user/_ls user/_mkdir user/_rm user/_sh user/_stressfs user/_usertests user/_grind user/_wc user/_zombie 
nmeta 46 (boot, super, log blocks 30 inode blocks 13, bitmap blocks 1) blocks 954 total 1000
balloc: first 591 blocks have been allocated
balloc: write bitmap block at sector 45
qemu-system-riscv64 -machine virt -bios none -kernel kernel/kernel -m 128M -smp 3 -nographic -drive file=fs.img,if=none,format=raw,id=x0 -device virtio-blk-device,drive=x0,bus=virtio-mmio-bus.0

xv6 kernel is booting

hart 2 starting
hart 1 starting
init: starting sh
$

如果你使用ls命令,可以看到以下输出:

$ ls
.              1 1 1024
..             1 1 1024
README         2 2 2059
xargstest.sh   2 3 93
cat            2 4 24256
echo           2 5 23080
forktest       2 6 13272
grep           2 7 27560
init           2 8 23816
kill           2 9 23024
ln             2 10 22880
ls             2 11 26448
mkdir          2 12 23176
rm             2 13 23160
sh             2 14 41976
stressfs       2 15 24016
usertests      2 16 148456
grind          2 17 38144
wc             2 18 25344
zombie         2 19 22408
console        3 20 0

这些都是在系统初始化文件 mkfs 中的命令。
使用 Ctrl + p 可以打印每个进程的信息,如果现在使用可以看到有两个进程:一个是init,另一个是sh
退出系统:Ctrl + a x

3. 开始实验

3.1 加入第一个实验函数sleep
  1. 自己添加的函数需要添加到/user目录下
  2. Makefile文件中添加sleep.c的编译规则
UPROGS=\
	_cat\
	_cp\
	_echo\
	_forktest\
	_grep\
	_init\
	_kill\
	_ln\
	_ls\
	_mkdir\
	_rm\
	_sh\
	_wc\
	_zombie\
    _copy\   # 添加copy.c编译规则
  1. 重新编译xv6
    $ make qemu
    
    3.2 测试分数
  2. 全部测试
    $ make grade
    
  3. 测试当前函数
    $ ./grade-lab-util sleep
    $ make GRADEFLAGS=sleep grade
    

    以上两个命令的效果相同。

    提示:

如果运行命令 ./grade-lab-util sleep 报 /usr/bin/env: ‘python’: No such file or directory 错误,请使用命令 vim grade-lab-util,把第一行 python 改为 python3

另外:

如果系统没装 python3,请先安装 sudo apt-get install python3

参考:CSDN

3.3 使用git管理分支
# 初始化一个git仓库
$ git init
# 创建一个新分支
$ git branch <new-branch>
# 切换到某个分支
$ git checkout <branch-name>
# 将修改的文件全部添加到缓存区
$ git add .
# 将所有文件提交
$ git commit -m "something to say"
# 查看当前分支的提交记录
$ git log
# 合并分支到当前分支
$ git merge <branch-name>
# 展示某分支最新修改的内容
$ git show <branch-name>

** 注意:**新初始化的分支没有进行任何提交的时候分支不会显示

工作树:

git使用了工作树的概念,工作树是你正在处理的文件的本地副本。当子分支被创建的时候会继承创建子分支时当前分支的文件状态,但是在接下来的提交会和本子分支相关联。可以使用git show <branch-name:filename>来查看某个分支中某个文件的状态。

$ git checkout master
$ ls
init
$ git checkout test1
$ ls
init test1
$ git checkout -b test2
$ ls
init test1
$ git checkout master
$ git checkout -b test3
$ ls
init

由以上代码可以看出 master 分支中有 init 文件,test1 分支中有 inittest1 文件,test2test1 分支检出,而 test3master 分支检出,所以 test2 中包含了 test1 中所有文件的副本, test3 中包含了master 中所有文件的副本。