Git Product home page Git Product logo

gem5-fs-handbook's Introduction

gem5 FS模式实验手册

基于v22.0.0.1版本的gem5 Full System(FS)模式实验手册

由于gem5的主分支更新很快,但各ISA未必跟上主分支的更新,导致出现连教程都无法运行的情况,所以我写了这份基于v22.0.0.1版本的实验手册;这个版本解决了RISC-V的RVC指令的性能问题,非常适合做RISC-V的FS模式的实验。

编译安装gem5

环境准备

  • 根据Building gem5准备环境
  • 自行安装RISC-V工具链,从源码编译或用apt安装均可

获取代码

  • clone本仓库
    $ git clone https://github.com/lshpku/gem5-fs-handbook.git
  • 获取gem5源代码,clone时不checkout以加快速度
    $ git clone --no-checkout https://github.com/gem5/gem5.git
  • checkout正确的分支 警告:本手册严格基于v22.0.0.1版本的gem5编写,使用其他版本出现问题概不负责!
    $ cd gem5
    $ git checkout v22.0.0.1

打patch

  • v22.0.0.1版本的HiFive.py板子新增了PCI设备,但它的配套脚本(fs_linux.py)并不支持这一设备
  • 开发者又提供了一个新的板子(riscv_board.py)和脚本(riscv-fs.py),但新的脚本非常不完善,连基本的命令行参数都没有
  • 我提供了一个patch,可以移除HiFive.py中PCI的部分,这样就可以用原来的脚本了
  • 使用如下命令应用patch
    $ cd gem5
    $ git apply ../gem5-fs-handbook/remove-pci.patch

编译

  • 使用SCons编译,实测在24核的机器上用时10分钟
    $ python3 `which scons` build/RISCV/gem5.opt -j`nproc`

SE模式

本节首先测试一下Syscall Emulation(SE)模式是否正常

Hello World

  • 编译gem5自带的Hello World 注:SE模式务必使用-static编译
    $ cd gem5
    $ riscv64-unknown-elf-gcc tests/test-progs/hello/src/hello.c -static -o hello
  • 使用se.py脚本运行,gem5输出较多,这里只截取部分
    $ build/RISCV/gem5.opt configs/example/se.py -c hello
    # gem5 Simulator System.  https://www.gem5.org
    # ...
    # **** REAL SIMULATION ****
    # build/RISCV/sim/simulate.cc:194: info: Entering event queue @ 0.  Starting simulation...
    # Hello world!
    # Exiting @ tick 1056500 because exiting with last active thread context

输出动态指令流信息

  • gem5自带的DPRINTF功能可以输出系统中各个组件(包括流水线、内存系统等)的动态信息,DPRINTF默认是关闭的,需使用--debug-flags开启
  • 例如,下面开启程序的动态PC流输出,写到m5out/debug.log.gz文件中 注:--debug-file的路径含有一个隐式前缀m5out/
    $ build/RISCV/gem5.opt \
      --debug-flags=ExecEnable,ExecUser,ExecKernel \
      --debug-file=debug.log.gz \
      configs/example/se.py \
      --cmd=hello
  • 为了节约磁盘空间,我们使用压缩格式记录输出,可以使用如下命令查看前10行输出
    $ gzip -dc m5out/debug.log.gz | head -10
    #  500: system.cpu: 0x10116    : auipc gp, 4                :
    # 1500: system.cpu: 0x1011a    : addi gp, gp, -638          :
    # 2500: system.cpu: 0x1011e    : addi a0, gp, 1912          :
    # 3500: system.cpu: 0x10122    : auipc a2, 4                :
    # 4500: system.cpu: 0x10126    : addi a2, a2, 1398          :
    # ...
  • 更多的--debug-flag可以用下面的命令查看
    $ build/RISCV/gem5.opt --debug-help
    # ...
    # Compound Flags:
    #     AnnotateAll: All Annotation flags
    #         Annotate, AnnotateQ, AnnotateVerbose
    #     CacheAll:
    #         Cache, CacheComp, CachePort, CacheRepl, CacheVerbose,
    #         HWPrefetch, MSHR
    # ...

输出性能计数器

  • 若我们并不关心每条动态指令,只是想知道整个程序最终的运行情况,可以用gem5的性能计数器功能
  • gem5的性能计数器默认是开启的,例如运行下面的命令
    $ build/RISCV/gem5.opt configs/example/se.py \
      --cpu-type=O3CPU \
      --bp-type=TAGE_SC_L_64KB \
      --caches --l2cache \
      --cmd=hello
  • 就可以在m5out/stats.txt中看到整个程序最终的性能计数器的值
    $ cat m5out/stats.txt
    # ...
    # system.cpu.numCycles       13156  # Number of cpu cycles simulated (Cycle)
    # system.cpu.committedInsts   1760  # Number of Instructions Simulated (Count)
    # system.cpu.instsIssued      2665  # Number of instructions issued (Count)
    # ...

FS模式:启动Linux

本节介绍如何使用FS模式启动一个最基本的操作系统

编译m5term

  • m5term是gem5自带的用于连接控制台的小程序,直接编译即可
    $ cd gem5/util/term
    $ make CFLAGS=-O3

获取RISC-V内核与磁盘镜像

  • 进入网页RISCV Full System
  • 下载Bootloader:bootloader-vmlinux-5.10
    • 注:不是下载Kernel,只有Kernel无法启动,必须下载内嵌了Kernel的Bootloader
  • 下载Disk Image:riscv-disk.img.gz,然后解压
    $ gzip -cd riscv-disk.img.gz > riscv-disk.img
  • 假设你将bootloader-vmlinux-5.10riscv-disk.img放在和gem5/同一级目录下,如下所示
    $ ls
    # gem5/
    # gem5-fs-handbook/
    # bootloader-vmlinux-5.10
    # riscv-disk.img

修改磁盘镜像

如果你有sudo权限(Podman里的不算)

  • mount配合loop挂载,假设挂载到/mnt/rootfs目录
    $ sudo mkdir -p /mnt/rootfs
    $ sudo mount -o loop riscv-disk.img /mnt/rootfs
  • 拷贝benchmark,以hello为例
    $ cp gem5/hello /mnt/rootfs/root
  • 卸载
    $ sudo umount /mnt/rootfs

如果你没有sudo权限,但是有Podman

  • 启动一个Podman容器,假设你将工作目录映射到/mnt
    $ podman run -it -v $(pwd):/mnt ubuntu:20.04
  • 安装e2tools工具
    $ apt update
    $ apt install e2tools
  • 拷贝benchmark,以hello为例
    $ cd /mnt
    $ e2cp -p gem5/hello riscv-disk.img:/root

其他命令

  • 如果你的benchmark较大,可以对镜像扩容,例如扩容到300M 注:如果你已经用mount挂载了镜像,务必先卸载再扩容;用e2tools不存在此问题
    $ e2fsck -f riscv-disk.img
    $ resize2fs riscv-disk.img 300M

启动系统并使用m5term连接

  • 在其中一个窗口启动gem5,记住如下所示的port号(这里是3456
    $ cd gem5
    $ build/RISCV/gem5.opt configs/example/riscv/fs_linux.py \
      --kernel=../bootloader-vmlinux-5.10 \
      --disk-image=../riscv-disk.img
    # ...
    # board.platform.terminal: Listening for connections on port 3456
    # ...
  • 在另一个窗口用m5term连接,注意指定正确的port
    $ cd gem5
    $ util/term/m5term localhost <port>
  • 约2分钟后,看到如下界面,输入账号和密码即可登录
    # ...
    #  _   _  ____            _     _
    # | | | |/ ___|__ _ _ __ | |   (_)_ __  _   ___  __
    # | | | | |   / _` | '_ \| |   | | '_ \| | | \ \/ /
    # | |_| | |__| (_| | | | | |___| | | | | |_| |>  <
    #  \___/ \____\__,_|_| |_|_____|_|_| |_|\__,_/_/\_\
    # Welcome to RiscV
    #
    # UCanLinux login: root
    # Password: root
    root@UCanLinux:~ #
  • 测试先前拷贝进去的hello程序
    $ ./hello
    # Hello, world!
  • 注:m5term的退出方式为先输入~,再输入.

FS模式:高效实验

在上一节中我们只是能够启动操作系统,但还不能做任何有价值的实验,本节将介绍如何使用FS模式运行我们的benchmark,并且高效地完成整个实验流程

编译m5

  • m5是一个在FS容器中操作gem5的命令行小程序,m5的原理是执行自定义的指令并被gem5捕获,使得gem5执行一些外部动作,关于m5的更多介绍可见m5 README
  • 使用如下命令编译m5
    $ cd gem5/util/m5
    $ python3 `which scons` build/RISCV/out/m5
  • 参照修改磁盘镜像,将编译好的m5(位于gem5/util/m5/build/riscv/out/m5)拷贝到你的镜像的/root目录下

修改登录脚本

  • 由于默认的镜像需要输入密码登录,且登录后不会自动运行程序,所以我们需要修改登录脚本,让它自动登录和运行benchmark

关于修改方式

  • 如果你有root权限,可以mount镜像后直接用vim修改
  • 如果没有root权限,可以先用e2cp -p命令将文件复制出来,修改后再复制回去
    • 警告:使用e2cp -p命令时绝对不能漏掉-p参数!

设置免登录

  • Linux使用/etc/inittab设置启动第一个进程(/sbin/init)后应该做的事情
  • 修改/etc/inittab,将::respawn:/sbin/getty ...这一行修改为
    ::respawn:-/bin/sh /root/init.sh
    
  • 上述命令其实是说启动之后直接运行/root/init.sh脚本,不经过getty,也就是不需要登录

设置运行脚本

  • 在镜像中创建/root/init.sh文件,内容如下
    /root/m5 checkpoint
    /root/m5 readfile > /tmp/run.sh
    /bin/sh /tmp/run.sh
    /root/m5 exit
  • 这个脚本写得非常巧妙,其中/root/m5 checkpoint这句类似于fork(),请读者自己体会

准备Benchmark

  • 假设我们仍然用hello小程序,你已经将hello已经放在镜像的/root目录下
  • 镜像外创建一个调用hello的脚本run-hello.sh,内容如下
    /root/m5 resetstats
    /root/hello > /tmp/hello.out
    /root/m5 dumpstats
  • 警告:gem5的磁盘镜像是只读的,所以如果你的benchmark需要写,请将写的内容重定向到镜像的/tmp文件夹中
  • 注:镜像里虽然有C库,但由于Linux的库更新很快,镜像的C库已经有点过时了,所以建议benchmark都用-static编译

使用Atomic启动Linux

  • 为了避免每次运行程序都要启动一次系统,我们可以制作一个已经启动好的系统的镜像,以后每次都从创建镜像的地方开始运行benchmark
  • 由于上一步我们已经在登录脚本中设置了checkpoint命令,所以直接启动系统即可,启动完成后会自动保存镜像并退出
    $ cd gem5
    $ build/RISCV/gem5.opt configs/example/riscv/fs_linux.py \
      --kernel=../bootloader-vmlinux-5.10 \
      --disk-image=../riscv-disk.img
  • 生成的镜像位于m5out/cpt.xxx/(整个文件夹都是),其中xxx是创建checkpoint时的tick数
  • 注:gem5不是用文件夹名称而是tick数的大小顺序来识别checkpoint的,tick数最小的为1号checkpoint,次小的为2号,以此类推,所以建议不要修改文件夹的名字

使用O3CPU恢复Checkpoint

  • 恢复1号checkpoint(假设你的m5out/下只有一个checkpoint),注意设置--script为我们刚才准备的run-hello.sh脚本
    $ build/RISCV/gem5.opt \
      configs/example/riscv/fs_linux.py \
      --kernel=../bootloader-vmlinux-5.10 \
      --disk-image=../riscv-disk.img \
      --restore-with-cpu=O3CPU \
      --bp-type=TAGE_SC_L_64KB \
      --caches --l2cache \
      --checkpoint-restore=1 \
      --script=run-hello.sh
  • 运行完毕后,查看性能计数器的值,可以看到同一项出现了两次,因为run-hello.sh脚本自己调用了一次dumpstats,gem5运行结束时又自动记录了一次;第二次其实是多余的,应该以第一次为准
    $ grep -r system.switch_cpus.branchPred.lookups m5out/stats.txt
    # system.switch_cpus.branchPred.lookups  191847  # Number of BP lookups (Count)
    # system.switch_cpus.branchPred.lookups  336559  # Number of BP lookups (Count)

gem5-fs-handbook's People

Contributors

lshpku avatar

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.