Compare commits

...

20 Commits

Author SHA1 Message Date
Felix c8144787b0 docs(README): 更新标题链接指向 github 仓库
4 months ago
Felix 82fe15aa3e feat(makefile): 为lab9增加benchmarks
8 months ago
Felix 6b950d2ea0 fix(makefile): 修复lab9未删除历史trace的问题
8 months ago
Felix a60237e7fd fix(makefile): 修复测例执行顺序问题
8 months ago
Liphen 6293d1cd89 fix(mstatus.mpp): 写入非法值时,mpp保持原值
8 months ago
Felix 2f2f9e9b54 fix(difftest): 修复只实现M模式的CSR初始值
9 months ago
Liphen 6e3f2de95f perf(difftest/makefile): 增加 help 提示
9 months ago
Liphen ee417a132c docs(README): 增加实验环境说明
10 months ago
Wang Jiadong 98c42ca11b perf(test/lab4): 强化 lab4 的测例
10 months ago
Liphen abb03ef3c3 fix(test/bin): 增加 bin 文件序号
10 months ago
Liphen 80b1cd00f2 docs(difftest): 修正cpu_trace描述,删除无用参数
10 months ago
Felix b0832deab0 feat(difftest/Makefile): 增加指定测例生成波形命令
10 months ago
Liphen 43209019e7 docs: 增加各模块功能说明和一些关键代码注释
10 months ago
Liphen 67a04e71d4 docs(README): 增加环境完整性测试使用说明
10 months ago
Liphen 8e6db9f912 fix(ARegfile): 修正寄存器位宽注释为XLEN
10 months ago
Felix 5c2305b0ed feat(Decoder): 增加代码提示,降低实验难度
10 months ago
Liphen c8b3c4a4a4 docs: 更新README文件,修正文件名和使用说明
10 months ago
Liphen 6e65185521 fix(top_sram_wrapper): 补充difftest下SRAM的顶层文件
10 months ago
Liphen 1a9fcc12b6 chore(.gitignore): 移除不必要的文件规则
10 months ago
Liphen c38ce0b538 init: 初始化实验框架
11 months ago

4
.gitignore vendored

@ -0,0 +1,4 @@
.vscode/
.metals/
.VSCodeCounter/
.DS_Store

@ -0,0 +1,44 @@
STUID = 244050090
STUNAME = Felix
# DO NOT modify the following code!!!
TRACER = tracer-rvlab
GITFLAGS = -q --author='$(TRACER) <tracer@kairos.hdu.edu.cn>' --no-verify --allow-empty
RVLAB_HOME = $(RVDIFF_HOME)/..
WORK_BRANCH = $(shell git rev-parse --abbrev-ref HEAD)
WORK_INDEX = $(RVLAB_HOME)/.git/index.$(WORK_BRANCH)
TRACER_BRANCH = $(TRACER)
LOCK_DIR = $(RVLAB_HOME)/.git/
# prototype: git_soft_checkout(branch)
define git_soft_checkout
git checkout --detach -q && git reset --soft $(1) -q -- && git checkout $(1) -q --
endef
# prototype: git_commit(msg)
define git_commit
-@flock $(LOCK_DIR) $(MAKE) -C $(RVLAB_HOME) .git_commit MSG='$(1)'
-@sync $(LOCK_DIR)
endef
.git_commit:
-@while (test -e .git/index.lock); do sleep 0.1; done; `# wait for other git instances`
-@git branch $(TRACER_BRANCH) -q 2>/dev/null || true `# create tracer branch if not existent`
-@cp -a .git/index $(WORK_INDEX) `# backup git index`
-@$(call git_soft_checkout, $(TRACER_BRANCH)) `# switch to tracer branch`
-@git add . -A --ignore-errors `# add files to commit`
-@(echo "> $(MSG)" && echo $(STUID) $(STUNAME) && uname -a && uptime `# generate commit msg`) \
| git commit -F - $(GITFLAGS) `# commit changes in tracer branch`
-@$(call git_soft_checkout, $(WORK_BRANCH)) `# switch to work branch`
-@mv $(WORK_INDEX) .git/index `# restore git index`
.clean_index:
rm -f $(WORK_INDEX)
_default:
@echo "Please run 'make' under subprojects."
.PHONY: .git_commit .clean_index _default

@ -1,2 +1,183 @@
# riscv-lab
```
██████╗ ██╗███████╗ ██████╗██╗ ██╗ ██╗ █████╗ ██████╗
██╔══██╗██║██╔════╝██╔════╝██║ ██║ ██║ ██╔══██╗██╔══██╗
██████╔╝██║███████╗██║ ██║ ██║█████╗██║ ███████║██████╔╝
██╔══██╗██║╚════██║██║ ╚██╗ ██╔╝╚════╝██║ ██╔══██║██╔══██╗
██║ ██║██║███████║╚██████╗ ╚████╔╝ ███████╗██║ ██║██████╔╝
╚═╝ ╚═╝╚═╝╚══════╝ ╚═════╝ ╚═══╝ ╚══════╝╚═╝ ╚═╝╚═════╝
```
# 🚀 [RISCV-LAB](https://github.com/Ciliphen/riscv-lab)
从零开始的 RV64IMAZicsr_Zifencei 流水线设计实验
## 📚 简介
- 支持 RV64IMAZicsr_Zifencei 指令集的顺序动态双发射五级流水线
- 可接入差分测试框架,提供软件仿真测试
- 面向教学的实验设计,请搭配实验指导手册食用
## 🎬 目录结构
```bash
.
├── .git # 用于存储Git版本库
├── .gitignore # 用于配置Git忽略文件
├── .vscode # 用于配置VSCode编辑器
├── README.md # 项目说明文档
├── chisel # Chisel代码
│ ├── .bloop # 用于配置Bloop编译器
│ ├── .gitignore # 用于配置Git忽略文件
│ ├── .metals # 用于配置Metals编译器
│ ├── .scalafmt.conf # 用于配置Scalafmt代码格式化工具
│ ├── .vscode # 用于配置VSCode编辑器
│ ├── Makefile # 用于配置Make编译工具
│ ├── README.md # 项目说明文档
│ ├── build # 用于存储Chisel生成的Verilog文件
│ ├── build.sc # 用于配置Mill编译工具
│ ├── out # 用于存储mill编译后的文件
│ ├── playground
│ │ ├── resources # 用于存储CPU设计相关的Verilog文件
│ │ ├── src # 用于存储CPU设计相关的Chisel文件
│ │ └── test # 用于存储CPU设计相关的Chisel测试文件
│ └── utils # 用于存储firtool相关的文件
├── difftest # 差分测试框架
```
## 🛠️ 环境配置
- 以下配置流程在 Ubuntu22.04 以及 WSL2 的 Ubuntu22.04 版本下得到验证,可顺利执行
- 对于 Mac 用户,可使用 brew 工具直接安装对应的工具(由于 brew 安装的 Mill 的版本较新,需将 chisel/build.sc 的内容替换为 [chisel-playground/build.mill](https://github.com/OSCPU/chisel-playground/blob/master/build.mill) 中的内容以解决环境构建问题)
- 推荐使用 Ubuntu22.04 版本进行实验,对于其他环境出现的问题请先自己尝试解决
### 🍕 安装 Verilator
```bash
sudo apt-get install git help2man perl python3 make autoconf g++ flex bison ccache
sudo apt-get install libgoogle-perftools-dev numactl perl-doc
sudo apt-get install libfl2 # 如果报错忽略即可
sudo apt-get install libfl-dev # 如果报错忽略即可
sudo apt-get install zlibc zlib1g zlib1g-dev # 如果报错忽略即可
cd ~
git clone https://github.com/verilator/verilator # 拉取 verilator 的仓库,执行过一次即可
unset VERILATOR_ROOT
cd verilator
git checkout v5.010 # 推荐安装使用 5.010 版本
autoconf
./configure
make -j `nproc` # 如果报错请尝试直接输入 make 命令
sudo make install
# 经过以上步骤verilator应该已经安装完毕可以在终端中输入以下命令测试是否安装成功
verilator -version
# 如果正确的输出了版本号,则说明安装成功;如果报错,可以尝试重新安装。
```
### 🍔 安装 GTKWave
```bash
sudo apt-get install gtkwave
# 使用方法为
gtkwave <波形文件的路径>
```
### 🍟 安装 Java
```bash
sudo apt-get install openjdk-11-jdk
java --version # 若安装成功将输出对应版本号
```
### 🌭 安装 Mill
```bash
curl -L https://github.com/com-lihaoyi/mill/releases/download/0.11.6/0.11.6 > mill && chmod +x mill
mv mill /usr/bin/mill
mill --version # 若安装成功将输出对应版本号
```
### 🍖 安装 VS Code
- 安装 VS Code
- 安装 ScalaMetals插件
- 安装 Todo Tree 插件
- 安装 Git Graph 插件
### 🥓 安装实验框架
```bash
git clone https://bdgit.educoder.net/ppg69fuwb/riscv-lab.git
cd riscv-lab
git config --global user.name "244050090-Zhang San" # 设置学号和姓名
git config --global user.email "zhangsan@foo.com" # 设置邮箱
git config --global core.editor vim # 设置文本编辑器
git config --global color.ui true
bash init.sh difftest
source ~/.bashrc
echo $RVDIFF_HOME # 查看是否成功输出 difftest 文件夹的路径,这个很重要!
```
### 🥙 环境完整性测试
```bash
cd difftest
git checkout env_test # 切换到 env_test 分支
make envtest # 测试环境完整性
```
观察 chisel/build 目录下是否成功生成 GCD.sv 文件,若成功则说明 Chisel 环境配置成功
观察命令行是否存在以下输出:
```bash
Error!
reference: PC = 0x0000000080000010, wb_rf_wnum = 0x02, wb_rf_wdata = 0x0000000000000001
mycpu : PC = 0x0000000080000010, wb_rf_wnum = 0x02, wb_rf_wdata = 0x0000000000000000
```
若存在类似输出则说明差分测试环境配置成功
## 🛸 开始实验
```bash
git checkout main # 切换到 main 分支,实验代码均在 main 分支下
git pull # 拉取最新代码
```
建议使用 Vs Code 将 Chisel 目录作为工作目录,可以通过 `code <文件路径>` 命令使用 Vs Code 打开对应文件
所有的 make 指令均在 difftest 目录下执行,如 `make verilog``make lab1``make trace_lab1` 等
部分实验存在多个测例,此时 trace.fst 文件需手动生成,在 difftest 目录下使用以下命令手动生成 CPU 波形文件
```bash
make trace TESTBIN_DIR=<测例对应的bin文件的路径>
# 如在 difftest 目录下输入以下命令可生成CPU运行 am-tests/01-add-longlong.bin 测例的波形
make trace TESTBIN_DIR=./test/bin/am-tests/01-add-longlong.bin
```
## 📢 注意事项
- 编程位置位于 chisel 中
- 测试位置位于 difftest 中
- 进入 difftest 目录后
- 使用 `make verilog` 生成 verilog 代码(首次实验需要按实验要求补充代码,否则会报错)
- 使用 `make lab1` 进行 实验 1 的测试
- 使用 `make trace_lab1` 进行 实验 1 的 CPU 测试记录生成
- 实验 2 为 lab2以此类推
- difftest 目录下的 trace.txt 文件为测试结果,用于提交头歌平台,作为评分依据
- 在实验时务必确认 git 下有产生实验记录,这是重要的采分点之一,可通过 `git log tracer-rvlab` 查看(如果没有产生实验记录,请检查 RVDIFF_HOME 是否设置正确)
## 📦 资源
- 🧰[RISC-V Convertor](https://luplab.gitlab.io/rvcodecjs/) - RISC-V 汇编转换器
- 📑[Chisel Project Template](https://github.com/OSCPU/chisel-playground) - Chisel 项目模板

28
chisel/.gitignore vendored

@ -0,0 +1,28 @@
*.*
*
!*/
!Makefile
!*.mk
!*.scala
!*.[cSh]
!*.v
!*.cpp
!*.cc
!.gitignore
!.scalafmt.conf
!build.sc
!README.md
!utils/*
build/
# mill
out/
.bsp/
.idea/
.idea_modules/
test_run_dir/
# vscode
.metals/
.vscode/
.VSCodeCounter/

@ -0,0 +1,36 @@
version = 2.6.4
maxColumn = 120
align = most
continuationIndent.defnSite = 2
assumeStandardLibraryStripMargin = true
docstrings = ScalaDoc
lineEndings = preserve
includeCurlyBraceInSelectChains = false
danglingParentheses = true
align.tokens.add = [
{
code = ":"
},
{
code = ":="
},
{
code = "="
},
{
code = "->"
}
]
newlines.alwaysBeforeCurlyBraceLambdaParams = false
newlines.alwaysBeforeMultilineDef = false
newlines.implicitParamListModifierForce = [before]
verticalMultiline.atDefnSite = true
optIn.annotationNewlines = true
rewrite.rules = [SortImports, PreferCurlyFors, AvoidInfix]

@ -0,0 +1,46 @@
BUILD_DIR = ./build
DIFF_DIR = ../difftest/core
DIFF_WORK_DIR = ../difftest
export PATH := $(PATH):$(abspath ./utils)
verilog:
$(call git_commit, "generate verilog") # DO NOT REMOVE THIS LINE!!!
$(MAKE) clean
mkdir -p $(BUILD_DIR)
mill -i __.test.runMain Elaborate -td $(BUILD_DIR)
test:
@echo "make test"
$(call git_commit, "test chisel module") # DO NOT REMOVE THIS LINE!!!
$(MAKE) clean
mkdir -p $(BUILD_DIR)
mill -i __.test.runMain TestMain -td $(BUILD_DIR)
count:
find ./playground/ -name "*.scala" | xargs wc -l
help:
mill -i __.test.runMain Elaborate --help
compile:
mill -i __.compile
bsp:
mill -i mill.bsp.BSP/install
reformat:
mill -i __.reformat
checkformat:
mill -i __.checkFormat
clean:
-rm -rf $(BUILD_DIR)
.PHONY: test verilog help compile bsp reformat checkformat clean
sim:
@echo "Write this Makefile by yourself."
-include ../Makefile

@ -0,0 +1,38 @@
# Chisel Project Template
Another version of the [Chisel template](https://github.com/ucb-bar/chisel-template) supporting mill.
mill is another Scala/Java build tool without obscure DSL like SBT. It is much faster than SBT.
Contents at a glance:
- `.gitignore` - helps Git ignore junk like generated files, build products, and temporary files.
- `build.sc` - instructs mill to build the Chisel project
- `Makefile` - rules to call mill
- `playground/src/GCD.scala` - GCD source file
- `playground/src/DecoupledGCD.scala` - another GCD source file
- `playground/src/Elaborate.scala` - wrapper file to call chisel command with the GCD module
- `playground/test/src/GCDSpec.scala` - GCD tester
Feel free to rename or delete files under `playground/` or use them as a reference/template.
## Getting Started
First, install mill by referring to the documentation [here](https://com-lihaoyi.github.io/mill).
To run all tests in this design (recommended for test-driven development):
```bash
make test
```
To generate Verilog:
```bash
make verilog
```
## Change FIRRTL Compiler
You can change the FIRRTL compiler between SFC (Scala-based FIRRTL compiler) and
MFC (MLIR-based FIRRTL compiler) by modifying the `useMFC` variable in `playground/src/Elaborate.scala`.
The latter one requires `firtool`, which is included under `utils/`.

@ -0,0 +1,45 @@
// import Mill dependency
import mill._
import mill.scalalib._
import mill.scalalib.scalafmt.ScalafmtModule
import mill.scalalib.TestModule.ScalaTest
// support BSP
import mill.bsp._
object playground extends ScalaModule with ScalafmtModule { m =>
val useChisel5 = false
val useChisel6 = true
override def scalaVersion = "2.13.10"
override def scalacOptions = Seq(
"-language:reflectiveCalls",
"-deprecation",
"-feature",
"-Xcheckinit"
)
override def ivyDeps = Agg(
if (useChisel5) ivy"org.chipsalliance::chisel:5.0.0"
else if (useChisel6) ivy"org.chipsalliance::chisel:6.1.0"
else
ivy"edu.berkeley.cs::chisel3:3.6.0"
)
override def scalacPluginIvyDeps = Agg(
if (useChisel5) ivy"org.chipsalliance:::chisel-plugin:5.0.0"
else if (useChisel6) ivy"org.chipsalliance:::chisel-plugin:6.1.0"
else
ivy"edu.berkeley.cs:::chisel3-plugin:3.6.0"
)
object test extends ScalaTests with ScalaTest {
override def ivyDeps = m.ivyDeps() ++ Agg(
ivy"com.lihaoyi::utest:0.8.1",
if (useChisel5 || useChisel6) ivy"edu.berkeley.cs::chiseltest:5.0.0"
else
ivy"edu.berkeley.cs::chiseltest:0.6.0"
)
}
def repositoriesTask = T.task {
Seq(
coursier.MavenRepository("https://maven.aliyun.com/repository/central"),
coursier.MavenRepository("https://repo.scala-sbt.org/scalasbt/maven-releases")
) ++ super.repositoriesTask()
}
}

@ -0,0 +1,54 @@
module top(
input clock,
input reset,
// Interrupts
input mei, // to PLIC
input msi, // to CLINT
input mti, // to CLINT
input sei, // to PLIC
// inst sram interface
output inst_sram_en,
output [ 3:0] inst_sram_wen,
output [31:0] inst_sram_addr,
output [31:0] inst_sram_wdata,
input [31:0] inst_sram_rdata,
// data sram interface
output data_sram_en,
output [ 7:0] data_sram_wen,
output [31:0] data_sram_addr,
output [63:0] data_sram_wdata,
input [63:0] data_sram_rdata,
// trace debug interface
output debug_commit,
output [63:0] debug_pc,
output [4:0 ] debug_rf_wnum,
output [63:0] debug_rf_wdata
);
PuaCpu core(
.clock (clock),
.reset (reset),
// interrupts
.io_ext_int_mei (mei),
.io_ext_int_mti (mti),
.io_ext_int_msi (msi),
// inst sram interface
.io_inst_sram_en (inst_sram_en),
.io_inst_sram_wen (inst_sram_wen),
.io_inst_sram_addr (inst_sram_addr),
.io_inst_sram_wdata (inst_sram_wdata),
.io_inst_sram_rdata (inst_sram_rdata),
// data sram interface
.io_data_sram_en (data_sram_en),
.io_data_sram_wen (data_sram_wen),
.io_data_sram_addr (data_sram_addr),
.io_data_sram_wdata (data_sram_wdata),
.io_data_sram_rdata (data_sram_rdata),
// debug
.io_debug_pc (debug_pc),
.io_debug_commit (debug_commit),
.io_debug_rf_wnum (debug_rf_wnum),
.io_debug_rf_wdata (debug_rf_wdata)
);
endmodule

@ -0,0 +1,35 @@
package cpu
import chisel3._
import chisel3.util._
import defines._
import defines.Const._
import pipeline._
class Core extends Module {
val io = IO(new Bundle {
val interrupt = Input(new ExtInterrupt())
val instSram = new InstSram()
val dataSram = new DataSram()
val debug = new DEBUG()
})
val fetchUnit = Module(new FetchUnit()).io
val decodeStage = Module(new DecodeStage()).io
val decodeUnit = Module(new DecodeUnit()).io
val regfile = Module(new ARegFile()).io
val executeStage = Module(new ExecuteStage()).io
val executeUnit = Module(new ExecuteUnit()).io
val memoryStage = Module(new MemoryStage()).io
val memoryUnit = Module(new MemoryUnit()).io
val writeBackStage = Module(new WriteBackStage()).io
val writeBackUnit = Module(new WriteBackUnit()).io
// 取指单元
fetchUnit.instSram <> io.instSram
fetchUnit.decodeStage <> decodeStage.fetchUnit
// TODO: 完成Core模块的逻辑
// 在该模块中需要将各个模块连接起来形成一个完整的CPU核心
}

@ -0,0 +1,16 @@
package cpu
import chisel3.util._
import cpu.defines.Const._
case class CpuConfig(
// 指令集
val isRV32: Boolean = false, // 是否为RV32
val hasMExtension: Boolean = false, // 是否实现M扩展即乘除法指令
val hasZicsrExtension: Boolean = false, // 是否实现Zicsr扩展即CSR指令
val hasZifenceiExtension: Boolean = false, // 是否实现Zifencei扩展即FENCE.I指令
val hasAExtension: Boolean = false, // 是否实现A扩展即原子指令
// 特权模式
val hasSMode: Boolean = false, // 是否有S模式
val hasUMode: Boolean = false // 是否有U模式
)

@ -0,0 +1,9 @@
import cpu._
import circt.stage._
object Elaborate extends App {
implicit val cpuConfig = new CpuConfig()
def top = new PuaCpu()
val generator = Seq(chisel3.stage.ChiselGeneratorAnnotation(() => top))
(new ChiselStage).execute(args, generator :+ CIRCTTargetAnnotation(CIRCTTarget.Verilog))
}

@ -0,0 +1,20 @@
import chisel3._
import chisel3.util._
import cpu._
import cpu.defines._
class PuaCpu extends Module {
val io = IO(new Bundle {
val ext_int = Input(new ExtInterrupt())
val inst_sram = new InstSram()
val data_sram = new DataSram()
val debug = new DEBUG()
})
val core = Module(new Core())
io.ext_int <> core.io.interrupt
io.inst_sram <> core.io.instSram
io.data_sram <> core.io.dataSram
io.debug <> core.io.debug
}

@ -0,0 +1,59 @@
package cpu.defines
import chisel3._
import chisel3.util._
import cpu.defines._
import cpu.defines.Const._
import cpu.CpuConfig
class ExtInterrupt extends Bundle {
val mei = Bool()
val mti = Bool()
val msi = Bool()
}
class SrcInfo extends Bundle {
val src1_data = UInt(XLEN.W)
val src2_data = UInt(XLEN.W)
}
class RdInfo extends Bundle {
val wdata = UInt(XLEN.W)
}
class Info extends Bundle {
val valid = Bool() // 用于标识当前流水级中的指令是否有效
val src1_raddr = UInt(REG_ADDR_WID.W)
val src2_raddr = UInt(REG_ADDR_WID.W)
val op = FuOpType()
val reg_wen = Bool()
val reg_waddr = UInt(REG_ADDR_WID.W)
}
class SrcReadSignal extends Bundle {
val ren = Bool()
val raddr = UInt(REG_ADDR_WID.W)
}
class InstSram extends Bundle {
val en = Output(Bool())
val addr = Output(UInt(SRAM_ADDR_WID.W))
val wdata = Output(UInt(INST_SRAM_DATA_WID.W))
val wen = Output(UInt(INST_SRAM_WEN_WID.W))
val rdata = Input(UInt(INST_SRAM_DATA_WID.W))
}
class DataSram extends Bundle {
val en = Output(Bool())
val addr = Output(UInt(SRAM_ADDR_WID.W))
val wdata = Output(UInt(DATA_SRAM_DATA_WID.W))
val wen = Output(UInt(DATA_SRAM_WEN_WID.W))
val rdata = Input(UInt(DATA_SRAM_DATA_WID.W))
}
class DEBUG extends Bundle {
val commit = Output(Bool()) // 写回阶段的commit信号仅在每条指令提交时置为true
val pc = Output(UInt(XLEN.W)) // 写回阶段的pc
val rf_wnum = Output(UInt(REG_ADDR_WID.W)) // 写回阶段的寄存器写地址
val rf_wdata = Output(UInt(XLEN.W)) // 写回阶段的寄存器写数据
}

@ -0,0 +1,42 @@
package cpu.defines
import chisel3._
import chisel3.util._
import cpu.CpuConfig
trait CoreParameter {
def cpuConfig = new CpuConfig
val XLEN = if (cpuConfig.isRV32) 32 else 64
val VADDR_WID = if (cpuConfig.isRV32) 32 else 39
val PADDR_WID = 32
}
trait Constants extends CoreParameter {
// 全局
val PC_INIT = "h80000000".U(XLEN.W)
val INT_WID = 12
val EXC_WID = 16
// inst rom
val INST_WID = 32
// GPR RegFile
val AREG_NUM = 32
val REG_ADDR_WID = 5
}
trait SRAMConst extends Constants {
val SRAM_ADDR_WID = PADDR_WID // 32
val DATA_SRAM_DATA_WID = XLEN
val DATA_SRAM_WEN_WID = XLEN / 8
val INST_SRAM_DATA_WID = INST_WID
val INST_SRAM_WEN_WID = INST_WID / 8
}
object Const extends Constants with SRAMConst
object Instructions extends HasInstrType with CoreParameter {
def NOP = 0x00000013.U
val DecodeDefault = List(InstrN, FuType.alu, ALUOpType.add)
def DecodeTable = RVIInstr.table
}

@ -0,0 +1,29 @@
package cpu.defines
import chisel3._
import chisel3.util._
object SignedExtend {
def apply(a: UInt, len: Int) = {
val aLen = a.getWidth
val signBit = a(aLen - 1)
if (aLen >= len) a(len - 1, 0) else Cat(Fill(len - aLen, signBit), a)
}
}
object ZeroExtend {
def apply(a: UInt, len: Int) = {
val aLen = a.getWidth
if (aLen >= len) a(len - 1, 0) else Cat(0.U((len - aLen).W), a)
}
}
object LookupTree {
def apply[T <: Data](key: UInt, mapping: Iterable[(UInt, T)]): T =
Mux1H(mapping.map(p => (p._1 === key, p._2)))
}
object LookupTreeDefault {
def apply[T <: Data](key: UInt, default: T, mapping: Iterable[(UInt, T)]): T =
MuxLookup(key, default)(mapping.toSeq)
}

@ -0,0 +1,36 @@
package cpu.defines
import chisel3._
import chisel3.util._
// 指令类型
trait HasInstrType {
def InstrN = "b000".U
def InstrI = "b100".U
def InstrR = "b101".U
def InstrS = "b010".U
def InstrB = "b001".U
def InstrU = "b110".U
def InstrJ = "b111".U
// IRUJ类型的指令都需要写寄存器
def isRegWen(instrType: UInt): Bool = instrType(2)
}
// 功能单元类型 Function Unit Type
object FuType {
def num = 1
def alu = 0.U // arithmetic logic unit
def apply() = UInt(log2Up(num).W)
}
// 功能单元操作类型 Function Unit Operation Type
object FuOpType {
def apply() = UInt(5.W) // 宽度与最大的功能单元操作类型宽度一致
}
// 算术逻辑单元操作类型 Arithmetic Logic Unit Operation Type
object ALUOpType {
def add = "b00000".U
// TODO: 定义更多的ALU操作类型
}

@ -0,0 +1,61 @@
package cpu.defines
import chisel3._
import chisel3.util._
object RV32I_ALUInstr extends HasInstrType with CoreParameter {
def ADDI = BitPat("b????????????_?????_000_?????_0010011")
def SLLI = if (XLEN == 32) BitPat("b0000000?????_?????_001_?????_0010011")
else BitPat("b000000??????_?????_001_?????_0010011")
def SLTI = BitPat("b????????????_?????_010_?????_0010011")
def SLTIU = BitPat("b????????????_?????_011_?????_0010011")
def XORI = BitPat("b????????????_?????_100_?????_0010011")
def SRLI = if (XLEN == 32) BitPat("b0000000?????_?????_101_?????_0010011")
else BitPat("b000000??????_?????_101_?????_0010011")
def ORI = BitPat("b????????????_?????_110_?????_0010011")
def ANDI = BitPat("b????????????_?????_111_?????_0010011")
def SRAI = if (XLEN == 32) BitPat("b0100000?????_?????_101_?????_0010011")
else BitPat("b010000??????_?????_101_?????_0010011")
def ADD = BitPat("b0000000_?????_?????_000_?????_0110011")
def SLL = BitPat("b0000000_?????_?????_001_?????_0110011")
def SLT = BitPat("b0000000_?????_?????_010_?????_0110011")
def SLTU = BitPat("b0000000_?????_?????_011_?????_0110011")
def XOR = BitPat("b0000000_?????_?????_100_?????_0110011")
def SRL = BitPat("b0000000_?????_?????_101_?????_0110011")
def OR = BitPat("b0000000_?????_?????_110_?????_0110011")
def AND = BitPat("b0000000_?????_?????_111_?????_0110011")
def SUB = BitPat("b0100000_?????_?????_000_?????_0110011")
def SRA = BitPat("b0100000_?????_?????_101_?????_0110011")
def AUIPC = BitPat("b????????????????????_?????_0010111")
def LUI = BitPat("b????????????????????_?????_0110111")
// 在Decoder模块中搭配ListLookup函数使用
val table = Array(
// ADD指令将被解析为InstrR类型的指令功能单元类型为alu功能单元操作类型为add
ADD -> List(InstrR, FuType.alu, ALUOpType.add)
// TODO: 完成其他指令的解析
)
}
object RV64IInstr extends HasInstrType {
def ADDIW = BitPat("b???????_?????_?????_000_?????_0011011")
def SLLIW = BitPat("b0000000_?????_?????_001_?????_0011011")
def SRLIW = BitPat("b0000000_?????_?????_101_?????_0011011")
def SRAIW = BitPat("b0100000_?????_?????_101_?????_0011011")
def SLLW = BitPat("b0000000_?????_?????_001_?????_0111011")
def SRLW = BitPat("b0000000_?????_?????_101_?????_0111011")
def SRAW = BitPat("b0100000_?????_?????_101_?????_0111011")
def ADDW = BitPat("b0000000_?????_?????_000_?????_0111011")
def SUBW = BitPat("b0100000_?????_?????_000_?????_0111011")
val table = Array(
// TODO: 完成RV64I指令集的解析
)
}
object RVIInstr extends CoreParameter {
val table = RV32I_ALUInstr.table ++
(if (XLEN == 64) RV64IInstr.table else Array.empty)
}

@ -0,0 +1,41 @@
package cpu.pipeline
import chisel3._
import chisel3.util._
import cpu.defines._
import cpu.defines.Const._
import cpu.CpuConfig
class SrcRead extends Bundle {
val raddr = Output(UInt(REG_ADDR_WID.W))
val rdata = Input(UInt(XLEN.W))
}
class Src12Read extends Bundle {
val src1 = new SrcRead()
val src2 = new SrcRead()
}
class RegWrite extends Bundle {
val wen = Output(Bool())
val waddr = Output(UInt(REG_ADDR_WID.W))
val wdata = Output(UInt(XLEN.W))
}
class ARegFile extends Module {
val io = IO(new Bundle {
val read = Flipped(new Src12Read())
val write = Flipped(new RegWrite())
})
// 定义32个XLEN位寄存器
val regs = RegInit(VecInit(Seq.fill(AREG_NUM)(0.U(XLEN.W))))
// 写寄存器堆
// TODO:完成写寄存器堆逻辑
// 注意0号寄存器恒为0
// 读寄存器堆
// TODO:完成读寄存器堆逻辑
// 注意0号寄存器恒为0
}

@ -0,0 +1,30 @@
package cpu.pipeline
import chisel3._
import chisel3.util._
import cpu.defines._
import cpu.defines.Const._
import cpu.CpuConfig
class IfIdData extends Bundle {
val inst = UInt(XLEN.W)
val valid = Bool()
val pc = UInt(XLEN.W)
}
class FetchUnitDecodeUnit extends Bundle {
val data = Output(new IfIdData())
}
class DecodeStage extends Module {
val io = IO(new Bundle {
val fetchUnit = Flipped(new FetchUnitDecodeUnit())
val decodeUnit = new FetchUnitDecodeUnit()
})
val data = RegInit(0.U.asTypeOf(new IfIdData()))
data := io.fetchUnit.data
io.decodeUnit.data := data
}

@ -0,0 +1,38 @@
package cpu.pipeline
import chisel3._
import chisel3.util._
import cpu.defines._
import cpu.defines.Const._
class DecodeUnit extends Module {
val io = IO(new Bundle {
// 输入
val decodeStage = Flipped(new FetchUnitDecodeUnit())
val regfile = new Src12Read()
// 输出
val executeStage = Output(new DecodeUnitExecuteUnit())
})
// 译码阶段完成指令的译码操作以及源操作数的准备
val decoder = Module(new Decoder()).io
decoder.in.inst := io.decodeStage.data.inst
val pc = io.decodeStage.data.pc
val info = Wire(new Info())
info := decoder.out.info
info.valid := io.decodeStage.data.valid
// TODO:完成寄存器堆的读取
// io.regfile.src1.raddr :=
// io.regfile.src2.raddr :=
// TODO: 完成DecodeUnit模块的逻辑
// io.executeStage.data.pc :=
// io.executeStage.data.info :=
// io.executeStage.data.src_info.src1_data :=
// io.executeStage.data.src_info.src2_data :=
}

@ -0,0 +1,36 @@
package cpu.pipeline
import chisel3._
import chisel3.util._
import cpu.defines._
import cpu.defines.Const._
class Decoder extends Module with HasInstrType {
val io = IO(new Bundle {
// inputs
val in = Input(new Bundle {
val inst = UInt(XLEN.W)
})
// outputs
val out = Output(new Bundle {
val info = new Info()
})
})
val inst = io.in.inst
// 根据输入的指令inst从Instructions.DecodeTable中查找对应的指令类型功能单元类型和功能单元操作类型
// 如果找不到匹配的指令则使用Instructions.DecodeDefault作为默认值
// instrTypefuType和fuOpType分别被赋值为Instructions.DecodeTable中的对应值
val instrType :: fuType :: fuOpType :: Nil =
ListLookup(inst, Instructions.DecodeDefault, Instructions.DecodeTable)
val (rs, rt, rd) = (inst(19, 15), inst(24, 20), inst(11, 7))
// TODO: 完成Decoder模块的逻辑
// io.out.info.valid :=
// io.out.info.src1_raddr :=
// io.out.info.src2_raddr :=
// io.out.info.op :=
// io.out.info.reg_wen :=
// io.out.info.reg_waddr :=
}

@ -0,0 +1,28 @@
package cpu.pipeline
import chisel3._
import chisel3.util._
import cpu.defines._
import cpu.defines.Const._
import cpu.CpuConfig
class IdExeData extends Bundle {
val pc = UInt(XLEN.W)
val info = new Info()
val src_info = new SrcInfo()
}
class DecodeUnitExecuteUnit extends Bundle {
val data = new IdExeData()
}
class ExecuteStage extends Module {
val io = IO(new Bundle {
val decodeUnit = Input(new DecodeUnitExecuteUnit())
val executeUnit = Output(new DecodeUnitExecuteUnit())
})
val data = RegInit(0.U.asTypeOf(new IdExeData()))
// TODO: 完成ExecuteStage模块的逻辑
}

@ -0,0 +1,31 @@
package cpu.pipeline
import chisel3._
import chisel3.util._
import cpu.CpuConfig
import cpu.defines._
import cpu.defines.Const._
import chisel3.util.experimental.BoringUtils
class ExecuteUnit extends Module {
val io = IO(new Bundle {
val executeStage = Input(new DecodeUnitExecuteUnit())
val memoryStage = Output(new ExecuteUnitMemoryUnit())
val dataSram = new DataSram()
})
// 执行阶段完成指令的执行操作
val fu = Module(new Fu()).io
fu.data.pc := io.executeStage.data.pc
fu.data.info := io.executeStage.data.info
fu.data.src_info := io.executeStage.data.src_info
io.dataSram <> fu.dataSram
// TODO: 完成ExecuteUnit模块的逻辑
// io.memoryStage.data.pc :=
// io.memoryStage.data.info :=
// io.memoryStage.data.src_info :=
// io.memoryStage.data.rd_info :=
}

@ -0,0 +1,32 @@
package cpu.pipeline
import chisel3._
import chisel3.util._
import cpu.defines._
import cpu.defines.Const._
import cpu.CpuConfig
class Fu extends Module {
val io = IO(new Bundle {
val data = new Bundle {
val pc = Input(UInt(XLEN.W))
val info = Input(new Info())
val src_info = Input(new SrcInfo())
val rd_info = Output(new RdInfo())
}
val dataSram = new DataSram()
})
val alu = Module(new Alu()).io
io.dataSram.en := false.B
io.dataSram.addr := DontCare
io.dataSram.wdata := DontCare
io.dataSram.wen := 0.U
alu.info := io.data.info
alu.src_info := io.data.src_info
io.data.rd_info.wdata := alu.result
}

@ -0,0 +1,15 @@
package cpu.pipeline
import chisel3._
import chisel3.util._
import cpu.defines._
import cpu.defines.Const._
class Alu extends Module {
val io = IO(new Bundle {
val info = Input(new Info())
val src_info = Input(new SrcInfo())
val result = Output(UInt(XLEN.W))
})
// TODO: 完成ALU模块的逻辑
}

@ -0,0 +1,41 @@
package cpu.pipeline
import chisel3._
import chisel3.util._
import cpu.defines.Const._
import cpu.CpuConfig
import cpu.defines._
class FetchUnit extends Module {
val io = IO(new Bundle {
val decodeStage = new FetchUnitDecodeUnit()
val instSram = new InstSram()
})
val boot :: send :: receive :: Nil = Enum(3)
val state = RegInit(boot)
switch(state) {
is(boot) {
state := send
}
is(send) {
state := receive
}
is(receive) {}
}
// 取指阶段完成指令的取指操作
val pc = RegEnable(io.instSram.addr, (PC_INIT - 4.U), state =/= boot)
io.instSram.addr := pc + 4.U
io.decodeStage.data.valid := state === receive
io.decodeStage.data.pc := pc
io.decodeStage.data.inst := io.instSram.rdata
io.instSram.en := !reset.asBool
io.instSram.wen := 0.U
io.instSram.wdata := 0.U
}

@ -0,0 +1,29 @@
package cpu.pipeline
import chisel3._
import chisel3.util._
import cpu.defines._
import cpu.defines.Const._
import cpu.CpuConfig
class ExeMemData extends Bundle {
val pc = UInt(XLEN.W)
val info = new Info()
val rd_info = new RdInfo()
val src_info = new SrcInfo()
}
class ExecuteUnitMemoryUnit extends Bundle {
val data = new ExeMemData()
}
class MemoryStage extends Module {
val io = IO(new Bundle {
val executeUnit = Input(new ExecuteUnitMemoryUnit())
val memoryUnit = Output(new ExecuteUnitMemoryUnit())
})
val data = RegInit(0.U.asTypeOf(new ExeMemData()))
// TODO: 完成MemoryStage模块的逻辑
}

@ -0,0 +1,21 @@
package cpu.pipeline
import chisel3._
import chisel3.util._
import chisel3.util.experimental.BoringUtils
import cpu.defines._
import cpu.defines.Const._
import cpu.CpuConfig
class MemoryUnit extends Module {
val io = IO(new Bundle {
val memoryStage = Input(new ExecuteUnitMemoryUnit())
val writeBackStage = Output(new MemoryUnitWriteBackUnit())
})
// 访存阶段完成指令的访存操作
io.writeBackStage.data.pc := io.memoryStage.data.pc
io.writeBackStage.data.info := io.memoryStage.data.info
io.writeBackStage.data.rd_info.wdata := io.memoryStage.data.rd_info.wdata
}

@ -0,0 +1,27 @@
package cpu.pipeline
import chisel3._
import chisel3.util._
import cpu.defines._
import cpu.defines.Const._
import cpu.CpuConfig
class MemWbData extends Bundle {
val pc = UInt(XLEN.W)
val info = new Info()
val rd_info = new RdInfo()
}
class MemoryUnitWriteBackUnit extends Bundle {
val data = new MemWbData()
}
class WriteBackStage extends Module {
val io = IO(new Bundle {
val memoryUnit = Input(new MemoryUnitWriteBackUnit())
val writeBackUnit = Output(new MemoryUnitWriteBackUnit())
})
val data = RegInit(0.U.asTypeOf(new MemWbData()))
// TODO: 完成WriteBackStage模块的逻辑
}

@ -0,0 +1,19 @@
package cpu.pipeline
import chisel3._
import chisel3.util._
import cpu.defines._
import cpu.defines.Const._
import cpu.CpuConfig
class WriteBackUnit extends Module {
val io = IO(new Bundle {
val writeBackStage = Input(new MemoryUnitWriteBackUnit())
val regfile = Output(new RegWrite())
val debug = new DEBUG()
})
// 写回阶段完成数据的写回操作
// 同时该阶段还负责差分测试的比对工作
// TODO: 完成WriteBackUnit模块的逻辑
}

@ -0,0 +1,9 @@
// import cpu._
// import circt.stage._
// object TestMain extends App {
// implicit val cpuConfig = new CpuConfig()
// def top = new Top()
// val generator = Seq(chisel3.stage.ChiselGeneratorAnnotation(() => top))
// (new ChiselStage).execute(args, generator :+ CIRCTTargetAnnotation(CIRCTTarget.Verilog))
// }

@ -0,0 +1,2 @@
#!/usr/bin/env bash
firtool.elf.strip --lowering-options=disallowLocalVariables,disallowPackedArrays,locationInfoStyle=wrapInAtSquareBracket $@

Binary file not shown.

@ -0,0 +1,7 @@
*.vcd
obj_dir
core/*
!core/top_sram_wrapper.v
trace.*

@ -0,0 +1,145 @@
TOP_NAME := top
SRC_DIR := ./core
SRC_FILE := $(shell find $(SRC_DIR) -name '*.svh') $(shell find $(SRC_DIR) -name '*.h') $(shell find $(SRC_DIR) -name '*.v') $(shell find $(SRC_DIR) -name '*.sv')
CHISEL_DIR = ../chisel
BUILD_DIR = $(CHISEL_DIR)/build
TESTBIN_DIR = ./test/bin/am-tests/add.bin
.PHONY: clean
obj_dir/V$(TOP_NAME): src/* $(SRC_FILE)
verilator --cc -Wno-fatal --exe --trace-fst --trace-structs -LDFLAGS "-lpthread" --build src/sim_mycpu.cpp $(SRC_FILE) -I$(SRC_DIR) --top $(TOP_NAME) -j `nproc`
verilog:
$(MAKE) -C $(CHISEL_DIR) verilog
cp $(CHISEL_DIR)/build/PuaCpu.v $(SRC_DIR)
trace: obj_dir/V$(TOP_NAME)
$(call git_commit, "trace") # DO NOT REMOVE THIS LINE!!!
./obj_dir/V$(TOP_NAME) $(TESTBIN_DIR) -rvtest -trace 10000000 -pc
test:
$(MAKE) -C $(CHISEL_DIR) test
clean:
rm -rf obj_dir
rm -rf core/PuaCpu.v
perf: obj_dir/V$(TOP_NAME)
$(call git_commit, "perf test RTL") # DO NOT REMOVE THIS LINE!!!
count=0; \
for test in ./test/bin/riscv-test/benchmarks/*; do \
count=$$((count + 1)); \
echo "Running test $$count: $$test"; \
./obj_dir/V$(TOP_NAME) $$test -rvtest -pc -perf; \
done; \
qbench: obj_dir/V$(TOP_NAME)
@echo "==================================================================="
@echo "=========================quick benchmarks=========================="
@echo "==================================================================="
@count=0; \
for test in $$(find ./test/bin/riscv-test/benchmarks \( -name "*.bin" \) | sort | grep -vE "*dhrystone*|*mt-vvadd*"); do \
count=$$((count + 1)); \
echo "Running bench $$count: $$test"; \
./obj_dir/V$(TOP_NAME) $$test -rvtest -pc -perf; \
done; \
lab1: obj_dir/V$(TOP_NAME)
$(call git_commit, "test lab1") # DO NOT REMOVE THIS LINE!!!
./obj_dir/V$(TOP_NAME) ./test/bin/lab-test/lab1.bin -rvtest -initgprs -trace 10000000 -pc
trace_lab1: obj_dir/V$(TOP_NAME)
$(call git_commit, "trace lab1") # DO NOT REMOVE THIS LINE!!!
./obj_dir/V$(TOP_NAME) ./test/bin/lab-test/lab1.bin -rvtest -initgprs -cpu_trace
TESTS234 := lab2 lab3 lab4
TRACE_TESTS234 := $(addprefix trace_,$(TESTS234))
$(TESTS234): %: obj_dir/V$(TOP_NAME)
$(call git_commit, "test $@") # DO NOT REMOVE THIS LINE!!!
./obj_dir/V$(TOP_NAME) ./test/bin/lab-test/$@.bin -rvtest -trace 10000000 -pc
$(TRACE_TESTS234): trace_%: obj_dir/V$(TOP_NAME)
$(call git_commit, "trace $*") # DO NOT REMOVE THIS LINE!!!
./obj_dir/V$(TOP_NAME) ./test/bin/lab-test/$*.bin -rvtest -cpu_trace
lab5: obj_dir/V$(TOP_NAME)
$(call git_commit, "test lab5") # DO NOT REMOVE THIS LINE!!!
./obj_dir/V$(TOP_NAME) ./test/bin/lab-test/lab5.bin -rvtest -trace 10000000 -pc -hasdelayslot
trace_lab5: obj_dir/V$(TOP_NAME)
$(call git_commit, "trace lab5") # DO NOT REMOVE THIS LINE!!!
./obj_dir/V$(TOP_NAME) ./test/bin/lab-test/lab5.bin -rvtest -cpu_trace -hasdelayslot
TEST67 := lab6 lab7
TRACE_TESTS67 := $(addprefix trace_,$(TEST67))
$(TEST67): obj_dir/V$(TOP_NAME)
$(call git_commit, "test $@") # DO NOT REMOVE THIS LINE!!!
count=0; \
for test in $$(ls ./test/bin/am-tests/* | sort); do \
count=$$((count + 1)); \
echo "Running test $$count: $$test"; \
./obj_dir/V$(TOP_NAME) $$test -rvtest -pc; \
done; \
count=$$((count + 1)); \
echo "Running test $$count: ./test/bin/lab-test/lab6.bin"; \
./obj_dir/V$(TOP_NAME) ./test/bin/lab-test/lab6.bin -rvtest -pc -perf; \
echo "Total tests run: $$count";
$(TRACE_TESTS67): obj_dir/V$(TOP_NAME)
$(call git_commit, "trace $*") # DO NOT REMOVE THIS LINE!!!
rm -rf ./trace.txt
count=0; \
for test in $$(ls ./test/bin/am-tests/* | sort); do \
count=$$((count + 1)); \
echo "Running test $$count: $$test"; \
./obj_dir/V$(TOP_NAME) $$test -rvtest -cpu_trace -writeappend; \
done; \
count=$$((count + 1)); \
echo "Running test $$count: ./test/bin/lab-test/lab6.bin"; \
./obj_dir/V$(TOP_NAME) ./test/bin/lab-test/lab6.bin -rvtest -cpu_trace -writeappend; \
echo "Total tests run: $$count";
lab8: obj_dir/V$(TOP_NAME)
$(call git_commit, "test lab8") # DO NOT REMOVE THIS LINE!!!
./obj_dir/V$(TOP_NAME) ./test/bin/lab-test/lab8.bin -rvtest -trace 10000000 -pc -onlymodem
trace_lab8: obj_dir/V$(TOP_NAME)
$(call git_commit, "trace lab8") # DO NOT REMOVE THIS LINE!!!
rm -rf ./trace.txt
./obj_dir/V$(TOP_NAME) ./test/bin/lab-test/lab8.bin -rvtest -cpu_trace -onlymodem
lab9: obj_dir/V$(TOP_NAME)
$(call git_commit, "test lab9") # DO NOT REMOVE THIS LINE!!!
count=0; \
for test in $$(find ./test/bin/riscv-test/ \( -name "*rv64ui-p-*" -o -name "*rv64um-p-*" -o -name "*rv64mi-p-*" \) | sort | grep -vE "*rv64ui-p-fence_i|*rv64mi-p-access"); do \
count=$$((count + 1)); \
echo "Running test $$count: $$test"; \
./obj_dir/V$(TOP_NAME) $$test -rvtest -pc; \
done; \
echo "Total tests run: $$count";
$(MAKE) qbench
trace_lab9: obj_dir/V$(TOP_NAME)
$(call git_commit, "trace lab9") # DO NOT REMOVE THIS LINE!!!
rm -rf ./trace.txt
count=0; \
for test in $$(find ./test/bin/riscv-test/ \( -name "*rv64ui-p-*" -o -name "*rv64um-p-*" -o -name "*rv64mi-p-*" \) | sort | grep -vE "*rv64ui-p-fence_i|*rv64mi-p-access"); do \
count=$$((count + 1)); \
echo "Running test $$count: $$test"; \
./obj_dir/V$(TOP_NAME) $$test -rvtest -cpu_trace -writeappend; \
done; \
echo "Total tests run: $$count";
help:
@echo "Usage: make [target]"
@echo "Available targets:"
@echo " clean - Remove build artifacts"
@echo " verilog - Generate verilog files"
@echo " perf - Run performance tests"
@echo " lab<number> - Run lab<number>, eg. lab1, lab2, ..."
@echo " trace_lab<number> - Run lab<number> with trace, eg. trace_lab1, trace_lab2, ..."
-include ../Makefile

@ -0,0 +1,34 @@
# 🧬 RISCV-DIFFTEST
对 SRAM 结构的 [RISCV-LAB](https://code.educoder.net/ppg69fuwb/riscv-lab) 提供差分测试支持
差分测试框架修改自 [soc-simulator](https://github.com/cyyself/soc-simulator)
## 📑 目录说明
- `core` **存放待测试处理器的代码**,其顶层信号应与 `top_sram_wrapper` 中信号定义一致
- `test` 存放测试代码
- `src` 存放模拟器代码
## 🔨 使用方法
1. 将 CPU 代码放置到相对于本文件夹的 `core` 文件夹中。
2. 在本文件夹下,使用 `make` 命令完成编译,结果位于 `obj_dir/Vtop`
3. 每次修改 CPU 代码后,需要重新 `make`,如果引入了一些时间早于编译产物的代码,需要先 `make clean``make`
## 🧪 参数说明
`makefile` 中已经预置了常用命令,使用 `make help` 查看命令使用方法
在命令 `./obj_dir/Vtop` 后面可以加上不同参数,可以实现不同的功能:
- `无参数` 运行串口测试工具,打印 RISC-V LOGO
- `<测试文件路径> -rvtest` 运行对应测试文件的差分测试
- 在上述命令后继续增加参数:
- `-trace <记录波形时长>` 记录波形,并导出
- `-starttrace <开始记录波形的时刻>` 从指定时刻开始记录一段固定时长的波形
- `-pc` 报错时将额外输出最近的 PC 历史记录
- `-delay` 行为不一致时将继续运行一段时间再停止
- `-cpu_trace` 记录被测试的处理器的程序运行历史信息,生成 trace.txt
- `-perf` 打印处理器运行的IPC数据

@ -0,0 +1,54 @@
module top(
input clock,
input reset,
// Interrupts
input mei, // to PLIC
input msi, // to CLINT
input mti, // to CLINT
input sei, // to PLIC
// inst sram interface
output inst_sram_en,
output [ 3:0] inst_sram_wen,
output [31:0] inst_sram_addr,
output [31:0] inst_sram_wdata,
input [31:0] inst_sram_rdata,
// data sram interface
output data_sram_en,
output [ 7:0] data_sram_wen,
output [31:0] data_sram_addr,
output [63:0] data_sram_wdata,
input [63:0] data_sram_rdata,
// trace debug interface
output debug_commit,
output [63:0] debug_pc,
output [4:0 ] debug_rf_wnum,
output [63:0] debug_rf_wdata
);
PuaCpu core(
.clock (clock),
.reset (reset),
// interrupts
.io_ext_int_mei (mei),
.io_ext_int_mti (mti),
.io_ext_int_msi (msi),
// inst sram interface
.io_inst_sram_en (inst_sram_en),
.io_inst_sram_wen (inst_sram_wen),
.io_inst_sram_addr (inst_sram_addr),
.io_inst_sram_wdata (inst_sram_wdata),
.io_inst_sram_rdata (inst_sram_rdata),
// data sram interface
.io_data_sram_en (data_sram_en),
.io_data_sram_wen (data_sram_wen),
.io_data_sram_addr (data_sram_addr),
.io_data_sram_wdata (data_sram_wdata),
.io_data_sram_rdata (data_sram_rdata),
// debug
.io_debug_pc (debug_pc),
.io_debug_commit (debug_commit),
.io_debug_rf_wnum (debug_rf_wnum),
.io_debug_rf_wdata (debug_rf_wdata)
);
endmodule

@ -0,0 +1,10 @@
#ifndef MMIO_DEV_H
#define MMIO_DEV_H
class mmio_dev {
public:
virtual bool do_read (uint64_t start_addr, uint64_t size, uint8_t* buffer) = 0;
virtual bool do_write(uint64_t start_addr, uint64_t size, const uint8_t* buffer) = 0;
};
#endif

@ -0,0 +1,140 @@
#ifndef MMIO_MEM_H
#define MMIO_MEM_H
#include "mmio_dev.hpp"
#include <fstream>
#include <iostream>
extern bool running;
class mmio_mem : public mmio_dev
{
public:
mmio_mem(size_t size_bytes)
{
mem = new unsigned char[size_bytes];
mem_size = size_bytes;
}
mmio_mem(size_t size_bytes, const unsigned char *init_binary, size_t init_binary_len) : mmio_mem(size_bytes)
{
// Initalize memory
assert(init_binary_len <= size_bytes, "init_binary_len is larger than memory size.");
memcpy(mem, init_binary, init_binary_len);
}
mmio_mem(size_t size_bytes, const char *init_file) : mmio_mem(size_bytes)
{
std::ifstream file(init_file, std::ios::in | std::ios::binary | std::ios::ate);
size_t file_size = file.tellg();
file.seekg(std::ios_base::beg);
if (file_size > mem_size)
{
std::cerr << "mmio_mem size is not big enough for init file." << std::endl;
file_size = size_bytes;
}
file.read((char *)mem, file_size);
}
~mmio_mem()
{
delete[] mem;
}
bool do_read(uint64_t start_addr, uint64_t size, uint8_t *buffer)
{
if (start_addr + size <= mem_size)
{
memcpy(buffer, &mem[start_addr], size);
return true;
}
else if (allow_warp)
{
start_addr %= mem_size;
if (start_addr + size <= mem_size)
{
memcpy(buffer, &mem[start_addr], size);
return true;
}
else
return false;
}
else
return false;
}
bool do_write(uint64_t start_addr, uint64_t size, const uint8_t *buffer)
{
if (start_addr + size <= mem_size)
{
memcpy(&mem[start_addr], buffer, size);
if (diff_mem_write)
{
for (int i = 0; i < size; i++)
if (mem[start_addr + i] != diff_mem[start_addr + i])
{
running = false;
printf("Error writeback cache at addr %lx\n", start_addr + i);
}
}
return true;
}
else if (allow_warp)
{
start_addr %= mem_size;
if (start_addr + size <= mem_size)
{
memcpy(&mem[start_addr], buffer, size);
if (diff_mem_write)
{
for (int i = 0; i < size; i++)
if (mem[start_addr + i] != diff_mem[start_addr + i])
{
running = false;
printf("Error writeback cache at addr %lx\n", start_addr + i);
}
}
return true;
}
else
return false;
}
else
return false;
}
void load_binary(uint64_t start_addr, const char *init_file)
{
std::ifstream file(init_file, std::ios::in | std::ios::binary | std::ios::ate);
size_t file_size = file.tellg();
file.seekg(std::ios_base::beg);
if (start_addr >= mem_size || file_size > mem_size - start_addr)
{
std::cerr << "memory size is not big enough for init file." << std::endl;
file_size = mem_size;
}
file.read((char *)mem + start_addr, file_size);
}
void save_binary(const char *filename)
{
std::ofstream file(filename, std::ios::out | std::ios::binary);
file.write((char *)mem, mem_size);
}
void set_allow_warp(bool value)
{
allow_warp = true;
}
unsigned char *get_mem_ptr()
{
return mem;
}
void set_diff_mem(unsigned char *diff_mem_addr)
{
diff_mem = diff_mem_addr;
diff_mem_write = true;
}
private:
bool diff_mem_write = false;
unsigned char *mem;
unsigned char *diff_mem;
size_t mem_size;
bool allow_warp = false;
};
#endif

@ -0,0 +1,123 @@
#ifndef NSCSCC_SRAM_HPP
#define NSCSCC_SRAM_HPP
#include <verilated.h>
#include <condition_variable>
#include <cstdint>
#include <set>
#define AUTO_SIG(name, msb, lsb) \
typename std::conditional <(msb-lsb+1) <= 8, CData, \
typename std::conditional <(msb-lsb+1) <= 16, SData, \
typename std::conditional <(msb-lsb+1) <= 32, IData, QData >::type >::type >::type name
#define AUTO_IN(name, msb, lsb) AUTO_SIG(name, msb, lsb)
#define AUTO_OUT(name, msb, lsb) AUTO_SIG(name, msb, lsb)
struct nscscc_sram;
struct nscscc_sram_ptr {
// inst channel
AUTO_IN (*inst_sram_en, 0, 0) = NULL;
AUTO_IN (*inst_sram_wen, 3, 0) = NULL;
AUTO_IN (*inst_sram_addr, 31, 0) = NULL;
AUTO_IN (*inst_sram_wdata, 31, 0) = NULL;
AUTO_OUT(*inst_sram_rdata, 31, 0) = NULL;
// data channel
AUTO_IN (*data_sram_en, 0, 0) = NULL;
AUTO_IN (*data_sram_wen, 7, 0) = NULL;
AUTO_IN (*data_sram_addr, 31, 0) = NULL;
AUTO_IN (*data_sram_wdata, 63, 0) = NULL;
AUTO_OUT(*data_sram_rdata, 63, 0) = NULL;
bool check() {
std::set <void*> s;
s.insert((void*)inst_sram_en);
s.insert((void*)inst_sram_wen);
s.insert((void*)inst_sram_addr);
s.insert((void*)inst_sram_wdata);
s.insert((void*)inst_sram_rdata);
s.insert((void*)data_sram_en);
s.insert((void*)data_sram_wen);
s.insert((void*)data_sram_addr);
s.insert((void*)data_sram_wdata);
s.insert((void*)data_sram_rdata);
return s.size() == 10 && s.count(NULL) == 0;
}
};
struct nscscc_sram_ref {
// inst channel
AUTO_IN (&inst_sram_en, 0, 0);
AUTO_IN (&inst_sram_wen, 3, 0);
AUTO_IN (&inst_sram_addr, 31, 0);
AUTO_IN (&inst_sram_wdata, 31, 0);
AUTO_OUT(&inst_sram_rdata, 31, 0);
// data channel
AUTO_IN (&data_sram_en, 0, 0);
AUTO_IN (&data_sram_wen, 7, 0);
AUTO_IN (&data_sram_addr, 31, 0);
AUTO_IN (&data_sram_wdata, 63, 0);
AUTO_OUT(&data_sram_rdata, 63, 0);
nscscc_sram_ref(nscscc_sram_ptr &ptr):
inst_sram_en (*(ptr.inst_sram_en)),
inst_sram_wen (*(ptr.inst_sram_wen)),
inst_sram_addr (*(ptr.inst_sram_addr)),
inst_sram_wdata (*(ptr.inst_sram_wdata)),
inst_sram_rdata (*(ptr.inst_sram_rdata)),
data_sram_en (*(ptr.data_sram_en)),
data_sram_wen (*(ptr.data_sram_wen)),
data_sram_addr (*(ptr.data_sram_addr)),
data_sram_wdata (*(ptr.data_sram_wdata)),
data_sram_rdata (*(ptr.data_sram_rdata))
{}
nscscc_sram_ref(nscscc_sram &sram);
};
struct nscscc_sram {
// inst channel
AUTO_IN (inst_sram_en, 0, 0);
AUTO_IN (inst_sram_wen, 3, 0);
AUTO_IN (inst_sram_addr, 31, 0);
AUTO_IN (inst_sram_wdata, 31, 0);
AUTO_OUT(inst_sram_rdata, 31, 0);
// data channel
AUTO_IN (data_sram_en, 0, 0);
AUTO_IN (data_sram_wen, 7, 0);
AUTO_IN (data_sram_addr, 31, 0);
AUTO_IN (data_sram_wdata, 63, 0);
AUTO_OUT(data_sram_rdata, 63, 0);
nscscc_sram() {
// reset all pointer to zero
memset(this,0,sizeof(*this));
}
void update_input(nscscc_sram_ref &ref) {
inst_sram_en = ref.inst_sram_en;
inst_sram_wen = ref.inst_sram_wen;
inst_sram_addr = ref.inst_sram_addr;
inst_sram_wdata = ref.inst_sram_wdata;
data_sram_en = ref.data_sram_en;
data_sram_wen = ref.data_sram_wen;
data_sram_addr = ref.data_sram_addr;
data_sram_wdata = ref.data_sram_wdata;
}
void update_output(nscscc_sram_ref &ref) {
ref.inst_sram_rdata = inst_sram_rdata;
ref.data_sram_rdata = data_sram_rdata;
}
};
nscscc_sram_ref::nscscc_sram_ref(nscscc_sram &sram):
inst_sram_en (sram.inst_sram_en),
inst_sram_wen (sram.inst_sram_wen),
inst_sram_addr (sram.inst_sram_addr),
inst_sram_wdata (sram.inst_sram_wdata),
inst_sram_rdata (sram.inst_sram_rdata),
data_sram_en (sram.data_sram_en),
data_sram_wen (sram.data_sram_wen),
data_sram_addr (sram.data_sram_addr),
data_sram_wdata (sram.data_sram_wdata),
data_sram_rdata (sram.data_sram_rdata)
{}
#endif

@ -0,0 +1,76 @@
#ifndef NSCSCC_SRAM_SLAVE
#define NSCSCC_SRAM_SLAVE
#include "nscscc_sram.hpp"
#include <utility>
#include <vector>
class nscscc_sram_slave
{
public:
nscscc_sram_slave()
{
}
void beat(nscscc_sram_ref &pin)
{
inst_channel(pin);
data_channel(pin);
}
void inst_channel(nscscc_sram_ref &pin)
{
if (pin.inst_sram_en)
{
assert(!pin.inst_sram_wen);
do_read(pin.inst_sram_addr & address_mask, 4, (uint8_t *)&(pin.inst_sram_rdata));
}
}
void data_channel(nscscc_sram_ref &pin)
{
if (pin.data_sram_en)
{
if (pin.data_sram_wen)
{
std::vector<std::pair<int, int>> write_range = strb_to_range(pin.data_sram_wen);
for (std::pair<int, int> sub_range : write_range)
{
int &addr = sub_range.first;
int &len = sub_range.second;
do_write(((pin.data_sram_addr & address_mask) & 0xfffffff8) + addr, len, ((uint8_t *)&(pin.data_sram_wdata)) + addr);
}
}
do_read(pin.data_sram_addr & address_mask, 8, (uint8_t *)&(pin.data_sram_rdata));
}
}
void set_address_mask(uint32_t new_mask)
{
address_mask = new_mask;
}
protected:
virtual void do_read(uint64_t start_addr, uint64_t size, uint8_t *buffer) = 0;
virtual void do_write(uint64_t start_addr, uint64_t size, const uint8_t *buffer) = 0;
private:
uint32_t address_mask = 0xffffffff;
std::vector<std::pair<int, int>> strb_to_range(AUTO_IN(wen, 7, 0))
{
std::vector<std::pair<int, int>> res;
int l = 0;
while (l < 8)
{
if ((wen >> l) & 1)
{
int r = l;
while ((wen >> r) & 1 && r < 8)
r++;
res.emplace_back(l, r - l);
l = r + 1;
}
else
l++;
}
return res;
}
};
#endif

@ -0,0 +1,94 @@
#ifndef NSCSCC_SRAM_XBAR
#define NSCSCC_SRAM_XBAR
#include "nscscc_sram_slave.hpp"
#include "mmio_dev.hpp"
#include <map>
#include <utility>
#include <algorithm>
#include <climits>
void debug()
{
}
class nscscc_sram_xbar : public nscscc_sram_slave
{
public:
nscscc_sram_xbar()
{
}
bool add_dev(uint64_t start_addr, uint64_t length, mmio_dev *dev, bool byte_mode = false)
{
std::tuple<uint64_t, uint64_t, bool> addr_range = std::make_tuple(start_addr, start_addr + length, byte_mode);
if (start_addr % length)
return false;
// check range
auto it = devices.upper_bound(addr_range);
if (it != devices.end())
{
uint64_t l_max = std::max(std::get<0>(it->first), std::get<0>(addr_range));
uint64_t r_min = std::min(std::get<1>(it->first), std::get<1>(addr_range));
if (l_max < r_min)
return false; // overleap
}
if (it != devices.begin())
{
it = std::prev(it);
uint64_t l_max = std::max(std::get<0>(it->first), std::get<0>(addr_range));
uint64_t r_min = std::min(std::get<1>(it->first), std::get<1>(addr_range));
if (l_max < r_min)
return false; // overleap
}
// overleap check pass
devices[addr_range] = dev;
return true;
}
protected:
void do_read(uint64_t start_addr, uint64_t size, unsigned char *buffer)
{
auto it = devices.upper_bound(std::make_tuple(start_addr, ULONG_MAX, true));
if (it == devices.begin())
{
*((uint32_t *)buffer) = 0xdec0dee3;
return;
}
it = std::prev(it);
if (std::get<0>(it->first) <= start_addr && start_addr + 1 <= std::get<1>(it->first))
{
uint64_t dev_size = std::get<1>(it->first) - std::get<0>(it->first);
if (std::get<2>(it->first))
size = 1; // treat as byte device
else
start_addr -= start_addr & (size - 1);
it->second->do_read(start_addr % dev_size, size, buffer + (start_addr % size));
}
else
*((uint32_t *)buffer) = 0xdec0dee3;
}
void do_write(uint64_t start_addr, uint64_t size, const unsigned char *buffer)
{
auto it = devices.upper_bound(std::make_tuple(start_addr, ULONG_MAX, true));
if (it == devices.begin())
{
*((uint32_t *)buffer) = 0xdec0dee3;
return;
}
it = std::prev(it);
uint64_t end_addr = start_addr + size;
if (std::get<0>(it->first) <= start_addr && end_addr <= std::get<1>(it->first))
{
uint64_t dev_size = std::get<1>(it->first) - std::get<0>(it->first);
it->second->do_write(start_addr % dev_size, size, buffer);
}
else
*((uint32_t *)buffer) = 0xdec0dee3;
}
private:
std::map<std::tuple<uint64_t, uint64_t, bool>, mmio_dev *> devices;
};
#endif

@ -0,0 +1,124 @@
#ifndef RV_CLINT_HPP
#define RV_CLINT_HPP
#include "mmio_dev.hpp"
#include <cstdint>
template <unsigned int nr_hart = 1>
class rv_clint : public mmio_dev
{
public:
rv_clint()
{
mtime = 0;
for (int i = 0; i < nr_hart; i++)
{
mtimecmp[i] = 0;
msip[i] = 0;
}
}
bool do_read(uint64_t start_addr, uint64_t size, unsigned char *buffer)
{
if (start_addr >= 0x4000)
{
// mtimecmp, mtime
if (start_addr >= 0xbff8 && start_addr + size <= 0xc000)
{
// mtime
memcpy(buffer, ((char *)(&mtime)) + start_addr - 0xbff8, size);
// printf("read mtime\n");
}
else if (start_addr >= 0x4000 && start_addr + size <= 0x4000 + 8 * nr_hart)
{
memcpy(buffer, ((char *)(&mtimecmp)) + start_addr - 0x4000, size);
// printf("read mtimecmp\n");
}
else
return false;
}
else
{
// msip
if (start_addr + size <= 4 * nr_hart)
{
memcpy(buffer, ((char *)(&msip)) + start_addr, size);
// printf("read msip\n");
}
else
return false;
}
return true;
}
bool do_write(uint64_t start_addr, uint64_t size, const unsigned char *buffer)
{
if (start_addr >= 0x4000)
{
// mtimecmp, mtime
if (start_addr >= 0xbff8 && start_addr + size <= 0xc000)
{
// mtime
memcpy(((char *)(&mtime)) + start_addr - 0xbff8, buffer, size);
// printf("write mtime\n");
}
else if (start_addr >= 0x4000 && start_addr + size <= 0x4000 + 8 * nr_hart)
{
memcpy(((char *)(&mtimecmp)) + start_addr - 0x4000, buffer, size);
// printf("write mtimecmp %lx mtime %lx size %d diff %lx\n",mtimecmp[0],mtime,(int)size,mtimecmp[0]-mtime);
}
else
return false;
}
else
{
// msip
if (start_addr + size <= 4 * nr_hart)
{
memcpy(((char *)(&msip)) + start_addr, buffer, size);
for (int i = 0; i < nr_hart; i++)
msip[i] &= 1;
// printf("write msip[0] %x\n",msip[0]);
// printf("write msip[0] %x\n",msip[1]);
}
else
return false;
}
return true;
}
void tick()
{
mtime++;
}
void synchronize(uint64_t time)
{
mtime = time;
}
uint64_t get_mtime()
{
return mtime;
}
bool m_s_irq(unsigned int hart_id)
{ // machine software irq
if (hart_id >= nr_hart)
assert(false);
else
return (msip[hart_id] & 1);
}
bool m_t_irq(unsigned int hart_id)
{ // machine timer irq
if (hart_id >= nr_hart)
assert(false);
else
return mtime > mtimecmp[hart_id];
}
void set_cmp(uint64_t new_val)
{
mtimecmp = new_val;
}
private:
uint64_t mtime;
uint64_t mtimecmp[nr_hart];
uint32_t msip[nr_hart];
};
#endif

@ -0,0 +1,466 @@
#ifndef RV_COMMON
#define RV_COMMON
union rv_instr
{
struct rv_r
{
unsigned int opcode : 7;
unsigned int rd : 5;
unsigned int funct3 : 3;
unsigned int rs1 : 5;
unsigned int rs2 : 5;
unsigned int funct7 : 7;
} r_type;
struct rv_i
{
unsigned int opcode : 7;
unsigned int rd : 5;
unsigned int funct3 : 3;
unsigned int rs1 : 5;
int imm12 : 12;
} i_type;
struct rv_s
{
unsigned int opcode : 7;
unsigned int imm_4_0 : 5;
unsigned int funct3 : 3;
unsigned int rs1 : 5;
unsigned int rs2 : 5;
int imm_11_5 : 7;
} s_type;
struct rv_b
{
unsigned int opcode : 7;
unsigned int imm_11 : 1;
unsigned int imm_4_1 : 4;
unsigned int funct3 : 3;
unsigned int rs1 : 5;
unsigned int rs2 : 5;
unsigned int imm_10_5 : 6;
int imm_12 : 1;
} b_type;
struct rv_u
{
unsigned int opcode : 7;
unsigned int rd : 5;
int imm_31_12 : 20;
} u_type;
struct rv_j
{
unsigned int opcode : 7;
unsigned int rd : 5;
unsigned int imm_19_12 : 8;
unsigned int imm_11 : 1;
unsigned int imm_10_1 : 10;
int imm_20 : 1;
} j_type;
};
static_assert(sizeof(rv_instr) == 4, "Instruction Struct Error");
enum rv64i_opcode
{
OPCODE_LUI = 0b0110111,
OPCODE_AUIPC = 0b0010111,
OPCODE_JAL = 0b1101111,
OPCODE_JALR = 0b1100111,
OPCODE_BRANCH = 0b1100011,
OPCODE_LOAD = 0b0000011,
OPCODE_STORE = 0b0100011,
OPCODE_OPIMM = 0b0010011,
OPCODE_OPIMM32 = 0b0011011,
OPCODE_OP = 0b0110011,
OPCODE_OP32 = 0b0111011,
OPCODE_FENCE = 0b0001111,
OPCODE_SYSTEM = 0b1110011,
OPCODE_AMO = 0b0101111
};
// Concat(instr(1,0),instr(15,13))
enum rv64c_opcode
{ // without f/d
OPCODE_C_ADDI4SPN = 0b00000,
OPCODE_C_LW = 0b00010,
OPCODE_C_LD = 0b00011,
OPCODE_C_SW = 0b00110,
OPCODE_C_SD = 0b00111,
OPCODE_C_ADDI = 0b01000,
OPCODE_C_ADDIW = 0b01001,
OPCODE_C_LI = 0b01010,
OPCODE_C_ADDI16SPN_LUI = 0b01011,
OPCODE_C_ALU = 0b01100,
OPCODE_C_J = 0b01101,
OPCODE_C_BEQZ = 0b01110,
OPCODE_C_BNEZ = 0b01111,
OPCODE_C_SLLI = 0b10000,
OPCODE_C_LWSP = 0b10010,
OPCODE_C_LDSP = 0b10011,
OPCODE_C_JR_MV_EB_JALR_ADD = 0b10100,
OPCODE_C_SWSP = 0b10110,
OPCODE_C_SDSP = 0b10111
};
enum rv64c_funct2
{
FUNCT2_SUB = 0b00,
FUNCT2_XOR_ADDW = 0b01,
FUNCT2_OR = 0b10,
FUNCT2_AND = 0b11
};
enum funct3_branch
{
FUNCT3_BEQ = 0b000,
FUNCT3_BNE = 0b001,
FUNCT3_BLT = 0b100,
FUNCT3_BGE = 0b101,
FUNCT3_BLTU = 0b110,
FUNCT3_BGEU = 0b111
};
enum funct3_load
{
FUNCT3_LB = 0b000,
FUNCT3_LH = 0b001,
FUNCT3_LW = 0b010,
FUNCT3_LD = 0b011,
FUNCT3_LBU = 0b100,
FUNCT3_LHU = 0b101,
FUNCT3_LWU = 0b110
};
enum funct3_store
{
FUNCT3_SB = 0b000,
FUNCT3_SH = 0b001,
FUNCT3_SW = 0b010,
FUNCT3_SD = 0b011
};
enum funct3_op
{
FUNCT3_ADD_SUB = 0b000,
FUNCT3_SLL = 0b001,
FUNCT3_SLT = 0b010,
FUNCT3_SLTU = 0b011,
FUNCT3_XOR = 0b100,
FUNCT3_SRL_SRA = 0b101,
FUNCT3_OR = 0b110,
FUNCT3_AND = 0b111
};
enum funct3_m
{
FUNCT3_MUL = 0b000,
FUNCT3_MULH = 0b001,
FUNCT3_MULHSU = 0b010,
FUNCT3_MULHU = 0b011,
FUNCT3_DIV = 0b100,
FUNCT3_DIVU = 0b101,
FUNCT3_REM = 0b110,
FUNCT3_REMU = 0b111
};
enum funct3_system
{
FUNCT3_PRIV = 0b000,
FUNCT3_CSRRW = 0b001,
FUNCT3_CSRRS = 0b010,
FUNCT3_CSRRC = 0b011,
FUNCT3_HLSV = 0b100,
FUNCT3_CSRRWI = 0b101,
FUNCT3_CSRRSI = 0b110,
FUNCT3_CSRRCI = 0b111
};
enum funct7_priv
{
FUNCT7_ECALL_EBREAK = 0b0000000,
FUNCT7_SRET_WFI = 0b0001000,
FUNCT7_MRET = 0b0011000,
FUNCT7_SFENCE_VMA = 0b0001001
};
enum amo_funct
{
AMOLR = 0b00010,
AMOSC = 0b00011,
AMOSWAP = 0b00001,
AMOADD = 0b00000,
AMOXOR = 0b00100,
AMOAND = 0b01100,
AMOOR = 0b01000,
AMOMIN = 0b10000,
AMOMAX = 0b10100,
AMOMINU = 0b11000,
AMOMAXU = 0b11100
};
enum funct7
{
FUNCT7_NORMAL = 0b0000000,
FUNCT7_SUB_SRA = 0b0100000,
FUNCT7_MUL = 0b0000001
};
enum funct6
{
FUNCT6_NORMAL = 0b000000,
FUNCT6_SRA = 0b010000
};
enum priv_mode
{
U_MODE = 0,
S_MODE = 1,
H_MODE = 2,
M_MODE = 3
};
enum rv_csr_addr
{
// Unprivileged Counter/Timers
csr_cycle = 0xc00,
csr_time = 0xc01,
csr_instret = 0xc02,
// Supervisor Trap Setup
csr_sstatus = 0x100,
csr_sie = 0x104,
csr_stvec = 0x105,
csr_scounteren = 0x106,
// Supervisor Trap Handling
csr_sscratch = 0x140,
csr_sepc = 0x141,
csr_scause = 0x142,
csr_stval = 0x143,
csr_sip = 0x144,
// Supervisor Protection and Translation
csr_satp = 0x180,
// Machine Information Registers
csr_mvendorid = 0xf11,
csr_marchid = 0xf12,
csr_mimpid = 0xf13,
csr_mhartid = 0xf14,
csr_mconfigptr = 0xf15,
// Machine Trap Setup
csr_mstatus = 0x300,
csr_misa = 0x301,
csr_medeleg = 0x302,
csr_mideleg = 0x303,
csr_mie = 0x304,
csr_mtvec = 0x305,
csr_mcounteren = 0x306,
// Machine Trap Handling
csr_mscratch = 0x340,
csr_mepc = 0x341,
csr_mcause = 0x342,
csr_mtval = 0x343,
csr_mip = 0x344,
// Machine Memory Protection
csr_pmpcfg0 = 0x3a0,
csr_pmpcfg1 = 0x3a1,
csr_pmpcfg2 = 0x3a2,
csr_pmpcfg3 = 0x3a3,
csr_pmpaddr0 = 0x3b0,
csr_pmpaddr1 = 0x3b1,
csr_pmpaddr2 = 0x3b2,
csr_pmpaddr3 = 0x3b3,
csr_pmpaddr4 = 0x3b4,
csr_pmpaddr5 = 0x3b5,
csr_pmpaddr6 = 0x3b6,
csr_pmpaddr7 = 0x3b7,
csr_pmpaddr8 = 0x3b8,
csr_pmpaddr9 = 0x3b9,
csr_pmpaddr10 = 0x3ba,
csr_pmpaddr11 = 0x3bb,
csr_pmpaddr12 = 0x3bc,
csr_pmpaddr13 = 0x3bd,
csr_pmpaddr14 = 0x3be,
csr_pmpaddr15 = 0x3bf,
// Machine Counter/Timers
csr_mcycle = 0xb00,
csr_minstret = 0xb02,
csr_tselect = 0x7a0,
csr_tdata1 = 0x7a1
};
#define rv_ext(x) (1 << (x - 'a'))
struct csr_misa_def
{
uint64_t ext : 26;
uint64_t blank : 36;
uint64_t mxl : 2;
};
struct csr_mstatus_def
{
uint64_t blank0 : 1;
uint64_t sie : 1; // supervisor interrupt enable
uint64_t blank1 : 1;
uint64_t mie : 1; // machine interrupt enable
uint64_t blank2 : 1;
uint64_t spie : 1; // sie prior to trapping
uint64_t ube : 1; // u big-endian, zero
uint64_t mpie : 1; // mie prior to trapping
uint64_t spp : 1; // supervisor previous privilege mode.
uint64_t vs : 2; // without vector, zero
uint64_t mpp : 2; // machine previous privilege mode.
uint64_t fs : 2; // without float, zero
uint64_t xs : 2; // without user ext, zero
uint64_t mprv : 1; // Modify PRiVilege (Turn on virtual memory and protection for load/store in M-Mode) when mpp is not M-Mode
// mprv will be used by OpenSBI.
uint64_t sum : 1; // permit Supervisor User Memory access
uint64_t mxr : 1; // Make eXecutable Readable
uint64_t tvm : 1; // Trap Virtual Memory (raise trap when sfence.vma and sinval.vma executing in S-Mode)
uint64_t tw : 1; // Timeout Wait for WFI
uint64_t tsr : 1; // Trap SRET
uint64_t blank3 : 9;
uint64_t uxl : 2; // user xlen
uint64_t sxl : 2; // supervisor xlen
uint64_t sbe : 1; // s big-endian
uint64_t mbe : 1; // m big-endian
uint64_t blank4 : 25;
uint64_t sd : 1; // no vs,fs,xs, zero
};
struct csr_sstatus_def
{
uint64_t blank0 : 1;
uint64_t sie : 1; // supervisor interrupt enable
uint64_t blank1 : 3;
uint64_t spie : 1; // sie prior to trapping
uint64_t ube : 1; // u big-endian, zero
uint64_t blank2 : 1; // mie prior to trapping
uint64_t spp : 1; // supervisor previous privilege mode.
uint64_t vs : 2; // without vector, zero
uint64_t blank3 : 2; // machine previous privilege mode.
uint64_t fs : 2; // without float, zero
uint64_t xs : 2; // without user ext, zero
uint64_t blank4 : 1;
uint64_t sum : 1; // permit Supervisor User Memory access
uint64_t mxr : 1; // Make eXecutable Readable
uint64_t blank5 : 12;
uint64_t uxl : 2; // user xlen
uint64_t blank6 : 29;
uint64_t sd : 1; // no vs,fs,xs, zero
};
struct csr_cause_def
{
uint64_t cause : 63;
uint64_t interrupt : 1;
csr_cause_def(uint64_t cause, uint64_t interrupt = 0) : cause(cause), interrupt(interrupt) {}
csr_cause_def() : cause(0), interrupt(0) {}
};
struct csr_tvec_def
{
uint64_t mode : 2; // 0: Direct, 1: Vectored
uint64_t base : 62;
};
struct int_def
{ // interrupt pending
uint64_t blank0 : 1;
uint64_t s_s_ip : 1; // 1
uint64_t blank1 : 1;
uint64_t m_s_ip : 1; // 3
uint64_t blank2 : 1;
uint64_t s_t_ip : 1; // 5
uint64_t blank3 : 1;
uint64_t m_t_ip : 1; // 7
uint64_t blank4 : 1;
uint64_t s_e_ip : 1; // 9
uint64_t blank5 : 1;
uint64_t m_e_ip : 1; // 11
};
enum rv_int_code
{
int_s_sw = 1,
int_m_sw = 3,
int_s_timer = 5,
int_m_timer = 7,
int_s_ext = 9,
int_m_ext = 11
};
// supervisor interrupt mask
const uint64_t s_int_mask = (1ull << int_s_ext) | (1ull << int_s_sw) | (1ull << int_s_timer);
// machine interrupt mask
const uint64_t m_int_mask = s_int_mask | (1ull << int_m_ext) | (1ull << int_m_sw) | (1ull << int_m_timer);
enum rv_exc_code
{
exc_instr_misalign = 0,
exc_instr_acc_fault = 1,
exc_illegal_instr = 2,
exc_breakpoint = 3,
exc_load_misalign = 4,
exc_load_acc_fault = 5,
exc_store_misalign = 6, // including amo
exc_store_acc_fault = 7, // including amo
exc_ecall_from_user = 8,
exc_ecall_from_supervisor = 9,
exc_ecall_from_machine = 11,
exc_instr_pgfault = 12,
exc_load_pgfault = 13,
exc_store_pgfault = 15, // including amo
exc_custom_ok = 24
};
const uint64_t s_exc_mask = (1 << 16) - 1 - (1 << exc_ecall_from_machine);
struct csr_counteren_def
{
uint64_t cycle : 1;
uint64_t time : 1;
uint64_t instr_retire : 1;
uint64_t blank : 61;
};
const uint64_t counter_mask = (1 << 0) | (1 << 2);
struct sv39_pte
{
uint64_t V : 1; // valid
uint64_t R : 1; // read
uint64_t W : 1; // write
uint64_t X : 1; // execute
uint64_t U : 1; // user
uint64_t G : 1; // global
uint64_t A : 1; // access
uint64_t D : 1; // dirty
uint64_t RSW : 2; // reserved for use by supervisor softwar
uint64_t PPN0 : 9;
uint64_t PPN1 : 9;
uint64_t PPN2 : 26;
uint64_t reserved : 7;
uint64_t PBMT : 2; // Svpbmt is not implemented, return 0
uint64_t N : 1;
};
static_assert(sizeof(sv39_pte) == 8, "sv39_pte shoule be 8 bytes.");
// Note: A and D not implement. So use them as permission bit and raise page fault.
struct satp_def
{
uint64_t ppn : 44;
uint64_t asid : 16;
uint64_t mode : 4;
};
struct sv39_va
{
uint64_t page_off : 12;
uint64_t vpn_0 : 9;
uint64_t vpn_1 : 9;
uint64_t vpn_2 : 9;
uint64_t blank : 25;
};
#endif

File diff suppressed because it is too large Load Diff

@ -0,0 +1,136 @@
#ifndef RV_PLIC_HPP
#define RV_PLIC_HPP
#include "mmio_dev.hpp"
#include <cstring>
#include <climits>
#include <bitset>
// We need 2 context corresponding to meip and seip per hart.
template <int nr_source = 1, int nr_context = 2>
class rv_plic : public mmio_dev {
public:
rv_plic() {
for (int i=0;i<(nr_source+1);i++) {
priority[i] = 0;
}
for (int i=0;i<((nr_source+1+31)/32);i++) {
pending[i] = 0;
claimed[i] = 0;
}
for (int i=0;i<nr_context;i++) {
for (int j=0;j<((nr_source+1+31)/32);j++) enable[i][j] = 0;
threshold[i] = 0;
claim[i] = 0;
}
}
void update_ext(int source_id, bool fired) {
pending[source_id/32] &= ~(1u << (source_id % 32));
if (fired) pending[source_id/32] |= 1u << (source_id % 32);
}
bool get_int(int context_id) {
uint64_t max_priority = 0;
uint64_t max_priority_int = 0;
for (int i=1;i<=nr_source;i++) {
if (priority[i] >= threshold[context_id] && (pending[i/32]>>(i%32)) && (enable[context_id][i/32]>>(i%32)) && !(claimed[i/32]>>(i%32))) {
if (priority[i] > max_priority) {
max_priority = priority[i];
max_priority_int = i;
}
}
}
if (max_priority_int) claim[context_id] = max_priority_int;
else claim[context_id] = 0;
return claim[context_id] != 0;
}
bool do_read(uint64_t start_addr, uint64_t size, unsigned char* buffer) {
// printf("PLIC read: 0x%lx, size: 0x%lx\n", start_addr, size);
// assert(size == 4);
if (start_addr + size <= 0x1000) { // [0x4,0x1000] interrupt source priority
if (start_addr == 0) return false;
if (start_addr > 4 * nr_source || start_addr + size > 4 * (nr_source + 1)) return false;
*((uint32_t*)buffer) = priority[start_addr/4];
return true;
}
else if (start_addr + size <= 0x1080) { // [0x1000,0x1080] interrupt pending bits
uint64_t idx = (start_addr - 0x1000) / 4;
if (idx > nr_source) return false;
*((uint32_t*)buffer) = pending[idx];
return true;
}
else if (start_addr + size <= 0x2000) {
return false; // error
}
else if (start_addr + size <= 0x200000) { // enable bits for sources on context
uint64_t context_id = (start_addr - 0x2000) / 0x80;
uint64_t pos = start_addr % 0x80;
if (context_id >= nr_context) return false;
if (pos > nr_source) return false;
*((uint32_t*)buffer) = enable[context_id][pos];
return true;
}
else { // priority threshold and claim/complete
uint64_t context_id = (start_addr - 0x200000) / 0x1000;
if (context_id > nr_context) return false;
uint64_t offset = start_addr % 0x1000;
if (offset == 0) { // priority threshold
*((uint32_t*)buffer) = threshold[context_id];
return true;
}
else if (offset == 4) { // claim/complete
(*((uint32_t*)buffer)) = claim[context_id];
claimed[claim[context_id]/32] |= 1u << (claim[context_id]%32);
return true;
}
else return false;
}
return true;
}
bool do_write(uint64_t start_addr, uint64_t size, const unsigned char* buffer) {
if (start_addr + size <= 0x1000) { // [0x4,0x1000] interrupt source priority
if (start_addr == 0) return false;
if (start_addr > 4 * nr_source || start_addr + size > 4 * (nr_source + 1)) return false;
priority[start_addr/4] = *((uint32_t*)buffer);
return true;
}
else if (start_addr + size <= 0x1080) { // [0x1000,0x1080] interrupt pending bits
return true;
}
else if (start_addr + size <= 0x2000) {
return false; // error
}
else if (start_addr + size <= 0x200000) { // enable bits for sources on context
uint64_t context_id = (start_addr - 0x2000) / 0x80;
uint64_t pos = start_addr % 0x80;
if (context_id >= nr_context) return false;
if (pos > nr_source) return false;
enable[context_id][pos] = *((uint32_t*)buffer);
return true;
}
else { // priority threshold and claim/complete
uint64_t context_id = (start_addr - 0x200000) / 0x1000;
if (context_id > nr_context) return false;
uint64_t offset = start_addr % 0x1000;
if (offset == 0) { // priority threshold
threshold[context_id] = *((uint32_t*)buffer);
return true;
}
else if (offset == 4) { // claim/complete
claimed[(*((uint32_t*)buffer))/32] &= ~(1u << ((*((uint32_t*)buffer)%32)));
return true;
}
else return false;
}
return true;
}
private:
// source 0 is reserved.
uint32_t priority[nr_source+1];
uint32_t pending[(nr_source+1+31)/32];
uint32_t enable[nr_context][(nr_source+1+31)/32];
uint32_t threshold[nr_context];
uint32_t claim[nr_context];
uint32_t claimed[(nr_source+1+31)/32];
};
#endif

@ -0,0 +1,803 @@
#ifndef RV_CSR_HPP
#define RV_CSR_HPP
#include <cstdint>
#include <cstring>
#include <bitset>
#include <assert.h>
#include "rv_common.hpp"
#include "rv_systembus.hpp"
#include "rv_sv39.hpp"
extern bool run_riscv_test;
extern bool perf_counter;
extern long long total_instr;
extern long long total_cycle;
extern bool only_modeM;
class rv_priv
{
public:
void difftest_preexec(uint64_t pua_mcycle, uint64_t pua_minstret, uint64_t pua_mip, bool interrupt_on)
{
cur_need_trap = false;
mcycle = pua_mcycle;
minstret = pua_minstret;
ip = pua_mip;
cur_priv = next_priv;
}
rv_priv(uint64_t hart_id, uint64_t &pc, rv_systembus &bus) : hart_id(hart_id), cur_pc(pc), bus(bus), sv39(bus)
{
reset();
}
void reset()
{
trap_pc = 0;
cur_need_trap = false;
cur_priv = M_MODE;
next_priv = M_MODE;
status = 0;
csr_mstatus_def *mstatus = (csr_mstatus_def *)&status;
csr_misa_def *isa = (csr_misa_def *)&misa;
if (run_riscv_test)
{
if (only_modeM)
{
// 只实现M-Mode的CPU
isa->ext = rv_ext('i') | rv_ext('m');
mstatus->mpp = M_MODE;
}
else
{
// 实现M-Mode和U-Mode的CPU
mstatus->uxl = 2;
isa->ext = rv_ext('i') | rv_ext('m') | rv_ext('u');
}
}
isa->mxl = 2; // rv64
isa->blank = 0;
medeleg = 0;
mideleg = 0;
ie = 0;
mtvec = 0;
mscratch = 0;
mepc = 0;
mcause = 0;
mtval = 0;
mcounteren = 0;
ip = 0;
mcycle = 0;
minstret = 0;
stvec = 0;
sscratch = 0;
sepc = 0;
scause = 0;
stval = 0;
satp = 0;
scounteren = 0;
}
void check_and_raise_int()
{ // TODO: Find interrupts trap priority compare to exceptions. Now interrupts are prior to exceptions.
/*
An interrupt i will trap to M-mode (causing the privilege mode to change to M-mode) if all of
the following are true: (a) either the current privilege mode is M and the MIE bit in the mstatus
register is set, or the current privilege mode has less privilege than M-mode; (b) bit i is set in both
mip and mie; and (c) if register mideleg exists, bit i is not set in mideleg
*/
/*
An interrupt i will trap to S-mode if both of the following are true: (a) either the current privilege
mode is S and the SIE bit in the sstatus register is set, or the current privilege mode has less
privilege than S-mode; and (b) bit i is set in both sip and sie.
*/
/*
out of spec: mideleg layout as sip rather than mip.
M[EST]I bits in mideleg is hardwired 0.
OpenSBI will not delegate these ints to S-Mode. So we don't need to implement.
*/
// Note: WFI is not affacted by mstatus.mie and mstatus.sie and mideleg, but we implement WFI as nop currently.
csr_mstatus_def *mstatus = (csr_mstatus_def *)&status;
uint64_t int_bits = ip & ie;
uint64_t final_int_index = exc_custom_ok;
if (cur_priv == M_MODE)
{
// Note: We should use mideleg as interrupt disable in M-Mode as interrupts didn't transfer to lower levels.
uint64_t mmode_int_bits = int_bits & (~mideleg);
if (mmode_int_bits && mstatus->mie)
final_int_index = int2index(mmode_int_bits);
}
else
{
// check traps to smode or mmode
uint64_t int_index = int2index(int_bits);
if ((1ul << int_index) & mideleg)
{ // delegate to s
// Note: If delegate to S but sie is 0, we should not raise trap to M-Mode.
if (mstatus->sie || cur_priv < S_MODE)
final_int_index = int_index;
}
else
{
if (mstatus->mie || cur_priv < M_MODE)
final_int_index = int_index;
}
}
if (final_int_index != exc_custom_ok)
raise_trap(csr_cause_def(final_int_index, 1));
}
void pre_exec(bool meip, bool msip, bool mtip, bool seip)
{
mcycle++;
int_def *ip_bits = (int_def *)&ip;
ip_bits->m_e_ip = meip;
ip_bits->m_s_ip = msip;
ip_bits->m_t_ip = mtip;
ip_bits->s_e_ip = seip;
cur_need_trap = false;
cur_priv = next_priv;
check_and_raise_int();
}
bool need_trap()
{
return cur_need_trap;
}
uint64_t get_trap_pc()
{
return trap_pc;
}
void post_exec()
{
if (!cur_need_trap)
minstret++;
cur_need_trap = false;
csr_mstatus_def *mstatus = (csr_mstatus_def *)&status;
assert(mstatus->blank0 == 0);
assert(mstatus->blank1 == 0);
assert(mstatus->blank2 == 0);
assert(mstatus->blank3 == 0);
assert(mstatus->blank4 == 0);
}
// The following CSR operations didn't check permissions.
// If the csr didn't exist, return false. (and core should call raise_trap to raise illeagal instruction)
bool csr_read(rv_csr_addr csr_index, uint64_t &csr_result)
{
switch (csr_index)
{
case csr_mvendorid:
csr_result = 0;
break;
case csr_marchid:
csr_result = 0;
break;
case csr_mimpid:
csr_result = 0;
break;
case csr_mhartid:
csr_result = hart_id;
break;
case csr_mconfigptr:
csr_result = 0;
break;
case csr_mstatus:
csr_result = status;
break;
case csr_misa:
{
csr_result = misa;
break;
}
case csr_medeleg:
csr_result = medeleg;
break;
case csr_mideleg:
csr_result = mideleg;
break;
case csr_mie:
csr_result = ie;
break;
case csr_mtvec:
csr_result = mtvec;
break;
case csr_mcounteren:
csr_result = mcounteren;
break;
case csr_mscratch:
csr_result = mscratch;
break;
case csr_mepc:
csr_result = mepc;
break;
case csr_mcause:
csr_result = mcause;
break;
case csr_mtval:
csr_result = mtval;
break;
case csr_mip:
csr_result = ip;
break;
case csr_mcycle:
csr_result = mcycle;
break;
case csr_minstret:
csr_result = minstret;
break;
case csr_cycle:
{
csr_result = mcycle;
break;
}
case csr_tselect:
csr_result = 1;
break;
case csr_tdata1:
csr_result = 0;
break;
default:
{
csr_result = 0;
return false;
}
}
return true;
}
bool csr_write(rv_csr_addr csr_index, uint64_t csr_data)
{
switch (csr_index)
{
case csr_misa:
{
break;
}
case csr_mstatus:
{
csr_mstatus_def *nstatus = (csr_mstatus_def *)&csr_data;
csr_mstatus_def *mstatus = (csr_mstatus_def *)&status;
if (only_modeM && run_riscv_test)
{
mstatus->mie = nstatus->mie;
mstatus->mpie = nstatus->mpie;
}
else
{
// mstatus->sie = nstatus->sie;
mstatus->mie = nstatus->mie;
// mstatus->spie = nstatus->spie;
mstatus->mpie = nstatus->mpie;
assert(mstatus->spie != 2);
assert(mstatus->mpie != 2);
// mstatus->spp = nstatus->spp;
mstatus->mpp = (nstatus->mpp == 3 || nstatus->mpp == 0) ? nstatus->mpp : mstatus->mpp;
mstatus->mprv = nstatus->mprv;
// mstatus->sum = nstatus->sum; // always true
// mstatus->mxr = nstatus->mxr; // always true
// mstatus->tvm = nstatus->tvm;
// mstatus->tw = nstatus->tw; // not supported but wfi impl as nop
// mstatus->tsr = nstatus->tsr;
}
break;
}
case csr_mie:
ie = csr_data & m_int_mask;
break;
case csr_mtvec:
{
csr_tvec_def *tvec = (csr_tvec_def *)&csr_data;
assert(tvec->mode <= 1);
mtvec = csr_data;
break;
}
case csr_mcounteren:
{
break;
}
case csr_mscratch:
mscratch = csr_data;
break;
case csr_mepc:
mepc = csr_data;
break;
case csr_mcause:
mcause = csr_data;
break;
case csr_mtval:
mtval = csr_data;
break;
case csr_mip:
ip = csr_data & m_int_mask;
break;
case csr_mcycle:
mcycle = csr_data;
break;
case csr_tselect:
break;
case csr_tdata1:
break;
default:
return false;
}
return true;
}
bool csr_setbit(rv_csr_addr csr_index, uint64_t csr_mask)
{
uint64_t tmp;
bool ret = csr_read(csr_index, tmp);
if (!ret)
return false;
tmp |= csr_mask;
ret &= csr_write(csr_index, tmp);
return ret;
}
bool csr_clearbit(rv_csr_addr csr_index, uint64_t csr_mask)
{
uint64_t tmp;
bool ret = csr_read(csr_index, tmp);
if (!ret)
return false;
tmp &= ~csr_mask;
ret &= csr_write(csr_index, tmp);
return ret;
}
bool csr_op_permission_check(uint16_t csr_index, bool write)
{
/*
We can make a simple implementation for csr_cycle as following:
0. "cycle" is the only user level CSR we need to implement to pass the RISC-V Test.
1. mcounteren can be read only zero, so any privilege level other than Machine will cause trap.
2. If S-Mode didn't implement, we can just check whether the privilege mode is Machine for illegal instruction check.
*/
if (cur_priv != M_MODE)
return false;
if ((((csr_index >> 10) & 3) == 3) && write)
return false;
return true;
}
// Note: The core should raise exceptions when return value is not exc_custom_ok.
// fetch instruction
rv_exc_code va_if(uint64_t start_addr, uint64_t size, uint8_t *buffer, uint64_t &bad_va)
{
if (size == 4 && start_addr % 4 == 2)
{
rv_exc_code res0 = va_if(start_addr, 2, buffer, bad_va);
if (res0 != exc_custom_ok)
return res0;
rv_exc_code res1 = va_if(start_addr + 2, 2, buffer + 2, bad_va);
if (res1 != exc_custom_ok)
return res1;
return exc_custom_ok;
}
else
{
bad_va = start_addr;
const satp_def *satp_reg = (satp_def *)&satp;
if (cur_priv == M_MODE || satp_reg->mode == 0)
{
bool pstatus = bus.pa_read(start_addr, size, buffer);
if (!pstatus)
return exc_instr_acc_fault;
else
return exc_custom_ok;
}
else
{
// Note: If the pc misalign but didn't beyond page range, the exception should be raise by core.
if ((start_addr >> 12) != ((start_addr + size - 1) >> 12))
return exc_instr_misalign;
sv39_tlb_entry *tlb_e = sv39.local_tlbe_get(*satp_reg, start_addr);
if (!tlb_e || !tlb_e->A || !tlb_e->X)
return exc_instr_pgfault;
if ((cur_priv == U_MODE && !tlb_e->U) || (cur_priv == S_MODE && tlb_e->U))
return exc_instr_pgfault;
uint64_t pa = tlb_e->ppa + (start_addr % ((tlb_e->pagesize == 1) ? (1 << 12) : ((tlb_e->pagesize == 2) ? (1 << 21) : (1 << 30))));
bool pstatus = bus.pa_read(pa, size, buffer);
if (!pstatus)
return exc_instr_acc_fault;
else
return exc_custom_ok;
}
}
}
rv_exc_code va_read(uint64_t start_addr, uint64_t size, uint8_t *buffer)
{
const satp_def *satp_reg = (satp_def *)&satp;
const csr_mstatus_def *mstatus = (csr_mstatus_def *)&status;
if ((cur_priv == M_MODE && (!mstatus->mprv || mstatus->mpp == M_MODE)) || satp_reg->mode == 0)
{
bool pstatus = bus.pa_read(start_addr, size, buffer);
if (!pstatus)
return exc_load_acc_fault;
else
return exc_custom_ok;
}
else
{
if ((start_addr >> 12) != ((start_addr + size - 1) >> 12))
return exc_load_misalign;
sv39_tlb_entry *tlb_e = sv39.local_tlbe_get(*satp_reg, start_addr);
if (!tlb_e || !tlb_e->A || (!tlb_e->R && !(mstatus->mxr && !tlb_e->X)))
return exc_load_pgfault;
priv_mode priv = (mstatus->mprv && cur_priv == M_MODE) ? static_cast<priv_mode>(mstatus->mpp) : cur_priv;
if (priv == U_MODE && !tlb_e->U)
return exc_load_pgfault;
if (!mstatus->sum && priv == S_MODE && tlb_e->U)
return exc_load_acc_fault;
uint64_t pa = tlb_e->ppa + (start_addr % ((tlb_e->pagesize == 1) ? (1 << 12) : ((tlb_e->pagesize == 2) ? (1 << 21) : (1 << 30))));
bool pstatus = bus.pa_read(pa, size, buffer);
if (!pstatus)
return exc_load_acc_fault;
else
return exc_custom_ok;
}
}
rv_exc_code va_write(uint64_t start_addr, uint64_t size, const uint8_t *buffer)
{
const satp_def *satp_reg = (satp_def *)&satp;
const csr_mstatus_def *mstatus = (csr_mstatus_def *)&status;
if ((cur_priv == M_MODE && (!mstatus->mprv || mstatus->mpp == M_MODE)) || satp_reg->mode == 0)
{
if (run_riscv_test)
{
if (start_addr == 0x80001000)
{
uint64_t tohost = *(uint64_t *)buffer;
if (tohost == 1)
{
if (tohost == 1)
{
printf("\033[32mTest Pass!\n");
if (perf_counter)
{
printf("Total instr: %lld\n", total_instr);
printf("Total cycle: %lld\n", total_cycle);
printf("IPC: %lf\n", (double)total_instr / total_cycle);
}
printf("\033[0m"); // Reset the text color to default
exit(0);
}
else
{
printf("Failed with value 0x%lx\n", tohost);
exit(1);
}
}
}
}
bool pstatus = bus.pa_write(start_addr, size, buffer);
if (!pstatus)
return exc_store_acc_fault;
else
return exc_custom_ok;
}
else
{
if ((start_addr >> 12) != ((start_addr + size - 1) >> 12))
return exc_store_misalign;
sv39_tlb_entry *tlb_e = sv39.local_tlbe_get(*satp_reg, start_addr);
if (!tlb_e || !tlb_e->A || !tlb_e->D || !tlb_e->W)
return exc_store_pgfault;
priv_mode priv = (mstatus->mprv && cur_priv == M_MODE) ? static_cast<priv_mode>(mstatus->mpp) : cur_priv;
if (priv == U_MODE && !tlb_e->U)
return exc_store_pgfault;
if (!mstatus->sum && priv == S_MODE && tlb_e->U)
return exc_store_pgfault;
uint64_t pa = tlb_e->ppa + (start_addr % ((tlb_e->pagesize == 1) ? (1 << 12) : ((tlb_e->pagesize == 2) ? (1 << 21) : (1 << 30))));
if (run_riscv_test)
{
if (pa == 0x80001000)
{
uint64_t tohost = *(uint64_t *)buffer;
if (tohost == 1)
{
if (tohost == 1)
{
printf("\033[32mTest Pass!\n");
if (perf_counter)
{
printf("Total instr: %lld\n", total_instr);
printf("Total cycle: %lld\n", total_cycle);
printf("IPC: %lf\n", (double)total_instr / total_cycle);
}
printf("\033[0m"); // Reset the text color to default
exit(0);
}
else
{
printf("Failed with value 0x%lx\n", tohost);
exit(1);
}
}
}
}
bool pstatus = bus.pa_write(pa, size, buffer);
if (!pstatus)
return exc_store_pgfault;
else
return exc_custom_ok;
}
}
// note: core should check whether amoop and start_addr is valid
rv_exc_code va_lr(uint64_t start_addr, uint64_t size, uint8_t *buffer)
{
assert(size == 4 || size == 8);
const satp_def *satp_reg = (satp_def *)&satp;
const csr_mstatus_def *mstatus = (csr_mstatus_def *)&status;
if ((cur_priv == M_MODE && (!mstatus->mprv || mstatus->mpp == M_MODE)) || satp_reg->mode == 0)
{
bool pstatus = bus.pa_lr(start_addr, size, buffer, hart_id);
if (!pstatus)
return exc_store_acc_fault;
else
return exc_custom_ok;
}
else
{
if ((start_addr >> 12) != ((start_addr + size - 1) >> 12))
return exc_store_misalign;
sv39_tlb_entry *tlb_e = sv39.local_tlbe_get(*satp_reg, start_addr);
if (!tlb_e || !tlb_e->A || (!tlb_e->R && !(mstatus->mxr && !tlb_e->X)))
return exc_store_pgfault;
priv_mode priv = (mstatus->mprv && cur_priv == M_MODE) ? static_cast<priv_mode>(mstatus->mpp) : cur_priv;
if (priv == U_MODE && !tlb_e->U)
return exc_store_pgfault;
if (!mstatus->sum && priv == S_MODE && tlb_e->U)
return exc_store_acc_fault;
uint64_t pa = tlb_e->ppa + (start_addr % ((tlb_e->pagesize == 1) ? (1 << 12) : ((tlb_e->pagesize == 2) ? (1 << 21) : (1 << 30))));
bool pstatus = bus.pa_lr(pa, size, buffer, hart_id);
if (!pstatus)
return exc_store_acc_fault;
else
return exc_custom_ok;
}
}
// Note: if va_sc return != exc_custom_ok, sc_fail shouldn't commit.
rv_exc_code va_sc(uint64_t start_addr, uint64_t size, const uint8_t *buffer, bool &sc_fail)
{
assert(size == 4 || size == 8);
const satp_def *satp_reg = (satp_def *)&satp;
const csr_mstatus_def *mstatus = (csr_mstatus_def *)&status;
if ((cur_priv == M_MODE && (!mstatus->mprv || mstatus->mpp == M_MODE)) || satp_reg->mode == 0)
{
bool pstatus = bus.pa_sc(start_addr, size, buffer, hart_id, sc_fail);
if (!pstatus)
return exc_store_acc_fault;
else
return exc_custom_ok;
}
else
{
if ((start_addr >> 12) != ((start_addr + size - 1) >> 12))
return exc_store_misalign;
sv39_tlb_entry *tlb_e = sv39.local_tlbe_get(*satp_reg, start_addr);
if (!tlb_e || !tlb_e->A || !tlb_e->D || !tlb_e->W)
return exc_store_pgfault;
priv_mode priv = (mstatus->mprv && cur_priv == M_MODE) ? static_cast<priv_mode>(mstatus->mpp) : cur_priv;
if (priv == U_MODE && !tlb_e->U)
return exc_store_pgfault;
if (!mstatus->sum && priv == S_MODE && tlb_e->U)
return exc_store_pgfault;
uint64_t pa = tlb_e->ppa + (start_addr % ((tlb_e->pagesize == 1) ? (1 << 12) : ((tlb_e->pagesize == 2) ? (1 << 21) : (1 << 30))));
bool pstatus = bus.pa_sc(pa, size, buffer, hart_id, sc_fail);
if (!pstatus)
return exc_store_pgfault;
else
return exc_custom_ok;
}
}
rv_exc_code va_amo(uint64_t start_addr, uint64_t size, amo_funct op, int64_t src, int64_t &dst)
{
assert(size == 4 || size == 8);
const satp_def *satp_reg = (satp_def *)&satp;
const csr_mstatus_def *mstatus = (csr_mstatus_def *)&status;
if ((cur_priv == M_MODE && (!mstatus->mprv || mstatus->mpp == M_MODE)) || satp_reg->mode == 0)
{
bool pstatus = bus.pa_amo_op(start_addr, size, op, src, dst);
if (!pstatus)
return exc_store_acc_fault;
else
return exc_custom_ok;
}
else
{
if ((start_addr >> 12) != ((start_addr + size - 1) >> 12))
return exc_store_misalign;
sv39_tlb_entry *tlb_e = sv39.local_tlbe_get(*satp_reg, start_addr);
if (!tlb_e || !tlb_e->A || !tlb_e->D || !tlb_e->W)
return exc_store_pgfault;
priv_mode priv = (mstatus->mprv && cur_priv == M_MODE) ? static_cast<priv_mode>(mstatus->mpp) : cur_priv;
if (priv == U_MODE && !tlb_e->U)
return exc_store_pgfault;
if (!mstatus->sum && priv == S_MODE && tlb_e->U)
return exc_store_pgfault;
uint64_t pa = tlb_e->ppa + (start_addr % ((tlb_e->pagesize == 1) ? (1 << 12) : ((tlb_e->pagesize == 2) ? (1 << 21) : (1 << 30))));
bool pstatus = bus.pa_amo_op(pa, size, op, src, dst);
if (!pstatus)
return exc_store_pgfault;
else
return exc_custom_ok;
}
}
void ecall()
{
csr_cause_def cause;
cause.cause = cur_priv + 8;
cause.interrupt = 0;
raise_trap(cause);
}
void ebreak()
{
csr_cause_def cause;
cause.cause = exc_breakpoint;
cause.interrupt = 0;
raise_trap(cause);
}
bool mret()
{ // if return false, raise illegal instruction
if (cur_priv != M_MODE)
return false;
csr_mstatus_def *mstatus = (csr_mstatus_def *)&status;
mstatus->mie = mstatus->mpie;
next_priv = static_cast<priv_mode>(mstatus->mpp);
mstatus->mpie = 1;
if (mstatus->mpp != M_MODE)
mstatus->mprv = 0;
mstatus->mpp = U_MODE;
cur_need_trap = true;
trap_pc = mepc;
return true;
}
bool sret()
{ // if return false, raise illegal instruction
const csr_mstatus_def *mstatus = (csr_mstatus_def *)&status;
if (cur_priv < S_MODE || mstatus->tsr)
return false;
csr_mstatus_def *sstatus = (csr_mstatus_def *)&status;
sstatus->sie = sstatus->spie;
next_priv = static_cast<priv_mode>(sstatus->spp);
sstatus->spie = 1;
if (sstatus->spp != M_MODE)
sstatus->mprv = 0; // It's correct to set mprv rather than sprv.
sstatus->spp = U_MODE;
cur_need_trap = true;
trap_pc = sepc;
return true;
}
bool sfence_vma(uint64_t vaddr, uint64_t asid)
{
const csr_mstatus_def *mstatus = (csr_mstatus_def *)&status;
if (cur_priv < S_MODE || (cur_priv == S_MODE && mstatus->tvm))
return false;
sv39.sfence_vma(vaddr, asid);
return true;
}
void raise_trap(csr_cause_def cause, uint64_t tval = 0)
{
assert(!cur_need_trap);
cur_need_trap = true;
bool trap_to_s = false;
// printf("trap %ld, tval = 0x%lx, pc=0x%lx, mode=%d\n",cause.cause,tval,cur_pc,cur_priv);
// check delegate to s
if (cur_priv != M_MODE)
{
if (cause.interrupt)
{
if (mideleg & (1 << cause.cause))
trap_to_s = true;
}
else
{
if (medeleg & (1 << cause.cause))
trap_to_s = true;
}
}
if (trap_to_s)
{
stval = tval;
scause = *((uint64_t *)&cause);
sepc = cur_pc;
csr_sstatus_def *sstatus = (csr_sstatus_def *)&status;
sstatus->spie = sstatus->sie;
sstatus->sie = 0;
sstatus->spp = cur_priv;
csr_tvec_def *tvec = (csr_tvec_def *)&stvec;
trap_pc = (tvec->base << 2) + ((tvec->mode == 1) ? (cause.cause) * 4 : 0);
next_priv = S_MODE;
}
else
{
mtval = tval;
mcause = *((uint64_t *)&cause);
mepc = cur_pc;
csr_mstatus_def *mstatus = (csr_mstatus_def *)&status;
mstatus->mpie = mstatus->mie;
mstatus->mie = 0;
mstatus->mpp = cur_priv;
csr_tvec_def *tvec = (csr_tvec_def *)&mtvec;
trap_pc = (tvec->base << 2) + (tvec->mode ? (cause.cause) * 4 : 0);
next_priv = M_MODE;
}
if (cause.cause == exc_instr_pgfault && tval == trap_pc)
assert(false);
}
uint64_t get_cycle()
{
return mcycle;
}
private:
uint64_t int2index(uint64_t int_mask)
{ // with priority
/*
According to spec, multiple simultaneous
interrupts destined for M-mode are handled
in the following decreasing :
MEI, MSI, MTI, SEI, SSI, STI.
*/
if (int_mask & (1ull << int_m_ext))
{
return int_m_ext;
}
else if (int_mask & (1ull << int_m_sw))
{
return int_m_sw;
}
else if (int_mask & (1ull << int_m_timer))
{
return int_m_timer;
}
else if (int_mask & (1ull << int_s_ext))
{
return int_s_ext;
}
else if (int_mask & (1ull << int_s_sw))
{
return int_s_sw;
}
else if (int_mask & (1ull << int_s_timer))
{
return int_s_timer;
}
else
return exc_custom_ok;
}
// status
const uint64_t &cur_pc;
priv_mode cur_priv;
uint64_t hart_id;
// hart
bool cur_need_trap;
uint64_t trap_pc;
priv_mode next_priv;
// sv39
rv_sv39<32> sv39;
// pbus
rv_systembus &bus;
// CSRs
uint64_t status;
uint64_t misa;
uint64_t medeleg;
uint64_t mideleg;
uint64_t ie;
uint64_t mtvec;
uint64_t mscratch;
uint64_t mepc;
uint64_t mcause;
uint64_t mtval;
uint64_t mcounteren;
uint64_t ip;
uint64_t mcycle;
uint64_t minstret;
uint64_t stvec;
uint64_t sscratch;
uint64_t sepc;
uint64_t scause;
uint64_t stval;
uint64_t satp;
uint64_t scounteren;
};
#endif

@ -0,0 +1,218 @@
#ifndef RV_SV39_HPP
#define RV_SV39_HPP
#include <cstdint>
#include <utility>
#include "rv_common.hpp"
#include "rv_systembus.hpp"
struct sv39_tlb_entry
{
uint64_t ppa;
uint64_t vpa;
uint16_t asid;
uint8_t pagesize; // 0: invalid, 1: 4KB , 2: 2M, 3: 1G
bool R; // read
bool W; // write
bool X; // execute
bool U; // user
bool G; // global
bool A; // access
bool D; // dirty
};
#ifdef MM_SANITIZER
void mmassert(bool exp, uint64_t satp, uint64_t va, const char *msg = "")
{
if (!exp)
{
printf("TLB Assert False. satp=%lx, va=%lx\n", satp, va);
printf("%s\n", msg);
}
}
#endif
template <unsigned int nr_tlb_entry = 32>
class rv_sv39
{
public:
rv_sv39(rv_systembus &bus) : bus(bus)
{
random = 0;
for (int i = 0; i < nr_tlb_entry; i++)
tlb[i].pagesize = 0;
}
void sfence_vma(uint64_t vaddr, uint64_t asid)
{
for (int i = 0; i < nr_tlb_entry; i++)
{
if (tlb[i].asid == asid || asid == 0)
{
if (vaddr == 0)
tlb[i].pagesize = 0;
else
{
switch (tlb[i].pagesize)
{
case 1: // 4KB
if ((tlb[i].vpa & (-(1ll << 12))) == (vaddr & (-(1ll << 12))))
tlb[i].pagesize = 0;
break;
case 2: // 2MB
if ((tlb[i].vpa & (-(1ll << 21))) == (vaddr & (-(1ll << 21))))
tlb[i].pagesize = 0;
break;
case 3: // 1G
if ((tlb[i].vpa & (-(1ll << 30))) == (vaddr & (-(1ll << 30))))
tlb[i].pagesize = 0;
default:
break;
}
}
}
}
}
sv39_tlb_entry *local_tlbe_get(satp_def satp, uint64_t va)
{
sv39_va *va_struct = (sv39_va *)&va;
assert((va_struct->blank == 0b1111111111111111111111111 && (va_struct->vpn_2 >> 8)) || (va_struct->blank == 0 && ((va_struct->vpn_2 >> 8) == 0)));
// we should raise access fault before call sv39
sv39_tlb_entry *res = local_tlb_get(satp, va);
if (res)
{
#ifdef MM_SANITIZER
sv39_pte pte2;
uint64_t page_size2;
bool ptw_result2 = ptw(satp, va, pte2, page_size2);
mmassert(ptw_result2, *((uint64_t *)&satp), va, "ptw ok");
uint64_t ppa = (((((uint64_t)pte2.PPN2 << 9) | (uint64_t)pte2.PPN1) << 9) | (uint64_t)pte2.PPN0) << 12;
mmassert(ppa == res->ppa, *((uint64_t *)&satp), va, "ppa");
mmassert(satp.asid == res->asid || pte2.G, *((uint64_t *)&satp), va, "asid");
mmassert((8ll << (res->pagesize * 9)) == page_size2, *((uint64_t *)&satp), va, "page_size");
mmassert(res->R <= pte2.R, *((uint64_t *)&satp), va, "R");
if (res->W != pte2.W)
printf("error at asid %lx\n", (uint64_t)satp.asid);
// res->W = pte2.W;
mmassert(res->W <= pte2.W, *((uint64_t *)&satp), va, "W");
mmassert(res->X <= pte2.X, *((uint64_t *)&satp), va, "X");
mmassert(res->U <= pte2.U, *((uint64_t *)&satp), va, "U");
mmassert(res->G == pte2.G, *((uint64_t *)&satp), va, "G");
mmassert(res->A <= pte2.A, *((uint64_t *)&satp), va, "A");
mmassert(res->D <= pte2.D, *((uint64_t *)&satp), va, "D");
#endif
return res; // 如果tlb hit直接返回
}
// 如果tlb miss需要进行ptw
// slow path, ptw
// printf("va = %lx\n", va);
// printf("tlb miss\n");
sv39_pte pte;
uint64_t page_size;
bool ptw_result = ptw(satp, va, pte, page_size);
if (!ptw_result)
{
// printf("page fault\n");
return NULL;
} // return null when page fault.
// write back to tlb
res = &tlb[random];
random = (random + 1) % nr_tlb_entry;
res->ppa = (((((uint64_t)pte.PPN2 << 9) | (uint64_t)pte.PPN1) << 9) | (uint64_t)pte.PPN0) << 12;
res->vpa = (page_size == (1 << 12)) ? (va - (va % (1 << 12))) : (page_size == (1 << 21)) ? (va - (va % (1 << 21)))
: (va - (va % (1 << 30)));
res->asid = satp.asid;
res->pagesize = (page_size == (1 << 12)) ? 1 : (page_size == (1 << 21)) ? 2
: 3;
res->R = pte.R;
res->W = pte.W;
res->X = pte.X;
res->U = pte.U;
res->G = pte.G;
res->A = pte.A;
res->D = pte.D;
if (local_tlb_get(satp, va) != res)
assert(false);
return res;
}
private:
rv_systembus &bus;
unsigned int random;
sv39_tlb_entry tlb[nr_tlb_entry];
bool ptw(satp_def satp, uint64_t va_in, sv39_pte &pte_out, uint64_t &pagesize)
{
sv39_va *va = (sv39_va *)&va_in;
if (satp.mode != 8)
return false; // mode is not sv39
uint64_t pt_addr = ((satp.ppn) << 12);
sv39_pte pte;
for (int i = 2; i >= 0; i--)
{
// printf("ptw: va=%lx\n", pt_addr + ((i == 2 ? va->vpn_2 : (i == 1 ? va->vpn_1 : va->vpn_0)) * sizeof(sv39_pte)));
bool res = bus.pa_read(pt_addr + ((i == 2 ? va->vpn_2 : (i == 1 ? va->vpn_1 : va->vpn_0)) * sizeof(sv39_pte)), sizeof(sv39_pte), (uint8_t *)&pte);
// printf("pte: %lx\n", *((uint64_t *)&pte));
if (!res)
{
// invalid pte address
return false;
}
if (!pte.V || (!pte.R && pte.W) || pte.reserved || pte.PBMT)
{
return false;
}
if (pte.R || pte.X)
{ // leaf
if (i == 2 && (pte.PPN1 || pte.PPN0))
return false; // Make sure that superpage entries trap when PPN LSBs are set.
if (i == 1 && pte.PPN0)
return false; // Make sure that superpage entries trap when PPN LSBs are set.
pte_out = pte;
pagesize = (1 << 12) << (9 * i);
uint64_t pa = (((((uint64_t)pte.PPN2 << 9) | (uint64_t)pte.PPN1) << 9) | (uint64_t)pte.PPN0) << 12;
return true;
}
else
{ // valid non-leaf
pt_addr = (((((uint64_t)pte.PPN2 << 9) | (uint64_t)pte.PPN1) << 9) | (uint64_t)pte.PPN0) << 12;
}
}
return false;
}
sv39_tlb_entry *local_tlb_get(satp_def satp, uint64_t va)
{
sv39_tlb_entry *res = NULL;
for (int i = 0; i < nr_tlb_entry; i++)
{
if (tlb[i].asid == satp.asid || tlb[i].G)
{
switch (tlb[i].pagesize)
{
case 1: // 4KB
if ((va & (-(1ll << 12))) == tlb[i].vpa)
{
assert(res == NULL);
res = &tlb[i];
}
break;
case 2: // 2MB
if ((va & (-(1ll << 21))) == tlb[i].vpa)
{
assert(res == NULL);
res = &tlb[i];
}
break;
case 3: // 1G
if ((va & (-(1ll << 30))) == tlb[i].vpa)
{
assert(res == NULL);
res = &tlb[i];
}
default:
break;
}
}
}
return res;
}
};
#endif

@ -0,0 +1,184 @@
#ifndef RV_SYSTEMBUS
#define RV_SYSTEMBUS
#include "rv_common.hpp"
#include <cstdint>
#include <assert.h>
#include <algorithm>
#include "mmio_dev.hpp"
#include <map>
#include <utility>
#include <climits>
extern long long current_pc;
// TODO: add pma and check pma
class rv_systembus
{
public:
bool pa_read(uint64_t start_addr, uint64_t size, uint8_t *buffer)
{
// if (start_addr < 0x80000000)
// {
// printf("pc = 0x%016lx\n", current_pc);
// printf("mmio read %lx size %lu data ", start_addr, size);
// for (uint64_t i = 0; i < size; i++)
// {
// printf("%02x", buffer[i]);
// }
// printf("\n");
// }
auto it = devices.upper_bound(std::make_pair(start_addr, ULONG_MAX));
if (it == devices.begin())
return false;
it = std::prev(it);
uint64_t end_addr = start_addr + size;
if (it->first.first <= start_addr && end_addr <= it->first.second)
{
uint64_t dev_size = it->first.second - it->first.first;
return it->second.first->do_read(it->second.second ? start_addr : start_addr % dev_size, size, buffer);
}
else
return false;
}
bool pa_write(uint64_t start_addr, uint64_t size, const uint8_t *buffer)
{
// if (start_addr < 0x80000000)
// {
// printf("pc = 0x%016lx\n", current_pc);
// printf("mmio write %lx size %lu data ", start_addr, size);
// for (uint64_t i = 0; i < size; i++)
// {
// printf("%02x", buffer[i]);
// }
// printf("\n");
// }
if (start_addr <= lr_pa && lr_pa + size <= start_addr + size)
{
lr_valid = false;
}
auto it = devices.upper_bound(std::make_pair(start_addr, ULONG_MAX));
if (it == devices.begin())
return false;
it = std::prev(it);
uint64_t end_addr = start_addr + size;
if (it->first.first <= start_addr && end_addr <= it->first.second)
{
uint64_t dev_size = it->first.second - it->first.first;
return it->second.first->do_write(it->second.second ? start_addr : start_addr % dev_size, size, buffer);
}
else
return false;
}
// note: check address alignment in the core and raise address misalign exception
bool pa_lr(uint64_t pa, uint64_t size, uint8_t *dst, uint64_t hart_id)
{
lr_pa = pa;
lr_size = size;
lr_valid = true;
lr_hart = hart_id;
return pa_read(pa, size, dst);
}
// Note: if pa_write return false, sc_fail shouldn't commit.
bool pa_sc(uint64_t pa, uint64_t size, const uint8_t *src, uint64_t hart_id, bool &sc_fail)
{
if (!lr_valid || lr_pa != pa || lr_size != size || lr_hart != hart_id)
{
sc_fail = true;
if (hart_id == lr_hart)
lr_valid = false;
return true;
}
sc_fail = false;
lr_valid = false;
return pa_write(pa, size, src);
}
// note: core should check whether amoop is valid
bool pa_amo_op(uint64_t pa, uint64_t size, amo_funct op, int64_t src, int64_t &dst)
{
int64_t res;
bool read_ok = true;
if (size == 4)
{
int32_t res32;
read_ok &= pa_read(pa, size, (uint8_t *)&res32);
res = res32;
}
else
{
read_ok &= pa_read(pa, size, (uint8_t *)&res);
}
if (!read_ok)
return false;
int64_t to_write;
switch (op)
{
case AMOSWAP:
to_write = src;
break;
case AMOADD:
to_write = src + res;
break;
case AMOAND:
to_write = src & res;
break;
case AMOOR:
to_write = src | res;
break;
case AMOXOR:
to_write = src ^ res;
break;
case AMOMAX:
to_write = std::max(src, res);
break;
case AMOMIN:
to_write = std::min(src, res);
break;
case AMOMAXU:
to_write = std::max((uint64_t)src, (uint64_t)res);
break;
case AMOMINU:
to_write = std::min((uint64_t)src, (uint64_t)res);
break;
default:
assert(false);
}
dst = res;
return pa_write(pa, size, (uint8_t *)&to_write);
}
bool add_dev(uint64_t start_addr, uint64_t length, mmio_dev *dev, bool raw_addr = false)
{
std::pair<uint64_t, uint64_t> addr_range = std::make_pair(start_addr, start_addr + length);
if (start_addr % length)
return false;
// check range
auto it = devices.upper_bound(addr_range);
if (it != devices.end())
{
uint64_t l_max = std::max(it->first.first, addr_range.first);
uint64_t r_min = std::min(it->first.second, addr_range.second);
if (l_max < r_min)
return false; // overleap
}
if (it != devices.begin())
{
it = std::prev(it);
uint64_t l_max = std::max(it->first.first, addr_range.first);
uint64_t r_min = std::min(it->first.second, addr_range.second);
if (l_max < r_min)
return false; // overleap
}
// overleap check pass
devices[addr_range] = std::make_pair(dev, raw_addr);
return true;
}
private:
uint64_t lr_pa;
uint64_t lr_size;
uint64_t lr_hart;
bool lr_valid = false;
std::map<std::pair<uint64_t, uint64_t>, std::pair<mmio_dev *, bool>> devices;
};
#endif

@ -0,0 +1,466 @@
#include "verilated.h"
// #include "verilated_fst_c.h"
#include "verilated_fst_c.h"
#include "Vtop.h"
#include "rv_systembus.hpp"
#include "rv_core.hpp"
#include "rv_clint.hpp"
#include "rv_plic.hpp"
#include <stdio.h>
bool running = true;
bool run_riscv_test = false;
bool dump_pc_history = false;
bool print_pc = false;
bool should_delay = false;
bool dual_issue = false;
bool perf_counter = false;
bool init_gprs = false;
bool write_append = false;
bool has_delayslot = false;
bool only_modeM = false;
const uint64_t commit_timeout = 3000;
const uint64_t print_pc_cycle = 5e5;
long trace_start_time = 0; // -starttrace [time]
std::atomic_bool trace_on = false;
long sim_time = 1e8;
long long total_cycle = 0;
long long total_instr = 0;
VerilatedFstC fst;
void open_trace()
{
fst.open("trace.fst");
trace_on.store(true, std::memory_order_seq_cst);
}
#undef assert
void assert(bool expr, const char *msg = "")
{
if (!expr)
{
running = false;
printf("%s\n", msg);
printf("soc_simulator assert failed!\n");
}
}
#include "nscscc_sram.hpp"
#include "nscscc_sram_slave.hpp"
#include "nscscc_sram_xbar.hpp"
#include "mmio_mem.hpp"
#include <iostream>
#include <termios.h>
#include <unistd.h>
#include <thread>
#include <csignal>
#include <sstream>
void connect_wire(nscscc_sram_ptr &sram_ptr, Vtop *top)
{
sram_ptr.inst_sram_en = &(top->inst_sram_en);
sram_ptr.inst_sram_addr = &(top->inst_sram_addr);
sram_ptr.inst_sram_wen = &(top->inst_sram_wen);
sram_ptr.inst_sram_rdata = &(top->inst_sram_rdata);
sram_ptr.inst_sram_wdata = &(top->inst_sram_wdata);
sram_ptr.data_sram_en = &(top->data_sram_en);
sram_ptr.data_sram_addr = &(top->data_sram_addr);
sram_ptr.data_sram_wen = &(top->data_sram_wen);
sram_ptr.data_sram_rdata = &(top->data_sram_rdata);
sram_ptr.data_sram_wdata = &(top->data_sram_wdata);
}
void riscv_test_run(Vtop *top, nscscc_sram_ref &mmio_ref, const char *riscv_test_path)
{
// setup cemu {
rv_systembus cemu_system_bus;
mmio_mem cemu_mem(128 * 1024 * 1024, riscv_test_path);
assert(cemu_system_bus.add_dev(0x80000000, 0x80000000, &cemu_mem));
rv_core cemu_rvcore(cemu_system_bus);
cemu_rvcore.jump(0x80000000);
if (init_gprs)
{
for (int i = 0; i < 32; i++)
{
cemu_rvcore.set_GPR(i, i);
}
}
// cemu_rvcore.set_difftest_mode(true);
// setup cemu }
// setup rtl {
nscscc_sram mmio_sigs;
nscscc_sram_ref mmio_sigs_ref(mmio_sigs);
nscscc_sram_xbar mmio;
mmio_mem rtl_mem(128 * 1024 * 1024, riscv_test_path);
assert(mmio.add_dev(0x80000000, 0x80000000, &rtl_mem));
// setup rtl }
// connect Vcd for trace
if (trace_on)
{
top->trace(&fst, 0);
fst.open("trace.fst");
}
uint64_t rst_ticks = 10;
uint64_t ticks = 0;
uint64_t last_commit = ticks;
uint64_t pc_cnt = print_pc_cycle;
int delayslot_cnt = 0;
bool delayslot_flag = true;
int delay = 1500;
while (!Verilated::gotFinish() && sim_time > 0 && running)
{
if (rst_ticks > 0)
{
top->reset = 1;
rst_ticks--;
}
else
top->reset = 0;
top->clock = !top->clock;
if (top->clock && !top->reset)
mmio_sigs.update_input(mmio_ref);
top->eval();
if (top->clock && !top->reset)
{
mmio.beat(mmio_sigs_ref);
mmio_sigs.update_output(mmio_ref);
top->eval();
}
//===性能计数器=====
if (!top->reset && top->clock)
total_cycle++;
if (((top->clock && !dual_issue) || dual_issue) && top->debug_commit)
total_instr++;
//==================
if (((top->clock && !dual_issue) || dual_issue) && top->debug_commit)
{ // instr retire
// cemu_rvcore.import_diff_test_info(top->debug_csr_mcycle, top->debug_csr_minstret, top->debug_csr_mip, top->debug_csr_interrupt);
if (has_delayslot)
{
if (!delayslot_cnt)
{
cemu_rvcore.step(0, 0, 0, 0);
delayslot_flag = true;
}
}
else
{
cemu_rvcore.step(0, 0, 0, 0);
}
last_commit = ticks;
if (pc_cnt++ >= print_pc_cycle && print_pc)
{
printf("PC = 0x%016lx\n", cemu_rvcore.debug_pc);
pc_cnt = 0;
}
if ((top->debug_pc != cemu_rvcore.debug_pc ||
cemu_rvcore.debug_reg_num != 0 &&
(top->debug_rf_wnum != cemu_rvcore.debug_reg_num ||
top->debug_rf_wdata != cemu_rvcore.debug_reg_wdata)) &&
!delayslot_cnt)
{
printf("\033[1;31mError!\033[0m\n");
printf("reference: PC = 0x%016lx, wb_rf_wnum = 0x%02lx, wb_rf_wdata = 0x%016lx\n", cemu_rvcore.debug_pc, cemu_rvcore.debug_reg_num, cemu_rvcore.debug_reg_wdata);
printf("mycpu : PC = 0x%016lx, wb_rf_wnum = 0x%02x, wb_rf_wdata = 0x%016lx\n", top->debug_pc, top->debug_rf_wnum, top->debug_rf_wdata);
if (!should_delay)
{
running = false;
if (dump_pc_history)
cemu_rvcore.dump_pc_history();
}
else if (dump_pc_history && delay-- == 10)
cemu_rvcore.dump_pc_history();
else if (delay-- == 0)
running = false;
}
// ==========================
if (has_delayslot)
{
if (delayslot_cnt > 0)
delayslot_cnt--;
if (cemu_rvcore.debug_is_branch && delayslot_flag)
{
delayslot_cnt = 2;
delayslot_flag = false;
}
}
// ==========================
}
if (trace_on)
{
fst.dump(ticks);
sim_time--;
}
ticks++;
if (ticks - last_commit >= commit_timeout)
{
printf("\033[1;31mError!\033[0m\n");
printf("CPU stuck for %ld cycles!\n", commit_timeout / 2);
running = false;
if (dump_pc_history)
cemu_rvcore.dump_pc_history();
}
}
printf("total_ticks: %lu\n", ticks);
}
void make_cpu_trace(Vtop *top, nscscc_sram_ref &mmio_ref, const char *riscv_test_path)
{
// setup cemu {
rv_systembus cemu_system_bus;
mmio_mem cemu_mem(128 * 1024 * 1024, riscv_test_path);
assert(cemu_system_bus.add_dev(0x80000000, 0x80000000, &cemu_mem));
rv_core cemu_rvcore(cemu_system_bus);
cemu_rvcore.jump(0x80000000);
if (init_gprs)
{
for (int i = 0; i < 32; i++)
{
cemu_rvcore.set_GPR(i, i);
}
}
// setup cemu }
// setup rtl {
nscscc_sram mmio_sigs;
nscscc_sram_ref mmio_sigs_ref(mmio_sigs);
nscscc_sram_xbar mmio;
mmio_mem rtl_mem(128 * 1024 * 1024, riscv_test_path);
assert(mmio.add_dev(0x80000000, 0x80000000, &rtl_mem));
// setup rtl }
// connect Vcd for trace
if (trace_on)
{
top->trace(&fst, 0);
fst.open("trace.fst");
}
FILE *trace_file;
if (write_append)
{
trace_file = fopen("trace.txt", "a");
}
else
{
trace_file = fopen("trace.txt", "w");
}
if (trace_file == NULL)
{
printf("Error opening file!\n");
}
uint64_t rst_ticks = 10;
uint64_t ticks = 0;
uint64_t last_commit = ticks;
int delay = 10;
int delayslot_cnt = 0;
bool delayslot_flag = true;
while (!Verilated::gotFinish() && sim_time > 0 && running)
{
if (rst_ticks > 0)
{
top->reset = 1;
rst_ticks--;
}
else
top->reset = 0;
top->clock = !top->clock;
if (top->clock && !top->reset)
mmio_sigs.update_input(mmio_ref);
top->eval();
if (top->clock && !top->reset)
{
mmio.beat(mmio_sigs_ref);
mmio_sigs.update_output(mmio_ref);
top->eval();
}
if (((top->clock && !dual_issue) || dual_issue) && top->debug_commit)
{ // instr retire
if (has_delayslot)
{
if (!delayslot_cnt)
{
cemu_rvcore.step(0, 0, 0, 0);
delayslot_flag = true;
}
}
else
{
cemu_rvcore.step(0, 0, 0, 0);
}
last_commit = ticks;
if ((top->debug_pc != cemu_rvcore.debug_pc ||
cemu_rvcore.debug_reg_num != 0 &&
(top->debug_rf_wnum != cemu_rvcore.debug_reg_num ||
top->debug_rf_wdata != cemu_rvcore.debug_reg_wdata)) &&
!delayslot_cnt)
{
printf("\033[1;31mError!\033[0m\n");
printf("reference: PC = 0x%016lx, wb_rf_wnum = 0x%02lx, wb_rf_wdata = 0x%016lx\n", cemu_rvcore.debug_pc, cemu_rvcore.debug_reg_num, cemu_rvcore.debug_reg_wdata);
printf("mycpu : PC = 0x%016lx, wb_rf_wnum = 0x%02x, wb_rf_wdata = 0x%016lx\n", top->debug_pc, top->debug_rf_wnum, top->debug_rf_wdata);
if (!should_delay)
{
running = false;
if (dump_pc_history)
cemu_rvcore.dump_pc_history();
}
else if (dump_pc_history && delay-- == 10)
cemu_rvcore.dump_pc_history();
else if (delay-- == 0)
running = false;
}
// ==========================
if (has_delayslot)
{
if (delayslot_cnt > 0)
delayslot_cnt--;
if (cemu_rvcore.debug_is_branch && delayslot_flag)
{
delayslot_cnt = 2;
delayslot_flag = false;
}
}
// ==========================
fprintf(trace_file, "1 %016lx %02lx %016lx\n", cemu_rvcore.debug_pc, cemu_rvcore.debug_reg_num, cemu_rvcore.debug_reg_wdata);
}
if (trace_on)
{
fst.dump(ticks);
sim_time--;
}
ticks++;
if (ticks - last_commit >= commit_timeout)
{
printf("\033[1;31mError!\033[0m\n");
printf("CPU stuck for %ld cycles!\n", commit_timeout / 2);
running = false;
if (dump_pc_history)
cemu_rvcore.dump_pc_history();
}
}
printf("total_ticks: %lu\n", ticks);
fclose(trace_file);
}
int main(int argc, char **argv, char **env)
{
Verilated::commandArgs(argc, argv);
std::signal(SIGINT, [](int)
{ running = false; });
char *file_load_path;
enum
{
NOP,
RISCV_TEST,
CPU_TRACE,
} run_mode = RISCV_TEST;
for (int i = 1; i < argc; i++)
{
if (strcmp(argv[i], "-trace") == 0)
{
trace_on = true;
if (i + 1 < argc)
{
sscanf(argv[++i], "%lu", &sim_time);
}
}
else if (strcmp(argv[i], "-starttrace") == 0)
{
if (i + 1 < argc)
{
sscanf(argv[++i], "%lu", &trace_start_time);
}
printf("trace start time: %lu\n", trace_start_time);
}
else if (strcmp(argv[i], "-rvtest") == 0)
{
run_riscv_test = true;
run_mode = RISCV_TEST;
}
else if (strcmp(argv[i], "-perf") == 0)
{
perf_counter = true;
}
else if (strcmp(argv[i], "-pc") == 0) // 打印历史PC
{
dump_pc_history = true;
}
else if (strcmp(argv[i], "-printpc") == 0) // 间隔一定时间输出一次PC
{
print_pc = true;
}
else if (strcmp(argv[i], "-delay") == 0) // 出错后延迟一段时间再停止
{
should_delay = true;
}
else if (strcmp(argv[i], "-cpu_trace") == 0) // 生成cpu trace
{
run_mode = CPU_TRACE;
}
else if (strcmp(argv[i], "-initgprs") == 0) // 初始化寄存器
{
init_gprs = true;
}
else if (strcmp(argv[i], "-writeappend") == 0) // 追加写入
{
write_append = true;
}
else if (strcmp(argv[i], "-hasdelayslot") == 0) // 是否有延迟槽
{
has_delayslot = true;
}
else if (strcmp(argv[i], "-onlymodem") == 0) // 只有modeM
{
only_modeM = true;
}
else
{
file_load_path = argv[i];
}
}
Verilated::traceEverOn(true);
// setup soc
Vtop *top = new Vtop;
nscscc_sram_ptr mmio_ptr;
connect_wire(mmio_ptr, top);
assert(mmio_ptr.check());
nscscc_sram_ref mmio_ref(mmio_ptr);
switch (run_mode)
{
case RISCV_TEST:
riscv_test_run(top, mmio_ref, file_load_path);
break;
case CPU_TRACE:
make_cpu_trace(top, mmio_ref, file_load_path);
break;
default:
printf("Unknown running mode.\n");
exit(-ENOENT);
}
return 0;
}

@ -0,0 +1,89 @@
elf/am-tests/add: file format elf64-littleriscv
Disassembly of section .text:
0000000080000000 <_start>:
80000000: 00000413 addi x8,x0,0
80000004: 00009117 auipc x2,0x9
80000008: ffc10113 addi x2,x2,-4 # 80009000 <_end>
8000000c: 0fc000ef jal x1,80000108 <_trm_init>
0000000080000010 <check>:
80000010: 00050463 beq x10,x0,80000018 <check+0x8>
80000014: 00008067 jalr x0,0(x1)
80000018: ff010113 addi x2,x2,-16
8000001c: 00100513 addi x10,x0,1
80000020: 00113423 sd x1,8(x2)
80000024: 0d8000ef jal x1,800000fc <halt>
0000000080000028 <main>:
80000028: fb010113 addi x2,x2,-80
8000002c: 01713423 sd x23,8(x2)
80000030: 00000b97 auipc x23,0x0
80000034: 200b8b93 addi x23,x23,512 # 80000230 <test_data>
80000038: 03313423 sd x19,40(x2)
8000003c: 03413023 sd x20,32(x2)
80000040: 01513c23 sd x21,24(x2)
80000044: 01613823 sd x22,16(x2)
80000048: 01813023 sd x24,0(x2)
8000004c: 04113423 sd x1,72(x2)
80000050: 04813023 sd x8,64(x2)
80000054: 02913c23 sd x9,56(x2)
80000058: 03213823 sd x18,48(x2)
8000005c: 00000b17 auipc x22,0x0
80000060: 0d4b0b13 addi x22,x22,212 # 80000130 <ans>
80000064: 000b8a93 addi x21,x23,0
80000068: 00000a13 addi x20,x0,0
8000006c: 00000997 auipc x19,0x0
80000070: 1e498993 addi x19,x19,484 # 80000250 <_bss_start>
80000074: 04000c13 addi x24,x0,64
80000078: 000aa903 lw x18,0(x21)
8000007c: 000b0493 addi x9,x22,0
80000080: 000b8413 addi x8,x23,0
80000084: 00042503 lw x10,0(x8)
80000088: 0004a783 lw x15,0(x9)
8000008c: 00440413 addi x8,x8,4
80000090: 0125053b addw x10,x10,x18
80000094: 40f50533 sub x10,x10,x15
80000098: 00153513 sltiu x10,x10,1
8000009c: f75ff0ef jal x1,80000010 <check>
800000a0: 00448493 addi x9,x9,4
800000a4: fe8990e3 bne x19,x8,80000084 <main+0x5c>
800000a8: 00100513 addi x10,x0,1
800000ac: 008a0a1b addiw x20,x20,8
800000b0: f61ff0ef jal x1,80000010 <check>
800000b4: 004a8a93 addi x21,x21,4
800000b8: 020b0b13 addi x22,x22,32
800000bc: fb8a1ee3 bne x20,x24,80000078 <main+0x50>
800000c0: 00100513 addi x10,x0,1
800000c4: f4dff0ef jal x1,80000010 <check>
800000c8: 04813083 ld x1,72(x2)
800000cc: 04013403 ld x8,64(x2)
800000d0: 03813483 ld x9,56(x2)
800000d4: 03013903 ld x18,48(x2)
800000d8: 02813983 ld x19,40(x2)
800000dc: 02013a03 ld x20,32(x2)
800000e0: 01813a83 ld x21,24(x2)
800000e4: 01013b03 ld x22,16(x2)
800000e8: 00813b83 ld x23,8(x2)
800000ec: 00013c03 ld x24,0(x2)
800000f0: 00000513 addi x10,x0,0
800000f4: 05010113 addi x2,x2,80
800000f8: 00008067 jalr x0,0(x1)
00000000800000fc <halt>:
800000fc: 00050513 addi x10,x10,0
80000100: 00100073 ebreak
80000104: 0000006f jal x0,80000104 <halt+0x8>
0000000080000108 <_trm_init>:
80000108: ff010113 addi x2,x2,-16
8000010c: 00000517 auipc x10,0x0
80000110: 01c50513 addi x10,x10,28 # 80000128 <_etext>
80000114: 00113423 sd x1,8(x2)
80000118: f11ff0ef jal x1,80000028 <main>
8000011c: 00050513 addi x10,x10,0
80000120: 00100073 ebreak
80000124: 0000006f jal x0,80000124 <_trm_init+0x1c>

@ -0,0 +1,85 @@
elf/am-tests/add-longlong: file format elf64-littleriscv
Disassembly of section .text:
0000000080000000 <_start>:
80000000: 00000413 addi x8,x0,0
80000004: 00009117 auipc x2,0x9
80000008: ffc10113 addi x2,x2,-4 # 80009000 <_end>
8000000c: 0ec000ef jal x1,800000f8 <_trm_init>
0000000080000010 <check>:
80000010: 00050463 beq x10,x0,80000018 <check+0x8>
80000014: 00008067 jalr x0,0(x1)
80000018: ff010113 addi x2,x2,-16
8000001c: 00100513 addi x10,x0,1
80000020: 00113423 sd x1,8(x2)
80000024: 0c8000ef jal x1,800000ec <halt>
0000000080000028 <main>:
80000028: fb010113 addi x2,x2,-80
8000002c: 01713423 sd x23,8(x2)
80000030: 00000b97 auipc x23,0x0
80000034: 2f0b8b93 addi x23,x23,752 # 80000320 <test_data>
80000038: 03313423 sd x19,40(x2)
8000003c: 03413023 sd x20,32(x2)
80000040: 01513c23 sd x21,24(x2)
80000044: 01613823 sd x22,16(x2)
80000048: 01813023 sd x24,0(x2)
8000004c: 04113423 sd x1,72(x2)
80000050: 04813023 sd x8,64(x2)
80000054: 02913c23 sd x9,56(x2)
80000058: 03213823 sd x18,48(x2)
8000005c: 00000b17 auipc x22,0x0
80000060: 0c4b0b13 addi x22,x22,196 # 80000120 <ans>
80000064: 000b8a93 addi x21,x23,0
80000068: 00000a13 addi x20,x0,0
8000006c: 00000997 auipc x19,0x0
80000070: 2f498993 addi x19,x19,756 # 80000360 <_bss_start>
80000074: 04000c13 addi x24,x0,64
80000078: 000ab903 ld x18,0(x21)
8000007c: 000b0493 addi x9,x22,0
80000080: 000b8413 addi x8,x23,0
80000084: 00043503 ld x10,0(x8)
80000088: 0004b783 ld x15,0(x9)
8000008c: 00840413 addi x8,x8,8
80000090: 00a90533 add x10,x18,x10
80000094: 40f50533 sub x10,x10,x15
80000098: 00153513 sltiu x10,x10,1
8000009c: f75ff0ef jal x1,80000010 <check>
800000a0: 00848493 addi x9,x9,8
800000a4: fe8990e3 bne x19,x8,80000084 <main+0x5c>
800000a8: 008a0a1b addiw x20,x20,8
800000ac: 008a8a93 addi x21,x21,8
800000b0: 040b0b13 addi x22,x22,64
800000b4: fd8a12e3 bne x20,x24,80000078 <main+0x50>
800000b8: 04813083 ld x1,72(x2)
800000bc: 04013403 ld x8,64(x2)
800000c0: 03813483 ld x9,56(x2)
800000c4: 03013903 ld x18,48(x2)
800000c8: 02813983 ld x19,40(x2)
800000cc: 02013a03 ld x20,32(x2)
800000d0: 01813a83 ld x21,24(x2)
800000d4: 01013b03 ld x22,16(x2)
800000d8: 00813b83 ld x23,8(x2)
800000dc: 00013c03 ld x24,0(x2)
800000e0: 00000513 addi x10,x0,0
800000e4: 05010113 addi x2,x2,80
800000e8: 00008067 jalr x0,0(x1)
00000000800000ec <halt>:
800000ec: 00050513 addi x10,x10,0
800000f0: 00100073 ebreak
800000f4: 0000006f jal x0,800000f4 <halt+0x8>
00000000800000f8 <_trm_init>:
800000f8: ff010113 addi x2,x2,-16
800000fc: 00000517 auipc x10,0x0
80000100: 01c50513 addi x10,x10,28 # 80000118 <_etext>
80000104: 00113423 sd x1,8(x2)
80000108: f21ff0ef jal x1,80000028 <main>
8000010c: 00050513 addi x10,x10,0
80000110: 00100073 ebreak
80000114: 0000006f jal x0,80000114 <_trm_init+0x1c>

@ -0,0 +1,156 @@
elf/am-tests/bit: file format elf64-littleriscv
Disassembly of section .text:
0000000080000000 <_start>:
80000000: 00000413 addi x8,x0,0
80000004: 00009117 auipc x2,0x9
80000008: ffc10113 addi x2,x2,-4 # 80009000 <_end>
8000000c: 1f8000ef jal x1,80000204 <_trm_init>
0000000080000010 <check>:
80000010: 00050463 beq x10,x0,80000018 <check+0x8>
80000014: 00008067 jalr x0,0(x1)
80000018: ff010113 addi x2,x2,-16
8000001c: 00100513 addi x10,x0,1
80000020: 00113423 sd x1,8(x2)
80000024: 1d4000ef jal x1,800001f8 <halt>
0000000080000028 <getbit>:
80000028: 4035d793 srai x15,x11,0x3
8000002c: 00f50533 add x10,x10,x15
80000030: 00054503 lbu x10,0(x10)
80000034: 0075f593 andi x11,x11,7
80000038: 00100793 addi x15,x0,1
8000003c: 00b797bb sllw x15,x15,x11
80000040: 00f57533 and x10,x10,x15
80000044: 00a03533 sltu x10,x0,x10
80000048: 00008067 jalr x0,0(x1)
000000008000004c <setbit>:
8000004c: 4035d793 srai x15,x11,0x3
80000050: ff010113 addi x2,x2,-16
80000054: 00f50533 add x10,x10,x15
80000058: 00a13423 sd x10,8(x2)
8000005c: 00813783 ld x15,8(x2)
80000060: 0075f593 andi x11,x11,7
80000064: 00100713 addi x14,x0,1
80000068: 00b7173b sllw x14,x14,x11
8000006c: 02061063 bne x12,x0,8000008c <setbit+0x40>
80000070: 0007c783 lbu x15,0(x15)
80000074: fff74713 xori x14,x14,-1
80000078: 00e7f7b3 and x15,x15,x14
8000007c: 00813703 ld x14,8(x2)
80000080: 00f70023 sb x15,0(x14)
80000084: 01010113 addi x2,x2,16
80000088: 00008067 jalr x0,0(x1)
8000008c: 0007c783 lbu x15,0(x15)
80000090: 00e7e7b3 or x15,x15,x14
80000094: 00813703 ld x14,8(x2)
80000098: 0ff7f793 andi x15,x15,255
8000009c: 00f70023 sb x15,0(x14)
800000a0: 01010113 addi x2,x2,16
800000a4: 00008067 jalr x0,0(x1)
00000000800000a8 <main>:
800000a8: fe010113 addi x2,x2,-32
800000ac: 0aa00793 addi x15,x0,170
800000b0: 00000593 addi x11,x0,0
800000b4: 00810513 addi x10,x2,8
800000b8: 00113c23 sd x1,24(x2)
800000bc: 00f11423 sh x15,8(x2)
800000c0: f69ff0ef jal x1,80000028 <getbit>
800000c4: 00154513 xori x10,x10,1
800000c8: 0ff57513 andi x10,x10,255
800000cc: f45ff0ef jal x1,80000010 <check>
800000d0: 00100593 addi x11,x0,1
800000d4: 00810513 addi x10,x2,8
800000d8: f51ff0ef jal x1,80000028 <getbit>
800000dc: f35ff0ef jal x1,80000010 <check>
800000e0: 00200593 addi x11,x0,2
800000e4: 00810513 addi x10,x2,8
800000e8: f41ff0ef jal x1,80000028 <getbit>
800000ec: 00154513 xori x10,x10,1
800000f0: 0ff57513 andi x10,x10,255
800000f4: f1dff0ef jal x1,80000010 <check>
800000f8: 00300593 addi x11,x0,3
800000fc: 00810513 addi x10,x2,8
80000100: f29ff0ef jal x1,80000028 <getbit>
80000104: f0dff0ef jal x1,80000010 <check>
80000108: 00400593 addi x11,x0,4
8000010c: 00810513 addi x10,x2,8
80000110: f19ff0ef jal x1,80000028 <getbit>
80000114: 00154513 xori x10,x10,1
80000118: 0ff57513 andi x10,x10,255
8000011c: ef5ff0ef jal x1,80000010 <check>
80000120: 00500593 addi x11,x0,5
80000124: 00810513 addi x10,x2,8
80000128: f01ff0ef jal x1,80000028 <getbit>
8000012c: ee5ff0ef jal x1,80000010 <check>
80000130: 00600593 addi x11,x0,6
80000134: 00810513 addi x10,x2,8
80000138: ef1ff0ef jal x1,80000028 <getbit>
8000013c: 00154513 xori x10,x10,1
80000140: 0ff57513 andi x10,x10,255
80000144: ecdff0ef jal x1,80000010 <check>
80000148: 00700593 addi x11,x0,7
8000014c: 00810513 addi x10,x2,8
80000150: ed9ff0ef jal x1,80000028 <getbit>
80000154: ebdff0ef jal x1,80000010 <check>
80000158: 00810513 addi x10,x2,8
8000015c: 00100613 addi x12,x0,1
80000160: 00800593 addi x11,x0,8
80000164: ee9ff0ef jal x1,8000004c <setbit>
80000168: 00810513 addi x10,x2,8
8000016c: 00000613 addi x12,x0,0
80000170: 00900593 addi x11,x0,9
80000174: ed9ff0ef jal x1,8000004c <setbit>
80000178: 00810513 addi x10,x2,8
8000017c: 00100613 addi x12,x0,1
80000180: 00a00593 addi x11,x0,10
80000184: ec9ff0ef jal x1,8000004c <setbit>
80000188: 00810513 addi x10,x2,8
8000018c: 00000613 addi x12,x0,0
80000190: 00b00593 addi x11,x0,11
80000194: eb9ff0ef jal x1,8000004c <setbit>
80000198: 00810513 addi x10,x2,8
8000019c: 00100613 addi x12,x0,1
800001a0: 00c00593 addi x11,x0,12
800001a4: ea9ff0ef jal x1,8000004c <setbit>
800001a8: 00810513 addi x10,x2,8
800001ac: 00000613 addi x12,x0,0
800001b0: 00d00593 addi x11,x0,13
800001b4: e99ff0ef jal x1,8000004c <setbit>
800001b8: 00810513 addi x10,x2,8
800001bc: 00100613 addi x12,x0,1
800001c0: 00e00593 addi x11,x0,14
800001c4: e89ff0ef jal x1,8000004c <setbit>
800001c8: 00810513 addi x10,x2,8
800001cc: 00000613 addi x12,x0,0
800001d0: 00f00593 addi x11,x0,15
800001d4: e79ff0ef jal x1,8000004c <setbit>
800001d8: 00914503 lbu x10,9(x2)
800001dc: fab50513 addi x10,x10,-85
800001e0: 00153513 sltiu x10,x10,1
800001e4: e2dff0ef jal x1,80000010 <check>
800001e8: 01813083 ld x1,24(x2)
800001ec: 00000513 addi x10,x0,0
800001f0: 02010113 addi x2,x2,32
800001f4: 00008067 jalr x0,0(x1)
00000000800001f8 <halt>:
800001f8: 00050513 addi x10,x10,0
800001fc: 00100073 ebreak
80000200: 0000006f jal x0,80000200 <halt+0x8>
0000000080000204 <_trm_init>:
80000204: ff010113 addi x2,x2,-16
80000208: 00000517 auipc x10,0x0
8000020c: 02050513 addi x10,x10,32 # 80000228 <mainargs>
80000210: 00113423 sd x1,8(x2)
80000214: e95ff0ef jal x1,800000a8 <main>
80000218: 00050513 addi x10,x10,0
8000021c: 00100073 ebreak
80000220: 0000006f jal x0,80000220 <_trm_init+0x1c>

@ -0,0 +1,99 @@
elf/am-tests/bubble-sort: file format elf64-littleriscv
Disassembly of section .text:
0000000080000000 <_start>:
80000000: 00000413 addi x8,x0,0
80000004: 00009117 auipc x2,0x9
80000008: ffc10113 addi x2,x2,-4 # 80009000 <_end>
8000000c: 11c000ef jal x1,80000128 <_trm_init>
0000000080000010 <check>:
80000010: 00050463 beq x10,x0,80000018 <check+0x8>
80000014: 00008067 jalr x0,0(x1)
80000018: ff010113 addi x2,x2,-16
8000001c: 00100513 addi x10,x0,1
80000020: 00113423 sd x1,8(x2)
80000024: 0f8000ef jal x1,8000011c <halt>
0000000080000028 <bubble_sort>:
80000028: 01300793 addi x15,x0,19
8000002c: 00000517 auipc x10,0x0
80000030: 12850513 addi x10,x10,296 # 80000154 <a+0x4>
80000034: 04078063 beq x15,x0,80000074 <bubble_sort+0x4c>
80000038: fff7859b addiw x11,x15,-1
8000003c: 02059793 slli x15,x11,0x20
80000040: 01e7d613 srli x12,x15,0x1e
80000044: 00a60633 add x12,x12,x10
80000048: 00000797 auipc x15,0x0
8000004c: 10878793 addi x15,x15,264 # 80000150 <a>
80000050: 0007a703 lw x14,0(x15)
80000054: 0047a683 lw x13,4(x15)
80000058: 00e6d663 bge x13,x14,80000064 <bubble_sort+0x3c>
8000005c: 00d7a023 sw x13,0(x15)
80000060: 00e7a223 sw x14,4(x15)
80000064: 00478793 addi x15,x15,4
80000068: fec794e3 bne x15,x12,80000050 <bubble_sort+0x28>
8000006c: 0005879b addiw x15,x11,0
80000070: fc0794e3 bne x15,x0,80000038 <bubble_sort+0x10>
80000074: 00008067 jalr x0,0(x1)
0000000080000078 <main>:
80000078: fd010113 addi x2,x2,-48
8000007c: 00913c23 sd x9,24(x2)
80000080: 00000497 auipc x9,0x0
80000084: 0d048493 addi x9,x9,208 # 80000150 <a>
80000088: 02813023 sd x8,32(x2)
8000008c: 01213823 sd x18,16(x2)
80000090: 01313423 sd x19,8(x2)
80000094: 02113423 sd x1,40(x2)
80000098: 00048913 addi x18,x9,0
8000009c: f8dff0ef jal x1,80000028 <bubble_sort>
800000a0: 00000413 addi x8,x0,0
800000a4: 01400993 addi x19,x0,20
800000a8: 00092503 lw x10,0(x18)
800000ac: 00490913 addi x18,x18,4
800000b0: 40850533 sub x10,x10,x8
800000b4: 00153513 sltiu x10,x10,1
800000b8: 0014041b addiw x8,x8,1
800000bc: f55ff0ef jal x1,80000010 <check>
800000c0: ff3414e3 bne x8,x19,800000a8 <main+0x30>
800000c4: 00100513 addi x10,x0,1
800000c8: f49ff0ef jal x1,80000010 <check>
800000cc: 00000413 addi x8,x0,0
800000d0: f59ff0ef jal x1,80000028 <bubble_sort>
800000d4: 01400913 addi x18,x0,20
800000d8: 0004a503 lw x10,0(x9)
800000dc: 00448493 addi x9,x9,4
800000e0: 40850533 sub x10,x10,x8
800000e4: 00153513 sltiu x10,x10,1
800000e8: 0014041b addiw x8,x8,1
800000ec: f25ff0ef jal x1,80000010 <check>
800000f0: ff2414e3 bne x8,x18,800000d8 <main+0x60>
800000f4: 00100513 addi x10,x0,1
800000f8: f19ff0ef jal x1,80000010 <check>
800000fc: 02813083 ld x1,40(x2)
80000100: 02013403 ld x8,32(x2)
80000104: 01813483 ld x9,24(x2)
80000108: 01013903 ld x18,16(x2)
8000010c: 00813983 ld x19,8(x2)
80000110: 00000513 addi x10,x0,0
80000114: 03010113 addi x2,x2,48
80000118: 00008067 jalr x0,0(x1)
000000008000011c <halt>:
8000011c: 00050513 addi x10,x10,0
80000120: 00100073 ebreak
80000124: 0000006f jal x0,80000124 <halt+0x8>
0000000080000128 <_trm_init>:
80000128: ff010113 addi x2,x2,-16
8000012c: 00000517 auipc x10,0x0
80000130: 01c50513 addi x10,x10,28 # 80000148 <_etext>
80000134: 00113423 sd x1,8(x2)
80000138: f41ff0ef jal x1,80000078 <main>
8000013c: 00050513 addi x10,x10,0
80000140: 00100073 ebreak
80000144: 0000006f jal x0,80000144 <_trm_init+0x1c>

@ -0,0 +1,90 @@
elf/am-tests/div: file format elf64-littleriscv
Disassembly of section .text:
0000000080000000 <_start>:
80000000: 00000413 addi x8,x0,0
80000004: 00009117 auipc x2,0x9
80000008: ffc10113 addi x2,x2,-4 # 80009000 <_end>
8000000c: 100000ef jal x1,8000010c <_trm_init>
0000000080000010 <check>:
80000010: 00050463 beq x10,x0,80000018 <check+0x8>
80000014: 00008067 jalr x0,0(x1)
80000018: ff010113 addi x2,x2,-16
8000001c: 00100513 addi x10,x0,1
80000020: 00113423 sd x1,8(x2)
80000024: 0dc000ef jal x1,80000100 <halt>
0000000080000028 <main>:
80000028: fe010113 addi x2,x2,-32
8000002c: 00913423 sd x9,8(x2)
80000030: 00000497 auipc x9,0x0
80000034: 10848493 addi x9,x9,264 # 80000138 <a>
80000038: 00113c23 sd x1,24(x2)
8000003c: 00813823 sd x8,16(x2)
80000040: 01213023 sd x18,0(x2)
80000044: 00048713 addi x14,x9,0
80000048: 00000793 addi x15,x0,0
8000004c: 00a00693 addi x13,x0,10
80000050: 00f72023 sw x15,0(x14)
80000054: 0017879b addiw x15,x15,1
80000058: 00470713 addi x14,x14,4
8000005c: fed79ae3 bne x15,x13,80000050 <main+0x28>
80000060: 00000597 auipc x11,0x0
80000064: 10058593 addi x11,x11,256 # 80000160 <a+0x28>
80000068: 00000617 auipc x12,0x0
8000006c: 0d060613 addi x12,x12,208 # 80000138 <a>
80000070: 00b00693 addi x13,x0,11
80000074: 00062703 lw x14,0(x12)
80000078: 00100793 addi x15,x0,1
8000007c: 02f7073b mulw x14,x14,x15
80000080: 0017879b addiw x15,x15,1
80000084: fed79ce3 bne x15,x13,8000007c <main+0x54>
80000088: 00e62023 sw x14,0(x12)
8000008c: 00460613 addi x12,x12,4
80000090: feb612e3 bne x12,x11,80000074 <main+0x4c>
80000094: 00000617 auipc x12,0x0
80000098: 0a460613 addi x12,x12,164 # 80000138 <a>
8000009c: 00b00693 addi x13,x0,11
800000a0: 00062703 lw x14,0(x12)
800000a4: 00100793 addi x15,x0,1
800000a8: 02f7473b divw x14,x14,x15
800000ac: 0017879b addiw x15,x15,1
800000b0: fed79ce3 bne x15,x13,800000a8 <main+0x80>
800000b4: 00e62023 sw x14,0(x12)
800000b8: 00460613 addi x12,x12,4
800000bc: feb612e3 bne x12,x11,800000a0 <main+0x78>
800000c0: 00000413 addi x8,x0,0
800000c4: 00a00913 addi x18,x0,10
800000c8: 0004a503 lw x10,0(x9)
800000cc: 00448493 addi x9,x9,4
800000d0: 40850533 sub x10,x10,x8
800000d4: 00153513 sltiu x10,x10,1
800000d8: 0014041b addiw x8,x8,1
800000dc: f35ff0ef jal x1,80000010 <check>
800000e0: ff2414e3 bne x8,x18,800000c8 <main+0xa0>
800000e4: 01813083 ld x1,24(x2)
800000e8: 01013403 ld x8,16(x2)
800000ec: 00813483 ld x9,8(x2)
800000f0: 00013903 ld x18,0(x2)
800000f4: 00000513 addi x10,x0,0
800000f8: 02010113 addi x2,x2,32
800000fc: 00008067 jalr x0,0(x1)
0000000080000100 <halt>:
80000100: 00050513 addi x10,x10,0
80000104: 00100073 ebreak
80000108: 0000006f jal x0,80000108 <halt+0x8>
000000008000010c <_trm_init>:
8000010c: ff010113 addi x2,x2,-16
80000110: 00000517 auipc x10,0x0
80000114: 02050513 addi x10,x10,32 # 80000130 <mainargs>
80000118: 00113423 sd x1,8(x2)
8000011c: f0dff0ef jal x1,80000028 <main>
80000120: 00050513 addi x10,x10,0
80000124: 00100073 ebreak
80000128: 0000006f jal x0,80000128 <_trm_init+0x1c>

@ -0,0 +1,25 @@
elf/am-tests/dummy: file format elf64-littleriscv
Disassembly of section .text:
0000000080000000 <_start>:
80000000: 00000413 addi x8,x0,0
80000004: 00009117 auipc x2,0x9
80000008: ffc10113 addi x2,x2,-4 # 80009000 <_end>
8000000c: 00c000ef jal x1,80000018 <_trm_init>
0000000080000010 <main>:
80000010: 00000513 addi x10,x0,0
80000014: 00008067 jalr x0,0(x1)
0000000080000018 <_trm_init>:
80000018: ff010113 addi x2,x2,-16
8000001c: 00000517 auipc x10,0x0
80000020: 01c50513 addi x10,x10,28 # 80000038 <_etext>
80000024: 00113423 sd x1,8(x2)
80000028: fe9ff0ef jal x1,80000010 <main>
8000002c: 00050513 addi x10,x10,0
80000030: 00100073 ebreak
80000034: 0000006f jal x0,80000034 <_trm_init+0x1c>

@ -0,0 +1,85 @@
elf/am-tests/fact: file format elf64-littleriscv
Disassembly of section .text:
0000000080000000 <_start>:
80000000: 00000413 addi x8,x0,0
80000004: 00009117 auipc x2,0x9
80000008: ffc10113 addi x2,x2,-4 # 80009000 <_end>
8000000c: 0ec000ef jal x1,800000f8 <_trm_init>
0000000080000010 <check>:
80000010: 00050463 beq x10,x0,80000018 <check+0x8>
80000014: 00008067 jalr x0,0(x1)
80000018: ff010113 addi x2,x2,-16
8000001c: 00100513 addi x10,x0,1
80000020: 00113423 sd x1,8(x2)
80000024: 0c8000ef jal x1,800000ec <halt>
0000000080000028 <main>:
80000028: fd010113 addi x2,x2,-48
8000002c: 01213823 sd x18,16(x2)
80000030: 00000917 auipc x18,0x0
80000034: 0f090913 addi x18,x18,240 # 80000120 <ans>
80000038: 00092503 lw x10,0(x18)
8000003c: 00100713 addi x14,x0,1
80000040: 00913c23 sd x9,24(x2)
80000044: 40e50533 sub x10,x10,x14
80000048: 00000493 addi x9,x0,0
8000004c: 01313423 sd x19,8(x2)
80000050: 01413023 sd x20,0(x2)
80000054: 00000997 auipc x19,0x0
80000058: 10498993 addi x19,x19,260 # 80000158 <f>
8000005c: 00d00a13 addi x20,x0,13
80000060: 0014849b addiw x9,x9,1
80000064: 00153513 sltiu x10,x10,1
80000068: 02813023 sd x8,32(x2)
8000006c: 02113423 sd x1,40(x2)
80000070: 00100413 addi x8,x0,1
80000074: 00e9a023 sw x14,0(x19)
80000078: f99ff0ef jal x1,80000010 <check>
8000007c: 05448263 beq x9,x20,800000c0 <main+0x98>
80000080: 06848263 beq x9,x8,800000e4 <main+0xbc>
80000084: 00048793 addi x15,x9,0
80000088: 00100713 addi x14,x0,1
8000008c: 00078693 addi x13,x15,0
80000090: fff7879b addiw x15,x15,-1
80000094: 02e6873b mulw x14,x13,x14
80000098: fe879ae3 bne x15,x8,8000008c <main+0x64>
8000009c: 00492503 lw x10,4(x18)
800000a0: 0014849b addiw x9,x9,1
800000a4: 00498993 addi x19,x19,4
800000a8: 40e50533 sub x10,x10,x14
800000ac: 00153513 sltiu x10,x10,1
800000b0: 00490913 addi x18,x18,4
800000b4: 00e9a023 sw x14,0(x19)
800000b8: f59ff0ef jal x1,80000010 <check>
800000bc: fd4492e3 bne x9,x20,80000080 <main+0x58>
800000c0: 02813083 ld x1,40(x2)
800000c4: 02013403 ld x8,32(x2)
800000c8: 01813483 ld x9,24(x2)
800000cc: 01013903 ld x18,16(x2)
800000d0: 00813983 ld x19,8(x2)
800000d4: 00013a03 ld x20,0(x2)
800000d8: 00000513 addi x10,x0,0
800000dc: 03010113 addi x2,x2,48
800000e0: 00008067 jalr x0,0(x1)
800000e4: 00100713 addi x14,x0,1
800000e8: fb5ff06f jal x0,8000009c <main+0x74>
00000000800000ec <halt>:
800000ec: 00050513 addi x10,x10,0
800000f0: 00100073 ebreak
800000f4: 0000006f jal x0,800000f4 <halt+0x8>
00000000800000f8 <_trm_init>:
800000f8: ff010113 addi x2,x2,-16
800000fc: 00000517 auipc x10,0x0
80000100: 01c50513 addi x10,x10,28 # 80000118 <_etext>
80000104: 00113423 sd x1,8(x2)
80000108: f21ff0ef jal x1,80000028 <main>
8000010c: 00050513 addi x10,x10,0
80000110: 00100073 ebreak
80000114: 0000006f jal x0,80000114 <_trm_init+0x1c>

@ -0,0 +1,67 @@
elf/am-tests/fib: file format elf64-littleriscv
Disassembly of section .text:
0000000080000000 <_start>:
80000000: 00000413 addi x8,x0,0
80000004: 00009117 auipc x2,0x9
80000008: ffc10113 addi x2,x2,-4 # 80009000 <_end>
8000000c: 0a4000ef jal x1,800000b0 <_trm_init>
0000000080000010 <check>:
80000010: 00050463 beq x10,x0,80000018 <check+0x8>
80000014: 00008067 jalr x0,0(x1)
80000018: ff010113 addi x2,x2,-16
8000001c: 00100513 addi x10,x0,1
80000020: 00113423 sd x1,8(x2)
80000024: 080000ef jal x1,800000a4 <halt>
0000000080000028 <main>:
80000028: fe010113 addi x2,x2,-32
8000002c: 00813823 sd x8,16(x2)
80000030: 00913423 sd x9,8(x2)
80000034: 01213023 sd x18,0(x2)
80000038: 00113c23 sd x1,24(x2)
8000003c: 00000417 auipc x8,0x0
80000040: 13c40413 addi x8,x8,316 # 80000178 <fib>
80000044: 00000497 auipc x9,0x0
80000048: 09c48493 addi x9,x9,156 # 800000e0 <ans+0x8>
8000004c: 00000917 auipc x18,0x0
80000050: 1c490913 addi x18,x18,452 # 80000210 <fib+0x98>
80000054: 00442703 lw x14,4(x8)
80000058: 00042783 lw x15,0(x8)
8000005c: 0004a503 lw x10,0(x9)
80000060: 00440413 addi x8,x8,4
80000064: 00e7873b addw x14,x15,x14
80000068: 40e50533 sub x10,x10,x14
8000006c: 00153513 sltiu x10,x10,1
80000070: 00e42223 sw x14,4(x8)
80000074: 00448493 addi x9,x9,4
80000078: f99ff0ef jal x1,80000010 <check>
8000007c: fd241ce3 bne x8,x18,80000054 <main+0x2c>
80000080: 00100513 addi x10,x0,1
80000084: f8dff0ef jal x1,80000010 <check>
80000088: 01813083 ld x1,24(x2)
8000008c: 01013403 ld x8,16(x2)
80000090: 00813483 ld x9,8(x2)
80000094: 00013903 ld x18,0(x2)
80000098: 00000513 addi x10,x0,0
8000009c: 02010113 addi x2,x2,32
800000a0: 00008067 jalr x0,0(x1)
00000000800000a4 <halt>:
800000a4: 00050513 addi x10,x10,0
800000a8: 00100073 ebreak
800000ac: 0000006f jal x0,800000ac <halt+0x8>
00000000800000b0 <_trm_init>:
800000b0: ff010113 addi x2,x2,-16
800000b4: 00000517 auipc x10,0x0
800000b8: 01c50513 addi x10,x10,28 # 800000d0 <_etext>
800000bc: 00113423 sd x1,8(x2)
800000c0: f69ff0ef jal x1,80000028 <main>
800000c4: 00050513 addi x10,x10,0
800000c8: 00100073 ebreak
800000cc: 0000006f jal x0,800000cc <_trm_init+0x1c>

@ -0,0 +1,92 @@
elf/am-tests/goldbach: file format elf64-littleriscv
Disassembly of section .text:
0000000080000000 <_start>:
80000000: 00000413 addi x8,x0,0
80000004: 00009117 auipc x2,0x9
80000008: ffc10113 addi x2,x2,-4 # 80009000 <_end>
8000000c: 100000ef jal x1,8000010c <_trm_init>
0000000080000010 <check>:
80000010: 00050463 beq x10,x0,80000018 <check+0x8>
80000014: 00008067 jalr x0,0(x1)
80000018: ff010113 addi x2,x2,-16
8000001c: 00100513 addi x10,x0,1
80000020: 00113423 sd x1,8(x2)
80000024: 0dc000ef jal x1,80000100 <halt>
0000000080000028 <goldbach>:
80000028: 00200793 addi x15,x0,2
8000002c: 08a7d063 bge x15,x10,800000ac <goldbach+0x84>
80000030: ffe5059b addiw x11,x10,-2
80000034: 00200693 addi x13,x0,2
80000038: 00200813 addi x16,x0,2
8000003c: 00100893 addi x17,x0,1
80000040: 03068463 beq x13,x16,80000068 <goldbach+0x40>
80000044: 0016f793 andi x15,x13,1
80000048: 04078c63 beq x15,x0,800000a0 <goldbach+0x78>
8000004c: 00200713 addi x14,x0,2
80000050: 00c0006f jal x0,8000005c <goldbach+0x34>
80000054: 02f6e7bb remw x15,x13,x15
80000058: 04078463 beq x15,x0,800000a0 <goldbach+0x78>
8000005c: 0017071b addiw x14,x14,1
80000060: 00070793 addi x15,x14,0
80000064: fed718e3 bne x14,x13,80000054 <goldbach+0x2c>
80000068: 0005861b addiw x12,x11,0
8000006c: 03158a63 beq x11,x17,800000a0 <goldbach+0x78>
80000070: 03060463 beq x12,x16,80000098 <goldbach+0x70>
80000074: 0015f793 andi x15,x11,1
80000078: 02078463 beq x15,x0,800000a0 <goldbach+0x78>
8000007c: 00200713 addi x14,x0,2
80000080: 00c0006f jal x0,8000008c <goldbach+0x64>
80000084: 02f667bb remw x15,x12,x15
80000088: 00078c63 beq x15,x0,800000a0 <goldbach+0x78>
8000008c: 0017071b addiw x14,x14,1
80000090: 00070793 addi x15,x14,0
80000094: fee618e3 bne x12,x14,80000084 <goldbach+0x5c>
80000098: 00100513 addi x10,x0,1
8000009c: 00008067 jalr x0,0(x1)
800000a0: 0016869b addiw x13,x13,1
800000a4: fff5859b addiw x11,x11,-1
800000a8: f8d51ce3 bne x10,x13,80000040 <goldbach+0x18>
800000ac: 00000513 addi x10,x0,0
800000b0: 00008067 jalr x0,0(x1)
00000000800000b4 <main>:
800000b4: fe010113 addi x2,x2,-32
800000b8: 00813823 sd x8,16(x2)
800000bc: 00913423 sd x9,8(x2)
800000c0: 00113c23 sd x1,24(x2)
800000c4: 00400413 addi x8,x0,4
800000c8: 02000493 addi x9,x0,32
800000cc: 00040513 addi x10,x8,0
800000d0: f59ff0ef jal x1,80000028 <goldbach>
800000d4: fff50513 addi x10,x10,-1
800000d8: 0024041b addiw x8,x8,2
800000dc: 00153513 sltiu x10,x10,1
800000e0: f31ff0ef jal x1,80000010 <check>
800000e4: fe9414e3 bne x8,x9,800000cc <main+0x18>
800000e8: 01813083 ld x1,24(x2)
800000ec: 01013403 ld x8,16(x2)
800000f0: 00813483 ld x9,8(x2)
800000f4: 00000513 addi x10,x0,0
800000f8: 02010113 addi x2,x2,32
800000fc: 00008067 jalr x0,0(x1)
0000000080000100 <halt>:
80000100: 00050513 addi x10,x10,0
80000104: 00100073 ebreak
80000108: 0000006f jal x0,80000108 <halt+0x8>
000000008000010c <_trm_init>:
8000010c: ff010113 addi x2,x2,-16
80000110: 00000517 auipc x10,0x0
80000114: 02050513 addi x10,x10,32 # 80000130 <mainargs>
80000118: 00113423 sd x1,8(x2)
8000011c: f99ff0ef jal x1,800000b4 <main>
80000120: 00050513 addi x10,x10,0
80000124: 00100073 ebreak
80000128: 0000006f jal x0,80000128 <_trm_init+0x1c>

@ -0,0 +1,85 @@
elf/am-tests/if-else: file format elf64-littleriscv
Disassembly of section .text:
0000000080000000 <_start>:
80000000: 00000413 addi x8,x0,0
80000004: 00009117 auipc x2,0x9
80000008: ffc10113 addi x2,x2,-4 # 80009000 <_end>
8000000c: 0ec000ef jal x1,800000f8 <_trm_init>
0000000080000010 <check>:
80000010: 00050463 beq x10,x0,80000018 <check+0x8>
80000014: 00008067 jalr x0,0(x1)
80000018: ff010113 addi x2,x2,-16
8000001c: 00100513 addi x10,x0,1
80000020: 00113423 sd x1,8(x2)
80000024: 0c8000ef jal x1,800000ec <halt>
0000000080000028 <main>:
80000028: fc010113 addi x2,x2,-64
8000002c: 02813823 sd x8,48(x2)
80000030: 02913423 sd x9,40(x2)
80000034: 03213023 sd x18,32(x2)
80000038: 01313c23 sd x19,24(x2)
8000003c: 01413823 sd x20,16(x2)
80000040: 01513423 sd x21,8(x2)
80000044: 01613023 sd x22,0(x2)
80000048: 02113c23 sd x1,56(x2)
8000004c: 00000417 auipc x8,0x0
80000050: 10c40413 addi x8,x8,268 # 80000158 <test_data>
80000054: 00000497 auipc x9,0x0
80000058: 0cc48493 addi x9,x9,204 # 80000120 <ans>
8000005c: 00000997 auipc x19,0x0
80000060: 13498993 addi x19,x19,308 # 80000190 <_bss_start>
80000064: 1f400913 addi x18,x0,500
80000068: 12c00a93 addi x21,x0,300
8000006c: 06400b13 addi x22,x0,100
80000070: 03200a13 addi x20,x0,50
80000074: 00042783 lw x15,0(x8)
80000078: 09600713 addi x14,x0,150
8000007c: 00440413 addi x8,x8,4
80000080: 02f94063 blt x18,x15,800000a0 <main+0x78>
80000084: 00fa2733 slt x14,x20,x15
80000088: 40e006b3 sub x13,x0,x14
8000008c: 06400713 addi x14,x0,100
80000090: 00fac863 blt x21,x15,800000a0 <main+0x78>
80000094: 04b00713 addi x14,x0,75
80000098: 00fb4463 blt x22,x15,800000a0 <main+0x78>
8000009c: 0326f713 andi x14,x13,50
800000a0: 0004a503 lw x10,0(x9)
800000a4: 00448493 addi x9,x9,4
800000a8: 40e50533 sub x10,x10,x14
800000ac: 00153513 sltiu x10,x10,1
800000b0: f61ff0ef jal x1,80000010 <check>
800000b4: fd3410e3 bne x8,x19,80000074 <main+0x4c>
800000b8: 00100513 addi x10,x0,1
800000bc: f55ff0ef jal x1,80000010 <check>
800000c0: 03813083 ld x1,56(x2)
800000c4: 03013403 ld x8,48(x2)
800000c8: 02813483 ld x9,40(x2)
800000cc: 02013903 ld x18,32(x2)
800000d0: 01813983 ld x19,24(x2)
800000d4: 01013a03 ld x20,16(x2)
800000d8: 00813a83 ld x21,8(x2)
800000dc: 00013b03 ld x22,0(x2)
800000e0: 00000513 addi x10,x0,0
800000e4: 04010113 addi x2,x2,64
800000e8: 00008067 jalr x0,0(x1)
00000000800000ec <halt>:
800000ec: 00050513 addi x10,x10,0
800000f0: 00100073 ebreak
800000f4: 0000006f jal x0,800000f4 <halt+0x8>
00000000800000f8 <_trm_init>:
800000f8: ff010113 addi x2,x2,-16
800000fc: 00000517 auipc x10,0x0
80000100: 01c50513 addi x10,x10,28 # 80000118 <_etext>
80000104: 00113423 sd x1,8(x2)
80000108: f21ff0ef jal x1,80000028 <main>
8000010c: 00050513 addi x10,x10,0
80000110: 00100073 ebreak
80000114: 0000006f jal x0,80000114 <_trm_init+0x1c>

@ -0,0 +1,74 @@
elf/am-tests/leap-year: file format elf64-littleriscv
Disassembly of section .text:
0000000080000000 <_start>:
80000000: 00000413 addi x8,x0,0
80000004: 00009117 auipc x2,0x9
80000008: ffc10113 addi x2,x2,-4 # 80009000 <_end>
8000000c: 0c0000ef jal x1,800000cc <_trm_init>
0000000080000010 <check>:
80000010: 00050463 beq x10,x0,80000018 <check+0x8>
80000014: 00008067 jalr x0,0(x1)
80000018: ff010113 addi x2,x2,-16
8000001c: 00100513 addi x10,x0,1
80000020: 00113423 sd x1,8(x2)
80000024: 09c000ef jal x1,800000c0 <halt>
0000000080000028 <main>:
80000028: fd010113 addi x2,x2,-48
8000002c: 02813023 sd x8,32(x2)
80000030: 00913c23 sd x9,24(x2)
80000034: 01213823 sd x18,16(x2)
80000038: 01313423 sd x19,8(x2)
8000003c: 01413023 sd x20,0(x2)
80000040: 02113423 sd x1,40(x2)
80000044: 00000497 auipc x9,0x0
80000048: 0b448493 addi x9,x9,180 # 800000f8 <ans>
8000004c: 00000917 auipc x18,0x0
80000050: 2a090913 addi x18,x18,672 # 800002ec <_bss_start>
80000054: 76200413 addi x8,x0,1890
80000058: 19000993 addi x19,x0,400
8000005c: 06400a13 addi x20,x0,100
80000060: 00347793 andi x15,x8,3
80000064: 0004071b addiw x14,x8,0
80000068: 00079863 bne x15,x0,80000078 <main+0x50>
8000006c: 034766bb remw x13,x14,x20
80000070: 00100793 addi x15,x0,1
80000074: 00069663 bne x13,x0,80000080 <main+0x58>
80000078: 0337673b remw x14,x14,x19
8000007c: 00173793 sltiu x15,x14,1
80000080: 0004a503 lw x10,0(x9)
80000084: 00448493 addi x9,x9,4
80000088: 0014041b addiw x8,x8,1
8000008c: 40f50533 sub x10,x10,x15
80000090: 00153513 sltiu x10,x10,1
80000094: f7dff0ef jal x1,80000010 <check>
80000098: fd2494e3 bne x9,x18,80000060 <main+0x38>
8000009c: 02813083 ld x1,40(x2)
800000a0: 02013403 ld x8,32(x2)
800000a4: 01813483 ld x9,24(x2)
800000a8: 01013903 ld x18,16(x2)
800000ac: 00813983 ld x19,8(x2)
800000b0: 00013a03 ld x20,0(x2)
800000b4: 00000513 addi x10,x0,0
800000b8: 03010113 addi x2,x2,48
800000bc: 00008067 jalr x0,0(x1)
00000000800000c0 <halt>:
800000c0: 00050513 addi x10,x10,0
800000c4: 00100073 ebreak
800000c8: 0000006f jal x0,800000c8 <halt+0x8>
00000000800000cc <_trm_init>:
800000cc: ff010113 addi x2,x2,-16
800000d0: 00000517 auipc x10,0x0
800000d4: 02050513 addi x10,x10,32 # 800000f0 <mainargs>
800000d8: 00113423 sd x1,8(x2)
800000dc: f4dff0ef jal x1,80000028 <main>
800000e0: 00050513 addi x10,x10,0
800000e4: 00100073 ebreak
800000e8: 0000006f jal x0,800000e8 <_trm_init+0x1c>

@ -0,0 +1,145 @@
elf/am-tests/load-store: file format elf64-littleriscv
Disassembly of section .text:
0000000080000000 <_start>:
80000000: 00000413 addi x8,x0,0
80000004: 00009117 auipc x2,0x9
80000008: ffc10113 addi x2,x2,-4 # 80009000 <_end>
8000000c: 1dc000ef jal x1,800001e8 <_trm_init>
0000000080000010 <check>:
80000010: 00050463 beq x10,x0,80000018 <check+0x8>
80000014: 00008067 jalr x0,0(x1)
80000018: ff010113 addi x2,x2,-16
8000001c: 00100513 addi x10,x0,1
80000020: 00113423 sd x1,8(x2)
80000024: 1b8000ef jal x1,800001dc <halt>
0000000080000028 <main>:
80000028: fd010113 addi x2,x2,-48
8000002c: 01313423 sd x19,8(x2)
80000030: 00000997 auipc x19,0x0
80000034: 23098993 addi x19,x19,560 # 80000260 <mem>
80000038: 02813023 sd x8,32(x2)
8000003c: 00913c23 sd x9,24(x2)
80000040: 01213823 sd x18,16(x2)
80000044: 02113423 sd x1,40(x2)
80000048: 01413023 sd x20,0(x2)
8000004c: 00000917 auipc x18,0x0
80000050: 1c490913 addi x18,x18,452 # 80000210 <lh_ans>
80000054: 00000497 auipc x9,0x0
80000058: 21c48493 addi x9,x9,540 # 80000270 <sh_ans>
8000005c: 00098413 addi x8,x19,0
80000060: 00041503 lh x10,0(x8)
80000064: 00092783 lw x15,0(x18)
80000068: 00240413 addi x8,x8,2
8000006c: 00490913 addi x18,x18,4
80000070: 40f50533 sub x10,x10,x15
80000074: 00153513 sltiu x10,x10,1
80000078: f99ff0ef jal x1,80000010 <check>
8000007c: fe9412e3 bne x8,x9,80000060 <main+0x38>
80000080: 00000917 auipc x18,0x0
80000084: 1b090913 addi x18,x18,432 # 80000230 <lhu_ans>
80000088: 00000417 auipc x8,0x0
8000008c: 1d840413 addi x8,x8,472 # 80000260 <mem>
80000090: 00045503 lhu x10,0(x8)
80000094: 00092783 lw x15,0(x18)
80000098: 00240413 addi x8,x8,2
8000009c: 00490913 addi x18,x18,4
800000a0: 40f50533 sub x10,x10,x15
800000a4: 00153513 sltiu x10,x10,1
800000a8: f69ff0ef jal x1,80000010 <check>
800000ac: fe9412e3 bne x8,x9,80000090 <main+0x68>
800000b0: 0029c683 lbu x13,2(x19)
800000b4: 0019c603 lbu x12,1(x19)
800000b8: 0039c703 lbu x14,3(x19)
800000bc: 0049c783 lbu x15,4(x19)
800000c0: 00869693 slli x13,x13,0x8
800000c4: 00000417 auipc x8,0x0
800000c8: 18c40413 addi x8,x8,396 # 80000250 <lwlr_ans>
800000cc: 00c6e6b3 or x13,x13,x12
800000d0: 01071713 slli x14,x14,0x10
800000d4: 00d76733 or x14,x14,x13
800000d8: 00042503 lw x10,0(x8)
800000dc: 01879793 slli x15,x15,0x18
800000e0: 00e7e7b3 or x15,x15,x14
800000e4: 0007879b addiw x15,x15,0
800000e8: 40f50533 sub x10,x10,x15
800000ec: 00153513 sltiu x10,x10,1
800000f0: f21ff0ef jal x1,80000010 <check>
800000f4: 0069c683 lbu x13,6(x19)
800000f8: 0059c603 lbu x12,5(x19)
800000fc: 0079c703 lbu x14,7(x19)
80000100: 0089c783 lbu x15,8(x19)
80000104: 00869693 slli x13,x13,0x8
80000108: 00c6e6b3 or x13,x13,x12
8000010c: 01071713 slli x14,x14,0x10
80000110: 00d76733 or x14,x14,x13
80000114: 00442503 lw x10,4(x8)
80000118: 01879793 slli x15,x15,0x18
8000011c: 00e7e7b3 or x15,x15,x14
80000120: 0007879b addiw x15,x15,0
80000124: 40f50533 sub x10,x10,x15
80000128: 00153513 sltiu x10,x10,1
8000012c: ee5ff0ef jal x1,80000010 <check>
80000130: 00a9c683 lbu x13,10(x19)
80000134: 0099c603 lbu x12,9(x19)
80000138: 00b9c703 lbu x14,11(x19)
8000013c: 00c9c783 lbu x15,12(x19)
80000140: 00869693 slli x13,x13,0x8
80000144: 00c6e6b3 or x13,x13,x12
80000148: 01071713 slli x14,x14,0x10
8000014c: 00842503 lw x10,8(x8)
80000150: 00d76733 or x14,x14,x13
80000154: 01879793 slli x15,x15,0x18
80000158: 00e7e7b3 or x15,x15,x14
8000015c: 0007879b addiw x15,x15,0
80000160: 40f50533 sub x10,x10,x15
80000164: 00153513 sltiu x10,x10,1
80000168: 00100a13 addi x20,x0,1
8000016c: ea5ff0ef jal x1,80000010 <check>
80000170: 00000917 auipc x18,0x0
80000174: 10090913 addi x18,x18,256 # 80000270 <sh_ans>
80000178: 00000417 auipc x8,0x0
8000017c: 0e840413 addi x8,x8,232 # 80000260 <mem>
80000180: 413a09bb subw x19,x20,x19
80000184: 008987bb addw x15,x19,x8
80000188: 00fa17bb sllw x15,x20,x15
8000018c: 00092503 lw x10,0(x18)
80000190: fff7c793 xori x15,x15,-1
80000194: 03079793 slli x15,x15,0x30
80000198: 0307d793 srli x15,x15,0x30
8000019c: 40f50533 sub x10,x10,x15
800001a0: 00f41023 sh x15,0(x8)
800001a4: 00153513 sltiu x10,x10,1
800001a8: 00240413 addi x8,x8,2
800001ac: e65ff0ef jal x1,80000010 <check>
800001b0: 00490913 addi x18,x18,4
800001b4: fc9418e3 bne x8,x9,80000184 <main+0x15c>
800001b8: 02813083 ld x1,40(x2)
800001bc: 02013403 ld x8,32(x2)
800001c0: 01813483 ld x9,24(x2)
800001c4: 01013903 ld x18,16(x2)
800001c8: 00813983 ld x19,8(x2)
800001cc: 00013a03 ld x20,0(x2)
800001d0: 00000513 addi x10,x0,0
800001d4: 03010113 addi x2,x2,48
800001d8: 00008067 jalr x0,0(x1)
00000000800001dc <halt>:
800001dc: 00050513 addi x10,x10,0
800001e0: 00100073 ebreak
800001e4: 0000006f jal x0,800001e4 <halt+0x8>
00000000800001e8 <_trm_init>:
800001e8: ff010113 addi x2,x2,-16
800001ec: 00000517 auipc x10,0x0
800001f0: 01c50513 addi x10,x10,28 # 80000208 <_etext>
800001f4: 00113423 sd x1,8(x2)
800001f8: e31ff0ef jal x1,80000028 <main>
800001fc: 00050513 addi x10,x10,0
80000200: 00100073 ebreak
80000204: 0000006f jal x0,80000204 <_trm_init+0x1c>

@ -0,0 +1,104 @@
elf/am-tests/matrix-mul: file format elf64-littleriscv
Disassembly of section .text:
0000000080000000 <_start>:
80000000: 00000413 addi x8,x0,0
80000004: 00009117 auipc x2,0x9
80000008: ffc10113 addi x2,x2,-4 # 80009000 <_end>
8000000c: 138000ef jal x1,80000144 <_trm_init>
0000000080000010 <check>:
80000010: 00050463 beq x10,x0,80000018 <check+0x8>
80000014: 00008067 jalr x0,0(x1)
80000018: ff010113 addi x2,x2,-16
8000001c: 00100513 addi x10,x0,1
80000020: 00113423 sd x1,8(x2)
80000024: 114000ef jal x1,80000138 <halt>
0000000080000028 <main>:
80000028: fb010113 addi x2,x2,-80
8000002c: 02913c23 sd x9,56(x2)
80000030: 03213823 sd x18,48(x2)
80000034: 03313423 sd x19,40(x2)
80000038: 03413023 sd x20,32(x2)
8000003c: 01513c23 sd x21,24(x2)
80000040: 01613823 sd x22,16(x2)
80000044: 04113423 sd x1,72(x2)
80000048: 04813023 sd x8,64(x2)
8000004c: 01713423 sd x23,8(x2)
80000050: 01813023 sd x24,0(x2)
80000054: 00000497 auipc x9,0x0
80000058: 11c48493 addi x9,x9,284 # 80000170 <a>
8000005c: 00000a17 auipc x20,0x0
80000060: 5c4a0a13 addi x20,x20,1476 # 80000620 <c>
80000064: 00000997 auipc x19,0x0
80000068: 29c98993 addi x19,x19,668 # 80000300 <ans>
8000006c: 00000b17 auipc x22,0x0
80000070: 294b0b13 addi x22,x22,660 # 80000300 <ans>
80000074: 00000917 auipc x18,0x0
80000078: 5d490913 addi x18,x18,1492 # 80000648 <c+0x28>
8000007c: 00000a97 auipc x21,0x0
80000080: 5a4a8a93 addi x21,x21,1444 # 80000620 <c>
80000084: 000a8593 addi x11,x21,0
80000088: 00098c13 addi x24,x19,0
8000008c: 000a0b93 addi x23,x20,0
80000090: e7058413 addi x8,x11,-400
80000094: 00048713 addi x14,x9,0
80000098: 00000693 addi x13,x0,0
8000009c: 00072603 lw x12,0(x14)
800000a0: 00042783 lw x15,0(x8)
800000a4: 02840413 addi x8,x8,40
800000a8: 00470713 addi x14,x14,4
800000ac: 02c787bb mulw x15,x15,x12
800000b0: 00d786bb addw x13,x15,x13
800000b4: feb414e3 bne x8,x11,8000009c <main+0x74>
800000b8: 000c2503 lw x10,0(x24)
800000bc: 00dba023 sw x13,0(x23)
800000c0: 004c0c13 addi x24,x24,4
800000c4: 40d50533 sub x10,x10,x13
800000c8: 00153513 sltiu x10,x10,1
800000cc: f45ff0ef jal x1,80000010 <check>
800000d0: 00100513 addi x10,x0,1
800000d4: f3dff0ef jal x1,80000010 <check>
800000d8: 00440593 addi x11,x8,4
800000dc: 004b8b93 addi x23,x23,4
800000e0: fab918e3 bne x18,x11,80000090 <main+0x68>
800000e4: 00100513 addi x10,x0,1
800000e8: 02848493 addi x9,x9,40
800000ec: f25ff0ef jal x1,80000010 <check>
800000f0: 028a0a13 addi x20,x20,40
800000f4: 02898993 addi x19,x19,40
800000f8: f96496e3 bne x9,x22,80000084 <main+0x5c>
800000fc: 00100513 addi x10,x0,1
80000100: f11ff0ef jal x1,80000010 <check>
80000104: 04813083 ld x1,72(x2)
80000108: 04013403 ld x8,64(x2)
8000010c: 03813483 ld x9,56(x2)
80000110: 03013903 ld x18,48(x2)
80000114: 02813983 ld x19,40(x2)
80000118: 02013a03 ld x20,32(x2)
8000011c: 01813a83 ld x21,24(x2)
80000120: 01013b03 ld x22,16(x2)
80000124: 00813b83 ld x23,8(x2)
80000128: 00013c03 ld x24,0(x2)
8000012c: 00000513 addi x10,x0,0
80000130: 05010113 addi x2,x2,80
80000134: 00008067 jalr x0,0(x1)
0000000080000138 <halt>:
80000138: 00050513 addi x10,x10,0
8000013c: 00100073 ebreak
80000140: 0000006f jal x0,80000140 <halt+0x8>
0000000080000144 <_trm_init>:
80000144: ff010113 addi x2,x2,-16
80000148: 00000517 auipc x10,0x0
8000014c: 02050513 addi x10,x10,32 # 80000168 <mainargs>
80000150: 00113423 sd x1,8(x2)
80000154: ed5ff0ef jal x1,80000028 <main>
80000158: 00050513 addi x10,x10,0
8000015c: 00100073 ebreak
80000160: 0000006f jal x0,80000160 <_trm_init+0x1c>

@ -0,0 +1,94 @@
elf/am-tests/max: file format elf64-littleriscv
Disassembly of section .text:
0000000080000000 <_start>:
80000000: 00000413 addi x8,x0,0
80000004: 00009117 auipc x2,0x9
80000008: ffc10113 addi x2,x2,-4 # 80009000 <_end>
8000000c: 110000ef jal x1,8000011c <_trm_init>
0000000080000010 <check>:
80000010: 00050463 beq x10,x0,80000018 <check+0x8>
80000014: 00008067 jalr x0,0(x1)
80000018: ff010113 addi x2,x2,-16
8000001c: 00100513 addi x10,x0,1
80000020: 00113423 sd x1,8(x2)
80000024: 0ec000ef jal x1,80000110 <halt>
0000000080000028 <main>:
80000028: fa010113 addi x2,x2,-96
8000002c: 01713c23 sd x23,24(x2)
80000030: 00000b97 auipc x23,0x0
80000034: 218b8b93 addi x23,x23,536 # 80000248 <test_data>
80000038: 05213023 sd x18,64(x2)
8000003c: 03413823 sd x20,48(x2)
80000040: 03513423 sd x21,40(x2)
80000044: 03613023 sd x22,32(x2)
80000048: 01813823 sd x24,16(x2)
8000004c: 04113c23 sd x1,88(x2)
80000050: 04813823 sd x8,80(x2)
80000054: 04913423 sd x9,72(x2)
80000058: 03313c23 sd x19,56(x2)
8000005c: 01913423 sd x25,8(x2)
80000060: 00000b17 auipc x22,0x0
80000064: 0e8b0b13 addi x22,x22,232 # 80000148 <ans>
80000068: 000b8a93 addi x21,x23,0
8000006c: 00000a13 addi x20,x0,0
80000070: 00000917 auipc x18,0x0
80000074: 1f890913 addi x18,x18,504 # 80000268 <_bss_start>
80000078: 04000c13 addi x24,x0,64
8000007c: 000aa483 lw x9,0(x21)
80000080: 000b0c93 addi x25,x22,0
80000084: 000b8413 addi x8,x23,0
80000088: 00048993 addi x19,x9,0
8000008c: 00042783 lw x15,0(x8)
80000090: 00440413 addi x8,x8,4
80000094: 0007851b addiw x10,x15,0
80000098: 0097d463 bge x15,x9,800000a0 <main+0x78>
8000009c: 0009851b addiw x10,x19,0
800000a0: 000ca783 lw x15,0(x25)
800000a4: 004c8c93 addi x25,x25,4
800000a8: 40f50533 sub x10,x10,x15
800000ac: 00153513 sltiu x10,x10,1
800000b0: f61ff0ef jal x1,80000010 <check>
800000b4: fc891ce3 bne x18,x8,8000008c <main+0x64>
800000b8: 00100513 addi x10,x0,1
800000bc: 008a0a1b addiw x20,x20,8
800000c0: f51ff0ef jal x1,80000010 <check>
800000c4: 004a8a93 addi x21,x21,4
800000c8: 020b0b13 addi x22,x22,32
800000cc: fb8a18e3 bne x20,x24,8000007c <main+0x54>
800000d0: 00100513 addi x10,x0,1
800000d4: f3dff0ef jal x1,80000010 <check>
800000d8: 05813083 ld x1,88(x2)
800000dc: 05013403 ld x8,80(x2)
800000e0: 04813483 ld x9,72(x2)
800000e4: 04013903 ld x18,64(x2)
800000e8: 03813983 ld x19,56(x2)
800000ec: 03013a03 ld x20,48(x2)
800000f0: 02813a83 ld x21,40(x2)
800000f4: 02013b03 ld x22,32(x2)
800000f8: 01813b83 ld x23,24(x2)
800000fc: 01013c03 ld x24,16(x2)
80000100: 00813c83 ld x25,8(x2)
80000104: 00000513 addi x10,x0,0
80000108: 06010113 addi x2,x2,96
8000010c: 00008067 jalr x0,0(x1)
0000000080000110 <halt>:
80000110: 00050513 addi x10,x10,0
80000114: 00100073 ebreak
80000118: 0000006f jal x0,80000118 <halt+0x8>
000000008000011c <_trm_init>:
8000011c: ff010113 addi x2,x2,-16
80000120: 00000517 auipc x10,0x0
80000124: 02050513 addi x10,x10,32 # 80000140 <mainargs>
80000128: 00113423 sd x1,8(x2)
8000012c: efdff0ef jal x1,80000028 <main>
80000130: 00050513 addi x10,x10,0
80000134: 00100073 ebreak
80000138: 0000006f jal x0,80000138 <_trm_init+0x1c>

@ -0,0 +1,107 @@
elf/am-tests/min3: file format elf64-littleriscv
Disassembly of section .text:
0000000080000000 <_start>:
80000000: 00000413 addi x8,x0,0
80000004: 00009117 auipc x2,0x9
80000008: ffc10113 addi x2,x2,-4 # 80009000 <_end>
8000000c: 144000ef jal x1,80000150 <_trm_init>
0000000080000010 <check>:
80000010: 00050463 beq x10,x0,80000018 <check+0x8>
80000014: 00008067 jalr x0,0(x1)
80000018: ff010113 addi x2,x2,-16
8000001c: 00100513 addi x10,x0,1
80000020: 00113423 sd x1,8(x2)
80000024: 120000ef jal x1,80000144 <halt>
0000000080000028 <main>:
80000028: f9010113 addi x2,x2,-112
8000002c: 03613823 sd x22,48(x2)
80000030: 00000b17 auipc x22,0x0
80000034: 248b0b13 addi x22,x22,584 # 80000278 <test_data>
80000038: 05213823 sd x18,80(x2)
8000003c: 03713423 sd x23,40(x2)
80000040: 03813023 sd x24,32(x2)
80000044: 06113423 sd x1,104(x2)
80000048: 06813023 sd x8,96(x2)
8000004c: 04913c23 sd x9,88(x2)
80000050: 05313423 sd x19,72(x2)
80000054: 05413023 sd x20,64(x2)
80000058: 03513c23 sd x21,56(x2)
8000005c: 01913c23 sd x25,24(x2)
80000060: 01a13823 sd x26,16(x2)
80000064: 01b13423 sd x27,8(x2)
80000068: 00000c17 auipc x24,0x0
8000006c: 110c0c13 addi x24,x24,272 # 80000178 <ans>
80000070: 00000917 auipc x18,0x0
80000074: 21890913 addi x18,x18,536 # 80000288 <_bss_start>
80000078: 000b0b93 addi x23,x22,0
8000007c: 000baa83 lw x21,0(x23)
80000080: 000c0993 addi x19,x24,0
80000084: 000b0493 addi x9,x22,0
80000088: 000a8c93 addi x25,x21,0
8000008c: 0004a783 lw x15,0(x9)
80000090: 0007841b addiw x8,x15,0
80000094: 00fad463 bge x21,x15,8000009c <main+0x74>
80000098: 000c841b addiw x8,x25,0
8000009c: 00098d93 addi x27,x19,0
800000a0: 000b0d13 addi x26,x22,0
800000a4: 00040a13 addi x20,x8,0
800000a8: 000d2783 lw x15,0(x26)
800000ac: 004d0d13 addi x26,x26,4
800000b0: 0007851b addiw x10,x15,0
800000b4: 00f45463 bge x8,x15,800000bc <main+0x94>
800000b8: 000a051b addiw x10,x20,0
800000bc: 000da783 lw x15,0(x27)
800000c0: 004d8d93 addi x27,x27,4
800000c4: 40f50533 sub x10,x10,x15
800000c8: 00153513 sltiu x10,x10,1
800000cc: f45ff0ef jal x1,80000010 <check>
800000d0: fd2d1ce3 bne x26,x18,800000a8 <main+0x80>
800000d4: 00100513 addi x10,x0,1
800000d8: 00448493 addi x9,x9,4
800000dc: f35ff0ef jal x1,80000010 <check>
800000e0: 01098993 addi x19,x19,16
800000e4: fba494e3 bne x9,x26,8000008c <main+0x64>
800000e8: 00100513 addi x10,x0,1
800000ec: 004b8b93 addi x23,x23,4
800000f0: f21ff0ef jal x1,80000010 <check>
800000f4: 040c0c13 addi x24,x24,64
800000f8: f89b92e3 bne x23,x9,8000007c <main+0x54>
800000fc: 00100513 addi x10,x0,1
80000100: f11ff0ef jal x1,80000010 <check>
80000104: 06813083 ld x1,104(x2)
80000108: 06013403 ld x8,96(x2)
8000010c: 05813483 ld x9,88(x2)
80000110: 05013903 ld x18,80(x2)
80000114: 04813983 ld x19,72(x2)
80000118: 04013a03 ld x20,64(x2)
8000011c: 03813a83 ld x21,56(x2)
80000120: 03013b03 ld x22,48(x2)
80000124: 02813b83 ld x23,40(x2)
80000128: 02013c03 ld x24,32(x2)
8000012c: 01813c83 ld x25,24(x2)
80000130: 01013d03 ld x26,16(x2)
80000134: 00813d83 ld x27,8(x2)
80000138: 00000513 addi x10,x0,0
8000013c: 07010113 addi x2,x2,112
80000140: 00008067 jalr x0,0(x1)
0000000080000144 <halt>:
80000144: 00050513 addi x10,x10,0
80000148: 00100073 ebreak
8000014c: 0000006f jal x0,8000014c <halt+0x8>
0000000080000150 <_trm_init>:
80000150: ff010113 addi x2,x2,-16
80000154: 00000517 auipc x10,0x0
80000158: 01c50513 addi x10,x10,28 # 80000170 <_etext>
8000015c: 00113423 sd x1,8(x2)
80000160: ec9ff0ef jal x1,80000028 <main>
80000164: 00050513 addi x10,x10,0
80000168: 00100073 ebreak
8000016c: 0000006f jal x0,8000016c <_trm_init+0x1c>

@ -0,0 +1,89 @@
elf/am-tests/mov-c: file format elf64-littleriscv
Disassembly of section .text:
0000000080000000 <_start>:
80000000: 00000413 addi x8,x0,0
80000004: 00009117 auipc x2,0x9
80000008: ffc10113 addi x2,x2,-4 # 80009000 <_end>
8000000c: 0fc000ef jal x1,80000108 <_trm_init>
0000000080000010 <check>:
80000010: 00050463 beq x10,x0,80000018 <check+0x8>
80000014: 00008067 jalr x0,0(x1)
80000018: ff010113 addi x2,x2,-16
8000001c: 00100513 addi x10,x0,1
80000020: 00113423 sd x1,8(x2)
80000024: 0d8000ef jal x1,800000fc <halt>
0000000080000028 <main>:
80000028: ff010113 addi x2,x2,-16
8000002c: 00813023 sd x8,0(x2)
80000030: 00000417 auipc x8,0x0
80000034: 10040413 addi x8,x8,256 # 80000130 <A>
80000038: 00042023 sw x0,0(x8)
8000003c: 00100793 addi x15,x0,1
80000040: 00f42223 sw x15,4(x8)
80000044: 00200793 addi x15,x0,2
80000048: 00f42423 sw x15,8(x8)
8000004c: 00300793 addi x15,x0,3
80000050: 00f42623 sw x15,12(x8)
80000054: 00400793 addi x15,x0,4
80000058: 00f42823 sw x15,16(x8)
8000005c: 00c42783 lw x15,12(x8)
80000060: 00113423 sd x1,8(x2)
80000064: 00000717 auipc x14,0x0
80000068: 0ef72a23 sw x15,244(x14) # 80000158 <b>
8000006c: 00000797 auipc x15,0x0
80000070: 0ec7a783 lw x15,236(x15) # 80000158 <b>
80000074: 00f42a23 sw x15,20(x8)
80000078: 00042503 lw x10,0(x8)
8000007c: 00153513 sltiu x10,x10,1
80000080: f91ff0ef jal x1,80000010 <check>
80000084: 00442503 lw x10,4(x8)
80000088: fff50513 addi x10,x10,-1
8000008c: 00153513 sltiu x10,x10,1
80000090: f81ff0ef jal x1,80000010 <check>
80000094: 00842503 lw x10,8(x8)
80000098: ffe50513 addi x10,x10,-2
8000009c: 00153513 sltiu x10,x10,1
800000a0: f71ff0ef jal x1,80000010 <check>
800000a4: 00c42503 lw x10,12(x8)
800000a8: ffd50513 addi x10,x10,-3
800000ac: 00153513 sltiu x10,x10,1
800000b0: f61ff0ef jal x1,80000010 <check>
800000b4: 01042503 lw x10,16(x8)
800000b8: ffc50513 addi x10,x10,-4
800000bc: 00153513 sltiu x10,x10,1
800000c0: f51ff0ef jal x1,80000010 <check>
800000c4: 00000517 auipc x10,0x0
800000c8: 09452503 lw x10,148(x10) # 80000158 <b>
800000cc: ffd50513 addi x10,x10,-3
800000d0: 00153513 sltiu x10,x10,1
800000d4: f3dff0ef jal x1,80000010 <check>
800000d8: 01442503 lw x10,20(x8)
800000dc: ffd50513 addi x10,x10,-3
800000e0: 00153513 sltiu x10,x10,1
800000e4: f2dff0ef jal x1,80000010 <check>
800000e8: 00813083 ld x1,8(x2)
800000ec: 00013403 ld x8,0(x2)
800000f0: 00000513 addi x10,x0,0
800000f4: 01010113 addi x2,x2,16
800000f8: 00008067 jalr x0,0(x1)
00000000800000fc <halt>:
800000fc: 00050513 addi x10,x10,0
80000100: 00100073 ebreak
80000104: 0000006f jal x0,80000104 <halt+0x8>
0000000080000108 <_trm_init>:
80000108: ff010113 addi x2,x2,-16
8000010c: 00000517 auipc x10,0x0
80000110: 01c50513 addi x10,x10,28 # 80000128 <_etext>
80000114: 00113423 sd x1,8(x2)
80000118: f11ff0ef jal x1,80000028 <main>
8000011c: 00050513 addi x10,x10,0
80000120: 00100073 ebreak
80000124: 0000006f jal x0,80000124 <_trm_init+0x1c>

@ -0,0 +1,132 @@
elf/am-tests/movsx: file format elf64-littleriscv
Disassembly of section .text:
0000000080000000 <_start>:
80000000: 00000413 addi x8,x0,0
80000004: 00009117 auipc x2,0x9
80000008: ffc10113 addi x2,x2,-4 # 80009000 <_end>
8000000c: 1a8000ef jal x1,800001b4 <_trm_init>
0000000080000010 <check>:
80000010: 00050463 beq x10,x0,80000018 <check+0x8>
80000014: 00008067 jalr x0,0(x1)
80000018: ff010113 addi x2,x2,-16
8000001c: 00100513 addi x10,x0,1
80000020: 00113423 sd x1,8(x2)
80000024: 184000ef jal x1,800001a8 <halt>
0000000080000028 <main>:
80000028: fe010113 addi x2,x2,-32
8000002c: 00813823 sd x8,16(x2)
80000030: 00000417 auipc x8,0x0
80000034: 1b040413 addi x8,x8,432 # 800001e0 <A>
80000038: 00042023 sw x0,0(x8)
8000003c: 00100793 addi x15,x0,1
80000040: 00f42223 sw x15,4(x8)
80000044: 00200793 addi x15,x0,2
80000048: 00f42423 sw x15,8(x8)
8000004c: 00300793 addi x15,x0,3
80000050: 00f42623 sw x15,12(x8)
80000054: 00400793 addi x15,x0,4
80000058: 00f42823 sw x15,16(x8)
8000005c: 00c42783 lw x15,12(x8)
80000060: 00913423 sd x9,8(x2)
80000064: 00000497 auipc x9,0x0
80000068: 1a448493 addi x9,x9,420 # 80000208 <C>
8000006c: 00000717 auipc x14,0x0
80000070: 1af72423 sw x15,424(x14) # 80000214 <b>
80000074: 00000797 auipc x15,0x0
80000078: 1a07a783 lw x15,416(x15) # 80000214 <b>
8000007c: 00f42a23 sw x15,20(x8)
80000080: 06100793 addi x15,x0,97
80000084: 00f48023 sb x15,0(x9)
80000088: 0004c503 lbu x10,0(x9)
8000008c: 00113c23 sd x1,24(x2)
80000090: 0185151b slliw x10,x10,0x18
80000094: 4185551b sraiw x10,x10,0x18
80000098: f9f50513 addi x10,x10,-97
8000009c: 00153513 sltiu x10,x10,1
800000a0: f71ff0ef jal x1,80000010 <check>
800000a4: 0004c783 lbu x15,0(x9)
800000a8: 0187979b slliw x15,x15,0x18
800000ac: 4187d79b sraiw x15,x15,0x18
800000b0: 00f480a3 sb x15,1(x9)
800000b4: 0014c503 lbu x10,1(x9)
800000b8: 0185151b slliw x10,x10,0x18
800000bc: 4185551b sraiw x10,x10,0x18
800000c0: f9f50513 addi x10,x10,-97
800000c4: 00153513 sltiu x10,x10,1
800000c8: f49ff0ef jal x1,80000010 <check>
800000cc: 0004c783 lbu x15,0(x9)
800000d0: 0187979b slliw x15,x15,0x18
800000d4: 4187d79b sraiw x15,x15,0x18
800000d8: 00f42023 sw x15,0(x8)
800000dc: 00042503 lw x10,0(x8)
800000e0: f9f50513 addi x10,x10,-97
800000e4: 00153513 sltiu x10,x10,1
800000e8: f29ff0ef jal x1,80000010 <check>
800000ec: f8000793 addi x15,x0,-128
800000f0: 00f480a3 sb x15,1(x9)
800000f4: 0014c783 lbu x15,1(x9)
800000f8: 0187979b slliw x15,x15,0x18
800000fc: 4187d79b sraiw x15,x15,0x18
80000100: 00f42023 sw x15,0(x8)
80000104: 00442503 lw x10,4(x8)
80000108: fff50513 addi x10,x10,-1
8000010c: 00153513 sltiu x10,x10,1
80000110: f01ff0ef jal x1,80000010 <check>
80000114: 00842503 lw x10,8(x8)
80000118: ffe50513 addi x10,x10,-2
8000011c: 00153513 sltiu x10,x10,1
80000120: ef1ff0ef jal x1,80000010 <check>
80000124: 00c42503 lw x10,12(x8)
80000128: ffd50513 addi x10,x10,-3
8000012c: 00153513 sltiu x10,x10,1
80000130: ee1ff0ef jal x1,80000010 <check>
80000134: 01042503 lw x10,16(x8)
80000138: ffc50513 addi x10,x10,-4
8000013c: 00153513 sltiu x10,x10,1
80000140: ed1ff0ef jal x1,80000010 <check>
80000144: 00000517 auipc x10,0x0
80000148: 0d052503 lw x10,208(x10) # 80000214 <b>
8000014c: ffd50513 addi x10,x10,-3
80000150: 00153513 sltiu x10,x10,1
80000154: ebdff0ef jal x1,80000010 <check>
80000158: 01442503 lw x10,20(x8)
8000015c: ffd50513 addi x10,x10,-3
80000160: 00153513 sltiu x10,x10,1
80000164: eadff0ef jal x1,80000010 <check>
80000168: 0014c503 lbu x10,1(x9)
8000016c: 0185151b slliw x10,x10,0x18
80000170: 4185551b sraiw x10,x10,0x18
80000174: 08050513 addi x10,x10,128
80000178: 00153513 sltiu x10,x10,1
8000017c: e95ff0ef jal x1,80000010 <check>
80000180: 00042503 lw x10,0(x8)
80000184: 08050513 addi x10,x10,128
80000188: 00153513 sltiu x10,x10,1
8000018c: e85ff0ef jal x1,80000010 <check>
80000190: 01813083 ld x1,24(x2)
80000194: 01013403 ld x8,16(x2)
80000198: 00813483 ld x9,8(x2)
8000019c: 00000513 addi x10,x0,0
800001a0: 02010113 addi x2,x2,32
800001a4: 00008067 jalr x0,0(x1)
00000000800001a8 <halt>:
800001a8: 00050513 addi x10,x10,0
800001ac: 00100073 ebreak
800001b0: 0000006f jal x0,800001b0 <halt+0x8>
00000000800001b4 <_trm_init>:
800001b4: ff010113 addi x2,x2,-16
800001b8: 00000517 auipc x10,0x0
800001bc: 02050513 addi x10,x10,32 # 800001d8 <mainargs>
800001c0: 00113423 sd x1,8(x2)
800001c4: e65ff0ef jal x1,80000028 <main>
800001c8: 00050513 addi x10,x10,0
800001cc: 00100073 ebreak
800001d0: 0000006f jal x0,800001d0 <_trm_init+0x1c>

@ -0,0 +1,102 @@
elf/am-tests/mul-longlong: file format elf64-littleriscv
Disassembly of section .text:
0000000080000000 <_start>:
80000000: 00000413 addi x8,x0,0
80000004: 00009117 auipc x2,0x9
80000008: ffc10113 addi x2,x2,-4 # 80009000 <_end>
8000000c: 130000ef jal x1,8000013c <_trm_init>
0000000080000010 <check>:
80000010: 00050463 beq x10,x0,80000018 <check+0x8>
80000014: 00008067 jalr x0,0(x1)
80000018: ff010113 addi x2,x2,-16
8000001c: 00100513 addi x10,x0,1
80000020: 00113423 sd x1,8(x2)
80000024: 10c000ef jal x1,80000130 <halt>
0000000080000028 <main>:
80000028: fa010113 addi x2,x2,-96
8000002c: 04913423 sd x9,72(x2)
80000030: 05213023 sd x18,64(x2)
80000034: 03313c23 sd x19,56(x2)
80000038: 03413823 sd x20,48(x2)
8000003c: 03513423 sd x21,40(x2)
80000040: 03613023 sd x22,32(x2)
80000044: 01813823 sd x24,16(x2)
80000048: 00000493 addi x9,x0,0
8000004c: 04113c23 sd x1,88(x2)
80000050: 04813823 sd x8,80(x2)
80000054: 01713c23 sd x23,24(x2)
80000058: 01913423 sd x25,8(x2)
8000005c: 00400913 addi x18,x0,4
80000060: 00000a17 auipc x20,0x0
80000064: 158a0a13 addi x20,x20,344 # 800001b8 <test_data>
80000068: 00000993 addi x19,x0,0
8000006c: 00000b17 auipc x22,0x0
80000070: 0fcb0b13 addi x22,x22,252 # 80000168 <ans>
80000074: 00300a93 addi x21,x0,3
80000078: 00048c1b addiw x24,x9,0
8000007c: 07248463 beq x9,x18,800000e4 <main+0xbc>
80000080: 000a2783 lw x15,0(x20)
80000084: 00399413 slli x8,x19,0x3
80000088: 008b0433 add x8,x22,x8
8000008c: 00078b93 addi x23,x15,0
80000090: 000a0c93 addi x25,x20,0
80000094: 037787b3 mul x15,x15,x23
80000098: 00043503 ld x10,0(x8)
8000009c: 001c0c1b addiw x24,x24,1
800000a0: 004c8c93 addi x25,x25,4
800000a4: 00840413 addi x8,x8,8
800000a8: 40f50533 sub x10,x10,x15
800000ac: 00153513 sltiu x10,x10,1
800000b0: f61ff0ef jal x1,80000010 <check>
800000b4: 012c0663 beq x24,x18,800000c0 <main+0x98>
800000b8: 000ca783 lw x15,0(x25)
800000bc: fd9ff06f jal x0,80000094 <main+0x6c>
800000c0: 0049899b addiw x19,x19,4
800000c4: 00100513 addi x10,x0,1
800000c8: 409989bb subw x19,x19,x9
800000cc: f45ff0ef jal x1,80000010 <check>
800000d0: 03548063 beq x9,x21,800000f0 <main+0xc8>
800000d4: 0014849b addiw x9,x9,1
800000d8: 004a0a13 addi x20,x20,4
800000dc: 00048c1b addiw x24,x9,0
800000e0: fb2490e3 bne x9,x18,80000080 <main+0x58>
800000e4: 00100513 addi x10,x0,1
800000e8: f29ff0ef jal x1,80000010 <check>
800000ec: fe9ff06f jal x0,800000d4 <main+0xac>
800000f0: 00100513 addi x10,x0,1
800000f4: f1dff0ef jal x1,80000010 <check>
800000f8: 05813083 ld x1,88(x2)
800000fc: 05013403 ld x8,80(x2)
80000100: 04813483 ld x9,72(x2)
80000104: 04013903 ld x18,64(x2)
80000108: 03813983 ld x19,56(x2)
8000010c: 03013a03 ld x20,48(x2)
80000110: 02813a83 ld x21,40(x2)
80000114: 02013b03 ld x22,32(x2)
80000118: 01813b83 ld x23,24(x2)
8000011c: 01013c03 ld x24,16(x2)
80000120: 00813c83 ld x25,8(x2)
80000124: 00000513 addi x10,x0,0
80000128: 06010113 addi x2,x2,96
8000012c: 00008067 jalr x0,0(x1)
0000000080000130 <halt>:
80000130: 00050513 addi x10,x10,0
80000134: 00100073 ebreak
80000138: 0000006f jal x0,80000138 <halt+0x8>
000000008000013c <_trm_init>:
8000013c: ff010113 addi x2,x2,-16
80000140: 00000517 auipc x10,0x0
80000144: 02050513 addi x10,x10,32 # 80000160 <mainargs>
80000148: 00113423 sd x1,8(x2)
8000014c: eddff0ef jal x1,80000028 <main>
80000150: 00050513 addi x10,x10,0
80000154: 00100073 ebreak
80000158: 0000006f jal x0,80000158 <_trm_init+0x1c>

@ -0,0 +1,92 @@
elf/am-tests/pascal: file format elf64-littleriscv
Disassembly of section .text:
0000000080000000 <_start>:
80000000: 00000413 addi x8,x0,0
80000004: 00009117 auipc x2,0x9
80000008: ffc10113 addi x2,x2,-4 # 80009000 <_end>
8000000c: 108000ef jal x1,80000114 <_trm_init>
0000000080000010 <check>:
80000010: 00050463 beq x10,x0,80000018 <check+0x8>
80000014: 00008067 jalr x0,0(x1)
80000018: ff010113 addi x2,x2,-16
8000001c: 00100513 addi x10,x0,1
80000020: 00113423 sd x1,8(x2)
80000024: 0e4000ef jal x1,80000108 <halt>
0000000080000028 <main>:
80000028: 00100793 addi x15,x0,1
8000002c: fe010113 addi x2,x2,-32
80000030: 02079793 slli x15,x15,0x20
80000034: 00113c23 sd x1,24(x2)
80000038: 00813823 sd x8,16(x2)
8000003c: 00913423 sd x9,8(x2)
80000040: 01213023 sd x18,0(x2)
80000044: 00000897 auipc x17,0x0
80000048: 17c88893 addi x17,x17,380 # 800001c0 <a>
8000004c: 00178793 addi x15,x15,1
80000050: 00f8b023 sd x15,0(x17)
80000054: 00000597 auipc x11,0x0
80000058: 17458593 addi x11,x11,372 # 800001c8 <a+0x8>
8000005c: 00000817 auipc x16,0x0
80000060: 1e080813 addi x16,x16,480 # 8000023c <a+0x7c>
80000064: 00100713 addi x14,x0,1
80000068: 00100513 addi x10,x0,1
8000006c: 00000417 auipc x8,0x0
80000070: 15840413 addi x8,x8,344 # 800001c4 <a+0x4>
80000074: 00040793 addi x15,x8,0
80000078: 00100693 addi x13,x0,1
8000007c: 0080006f jal x0,80000084 <main+0x5c>
80000080: 0007a703 lw x14,0(x15)
80000084: 00d7063b addw x12,x14,x13
80000088: 00c7a023 sw x12,0(x15)
8000008c: 00478793 addi x15,x15,4
80000090: 00070693 addi x13,x14,0
80000094: feb796e3 bne x15,x11,80000080 <main+0x58>
80000098: 00a7a023 sw x10,0(x15)
8000009c: 00478593 addi x11,x15,4
800000a0: 01058663 beq x11,x16,800000ac <main+0x84>
800000a4: 0048a703 lw x14,4(x17)
800000a8: fc5ff06f jal x0,8000006c <main+0x44>
800000ac: 00000497 auipc x9,0x0
800000b0: 09448493 addi x9,x9,148 # 80000140 <ans>
800000b4: 00000917 auipc x18,0x0
800000b8: 10890913 addi x18,x18,264 # 800001bc <ans+0x7c>
800000bc: 00100793 addi x15,x0,1
800000c0: 00c0006f jal x0,800000cc <main+0xa4>
800000c4: 00042783 lw x15,0(x8)
800000c8: 00440413 addi x8,x8,4
800000cc: 0004a503 lw x10,0(x9)
800000d0: 00448493 addi x9,x9,4
800000d4: 40f50533 sub x10,x10,x15
800000d8: 00153513 sltiu x10,x10,1
800000dc: f35ff0ef jal x1,80000010 <check>
800000e0: fe9912e3 bne x18,x9,800000c4 <main+0x9c>
800000e4: 00100513 addi x10,x0,1
800000e8: f29ff0ef jal x1,80000010 <check>
800000ec: 01813083 ld x1,24(x2)
800000f0: 01013403 ld x8,16(x2)
800000f4: 00813483 ld x9,8(x2)
800000f8: 00013903 ld x18,0(x2)
800000fc: 00000513 addi x10,x0,0
80000100: 02010113 addi x2,x2,32
80000104: 00008067 jalr x0,0(x1)
0000000080000108 <halt>:
80000108: 00050513 addi x10,x10,0
8000010c: 00100073 ebreak
80000110: 0000006f jal x0,80000110 <halt+0x8>
0000000080000114 <_trm_init>:
80000114: ff010113 addi x2,x2,-16
80000118: 00000517 auipc x10,0x0
8000011c: 02050513 addi x10,x10,32 # 80000138 <mainargs>
80000120: 00113423 sd x1,8(x2)
80000124: f05ff0ef jal x1,80000028 <main>
80000128: 00050513 addi x10,x10,0
8000012c: 00100073 ebreak
80000130: 0000006f jal x0,80000130 <_trm_init+0x1c>

@ -0,0 +1,72 @@
elf/am-tests/prime: file format elf64-littleriscv
Disassembly of section .text:
0000000080000000 <_start>:
80000000: 00000413 addi x8,x0,0
80000004: 00009117 auipc x2,0x9
80000008: ffc10113 addi x2,x2,-4 # 80009000 <_end>
8000000c: 0b8000ef jal x1,800000c4 <_trm_init>
0000000080000010 <check>:
80000010: 00050463 beq x10,x0,80000018 <check+0x8>
80000014: 00008067 jalr x0,0(x1)
80000018: ff010113 addi x2,x2,-16
8000001c: 00100513 addi x10,x0,1
80000020: 00113423 sd x1,8(x2)
80000024: 094000ef jal x1,800000b8 <halt>
0000000080000028 <main>:
80000028: fd010113 addi x2,x2,-48
8000002c: 02813023 sd x8,32(x2)
80000030: 00913c23 sd x9,24(x2)
80000034: 01213823 sd x18,16(x2)
80000038: 01313423 sd x19,8(x2)
8000003c: 02113423 sd x1,40(x2)
80000040: 00000493 addi x9,x0,0
80000044: 06500413 addi x8,x0,101
80000048: 00000997 auipc x19,0x0
8000004c: 0a898993 addi x19,x19,168 # 800000f0 <ans>
80000050: 09700913 addi x18,x0,151
80000054: 00200793 addi x15,x0,2
80000058: 02f4673b remw x14,x8,x15
8000005c: 0017879b addiw x15,x15,1
80000060: 02070263 beq x14,x0,80000084 <main+0x5c>
80000064: fe879ae3 bne x15,x8,80000058 <main+0x30>
80000068: 00249793 slli x15,x9,0x2
8000006c: 00f987b3 add x15,x19,x15
80000070: 0007a503 lw x10,0(x15)
80000074: 0014849b addiw x9,x9,1
80000078: 40850533 sub x10,x10,x8
8000007c: 00153513 sltiu x10,x10,1
80000080: f91ff0ef jal x1,80000010 <check>
80000084: 0024041b addiw x8,x8,2
80000088: fd2416e3 bne x8,x18,80000054 <main+0x2c>
8000008c: ff648513 addi x10,x9,-10
80000090: 00153513 sltiu x10,x10,1
80000094: f7dff0ef jal x1,80000010 <check>
80000098: 02813083 ld x1,40(x2)
8000009c: 02013403 ld x8,32(x2)
800000a0: 01813483 ld x9,24(x2)
800000a4: 01013903 ld x18,16(x2)
800000a8: 00813983 ld x19,8(x2)
800000ac: 00000513 addi x10,x0,0
800000b0: 03010113 addi x2,x2,48
800000b4: 00008067 jalr x0,0(x1)
00000000800000b8 <halt>:
800000b8: 00050513 addi x10,x10,0
800000bc: 00100073 ebreak
800000c0: 0000006f jal x0,800000c0 <halt+0x8>
00000000800000c4 <_trm_init>:
800000c4: ff010113 addi x2,x2,-16
800000c8: 00000517 auipc x10,0x0
800000cc: 02050513 addi x10,x10,32 # 800000e8 <mainargs>
800000d0: 00113423 sd x1,8(x2)
800000d4: f55ff0ef jal x1,80000028 <main>
800000d8: 00050513 addi x10,x10,0
800000dc: 00100073 ebreak
800000e0: 0000006f jal x0,800000e0 <_trm_init+0x1c>

@ -0,0 +1,264 @@
elf/am-tests/quick-sort: file format elf64-littleriscv
Disassembly of section .text:
0000000080000000 <_start>:
80000000: 00000413 addi x8,x0,0
80000004: 00009117 auipc x2,0x9
80000008: ffc10113 addi x2,x2,-4 # 80009000 <_end>
8000000c: 3a8000ef jal x1,800003b4 <_trm_init>
0000000080000010 <check>:
80000010: 00050463 beq x10,x0,80000018 <check+0x8>
80000014: 00008067 jalr x0,0(x1)
80000018: ff010113 addi x2,x2,-16
8000001c: 00100513 addi x10,x0,1
80000020: 00113423 sd x1,8(x2)
80000024: 384000ef jal x1,800003a8 <halt>
0000000080000028 <partition>:
80000028: 00259813 slli x16,x11,0x2
8000002c: 010506b3 add x13,x10,x16
80000030: 00050313 addi x6,x10,0
80000034: 0006a883 lw x17,0(x13)
80000038: 00060513 addi x10,x12,0
8000003c: 08c5d863 bge x11,x12,800000cc <partition+0xa4>
80000040: 00261793 slli x15,x12,0x2
80000044: 00f307b3 add x15,x6,x15
80000048: 0007a783 lw x15,0(x15)
8000004c: fff50693 addi x13,x10,-1
80000050: 00269693 slli x13,x13,0x2
80000054: 00d306b3 add x13,x6,x13
80000058: 00068713 addi x14,x13,0
8000005c: 02f8d663 bge x17,x15,80000088 <partition+0x60>
80000060: fff5051b addiw x10,x10,-1
80000064: 00072783 lw x15,0(x14)
80000068: ffc70693 addi x13,x14,-4
8000006c: fea5c6e3 blt x11,x10,80000058 <partition+0x30>
80000070: 010306b3 add x13,x6,x16
80000074: 00f6a023 sw x15,0(x13)
80000078: 00058513 addi x10,x11,0
8000007c: 00f72023 sw x15,0(x14)
80000080: 0116a023 sw x17,0(x13)
80000084: 00008067 jalr x0,0(x1)
80000088: 010306b3 add x13,x6,x16
8000008c: 00251713 slli x14,x10,0x2
80000090: 00f6a023 sw x15,0(x13)
80000094: 00e30733 add x14,x6,x14
80000098: 04a5d063 bge x11,x10,800000d8 <partition+0xb0>
8000009c: 00480613 addi x12,x16,4
800000a0: 00c30633 add x12,x6,x12
800000a4: 0015859b addiw x11,x11,1
800000a8: 00062783 lw x15,0(x12)
800000ac: 00060693 addi x13,x12,0
800000b0: 00460613 addi x12,x12,4
800000b4: fca584e3 beq x11,x10,8000007c <partition+0x54>
800000b8: fef8d6e3 bge x17,x15,800000a4 <partition+0x7c>
800000bc: 00f72023 sw x15,0(x14)
800000c0: 02a5d063 bge x11,x10,800000e0 <partition+0xb8>
800000c4: 00259813 slli x16,x11,0x2
800000c8: f85ff06f jal x0,8000004c <partition+0x24>
800000cc: 00058513 addi x10,x11,0
800000d0: 0116a023 sw x17,0(x13)
800000d4: 00008067 jalr x0,0(x1)
800000d8: 00058513 addi x10,x11,0
800000dc: fa1ff06f jal x0,8000007c <partition+0x54>
800000e0: 00259693 slli x13,x11,0x2
800000e4: 00d306b3 add x13,x6,x13
800000e8: 00058513 addi x10,x11,0
800000ec: f95ff06f jal x0,80000080 <partition+0x58>
00000000800000f0 <quick_sort>:
800000f0: 1ec5da63 bge x11,x12,800002e4 <quick_sort+0x1f4>
800000f4: f5010113 addi x2,x2,-176
800000f8: 0a813023 sd x8,160(x2)
800000fc: 07513c23 sd x21,120(x2)
80000100: 07713423 sd x23,104(x2)
80000104: 0a113423 sd x1,168(x2)
80000108: 08913c23 sd x9,152(x2)
8000010c: 09213823 sd x18,144(x2)
80000110: 09313423 sd x19,136(x2)
80000114: 09413023 sd x20,128(x2)
80000118: 07613823 sd x22,112(x2)
8000011c: 07813023 sd x24,96(x2)
80000120: 05913c23 sd x25,88(x2)
80000124: 05a13823 sd x26,80(x2)
80000128: 05b13423 sd x27,72(x2)
8000012c: 00058b93 addi x23,x11,0
80000130: 00060a93 addi x21,x12,0
80000134: 00050413 addi x8,x10,0
80000138: 000a8613 addi x12,x21,0
8000013c: 000b8593 addi x11,x23,0
80000140: 00040513 addi x10,x8,0
80000144: ee5ff0ef jal x1,80000028 <partition>
80000148: 00a13423 sd x10,8(x2)
8000014c: fff50c9b addiw x25,x10,-1
80000150: 159bd663 bge x23,x25,8000029c <quick_sort+0x1ac>
80000154: 000c8613 addi x12,x25,0
80000158: 000b8593 addi x11,x23,0
8000015c: 00040513 addi x10,x8,0
80000160: ec9ff0ef jal x1,80000028 <partition>
80000164: 00a13823 sd x10,16(x2)
80000168: fff50d1b addiw x26,x10,-1
8000016c: 13abd263 bge x23,x26,80000290 <quick_sort+0x1a0>
80000170: 000d0613 addi x12,x26,0
80000174: 000b8593 addi x11,x23,0
80000178: 00040513 addi x10,x8,0
8000017c: eadff0ef jal x1,80000028 <partition>
80000180: 00a13c23 sd x10,24(x2)
80000184: fff50d9b addiw x27,x10,-1
80000188: 0fbbde63 bge x23,x27,80000284 <quick_sort+0x194>
8000018c: 000d8613 addi x12,x27,0
80000190: 000b8593 addi x11,x23,0
80000194: 00040513 addi x10,x8,0
80000198: e91ff0ef jal x1,80000028 <partition>
8000019c: 02a13023 sd x10,32(x2)
800001a0: fff5099b addiw x19,x10,-1
800001a4: 0d3bda63 bge x23,x19,80000278 <quick_sort+0x188>
800001a8: 00098613 addi x12,x19,0
800001ac: 000b8593 addi x11,x23,0
800001b0: 00040513 addi x10,x8,0
800001b4: e75ff0ef jal x1,80000028 <partition>
800001b8: fff5091b addiw x18,x10,-1
800001bc: 00050493 addi x9,x10,0
800001c0: 0b2bd863 bge x23,x18,80000270 <quick_sort+0x180>
800001c4: 00090613 addi x12,x18,0
800001c8: 000b8593 addi x11,x23,0
800001cc: 00040513 addi x10,x8,0
800001d0: e59ff0ef jal x1,80000028 <partition>
800001d4: fff50b1b addiw x22,x10,-1
800001d8: 00050a13 addi x20,x10,0
800001dc: 096bd663 bge x23,x22,80000268 <quick_sort+0x178>
800001e0: 000b0613 addi x12,x22,0
800001e4: 000b8593 addi x11,x23,0
800001e8: 00040513 addi x10,x8,0
800001ec: e3dff0ef jal x1,80000028 <partition>
800001f0: 02a13423 sd x10,40(x2)
800001f4: fff50c1b addiw x24,x10,-1
800001f8: 078bd263 bge x23,x24,8000025c <quick_sort+0x16c>
800001fc: 000c0613 addi x12,x24,0
80000200: 000b8593 addi x11,x23,0
80000204: 00040513 addi x10,x8,0
80000208: e21ff0ef jal x1,80000028 <partition>
8000020c: fff5081b addiw x16,x10,-1
80000210: 00050713 addi x14,x10,0
80000214: 050bd063 bge x23,x16,80000254 <quick_sort+0x164>
80000218: 00080613 addi x12,x16,0
8000021c: 000b8593 addi x11,x23,0
80000220: 00040513 addi x10,x8,0
80000224: 02e13c23 sd x14,56(x2)
80000228: 03013823 sd x16,48(x2)
8000022c: dfdff0ef jal x1,80000028 <partition>
80000230: 00050893 addi x17,x10,0
80000234: 000b8593 addi x11,x23,0
80000238: fff5061b addiw x12,x10,-1
8000023c: 00040513 addi x10,x8,0
80000240: 00188b9b addiw x23,x17,1
80000244: eadff0ef jal x1,800000f0 <quick_sort>
80000248: 03013803 ld x16,48(x2)
8000024c: 03813703 ld x14,56(x2)
80000250: fd0bc4e3 blt x23,x16,80000218 <quick_sort+0x128>
80000254: 00170b9b addiw x23,x14,1
80000258: fb8bc2e3 blt x23,x24,800001fc <quick_sort+0x10c>
8000025c: 02813783 ld x15,40(x2)
80000260: 00178b9b addiw x23,x15,1
80000264: f76bcee3 blt x23,x22,800001e0 <quick_sort+0xf0>
80000268: 001a0b9b addiw x23,x20,1
8000026c: f52bcce3 blt x23,x18,800001c4 <quick_sort+0xd4>
80000270: 00148b9b addiw x23,x9,1
80000274: f33bcae3 blt x23,x19,800001a8 <quick_sort+0xb8>
80000278: 02013783 ld x15,32(x2)
8000027c: 00178b9b addiw x23,x15,1
80000280: f1bbc6e3 blt x23,x27,8000018c <quick_sort+0x9c>
80000284: 01813783 ld x15,24(x2)
80000288: 00178b9b addiw x23,x15,1
8000028c: efabc2e3 blt x23,x26,80000170 <quick_sort+0x80>
80000290: 01013783 ld x15,16(x2)
80000294: 00178b9b addiw x23,x15,1
80000298: eb9bcee3 blt x23,x25,80000154 <quick_sort+0x64>
8000029c: 00813783 ld x15,8(x2)
800002a0: 00178b9b addiw x23,x15,1
800002a4: e95bcae3 blt x23,x21,80000138 <quick_sort+0x48>
800002a8: 0a813083 ld x1,168(x2)
800002ac: 0a013403 ld x8,160(x2)
800002b0: 09813483 ld x9,152(x2)
800002b4: 09013903 ld x18,144(x2)
800002b8: 08813983 ld x19,136(x2)
800002bc: 08013a03 ld x20,128(x2)
800002c0: 07813a83 ld x21,120(x2)
800002c4: 07013b03 ld x22,112(x2)
800002c8: 06813b83 ld x23,104(x2)
800002cc: 06013c03 ld x24,96(x2)
800002d0: 05813c83 ld x25,88(x2)
800002d4: 05013d03 ld x26,80(x2)
800002d8: 04813d83 ld x27,72(x2)
800002dc: 0b010113 addi x2,x2,176
800002e0: 00008067 jalr x0,0(x1)
800002e4: 00008067 jalr x0,0(x1)
00000000800002e8 <main>:
800002e8: fd010113 addi x2,x2,-48
800002ec: 00000517 auipc x10,0x0
800002f0: 0f450513 addi x10,x10,244 # 800003e0 <a>
800002f4: 00913c23 sd x9,24(x2)
800002f8: 01300613 addi x12,x0,19
800002fc: 00050493 addi x9,x10,0
80000300: 00000593 addi x11,x0,0
80000304: 02813023 sd x8,32(x2)
80000308: 01213823 sd x18,16(x2)
8000030c: 01313423 sd x19,8(x2)
80000310: 02113423 sd x1,40(x2)
80000314: 00048913 addi x18,x9,0
80000318: dd9ff0ef jal x1,800000f0 <quick_sort>
8000031c: 00000413 addi x8,x0,0
80000320: 01400993 addi x19,x0,20
80000324: 00092503 lw x10,0(x18)
80000328: 00490913 addi x18,x18,4
8000032c: 40850533 sub x10,x10,x8
80000330: 00153513 sltiu x10,x10,1
80000334: 0014041b addiw x8,x8,1
80000338: cd9ff0ef jal x1,80000010 <check>
8000033c: ff3414e3 bne x8,x19,80000324 <main+0x3c>
80000340: 00100513 addi x10,x0,1
80000344: ccdff0ef jal x1,80000010 <check>
80000348: 01300613 addi x12,x0,19
8000034c: 00000593 addi x11,x0,0
80000350: 00000517 auipc x10,0x0
80000354: 09050513 addi x10,x10,144 # 800003e0 <a>
80000358: d99ff0ef jal x1,800000f0 <quick_sort>
8000035c: 00000413 addi x8,x0,0
80000360: 01400913 addi x18,x0,20
80000364: 0004a503 lw x10,0(x9)
80000368: 00448493 addi x9,x9,4
8000036c: 40850533 sub x10,x10,x8
80000370: 00153513 sltiu x10,x10,1
80000374: 0014041b addiw x8,x8,1
80000378: c99ff0ef jal x1,80000010 <check>
8000037c: ff2414e3 bne x8,x18,80000364 <main+0x7c>
80000380: 00100513 addi x10,x0,1
80000384: c8dff0ef jal x1,80000010 <check>
80000388: 02813083 ld x1,40(x2)
8000038c: 02013403 ld x8,32(x2)
80000390: 01813483 ld x9,24(x2)
80000394: 01013903 ld x18,16(x2)
80000398: 00813983 ld x19,8(x2)
8000039c: 00000513 addi x10,x0,0
800003a0: 03010113 addi x2,x2,48
800003a4: 00008067 jalr x0,0(x1)
00000000800003a8 <halt>:
800003a8: 00050513 addi x10,x10,0
800003ac: 00100073 ebreak
800003b0: 0000006f jal x0,800003b0 <halt+0x8>
00000000800003b4 <_trm_init>:
800003b4: ff010113 addi x2,x2,-16
800003b8: 00000517 auipc x10,0x0
800003bc: 02050513 addi x10,x10,32 # 800003d8 <mainargs>
800003c0: 00113423 sd x1,8(x2)
800003c4: f25ff0ef jal x1,800002e8 <main>
800003c8: 00050513 addi x10,x10,0
800003cc: 00100073 ebreak
800003d0: 0000006f jal x0,800003d0 <_trm_init+0x1c>

@ -0,0 +1,180 @@
elf/am-tests/recursion: file format elf64-littleriscv
Disassembly of section .text:
0000000080000000 <_start>:
80000000: 00000413 addi x8,x0,0
80000004: 00009117 auipc x2,0x9
80000008: ffc10113 addi x2,x2,-4 # 80009000 <_end>
8000000c: 248000ef jal x1,80000254 <_trm_init>
0000000080000010 <f0>:
80000010: 00000797 auipc x15,0x0
80000014: 2a078793 addi x15,x15,672 # 800002b0 <lvl>
80000018: 0007a703 lw x14,0(x15)
8000001c: 00b75463 bge x14,x11,80000024 <f0+0x14>
80000020: 00b7a023 sw x11,0(x15)
80000024: 00000717 auipc x14,0x0
80000028: 29070713 addi x14,x14,656 # 800002b4 <rec>
8000002c: 00072783 lw x15,0(x14)
80000030: 0017879b addiw x15,x15,1
80000034: 00f72023 sw x15,0(x14)
80000038: 00a05e63 bge x0,x10,80000054 <f0+0x44>
8000003c: 00300793 addi x15,x0,3
80000040: 02f5453b divw x10,x10,x15
80000044: 0015859b addiw x11,x11,1
80000048: 00000797 auipc x15,0x0
8000004c: 2607b783 ld x15,608(x15) # 800002a8 <func+0x18>
80000050: 00078067 jalr x0,0(x15)
80000054: 00100513 addi x10,x0,1
80000058: 00008067 jalr x0,0(x1)
000000008000005c <f1>:
8000005c: 00000797 auipc x15,0x0
80000060: 25478793 addi x15,x15,596 # 800002b0 <lvl>
80000064: 0007a703 lw x14,0(x15)
80000068: 00b75463 bge x14,x11,80000070 <f1+0x14>
8000006c: 00b7a023 sw x11,0(x15)
80000070: 00000717 auipc x14,0x0
80000074: 24470713 addi x14,x14,580 # 800002b4 <rec>
80000078: 00072783 lw x15,0(x14)
8000007c: 0017879b addiw x15,x15,1
80000080: 00f72023 sw x15,0(x14)
80000084: 00a05c63 bge x0,x10,8000009c <f1+0x40>
80000088: 0015859b addiw x11,x11,1
8000008c: fff5051b addiw x10,x10,-1
80000090: 00000797 auipc x15,0x0
80000094: 2007b783 ld x15,512(x15) # 80000290 <func>
80000098: 00078067 jalr x0,0(x15)
8000009c: 00100513 addi x10,x0,1
800000a0: 00008067 jalr x0,0(x1)
00000000800000a4 <f2>:
800000a4: 00000717 auipc x14,0x0
800000a8: 20c70713 addi x14,x14,524 # 800002b0 <lvl>
800000ac: 00072683 lw x13,0(x14)
800000b0: 00050793 addi x15,x10,0
800000b4: 00b6d463 bge x13,x11,800000bc <f2+0x18>
800000b8: 00b72023 sw x11,0(x14)
800000bc: 00000697 auipc x13,0x0
800000c0: 1f868693 addi x13,x13,504 # 800002b4 <rec>
800000c4: 0006a703 lw x14,0(x13)
800000c8: 00100513 addi x10,x0,1
800000cc: 0017071b addiw x14,x14,1
800000d0: 00e6a023 sw x14,0(x13)
800000d4: 02f05863 bge x0,x15,80000104 <f2+0x60>
800000d8: ff010113 addi x2,x2,-16
800000dc: 00113423 sd x1,8(x2)
800000e0: 00078513 addi x10,x15,0
800000e4: 0015859b addiw x11,x11,1
800000e8: 00000797 auipc x15,0x0
800000ec: 1b07b783 ld x15,432(x15) # 80000298 <func+0x8>
800000f0: 000780e7 jalr x1,0(x15)
800000f4: 00813083 ld x1,8(x2)
800000f8: 0095051b addiw x10,x10,9
800000fc: 01010113 addi x2,x2,16
80000100: 00008067 jalr x0,0(x1)
80000104: 00008067 jalr x0,0(x1)
0000000080000108 <f3>:
80000108: 00000717 auipc x14,0x0
8000010c: 1a870713 addi x14,x14,424 # 800002b0 <lvl>
80000110: 00072683 lw x13,0(x14)
80000114: 00050793 addi x15,x10,0
80000118: 00b6d463 bge x13,x11,80000120 <f3+0x18>
8000011c: 00b72023 sw x11,0(x14)
80000120: 00000697 auipc x13,0x0
80000124: 19468693 addi x13,x13,404 # 800002b4 <rec>
80000128: 0006a703 lw x14,0(x13)
8000012c: 00100513 addi x10,x0,1
80000130: 0017071b addiw x14,x14,1
80000134: 00e6a023 sw x14,0(x13)
80000138: 06f05a63 bge x0,x15,800001ac <f3+0xa4>
8000013c: fe010113 addi x2,x2,-32
80000140: 01213023 sd x18,0(x2)
80000144: 00000917 auipc x18,0x0
80000148: 14c90913 addi x18,x18,332 # 80000290 <func>
8000014c: 01093703 ld x14,16(x18)
80000150: 00813823 sd x8,16(x2)
80000154: 00913423 sd x9,8(x2)
80000158: 0015841b addiw x8,x11,1
8000015c: 4017d493 srai x9,x15,0x1
80000160: 00113c23 sd x1,24(x2)
80000164: 00040593 addi x11,x8,0
80000168: 00048513 addi x10,x9,0
8000016c: 000700e7 jalr x1,0(x14)
80000170: 01093783 ld x15,16(x18)
80000174: 00040593 addi x11,x8,0
80000178: 00050913 addi x18,x10,0
8000017c: 00048513 addi x10,x9,0
80000180: 000780e7 jalr x1,0(x15)
80000184: 01813083 ld x1,24(x2)
80000188: 01013403 ld x8,16(x2)
8000018c: 0019179b slliw x15,x18,0x1
80000190: 012787bb addw x15,x15,x18
80000194: 0015151b slliw x10,x10,0x1
80000198: 00813483 ld x9,8(x2)
8000019c: 00013903 ld x18,0(x2)
800001a0: 00a7853b addw x10,x15,x10
800001a4: 02010113 addi x2,x2,32
800001a8: 00008067 jalr x0,0(x1)
800001ac: 00008067 jalr x0,0(x1)
00000000800001b0 <check>:
800001b0: 00050463 beq x10,x0,800001b8 <check+0x8>
800001b4: 00008067 jalr x0,0(x1)
800001b8: ff010113 addi x2,x2,-16
800001bc: 00100513 addi x10,x0,1
800001c0: 00113423 sd x1,8(x2)
800001c4: 084000ef jal x1,80000248 <halt>
00000000800001c8 <main>:
800001c8: ff010113 addi x2,x2,-16
800001cc: 00004537 lui x10,0x4
800001d0: 00113423 sd x1,8(x2)
800001d4: 00813023 sd x8,0(x2)
800001d8: 00000593 addi x11,x0,0
800001dc: 00000797 auipc x15,0x0
800001e0: 0b47b783 ld x15,180(x15) # 80000290 <func>
800001e4: 82350513 addi x10,x10,-2013 # 3823 <_entry_offset+0x3823>
800001e8: 000780e7 jalr x1,0(x15)
800001ec: 00000417 auipc x8,0x0
800001f0: 09440413 addi x8,x8,148 # 80000280 <ans>
800001f4: 00042783 lw x15,0(x8)
800001f8: 40a78533 sub x10,x15,x10
800001fc: 00153513 sltiu x10,x10,1
80000200: fb1ff0ef jal x1,800001b0 <check>
80000204: 00442503 lw x10,4(x8)
80000208: 00000797 auipc x15,0x0
8000020c: 0ac7a783 lw x15,172(x15) # 800002b4 <rec>
80000210: 40f50533 sub x10,x10,x15
80000214: 00153513 sltiu x10,x10,1
80000218: f99ff0ef jal x1,800001b0 <check>
8000021c: 00842503 lw x10,8(x8)
80000220: 00000797 auipc x15,0x0
80000224: 0907a783 lw x15,144(x15) # 800002b0 <lvl>
80000228: 40f50533 sub x10,x10,x15
8000022c: 00153513 sltiu x10,x10,1
80000230: f81ff0ef jal x1,800001b0 <check>
80000234: 00813083 ld x1,8(x2)
80000238: 00013403 ld x8,0(x2)
8000023c: 00000513 addi x10,x0,0
80000240: 01010113 addi x2,x2,16
80000244: 00008067 jalr x0,0(x1)
0000000080000248 <halt>:
80000248: 00050513 addi x10,x10,0
8000024c: 00100073 ebreak
80000250: 0000006f jal x0,80000250 <halt+0x8>
0000000080000254 <_trm_init>:
80000254: ff010113 addi x2,x2,-16
80000258: 00000517 auipc x10,0x0
8000025c: 02050513 addi x10,x10,32 # 80000278 <mainargs>
80000260: 00113423 sd x1,8(x2)
80000264: f65ff0ef jal x1,800001c8 <main>
80000268: 00050513 addi x10,x10,0
8000026c: 00100073 ebreak
80000270: 0000006f jal x0,80000270 <_trm_init+0x1c>

@ -0,0 +1,106 @@
elf/am-tests/select-sort: file format elf64-littleriscv
Disassembly of section .text:
0000000080000000 <_start>:
80000000: 00000413 addi x8,x0,0
80000004: 00009117 auipc x2,0x9
80000008: ffc10113 addi x2,x2,-4 # 80009000 <_end>
8000000c: 138000ef jal x1,80000144 <_trm_init>
0000000080000010 <check>:
80000010: 00050463 beq x10,x0,80000018 <check+0x8>
80000014: 00008067 jalr x0,0(x1)
80000018: ff010113 addi x2,x2,-16
8000001c: 00100513 addi x10,x0,1
80000020: 00113423 sd x1,8(x2)
80000024: 114000ef jal x1,80000138 <halt>
0000000080000028 <select_sort>:
80000028: 00000897 auipc x17,0x0
8000002c: 14c88893 addi x17,x17,332 # 80000174 <a+0x4>
80000030: 00000813 addi x16,x0,0
80000034: 00000e97 auipc x29,0x0
80000038: 13ce8e93 addi x29,x29,316 # 80000170 <a>
8000003c: 01400513 addi x10,x0,20
80000040: 01300e13 addi x28,x0,19
80000044: ffc8a303 lw x6,-4(x17)
80000048: 00080593 addi x11,x16,0
8000004c: 0018081b addiw x16,x16,1
80000050: 00088713 addi x14,x17,0
80000054: 00030613 addi x12,x6,0
80000058: 00080793 addi x15,x16,0
8000005c: 00072683 lw x13,0(x14)
80000060: 00470713 addi x14,x14,4
80000064: 00c6d663 bge x13,x12,80000070 <select_sort+0x48>
80000068: 00078593 addi x11,x15,0
8000006c: 00068613 addi x12,x13,0
80000070: 0017879b addiw x15,x15,1
80000074: fea794e3 bne x15,x10,8000005c <select_sort+0x34>
80000078: 00259593 slli x11,x11,0x2
8000007c: fec8ae23 sw x12,-4(x17)
80000080: 00be85b3 add x11,x29,x11
80000084: 0065a023 sw x6,0(x11)
80000088: 00488893 addi x17,x17,4
8000008c: fbc81ce3 bne x16,x28,80000044 <select_sort+0x1c>
80000090: 00008067 jalr x0,0(x1)
0000000080000094 <main>:
80000094: fd010113 addi x2,x2,-48
80000098: 00913c23 sd x9,24(x2)
8000009c: 00000497 auipc x9,0x0
800000a0: 0d448493 addi x9,x9,212 # 80000170 <a>
800000a4: 02813023 sd x8,32(x2)
800000a8: 01213823 sd x18,16(x2)
800000ac: 01313423 sd x19,8(x2)
800000b0: 02113423 sd x1,40(x2)
800000b4: 00048913 addi x18,x9,0
800000b8: f71ff0ef jal x1,80000028 <select_sort>
800000bc: 00000413 addi x8,x0,0
800000c0: 01400993 addi x19,x0,20
800000c4: 00092503 lw x10,0(x18)
800000c8: 00490913 addi x18,x18,4
800000cc: 40850533 sub x10,x10,x8
800000d0: 00153513 sltiu x10,x10,1
800000d4: 0014041b addiw x8,x8,1
800000d8: f39ff0ef jal x1,80000010 <check>
800000dc: ff3414e3 bne x8,x19,800000c4 <main+0x30>
800000e0: 00100513 addi x10,x0,1
800000e4: f2dff0ef jal x1,80000010 <check>
800000e8: 00000413 addi x8,x0,0
800000ec: f3dff0ef jal x1,80000028 <select_sort>
800000f0: 01400913 addi x18,x0,20
800000f4: 0004a503 lw x10,0(x9)
800000f8: 00448493 addi x9,x9,4
800000fc: 40850533 sub x10,x10,x8
80000100: 00153513 sltiu x10,x10,1
80000104: 0014041b addiw x8,x8,1
80000108: f09ff0ef jal x1,80000010 <check>
8000010c: ff2414e3 bne x8,x18,800000f4 <main+0x60>
80000110: 00100513 addi x10,x0,1
80000114: efdff0ef jal x1,80000010 <check>
80000118: 02813083 ld x1,40(x2)
8000011c: 02013403 ld x8,32(x2)
80000120: 01813483 ld x9,24(x2)
80000124: 01013903 ld x18,16(x2)
80000128: 00813983 ld x19,8(x2)
8000012c: 00000513 addi x10,x0,0
80000130: 03010113 addi x2,x2,48
80000134: 00008067 jalr x0,0(x1)
0000000080000138 <halt>:
80000138: 00050513 addi x10,x10,0
8000013c: 00100073 ebreak
80000140: 0000006f jal x0,80000140 <halt+0x8>
0000000080000144 <_trm_init>:
80000144: ff010113 addi x2,x2,-16
80000148: 00000517 auipc x10,0x0
8000014c: 02050513 addi x10,x10,32 # 80000168 <mainargs>
80000150: 00113423 sd x1,8(x2)
80000154: f41ff0ef jal x1,80000094 <main>
80000158: 00050513 addi x10,x10,0
8000015c: 00100073 ebreak
80000160: 0000006f jal x0,80000160 <_trm_init+0x1c>

@ -0,0 +1,98 @@
elf/am-tests/shift: file format elf64-littleriscv
Disassembly of section .text:
0000000080000000 <_start>:
80000000: 00000413 addi x8,x0,0
80000004: 00009117 auipc x2,0x9
80000008: ffc10113 addi x2,x2,-4 # 80009000 <_end>
8000000c: 120000ef jal x1,8000012c <_trm_init>
0000000080000010 <check>:
80000010: 00050463 beq x10,x0,80000018 <check+0x8>
80000014: 00008067 jalr x0,0(x1)
80000018: ff010113 addi x2,x2,-16
8000001c: 00100513 addi x10,x0,1
80000020: 00113423 sd x1,8(x2)
80000024: 0fc000ef jal x1,80000120 <halt>
0000000080000028 <main>:
80000028: fd010113 addi x2,x2,-48
8000002c: 00913c23 sd x9,24(x2)
80000030: 00000497 auipc x9,0x0
80000034: 18848493 addi x9,x9,392 # 800001b8 <test>
80000038: 02813023 sd x8,32(x2)
8000003c: 01213823 sd x18,16(x2)
80000040: 01313423 sd x19,8(x2)
80000044: 02113423 sd x1,40(x2)
80000048: 01413023 sd x20,0(x2)
8000004c: 00000917 auipc x18,0x0
80000050: 12c90913 addi x18,x18,300 # 80000178 <srl_ans>
80000054: 00000997 auipc x19,0x0
80000058: 18498993 addi x19,x19,388 # 800001d8 <_bss_start>
8000005c: 00048413 addi x8,x9,0
80000060: 00042503 lw x10,0(x8)
80000064: 00092783 lw x15,0(x18)
80000068: 00440413 addi x8,x8,4
8000006c: 0075551b srliw x10,x10,0x7
80000070: 40f50533 sub x10,x10,x15
80000074: 00153513 sltiu x10,x10,1
80000078: f99ff0ef jal x1,80000010 <check>
8000007c: 00490913 addi x18,x18,4
80000080: ff3410e3 bne x8,x19,80000060 <main+0x38>
80000084: 00000997 auipc x19,0x0
80000088: 0d498993 addi x19,x19,212 # 80000158 <srav_ans>
8000008c: 00000917 auipc x18,0x0
80000090: 12c90913 addi x18,x18,300 # 800001b8 <test>
80000094: 00400413 addi x8,x0,4
80000098: 00c00a13 addi x20,x0,12
8000009c: 00092503 lw x10,0(x18)
800000a0: 0009a783 lw x15,0(x19)
800000a4: 00490913 addi x18,x18,4
800000a8: 4085553b sraw x10,x10,x8
800000ac: 40f50533 sub x10,x10,x15
800000b0: 00153513 sltiu x10,x10,1
800000b4: 0014041b addiw x8,x8,1
800000b8: f59ff0ef jal x1,80000010 <check>
800000bc: 00498993 addi x19,x19,4
800000c0: fd441ee3 bne x8,x20,8000009c <main+0x74>
800000c4: 00000917 auipc x18,0x0
800000c8: 0d490913 addi x18,x18,212 # 80000198 <srlv_ans>
800000cc: 00400413 addi x8,x0,4
800000d0: 00c00993 addi x19,x0,12
800000d4: 0004a503 lw x10,0(x9)
800000d8: 00092783 lw x15,0(x18)
800000dc: 00448493 addi x9,x9,4
800000e0: 0085553b srlw x10,x10,x8
800000e4: 40f50533 sub x10,x10,x15
800000e8: 00153513 sltiu x10,x10,1
800000ec: 0014041b addiw x8,x8,1
800000f0: f21ff0ef jal x1,80000010 <check>
800000f4: 00490913 addi x18,x18,4
800000f8: fd341ee3 bne x8,x19,800000d4 <main+0xac>
800000fc: 02813083 ld x1,40(x2)
80000100: 02013403 ld x8,32(x2)
80000104: 01813483 ld x9,24(x2)
80000108: 01013903 ld x18,16(x2)
8000010c: 00813983 ld x19,8(x2)
80000110: 00013a03 ld x20,0(x2)
80000114: 00000513 addi x10,x0,0
80000118: 03010113 addi x2,x2,48
8000011c: 00008067 jalr x0,0(x1)
0000000080000120 <halt>:
80000120: 00050513 addi x10,x10,0
80000124: 00100073 ebreak
80000128: 0000006f jal x0,80000128 <halt+0x8>
000000008000012c <_trm_init>:
8000012c: ff010113 addi x2,x2,-16
80000130: 00000517 auipc x10,0x0
80000134: 02050513 addi x10,x10,32 # 80000150 <mainargs>
80000138: 00113423 sd x1,8(x2)
8000013c: eedff0ef jal x1,80000028 <main>
80000140: 00050513 addi x10,x10,0
80000144: 00100073 ebreak
80000148: 0000006f jal x0,80000148 <_trm_init+0x1c>

@ -0,0 +1,90 @@
elf/am-tests/shuixianhua: file format elf64-littleriscv
Disassembly of section .text:
0000000080000000 <_start>:
80000000: 00000413 addi x8,x0,0
80000004: 00009117 auipc x2,0x9
80000008: ffc10113 addi x2,x2,-4 # 80009000 <_end>
8000000c: 100000ef jal x1,8000010c <_trm_init>
0000000080000010 <check>:
80000010: 00050463 beq x10,x0,80000018 <check+0x8>
80000014: 00008067 jalr x0,0(x1)
80000018: ff010113 addi x2,x2,-16
8000001c: 00100513 addi x10,x0,1
80000020: 00113423 sd x1,8(x2)
80000024: 0dc000ef jal x1,80000100 <halt>
0000000080000028 <main>:
80000028: fc010113 addi x2,x2,-64
8000002c: 02813823 sd x8,48(x2)
80000030: 02913423 sd x9,40(x2)
80000034: 03213023 sd x18,32(x2)
80000038: 01313c23 sd x19,24(x2)
8000003c: 01413823 sd x20,16(x2)
80000040: 01513423 sd x21,8(x2)
80000044: 02113c23 sd x1,56(x2)
80000048: 06400413 addi x8,x0,100
8000004c: 00000a93 addi x21,x0,0
80000050: 1f400993 addi x19,x0,500
80000054: 06400a13 addi x20,x0,100
80000058: 00a00913 addi x18,x0,10
8000005c: 00000497 auipc x9,0x0
80000060: 0dc48493 addi x9,x9,220 # 80000138 <ans>
80000064: 0014041b addiw x8,x8,1
80000068: 00040793 addi x15,x8,0
8000006c: 07340063 beq x8,x19,800000cc <main+0xa4>
80000070: 0327c6bb divw x13,x15,x18
80000074: 0347c53b divw x10,x15,x20
80000078: 0326e6bb remw x13,x13,x18
8000007c: 0327e7bb remw x15,x15,x18
80000080: 02d6873b mulw x14,x13,x13
80000084: 02a505bb mulw x11,x10,x10
80000088: 02f7863b mulw x12,x15,x15
8000008c: 02d7073b mulw x14,x14,x13
80000090: 02a585bb mulw x11,x11,x10
80000094: 02f606bb mulw x13,x12,x15
80000098: 00b707bb addw x15,x14,x11
8000009c: 00d787bb addw x15,x15,x13
800000a0: fc8792e3 bne x15,x8,80000064 <main+0x3c>
800000a4: 002a9793 slli x15,x21,0x2
800000a8: 00f487b3 add x15,x9,x15
800000ac: 0007a503 lw x10,0(x15)
800000b0: 001a8a9b addiw x21,x21,1
800000b4: 40850533 sub x10,x10,x8
800000b8: 00153513 sltiu x10,x10,1
800000bc: f55ff0ef jal x1,80000010 <check>
800000c0: 0014041b addiw x8,x8,1
800000c4: 00040793 addi x15,x8,0
800000c8: fb3414e3 bne x8,x19,80000070 <main+0x48>
800000cc: ffca8513 addi x10,x21,-4
800000d0: 00153513 sltiu x10,x10,1
800000d4: f3dff0ef jal x1,80000010 <check>
800000d8: 03813083 ld x1,56(x2)
800000dc: 03013403 ld x8,48(x2)
800000e0: 02813483 ld x9,40(x2)
800000e4: 02013903 ld x18,32(x2)
800000e8: 01813983 ld x19,24(x2)
800000ec: 01013a03 ld x20,16(x2)
800000f0: 00813a83 ld x21,8(x2)
800000f4: 00000513 addi x10,x0,0
800000f8: 04010113 addi x2,x2,64
800000fc: 00008067 jalr x0,0(x1)
0000000080000100 <halt>:
80000100: 00050513 addi x10,x10,0
80000104: 00100073 ebreak
80000108: 0000006f jal x0,80000108 <halt+0x8>
000000008000010c <_trm_init>:
8000010c: ff010113 addi x2,x2,-16
80000110: 00000517 auipc x10,0x0
80000114: 02050513 addi x10,x10,32 # 80000130 <mainargs>
80000118: 00113423 sd x1,8(x2)
8000011c: f0dff0ef jal x1,80000028 <main>
80000120: 00050513 addi x10,x10,0
80000124: 00100073 ebreak
80000128: 0000006f jal x0,80000128 <_trm_init+0x1c>

@ -0,0 +1,85 @@
elf/am-tests/sub-longlong: file format elf64-littleriscv
Disassembly of section .text:
0000000080000000 <_start>:
80000000: 00000413 addi x8,x0,0
80000004: 00009117 auipc x2,0x9
80000008: ffc10113 addi x2,x2,-4 # 80009000 <_end>
8000000c: 0ec000ef jal x1,800000f8 <_trm_init>
0000000080000010 <check>:
80000010: 00050463 beq x10,x0,80000018 <check+0x8>
80000014: 00008067 jalr x0,0(x1)
80000018: ff010113 addi x2,x2,-16
8000001c: 00100513 addi x10,x0,1
80000020: 00113423 sd x1,8(x2)
80000024: 0c8000ef jal x1,800000ec <halt>
0000000080000028 <main>:
80000028: fb010113 addi x2,x2,-80
8000002c: 01713423 sd x23,8(x2)
80000030: 00000b97 auipc x23,0x0
80000034: 2f0b8b93 addi x23,x23,752 # 80000320 <test_data>
80000038: 03313423 sd x19,40(x2)
8000003c: 03413023 sd x20,32(x2)
80000040: 01513c23 sd x21,24(x2)
80000044: 01613823 sd x22,16(x2)
80000048: 01813023 sd x24,0(x2)
8000004c: 04113423 sd x1,72(x2)
80000050: 04813023 sd x8,64(x2)
80000054: 02913c23 sd x9,56(x2)
80000058: 03213823 sd x18,48(x2)
8000005c: 00000b17 auipc x22,0x0
80000060: 0c4b0b13 addi x22,x22,196 # 80000120 <ans>
80000064: 000b8a93 addi x21,x23,0
80000068: 00000a13 addi x20,x0,0
8000006c: 00000997 auipc x19,0x0
80000070: 2f498993 addi x19,x19,756 # 80000360 <_bss_start>
80000074: 04000c13 addi x24,x0,64
80000078: 000ab903 ld x18,0(x21)
8000007c: 000b0493 addi x9,x22,0
80000080: 000b8413 addi x8,x23,0
80000084: 00043503 ld x10,0(x8)
80000088: 0004b783 ld x15,0(x9)
8000008c: 00840413 addi x8,x8,8
80000090: 40a90533 sub x10,x18,x10
80000094: 40f50533 sub x10,x10,x15
80000098: 00153513 sltiu x10,x10,1
8000009c: f75ff0ef jal x1,80000010 <check>
800000a0: 00848493 addi x9,x9,8
800000a4: fe8990e3 bne x19,x8,80000084 <main+0x5c>
800000a8: 008a0a1b addiw x20,x20,8
800000ac: 008a8a93 addi x21,x21,8
800000b0: 040b0b13 addi x22,x22,64
800000b4: fd8a12e3 bne x20,x24,80000078 <main+0x50>
800000b8: 04813083 ld x1,72(x2)
800000bc: 04013403 ld x8,64(x2)
800000c0: 03813483 ld x9,56(x2)
800000c4: 03013903 ld x18,48(x2)
800000c8: 02813983 ld x19,40(x2)
800000cc: 02013a03 ld x20,32(x2)
800000d0: 01813a83 ld x21,24(x2)
800000d4: 01013b03 ld x22,16(x2)
800000d8: 00813b83 ld x23,8(x2)
800000dc: 00013c03 ld x24,0(x2)
800000e0: 00000513 addi x10,x0,0
800000e4: 05010113 addi x2,x2,80
800000e8: 00008067 jalr x0,0(x1)
00000000800000ec <halt>:
800000ec: 00050513 addi x10,x10,0
800000f0: 00100073 ebreak
800000f4: 0000006f jal x0,800000f4 <halt+0x8>
00000000800000f8 <_trm_init>:
800000f8: ff010113 addi x2,x2,-16
800000fc: 00000517 auipc x10,0x0
80000100: 01c50513 addi x10,x10,28 # 80000118 <_etext>
80000104: 00113423 sd x1,8(x2)
80000108: f21ff0ef jal x1,80000028 <main>
8000010c: 00050513 addi x10,x10,0
80000110: 00100073 ebreak
80000114: 0000006f jal x0,80000114 <_trm_init+0x1c>

@ -0,0 +1,56 @@
elf/am-tests/sum: file format elf64-littleriscv
Disassembly of section .text:
0000000080000000 <_start>:
80000000: 00000413 addi x8,x0,0
80000004: 00009117 auipc x2,0x9
80000008: ffc10113 addi x2,x2,-4 # 80009000 <_end>
8000000c: 078000ef jal x1,80000084 <_trm_init>
0000000080000010 <check>:
80000010: 00050463 beq x10,x0,80000018 <check+0x8>
80000014: 00008067 jalr x0,0(x1)
80000018: ff010113 addi x2,x2,-16
8000001c: 00100513 addi x10,x0,1
80000020: 00113423 sd x1,8(x2)
80000024: 054000ef jal x1,80000078 <halt>
0000000080000028 <main>:
80000028: fe010113 addi x2,x2,-32
8000002c: 00113c23 sd x1,24(x2)
80000030: 00012623 sw x0,12(x2)
80000034: 00100793 addi x15,x0,1
80000038: 06500693 addi x13,x0,101
8000003c: 00c12703 lw x14,12(x2)
80000040: 00f7073b addw x14,x14,x15
80000044: 00e12623 sw x14,12(x2)
80000048: 0017879b addiw x15,x15,1
8000004c: fed798e3 bne x15,x13,8000003c <main+0x14>
80000050: 00c12503 lw x10,12(x2)
80000054: 000017b7 lui x15,0x1
80000058: 3ba78793 addi x15,x15,954 # 13ba <_entry_offset+0x13ba>
8000005c: 40f50533 sub x10,x10,x15
80000060: 00153513 sltiu x10,x10,1
80000064: fadff0ef jal x1,80000010 <check>
80000068: 01813083 ld x1,24(x2)
8000006c: 00000513 addi x10,x0,0
80000070: 02010113 addi x2,x2,32
80000074: 00008067 jalr x0,0(x1)
0000000080000078 <halt>:
80000078: 00050513 addi x10,x10,0
8000007c: 00100073 ebreak
80000080: 0000006f jal x0,80000080 <halt+0x8>
0000000080000084 <_trm_init>:
80000084: ff010113 addi x2,x2,-16
80000088: 00000517 auipc x10,0x0
8000008c: 02050513 addi x10,x10,32 # 800000a8 <mainargs>
80000090: 00113423 sd x1,8(x2)
80000094: f95ff0ef jal x1,80000028 <main>
80000098: 00050513 addi x10,x10,0
8000009c: 00100073 ebreak
800000a0: 0000006f jal x0,800000a0 <_trm_init+0x1c>

@ -0,0 +1,75 @@
elf/am-tests/switch: file format elf64-littleriscv
Disassembly of section .text:
0000000080000000 <_start>:
80000000: 00000413 addi x8,x0,0
80000004: 00009117 auipc x2,0x9
80000008: ffc10113 addi x2,x2,-4 # 80009000 <_end>
8000000c: 0c4000ef jal x1,800000d0 <_trm_init>
0000000080000010 <check>:
80000010: 00050463 beq x10,x0,80000018 <check+0x8>
80000014: 00008067 jalr x0,0(x1)
80000018: ff010113 addi x2,x2,-16
8000001c: 00100513 addi x10,x0,1
80000020: 00113423 sd x1,8(x2)
80000024: 0a0000ef jal x1,800000c4 <halt>
0000000080000028 <main>:
80000028: fd010113 addi x2,x2,-48
8000002c: 02813023 sd x8,32(x2)
80000030: 00913c23 sd x9,24(x2)
80000034: 01213823 sd x18,16(x2)
80000038: 01313423 sd x19,8(x2)
8000003c: 01413023 sd x20,0(x2)
80000040: 02113423 sd x1,40(x2)
80000044: 00000417 auipc x8,0x0
80000048: 0ec40413 addi x8,x8,236 # 80000130 <ans>
8000004c: 00000917 auipc x18,0x0
80000050: 0a490913 addi x18,x18,164 # 800000f0 <_etext>
80000054: 00000997 auipc x19,0x0
80000058: 11498993 addi x19,x19,276 # 80000168 <ans+0x38>
8000005c: 00000493 addi x9,x0,0
80000060: fff00793 addi x15,x0,-1
80000064: 00c00a13 addi x20,x0,12
80000068: 01c0006f jal x0,80000084 <main+0x5c>
8000006c: fff00793 addi x15,x0,-1
80000070: 009a6463 bltu x20,x9,80000078 <main+0x50>
80000074: 00092783 lw x15,0(x18)
80000078: 0014849b addiw x9,x9,1
8000007c: 00440413 addi x8,x8,4
80000080: 00490913 addi x18,x18,4
80000084: 00042503 lw x10,0(x8)
80000088: 40f50533 sub x10,x10,x15
8000008c: 00153513 sltiu x10,x10,1
80000090: f81ff0ef jal x1,80000010 <check>
80000094: fd341ce3 bne x8,x19,8000006c <main+0x44>
80000098: 00100513 addi x10,x0,1
8000009c: f75ff0ef jal x1,80000010 <check>
800000a0: 02813083 ld x1,40(x2)
800000a4: 02013403 ld x8,32(x2)
800000a8: 01813483 ld x9,24(x2)
800000ac: 01013903 ld x18,16(x2)
800000b0: 00813983 ld x19,8(x2)
800000b4: 00013a03 ld x20,0(x2)
800000b8: 00000513 addi x10,x0,0
800000bc: 03010113 addi x2,x2,48
800000c0: 00008067 jalr x0,0(x1)
00000000800000c4 <halt>:
800000c4: 00050513 addi x10,x10,0
800000c8: 00100073 ebreak
800000cc: 0000006f jal x0,800000cc <halt+0x8>
00000000800000d0 <_trm_init>:
800000d0: ff010113 addi x2,x2,-16
800000d4: 00000517 auipc x10,0x0
800000d8: 05450513 addi x10,x10,84 # 80000128 <mainargs>
800000dc: 00113423 sd x1,8(x2)
800000e0: f49ff0ef jal x1,80000028 <main>
800000e4: 00050513 addi x10,x10,0
800000e8: 00100073 ebreak
800000ec: 0000006f jal x0,800000ec <_trm_init+0x1c>

@ -0,0 +1,70 @@
elf/am-tests/to-lower-case: file format elf64-littleriscv
Disassembly of section .text:
0000000080000000 <_start>:
80000000: 00000413 addi x8,x0,0
80000004: 00009117 auipc x2,0x9
80000008: ffc10113 addi x2,x2,-4 # 80009000 <_end>
8000000c: 0b0000ef jal x1,800000bc <_trm_init>
0000000080000010 <check>:
80000010: 00050463 beq x10,x0,80000018 <check+0x8>
80000014: 00008067 jalr x0,0(x1)
80000018: ff010113 addi x2,x2,-16
8000001c: 00100513 addi x10,x0,1
80000020: 00113423 sd x1,8(x2)
80000024: 08c000ef jal x1,800000b0 <halt>
0000000080000028 <main>:
80000028: fd010113 addi x2,x2,-48
8000002c: 02813023 sd x8,32(x2)
80000030: 00913c23 sd x9,24(x2)
80000034: 01213823 sd x18,16(x2)
80000038: 01313423 sd x19,8(x2)
8000003c: 02113423 sd x1,40(x2)
80000040: 00000413 addi x8,x0,0
80000044: 00000793 addi x15,x0,0
80000048: 00000917 auipc x18,0x0
8000004c: 0a090913 addi x18,x18,160 # 800000e8 <ans>
80000050: 08000493 addi x9,x0,128
80000054: 01900993 addi x19,x0,25
80000058: 00890733 add x14,x18,x8
8000005c: 00074503 lbu x10,0(x14)
80000060: 0014041b addiw x8,x8,1
80000064: 40f50533 sub x10,x10,x15
80000068: 00153513 sltiu x10,x10,1
8000006c: fa5ff0ef jal x1,80000010 <check>
80000070: 0ff47793 andi x15,x8,255
80000074: fbf7871b addiw x14,x15,-65
80000078: 0ff77713 andi x14,x14,255
8000007c: 0207869b addiw x13,x15,32
80000080: 00940863 beq x8,x9,80000090 <main+0x68>
80000084: fce9eae3 bltu x19,x14,80000058 <main+0x30>
80000088: 0ff6f793 andi x15,x13,255
8000008c: fcdff06f jal x0,80000058 <main+0x30>
80000090: 02813083 ld x1,40(x2)
80000094: 02013403 ld x8,32(x2)
80000098: 01813483 ld x9,24(x2)
8000009c: 01013903 ld x18,16(x2)
800000a0: 00813983 ld x19,8(x2)
800000a4: 00000513 addi x10,x0,0
800000a8: 03010113 addi x2,x2,48
800000ac: 00008067 jalr x0,0(x1)
00000000800000b0 <halt>:
800000b0: 00050513 addi x10,x10,0
800000b4: 00100073 ebreak
800000b8: 0000006f jal x0,800000b8 <halt+0x8>
00000000800000bc <_trm_init>:
800000bc: ff010113 addi x2,x2,-16
800000c0: 00000517 auipc x10,0x0
800000c4: 02050513 addi x10,x10,32 # 800000e0 <mainargs>
800000c8: 00113423 sd x1,8(x2)
800000cc: f5dff0ef jal x1,80000028 <main>
800000d0: 00050513 addi x10,x10,0
800000d4: 00100073 ebreak
800000d8: 0000006f jal x0,800000d8 <_trm_init+0x1c>

@ -0,0 +1,99 @@
elf/am-tests/unalign: file format elf64-littleriscv
Disassembly of section .text:
0000000080000000 <_start>:
80000000: 00000413 addi x8,x0,0
80000004: 00009117 auipc x2,0x9
80000008: ffc10113 addi x2,x2,-4 # 80009000 <_end>
8000000c: 124000ef jal x1,80000130 <_trm_init>
0000000080000010 <check>:
80000010: 00050463 beq x10,x0,80000018 <check+0x8>
80000014: 00008067 jalr x0,0(x1)
80000018: ff010113 addi x2,x2,-16
8000001c: 00100513 addi x10,x0,1
80000020: 00113423 sd x1,8(x2)
80000024: 100000ef jal x1,80000124 <halt>
0000000080000028 <main>:
80000028: fb010113 addi x2,x2,-80
8000002c: 02913c23 sd x9,56(x2)
80000030: aabbd4b7 lui x9,0xaabbd
80000034: 04813023 sd x8,64(x2)
80000038: 03213823 sd x18,48(x2)
8000003c: 03313423 sd x19,40(x2)
80000040: 03413023 sd x20,32(x2)
80000044: 01513c23 sd x21,24(x2)
80000048: 01613823 sd x22,16(x2)
8000004c: 01713423 sd x23,8(x2)
80000050: 04113423 sd x1,72(x2)
80000054: 00400b13 addi x22,x0,4
80000058: 00000417 auipc x8,0x0
8000005c: 10040413 addi x8,x8,256 # 80000158 <buf>
80000060: 00000b97 auipc x23,0x0
80000064: 0f4b8b93 addi x23,x23,244 # 80000154 <x>
80000068: fdd00a93 addi x21,x0,-35
8000006c: fcc00a13 addi x20,x0,-52
80000070: fbb00993 addi x19,x0,-69
80000074: faa00913 addi x18,x0,-86
80000078: cdd48493 addi x9,x9,-803 # ffffffffaabbccdd <_end+0xffffffff2abb3cdd>
8000007c: 00344783 lbu x15,3(x8)
80000080: 015401a3 sb x21,3(x8)
80000084: 00444783 lbu x15,4(x8)
80000088: 01440223 sb x20,4(x8)
8000008c: 00544783 lbu x15,5(x8)
80000090: 013402a3 sb x19,5(x8)
80000094: 00644783 lbu x15,6(x8)
80000098: 01240323 sb x18,6(x8)
8000009c: 00344603 lbu x12,3(x8)
800000a0: 00444683 lbu x13,4(x8)
800000a4: 00544703 lbu x14,5(x8)
800000a8: 00644783 lbu x15,6(x8)
800000ac: 00869693 slli x13,x13,0x8
800000b0: 00c6e6b3 or x13,x13,x12
800000b4: 01071713 slli x14,x14,0x10
800000b8: 00d76733 or x14,x14,x13
800000bc: 01879793 slli x15,x15,0x18
800000c0: 00e7e7b3 or x15,x15,x14
800000c4: 0007879b addiw x15,x15,0
800000c8: 00fba023 sw x15,0(x23)
800000cc: 000ba503 lw x10,0(x23)
800000d0: fffb0b1b addiw x22,x22,-1
800000d4: 40950533 sub x10,x10,x9
800000d8: 00153513 sltiu x10,x10,1
800000dc: f35ff0ef jal x1,80000010 <check>
800000e0: 00000797 auipc x15,0x0
800000e4: 06078ca3 sb x0,121(x15) # 80000159 <buf+0x1>
800000e8: 00000797 auipc x15,0x0
800000ec: 06078823 sb x0,112(x15) # 80000158 <buf>
800000f0: f80b16e3 bne x22,x0,8000007c <main+0x54>
800000f4: 04813083 ld x1,72(x2)
800000f8: 04013403 ld x8,64(x2)
800000fc: 03813483 ld x9,56(x2)
80000100: 03013903 ld x18,48(x2)
80000104: 02813983 ld x19,40(x2)
80000108: 02013a03 ld x20,32(x2)
8000010c: 01813a83 ld x21,24(x2)
80000110: 01013b03 ld x22,16(x2)
80000114: 00813b83 ld x23,8(x2)
80000118: 00000513 addi x10,x0,0
8000011c: 05010113 addi x2,x2,80
80000120: 00008067 jalr x0,0(x1)
0000000080000124 <halt>:
80000124: 00050513 addi x10,x10,0
80000128: 00100073 ebreak
8000012c: 0000006f jal x0,8000012c <halt+0x8>
0000000080000130 <_trm_init>:
80000130: ff010113 addi x2,x2,-16
80000134: 00000517 auipc x10,0x0
80000138: 01c50513 addi x10,x10,28 # 80000150 <_etext>
8000013c: 00113423 sd x1,8(x2)
80000140: ee9ff0ef jal x1,80000028 <main>
80000144: 00050513 addi x10,x10,0
80000148: 00100073 ebreak
8000014c: 0000006f jal x0,8000014c <_trm_init+0x1c>

@ -0,0 +1,82 @@
elf/am-tests/wanshu: file format elf64-littleriscv
Disassembly of section .text:
0000000080000000 <_start>:
80000000: 00000413 addi x8,x0,0
80000004: 00009117 auipc x2,0x9
80000008: ffc10113 addi x2,x2,-4 # 80009000 <_end>
8000000c: 0e0000ef jal x1,800000ec <_trm_init>
0000000080000010 <check>:
80000010: 00050463 beq x10,x0,80000018 <check+0x8>
80000014: 00008067 jalr x0,0(x1)
80000018: ff010113 addi x2,x2,-16
8000001c: 00100513 addi x10,x0,1
80000020: 00113423 sd x1,8(x2)
80000024: 0bc000ef jal x1,800000e0 <halt>
0000000080000028 <main>:
80000028: fd010113 addi x2,x2,-48
8000002c: 00100613 addi x12,x0,1
80000030: 02813023 sd x8,32(x2)
80000034: 00913c23 sd x9,24(x2)
80000038: 01213823 sd x18,16(x2)
8000003c: 01313423 sd x19,8(x2)
80000040: 02113423 sd x1,40(x2)
80000044: 01e00493 addi x9,x0,30
80000048: 0016041b addiw x8,x12,1
8000004c: 00000993 addi x19,x0,0
80000050: 00000917 auipc x18,0x0
80000054: 0c890913 addi x18,x18,200 # 80000118 <ans>
80000058: 02940c63 beq x8,x9,80000090 <main+0x68>
8000005c: 00100793 addi x15,x0,1
80000060: 00000593 addi x11,x0,0
80000064: 02f4673b remw x14,x8,x15
80000068: 0017869b addiw x13,x15,1
8000006c: 00071463 bne x14,x0,80000074 <main+0x4c>
80000070: 00b785bb addw x11,x15,x11
80000074: 00c78663 beq x15,x12,80000080 <main+0x58>
80000078: 00068793 addi x15,x13,0
8000007c: fe9ff06f jal x0,80000064 <main+0x3c>
80000080: 02858e63 beq x11,x8,800000bc <main+0x94>
80000084: 00040613 addi x12,x8,0
80000088: 0016041b addiw x8,x12,1
8000008c: fc9418e3 bne x8,x9,8000005c <main+0x34>
80000090: ffe98513 addi x10,x19,-2
80000094: 00153513 sltiu x10,x10,1
80000098: f79ff0ef jal x1,80000010 <check>
8000009c: 02813083 ld x1,40(x2)
800000a0: 02013403 ld x8,32(x2)
800000a4: 01813483 ld x9,24(x2)
800000a8: 01013903 ld x18,16(x2)
800000ac: 00813983 ld x19,8(x2)
800000b0: 00000513 addi x10,x0,0
800000b4: 03010113 addi x2,x2,48
800000b8: 00008067 jalr x0,0(x1)
800000bc: 00299793 slli x15,x19,0x2
800000c0: 00f907b3 add x15,x18,x15
800000c4: 0007a503 lw x10,0(x15)
800000c8: 0019899b addiw x19,x19,1
800000cc: 40850533 sub x10,x10,x8
800000d0: 00153513 sltiu x10,x10,1
800000d4: f3dff0ef jal x1,80000010 <check>
800000d8: 00040613 addi x12,x8,0
800000dc: fadff06f jal x0,80000088 <main+0x60>
00000000800000e0 <halt>:
800000e0: 00050513 addi x10,x10,0
800000e4: 00100073 ebreak
800000e8: 0000006f jal x0,800000e8 <halt+0x8>
00000000800000ec <_trm_init>:
800000ec: ff010113 addi x2,x2,-16
800000f0: 00000517 auipc x10,0x0
800000f4: 02050513 addi x10,x10,32 # 80000110 <mainargs>
800000f8: 00113423 sd x1,8(x2)
800000fc: f2dff0ef jal x1,80000028 <main>
80000100: 00050513 addi x10,x10,0
80000104: 00100073 ebreak
80000108: 0000006f jal x0,80000108 <_trm_init+0x1c>

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

@ -0,0 +1,225 @@
./build/test: file format elf64-littleriscv
Disassembly of section .text:
0000000080000000 <_start>:
80000000: 00200193 addi x3,x0,2
80000004: 30102573 csrrs x10,misa,x0
80000008: 03e55513 srli x10,x10,0x3e
8000000c: 00200393 addi x7,x0,2
80000010: 26751463 bne x10,x7,80000278 <fail>
0000000080000014 <test_3>:
80000014: 00300193 addi x3,x0,3
80000018: f1402573 csrrs x10,mhartid,x0
8000001c: 00000393 addi x7,x0,0
80000020: 24751c63 bne x10,x7,80000278 <fail>
80000024: f1302573 csrrs x10,mimpid,x0
80000028: f1302573 csrrs x10,mimpid,x0
8000002c: f1202573 csrrs x10,marchid,x0
80000030: f1102573 csrrs x10,mvendorid,x0
80000034: 00000293 addi x5,x0,0
80000038: 3052a073 csrrs x0,mtvec,x5
8000003c: 3412a073 csrrs x0,mepc,x5
80000040: 000022b7 lui x5,0x2
80000044: 8002829b addiw x5,x5,-2048 # 1800 <_start-0x7fffe800>
80000048: 3002b073 csrrc x0,mstatus,x5
8000004c: 30002373 csrrs x6,mstatus,x0
80000050: 0062f2b3 and x5,x5,x6
80000054: 02029463 bne x5,x0,8000007c <test_5>
0000000080000058 <test_4>:
80000058: 00400193 addi x3,x0,4
8000005c: 30002573 csrrs x10,mstatus,x0
80000060: 0030059b addiw x11,x0,3
80000064: 02059593 slli x11,x11,0x20
80000068: 00b57533 and x10,x10,x11
8000006c: 0010039b addiw x7,x0,1
80000070: 02139393 slli x7,x7,0x21
80000074: 20751263 bne x10,x7,80000278 <fail>
80000078: 0200006f jal x0,80000098 <test_6>
000000008000007c <test_5>:
8000007c: 00500193 addi x3,x0,5
80000080: 30002573 csrrs x10,mstatus,x0
80000084: 0030059b addiw x11,x0,3
80000088: 02059593 slli x11,x11,0x20
8000008c: 00b57533 and x10,x10,x11
80000090: 00000393 addi x7,x0,0
80000094: 1e751263 bne x10,x7,80000278 <fail>
0000000080000098 <test_6>:
80000098: 00600193 addi x3,x0,6
8000009c: c0003073 csrrc x0,cycle,x0
800000a0: 00000393 addi x7,x0,0
800000a4: 1c701a63 bne x0,x7,80000278 <fail>
00000000800000a8 <test_7>:
800000a8: 00700193 addi x3,x0,7
800000ac: c0002073 csrrs x0,cycle,x0
800000b0: 00000393 addi x7,x0,0
800000b4: 1c701263 bne x0,x7,80000278 <fail>
00000000800000b8 <test_8>:
800000b8: 00800193 addi x3,x0,8
800000bc: c0007073 csrrci x0,cycle,0
800000c0: 00000393 addi x7,x0,0
800000c4: 1a701a63 bne x0,x7,80000278 <fail>
00000000800000c8 <test_9>:
800000c8: 00900193 addi x3,x0,9
800000cc: c0006073 csrrsi x0,cycle,0
800000d0: 00000393 addi x7,x0,0
800000d4: 1a701263 bne x0,x7,80000278 <fail>
00000000800000d8 <test_10>:
800000d8: 00a00193 addi x3,x0,10
800000dc: 34001073 csrrw x0,mscratch,x0
800000e0: 34002573 csrrs x10,mscratch,x0
800000e4: 00000393 addi x7,x0,0
800000e8: 18751863 bne x10,x7,80000278 <fail>
00000000800000ec <test_11>:
800000ec: 00b00193 addi x3,x0,11
800000f0: 34005573 csrrwi x10,mscratch,0
800000f4: 3407d573 csrrwi x10,mscratch,15
800000f8: 00000393 addi x7,x0,0
800000fc: 16751e63 bne x10,x7,80000278 <fail>
0000000080000100 <test_12>:
80000100: 00c00193 addi x3,x0,12
80000104: 34086073 csrrsi x0,mscratch,16
80000108: 34002573 csrrs x10,mscratch,x0
8000010c: 01f00393 addi x7,x0,31
80000110: 16751463 bne x10,x7,80000278 <fail>
80000114: 3401d073 csrrwi x0,mscratch,3
0000000080000118 <test_13>:
80000118: 00d00193 addi x3,x0,13
8000011c: 34002573 csrrs x10,mscratch,x0
80000120: 00300393 addi x7,x0,3
80000124: 14751a63 bne x10,x7,80000278 <fail>
0000000080000128 <test_14>:
80000128: 00e00193 addi x3,x0,14
8000012c: 3400f5f3 csrrci x11,mscratch,1
80000130: 00300393 addi x7,x0,3
80000134: 14759263 bne x11,x7,80000278 <fail>
0000000080000138 <test_15>:
80000138: 00f00193 addi x3,x0,15
8000013c: 34026673 csrrsi x12,mscratch,4
80000140: 00200393 addi x7,x0,2
80000144: 12761a63 bne x12,x7,80000278 <fail>
0000000080000148 <test_16>:
80000148: 01000193 addi x3,x0,16
8000014c: 340156f3 csrrwi x13,mscratch,2
80000150: 00600393 addi x7,x0,6
80000154: 12769263 bne x13,x7,80000278 <fail>
0000000080000158 <test_17>:
80000158: 01100193 addi x3,x0,17
8000015c: 0bad2537 lui x10,0xbad2
80000160: dea5051b addiw x10,x10,-534 # bad1dea <_start-0x7452e216>
80000164: 340515f3 csrrw x11,mscratch,x10
80000168: 00200393 addi x7,x0,2
8000016c: 10759663 bne x11,x7,80000278 <fail>
0000000080000170 <test_18>:
80000170: 01200193 addi x3,x0,18
80000174: 00002537 lui x10,0x2
80000178: dea5051b addiw x10,x10,-534 # 1dea <_start-0x7fffe216>
8000017c: 340535f3 csrrc x11,mscratch,x10
80000180: 0bad23b7 lui x7,0xbad2
80000184: dea3839b addiw x7,x7,-534 # bad1dea <_start-0x7452e216>
80000188: 0e759863 bne x11,x7,80000278 <fail>
000000008000018c <test_19>:
8000018c: 01300193 addi x3,x0,19
80000190: 0000c537 lui x10,0xc
80000194: eef5051b addiw x10,x10,-273 # beef <_start-0x7fff4111>
80000198: 340525f3 csrrs x11,mscratch,x10
8000019c: 0bad03b7 lui x7,0xbad0
800001a0: 0c759c63 bne x11,x7,80000278 <fail>
00000000800001a4 <test_20>:
800001a4: 01400193 addi x3,x0,20
800001a8: 0bad2537 lui x10,0xbad2
800001ac: dea5051b addiw x10,x10,-534 # bad1dea <_start-0x7452e216>
800001b0: 34051573 csrrw x10,mscratch,x10
800001b4: 0badc3b7 lui x7,0xbadc
800001b8: eef3839b addiw x7,x7,-273 # badbeef <_start-0x74524111>
800001bc: 0a751e63 bne x10,x7,80000278 <fail>
00000000800001c0 <test_21>:
800001c0: 01500193 addi x3,x0,21
800001c4: 00002537 lui x10,0x2
800001c8: dea5051b addiw x10,x10,-534 # 1dea <_start-0x7fffe216>
800001cc: 34053573 csrrc x10,mscratch,x10
800001d0: 0bad23b7 lui x7,0xbad2
800001d4: dea3839b addiw x7,x7,-534 # bad1dea <_start-0x7452e216>
800001d8: 0a751063 bne x10,x7,80000278 <fail>
00000000800001dc <test_22>:
800001dc: 01600193 addi x3,x0,22
800001e0: 0000c537 lui x10,0xc
800001e4: eef5051b addiw x10,x10,-273 # beef <_start-0x7fff4111>
800001e8: 34052573 csrrs x10,mscratch,x10
800001ec: 0bad03b7 lui x7,0xbad0
800001f0: 08751463 bne x10,x7,80000278 <fail>
00000000800001f4 <test_23>:
800001f4: 01700193 addi x3,x0,23
800001f8: 34002573 csrrs x10,mscratch,x0
800001fc: 0badc3b7 lui x7,0xbadc
80000200: eef3839b addiw x7,x7,-273 # badbeef <_start-0x74524111>
80000204: 06751a63 bne x10,x7,80000278 <fail>
80000208: 30102573 csrrs x10,misa,x0
8000020c: 02057513 andi x10,x10,32
80000210: 00050263 beq x10,x0,80000214 <test_23+0x20>
80000214: 30102573 csrrs x10,misa,x0
80000218: 01455513 srli x10,x10,0x14
8000021c: 00157513 andi x10,x10,1
80000220: 04050263 beq x10,x0,80000264 <finish>
80000224: 3060d073 csrrwi x0,mcounteren,1
80000228: 30102573 csrrs x10,misa,x0
8000022c: 01255513 srli x10,x10,0x12
80000230: 00157513 andi x10,x10,1
80000234: 00050463 beq x10,x0,8000023c <test_23+0x48>
80000238: 1060d073 csrrwi x0,scounteren,1
8000023c: 10000293 addi x5,x0,256
80000240: 3002b073 csrrc x0,mstatus,x5
80000244: 00000297 auipc x5,0x0
80000248: 01028293 addi x5,x5,16 # 80000254 <test_24>
8000024c: 34129073 csrrw x0,mepc,x5
80000250: 00000013 addi x0,x0,0
0000000080000254 <test_24>:
80000254: 01800193 addi x3,x0,24
80000258: 00000013 addi x0,x0,0
8000025c: 00000393 addi x7,x0,0
80000260: 00701c63 bne x0,x7,80000278 <fail>
0000000080000264 <finish>:
80000264: 00100193 addi x3,x0,1
80000268: 05d00893 addi x17,x0,93
8000026c: 00000513 addi x10,x0,0
80000270: 00000073 ecall
80000274: 00301e63 bne x0,x3,80000290 <pass>
0000000080000278 <fail>:
80000278: 00018063 beq x3,x0,80000278 <fail>
8000027c: 00119193 slli x3,x3,0x1
80000280: 0011e193 ori x3,x3,1
80000284: 05d00893 addi x17,x0,93
80000288: 00018513 addi x10,x3,0
8000028c: 00000073 ecall
0000000080000290 <pass>:
80000290: 00100193 addi x3,x0,1
80000294: 05d00893 addi x17,x0,93
80000298: 00000513 addi x10,x0,0
8000029c: 00000073 ecall

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

@ -0,0 +1,163 @@
./rv64mi-p-access: file format elf64-littleriscv
Disassembly of section .text.init:
0000000080000000 <_start>:
80000000: 04c0006f jal x0,8000004c <reset_vector>
0000000080000004 <trap_vector>:
80000004: 34202f73 csrrs x30,mcause,x0
80000008: 00800f93 addi x31,x0,8
8000000c: 03ff0a63 beq x30,x31,80000040 <write_tohost>
80000010: 00900f93 addi x31,x0,9
80000014: 03ff0663 beq x30,x31,80000040 <write_tohost>
80000018: 00b00f93 addi x31,x0,11
8000001c: 03ff0263 beq x30,x31,80000040 <write_tohost>
80000020: 00000f17 auipc x30,0x0
80000024: 1e8f0f13 addi x30,x30,488 # 80000208 <mtvec_handler>
80000028: 000f0463 beq x30,x0,80000030 <trap_vector+0x2c>
8000002c: 000f0067 jalr x0,0(x30)
80000030: 34202f73 csrrs x30,mcause,x0
80000034: 000f5463 bge x30,x0,8000003c <handle_exception>
80000038: 0040006f jal x0,8000003c <handle_exception>
000000008000003c <handle_exception>:
8000003c: 5391e193 ori x3,x3,1337
0000000080000040 <write_tohost>:
80000040: 00001f17 auipc x30,0x1
80000044: fc3f2023 sw x3,-64(x30) # 80001000 <tohost>
80000048: ff9ff06f jal x0,80000040 <write_tohost>
000000008000004c <reset_vector>:
8000004c: 00000093 addi x1,x0,0
80000050: 00000113 addi x2,x0,0
80000054: 00000193 addi x3,x0,0
80000058: 00000213 addi x4,x0,0
8000005c: 00000293 addi x5,x0,0
80000060: 00000313 addi x6,x0,0
80000064: 00000393 addi x7,x0,0
80000068: 00000413 addi x8,x0,0
8000006c: 00000493 addi x9,x0,0
80000070: 00000513 addi x10,x0,0
80000074: 00000593 addi x11,x0,0
80000078: 00000613 addi x12,x0,0
8000007c: 00000693 addi x13,x0,0
80000080: 00000713 addi x14,x0,0
80000084: 00000793 addi x15,x0,0
80000088: 00000813 addi x16,x0,0
8000008c: 00000893 addi x17,x0,0
80000090: 00000913 addi x18,x0,0
80000094: 00000993 addi x19,x0,0
80000098: 00000a13 addi x20,x0,0
8000009c: 00000a93 addi x21,x0,0
800000a0: 00000b13 addi x22,x0,0
800000a4: 00000b93 addi x23,x0,0
800000a8: 00000c13 addi x24,x0,0
800000ac: 00000c93 addi x25,x0,0
800000b0: 00000d13 addi x26,x0,0
800000b4: 00000d93 addi x27,x0,0
800000b8: 00000e13 addi x28,x0,0
800000bc: 00000e93 addi x29,x0,0
800000c0: 00000f13 addi x30,x0,0
800000c4: 00000f93 addi x31,x0,0
800000c8: f1402573 csrrs x10,mhartid,x0
800000cc: 00051063 bne x10,x0,800000cc <reset_vector+0x80>
800000d0: 00000297 auipc x5,0x0
800000d4: 01028293 addi x5,x5,16 # 800000e0 <reset_vector+0x94>
800000d8: 30529073 csrrw x0,mtvec,x5
800000dc: 18005073 csrrwi x0,satp,0
800000e0: 00000297 auipc x5,0x0
800000e4: 02428293 addi x5,x5,36 # 80000104 <reset_vector+0xb8>
800000e8: 30529073 csrrw x0,mtvec,x5
800000ec: 0010029b addiw x5,x0,1
800000f0: 03529293 slli x5,x5,0x35
800000f4: fff28293 addi x5,x5,-1
800000f8: 3b029073 csrrw x0,pmpaddr0,x5
800000fc: 01f00293 addi x5,x0,31
80000100: 3a029073 csrrw x0,pmpcfg0,x5
80000104: 30405073 csrrwi x0,mie,0
80000108: 00000297 auipc x5,0x0
8000010c: 01428293 addi x5,x5,20 # 8000011c <reset_vector+0xd0>
80000110: 30529073 csrrw x0,mtvec,x5
80000114: 30205073 csrrwi x0,medeleg,0
80000118: 30305073 csrrwi x0,mideleg,0
8000011c: 00000193 addi x3,x0,0
80000120: 00000297 auipc x5,0x0
80000124: ee428293 addi x5,x5,-284 # 80000004 <trap_vector>
80000128: 30529073 csrrw x0,mtvec,x5
8000012c: 00100513 addi x10,x0,1
80000130: 01f51513 slli x10,x10,0x1f
80000134: 00055c63 bge x10,x0,8000014c <reset_vector+0x100>
80000138: 0ff0000f fence iorw,iorw
8000013c: 00100193 addi x3,x0,1
80000140: 05d00893 addi x17,x0,93
80000144: 00000513 addi x10,x0,0
80000148: 00000073 ecall
8000014c: 00000293 addi x5,x0,0
80000150: 00028a63 beq x5,x0,80000164 <reset_vector+0x118>
80000154: 10529073 csrrw x0,stvec,x5
80000158: 0000b2b7 lui x5,0xb
8000015c: 1092829b addiw x5,x5,265 # b109 <_start-0x7fff4ef7>
80000160: 30229073 csrrw x0,medeleg,x5
80000164: 30005073 csrrwi x0,mstatus,0
80000168: 00002537 lui x10,0x2
8000016c: 8005051b addiw x10,x10,-2048 # 1800 <_start-0x7fffe800>
80000170: 30052073 csrrs x0,mstatus,x10
80000174: 00000297 auipc x5,0x0
80000178: 01428293 addi x5,x5,20 # 80000188 <reset_vector+0x13c>
8000017c: 34129073 csrrw x0,mepc,x5
80000180: f1402573 csrrs x10,mhartid,x0
80000184: 30200073 mret
80000188: 00000397 auipc x7,0x0
8000018c: 05038393 addi x7,x7,80 # 800001d8 <fail>
80000190: fff0029b addiw x5,x0,-1
80000194: 03f29293 slli x5,x5,0x3f
80000198: 0072c2b3 xor x5,x5,x7
8000019c: 00200193 addi x3,x0,2
800001a0: 00100313 addi x6,x0,1
800001a4: 00000497 auipc x9,0x0
800001a8: 01048493 addi x9,x9,16 # 800001b4 <reset_vector+0x168>
800001ac: 00000393 addi x7,x0,0
800001b0: 000283e7 jalr x7,0(x5)
800001b4: 00300193 addi x3,x0,3
800001b8: 00500313 addi x6,x0,5
800001bc: 00000497 auipc x9,0x0
800001c0: 01448493 addi x9,x9,20 # 800001d0 <reset_vector+0x184>
800001c4: 00048393 addi x7,x9,0
800001c8: 00028383 lb x7,0(x5)
800001cc: 00c0006f jal x0,800001d8 <fail>
800001d0: 0240006f jal x0,800001f4 <pass>
800001d4: 02301063 bne x0,x3,800001f4 <pass>
00000000800001d8 <fail>:
800001d8: 0ff0000f fence iorw,iorw
800001dc: 00018063 beq x3,x0,800001dc <fail+0x4>
800001e0: 00119193 slli x3,x3,0x1
800001e4: 0011e193 ori x3,x3,1
800001e8: 05d00893 addi x17,x0,93
800001ec: 00018513 addi x10,x3,0
800001f0: 00000073 ecall
00000000800001f4 <pass>:
800001f4: 0ff0000f fence iorw,iorw
800001f8: 00100193 addi x3,x0,1
800001fc: 05d00893 addi x17,x0,93
80000200: 00000513 addi x10,x0,0
80000204: 00000073 ecall
0000000080000208 <mtvec_handler>:
80000208: 00200513 addi x10,x0,2
8000020c: 00a18863 beq x3,x10,8000021c <mtvec_handler+0x14>
80000210: 00300513 addi x10,x0,3
80000214: 00a18463 beq x3,x10,8000021c <mtvec_handler+0x14>
80000218: fc1ff06f jal x0,800001d8 <fail>
8000021c: fa939ee3 bne x7,x9,800001d8 <fail>
80000220: 342023f3 csrrs x7,mcause,x0
80000224: fa639ae3 bne x7,x6,800001d8 <fail>
80000228: 34149073 csrrw x0,mepc,x9
8000022c: 30200073 mret
80000230: c0001073 unimp
...

Some files were not shown because too many files have changed in this diff Show More

Loading…
Cancel
Save