# 计算机组成与设计

LLMS index: [llms.txt](/wikis/llms.txt)

---

# 《计算机组成原理》课程实验相关

首先必须要吹一波《计原》课程的大实验[实验文档](https://lab.cs.tsinghua.edu.cn/cod-lab-docs-2022/)，基本涵盖了实验基础部分的所有内容，这里我就只再写一些个人感觉踩了不少坑的地方吧。

## 关于 uCore 的另一些提示

- 精确异常：异常或中断发生时考虑 mepc 或 sepc 是否设置在了正确的位置，同时是否真的将发生异常的这条指令效果**完全消除**。如 `sw a5, 0(a5)` 这里发生了异常，那么请确保你的设计不会修改 `a5` 的值。
- 异常种类：和页表相关的异常是较为繁琐的，这里我推荐使用和做网原路由器实验时相同的方式，直接将对应的文档原文作为注释粘贴到代码中，然后一句话一句话实现。注意 Page Table Walker 进行虚实地址转换时也可能会遇到中间结果 Not Valid 异常。
- 仿真工具：见下节。

## 关于仿真工具

私以为限制很多组工作效率的真正原因是仿真工具。跟 Hoxxxr9 聊天时，其阐述过造机时的状态：改几行代码，开始用 Vivado 自带的仿真，然后打开一集《中二病也要谈恋爱》开始看，看完一集基本仿真波形才能跑的差不多，然后去看波形调时序（<s>把波形拟合成自己想要的样子</s>）。然后再改几行代码，再开始仿真，进入下一个循环...

在这里我推荐一个速度更快的仿真工具 [Verilator](https://verilator.org/guide/latest/)，一般想要将 uCore 仿真到开机自检时你出错的地方，即使去改 uCore 的代码删掉一些没用的功能也要 30min ~ 1h 左右，<s>更有甚者甚至晚上把仿真打开，第二天早上起来看波形</s>，而 Verilator 可以在 1min 左右就完成这个工作。具体的安装过程我们这里不做赘述，请自行阅读其使用文档，而其使用过程大概可以概括为：写一个 Fake SRAM 与 Fake UART，然后在 testbench 里用这个器件换掉原来的器件，进而使用 Verilator 仿真。

所谓 Fake，是说你自己去模拟这个器件的功能，并尽可能的保持你的实现与器件原来的实现一致，同时可以输出一些调试信息，比如在 UART 收到字符时用 `$display` 直接打印到 stdout 里。

同时，Verilator 自带的 code linter 功能可以在某种程度上起到帮助检查代码中错误的作用，也帮助了笔者在造机过程中解决了一些问题。比如把一个 26 位宽的信号往下传时不小心输出写 `wire[25:0]`，输入写 `input wire` 而丢了位宽，Vivado 只会报 Warning，而 Verilator 对于位宽不匹配则会报 Error 并提醒你修改或忽略。

此外，也有 iVerilog 等更简单的仿真工具，<s>但可能也有一些坑</s>，欢迎同学们自由探索。

这样你就可以节省下来大量的时间不是在等仿真，而是直接去看《中二病也要谈恋爱》了。<s>笔者造机期间用三个晚上看完了两季 + 剧场版。</s>
