RISC-V CPU管道模拟
1.简介
RISC-V是源自伯克利的开源架构和指令集标准。 该项目要求您基于标准的五阶段管道实现RISC-V CPU管道模拟器。 您需要从RISC-V规范2.2中指定的RV32I指令设置中实现指令的子集。 实施完整的CPU模拟器可以有效地行使系统编程功能,并加深对与建筑有关的知识的了解。
2.项目简介
2.1。 项目要求
该项目最重要的部分是实施RISC-V CPU管道模拟器。 具体要求如下:
•命令行参数解析器模块,该模块允许解析通往RISC-V二进制的路径
命令行中指定的文件。 它还提供了一个选项,可以在文件末尾启用或禁用打印历史记录。 请确保您的模拟器可以通过Simulator XXX.RISCV运行,其中XXX.RISCV是RISCV二进制代码的路径。
•加载精灵文件(已在模板中实现)。
•历史模块(模板中具有参考结构)。
•内存管理(在模板中具有参考结构,某些需要
操作说明)。
•模拟所需的说明(请参阅第2.7节),包括处理系统调用(请参阅
第2.6节)。
•处理数据危害,控制危险和内存访问危害。
2.2。 可能的结构
注意:这只是可能的结构。 您可以设计自己的结构。
模拟器代码体系结构的概述图(图1)如下所示。 模拟器的输入点是main.cpp,其中包括解析参数,加载小精灵文件,初始化模拟器模块,最后调用Simulate()函数以输入模拟器的执行。 除非执行模拟器有错误,否则理论上,Simulate()函数将不会返回。
模拟器本身被设计为大型类,这是模拟器类中数据的类,包括PC,常规寄存器,管道寄存器,执行历史记录记录器,内存模块和分支预测模块(对您来说不需要,不会影响您的分数 )。 其中,由于内存模块和分支预测模块相对独立,因此将它们实现为两个独立的classermanager和branch predictor。
模拟器中最核心的函数是Simulate()函数,该函数在模拟代写RISC-V 器上执行周期级别的模拟。 在每个模拟中,它将执行fetch(),decode(),execute(),accessMemory()和writeback()五个函数,每个函数都以输入为输入
从上一个周期中的管道寄存器,并输出到下一个周期的管道寄存器。 在周期结束时,将新寄存器的内容复制到用作输入的内容中。 在执行过程中,每个功能都处理与数据危害,控制危害和内存访问危害相关的内容,并记录适当位置的历史信息。
图1:模拟器体系结构
2.3。 内存管理
MemoryManager的功能是为模拟器提供一个简单易用的内存访问接口,该接口必须支持任意的内存大小和内存地址访问,并可以检测非法内存地址访问。 您需要做的是根据该部分的虚拟内存地址和内存大小(不是文件大小)将不同部分从ELF文件加载到正确的内存位置。 然后,在模拟读取/写入指令的执行时,您只需要解析内存地址并在内存manager中直接使用此内存地址进行操作,而无需在之间进行任何转换。
MemoryManager的以下实现使用了类似于X86体系结构中使用的两个级别页面表(可以单级页表)的机制。 具体而言,它将逻辑上的32位存储空间(4GB)划分为4kb(2^12)的页面,使用内存地址的前10位作为一级级别的索引,然后是另外10位 位作为第二级页表的索引,最后将最后12位用作单页中的偏移。
)。
2.4。 精灵负载和初始化
您需要根据第3节来实现ELF文件加载程序并初始化模拟器。 ELF文件加载器负责将ELF文件加载到模拟器的内存中,并且初始化过程负责设置模拟器的初始状态,包括设置PC的初始值,设置常规寄存器的初始值,并 设置堆栈指针的初始值,等等。