RISC-V MCU中文社区

【分享】 CSR读写控制模块

发表于 开源蜂鸟E203 2023-05-15 08:07:30
0
1099
0

队伍编号:CICC1413

具体代码位于:

图片alt

概述

CSR是RISC-V中的控制状态寄存器(Control and Status Registers),用于控制处理器的行为和状态。CSR类指令是RISC-V中的一类指令,用于读取和写入控制状态寄存器(CSR)。 在RISC-V指令集中,CSR类指令主要包括以下几个:

  1. CSRRW:读取CSR寄存器的值,并将一个新值写入该寄存器。这条指令的格式为:CSRRW rd, csr, rs1,其中rd表示目标寄存器,csr表示CSR寄存器的编号,rs1表示要写入CSR寄存器的新值。
  2. CSRRS:读取CSR寄存器的值,并将该寄存器的值与一个立即数或寄存器中的值进行按位或运算,然后将结果写回CSR寄存器。这条指令的格式为:CSRRS rd, csr, rs1,其中rd表示目标寄存器,csr表示CSR寄存器的编号,rs1表示要进行按位或运算的立即数或寄存器。
  3. CSRRC:读取CSR寄存器的值,并将该寄存器的值与一个立即数或寄存器中的值进行按位与运算,然后将结果写回CSR寄存器。这条指令的格式为:CSRRC rd, csr, rs1,其中rd表示目标寄存器,csr表示CSR寄存器的编号,rs1表示要进行按位与运算的立即数或寄存器。
  4. CSRRWI:读取CSR寄存器的值,并将一个立即数写入该寄存器。这条指令的格式为:CSRRWI rd, csr, imm,其中rd表示目标寄存器,csr表示CSR寄存器的编号,imm表示要写入CSR寄存器的立即数。
  5. CSRRSI:读取CSR寄存器的值,并将该寄存器的值与一个立即数进行按位或运算,然后将结果写回CSR寄存器。这条指令的格式为:CSRRSI rd, csr, imm,其中rd表示目标寄存器,csr表示CSR寄存器的编号,imm表示要进行按位或运算的立即数。
  6. CSRRCI:读取CSR寄存器的值,并将该寄存器的值与一个立即数进行按位与运算,然后将结果写回CSR寄存器。这条指令的格式为:CSRRCI rd, csr, imm,其中rd表示目标寄存器,csr表示CSR寄存器的编号,imm表示要进行按位与运算的立即数。

代码分析

总览

这段代码是RISC-V处理器中的一个模块,用于实现CSR(Control and Status Registers)的控制和读写。

该模块的输入包括csr_i_valid(CSR读写请求的有效性)、csr_i_rs1(CSR读写请求的操作数)、csr_i_info(CSR读写请求的信息,包括操作码和CSR索引等)、csr_i_rdwen(CSR读写请求是否写入寄存器)等。输出包括csr_ena(CSR读写请求是否有效)、csr_wr_en(CSR写入使能)、csr_rd_en(CSR读取使能)、csr_idx(CSR索引)等。

除此之外,该模块还实现了特殊的CSR访问接口,用于访问NICE CSR(一种特殊的CSR)。如果访问的是NICE CSR,需要先检查nice_csr_ready是否准备好,然后才能访问。如果访问的是普通的CSR,则直接进行访问。在访问NICE CSR时,还需要将写入数据发送到NICE接口,并从NICE接口读取数据。

ctrl中CSR指令预处理

  1. csr_op1:这个信号是CSR操作中的一个操作数,用于根据CSR指令的不同类型选择正确的操作数。当CSR指令类型为CSRRWI和CSRRSI时,csr_op1将使用zimm作为操作数;当CSR指令类型为CSRRW、CSRRS和CSRRC时,csr_op1将使用rs1作为操作数。

  2. csr_rd_en:这个信号用于控制CSR指令是否需要读取CSR的值。当CSR指令类型为CSRRW、CSRRS和CSRRC时,需要读取CSR的值;当CSR指令类型为CSRRWI、CSRRSI时,不需要读取CSR的值。

  3. csr_wr_en:这个信号用于控制CSR指令是否需要写入CSR的值。当CSR指令类型为CSRRW、CSRRWI时,需要写入CSR的值;当CSR指令类型为CSRRS、CSRRC、CSRRSI和CSRRCI时,不需要写入CSR的值。

  4. csr_idx:这个信号用于指定CSR的编号,它在所有CSR操作中都是必需的。

  5. csr_ena:这个信号表示CSR操作的使能信号,表示CSR操作已准备好并且可以进行。当csr_o_valid和csr_o_ready都为1时,csr_ena将被置为1。

  6. wbck_csr_dat: 这个信号表示从 CSR 中读取的数据,用于写回到目标寄存器中。在这个模块中,wbck_csr_dat 的值是通过对 CSR 的读取操作得到的。

对于CSRRW指令,需要读取CSR的值,并将原来的值写入目标寄存器。这部分操作由以下代码实现:

assign wbck_csr_dat = ({`E203_XLEN{csrrw}} & csr_op1)

其中,csrrw为一个常量值,表示CSRRW指令的操作码,`E203_XLEN为定义的常量值,表示RISC-V指令集中的XLEN(数据位宽),csr_op1为从rs1寄存器或立即数中获取的操作数。

对于CSRRS指令,需要读取CSR的值,并将原来的值与rs1寄存器的值进行按位或运算,然后将结果写入CSR。这部分操作由以下代码实现:

assign wbck_csr_dat = ({`E203_XLEN{csrrs}} & (csr_op1 | read_csr_dat))

其中,csrrs为一个常量值,表示CSRRS指令的操作码,`E203_XLEN为定义的常量值,表示RISC-V指令集中的XLEN(数据位宽),csr_op1为从rs1寄存器或立即数中获取的操作数,read_csr_dat为CSR的原始值。

对于CSRRC指令,需要读取CSR的值,并将原来的值与rs1寄存器的值进行按位与运算,然后将结果写入CSR。这部分操作由以下代码实现:

assign wbck_csr_dat = ({`E203_XLEN{csrrc}} & ((~csr_op1) & read_csr_dat))

其中,csrrc为一个常量值,表示CSRRC指令的操作码,`E203_XLEN为定义的常量值,表示RISC-V指令集中的XLEN(数据位宽),csr_op1为从rs1寄存器或立即数中获取的操作数,read_csr_dat为CSR的原始值。

最后

将output与CSR模块相连,在模块中完成CSR指令的操作

图片alt

喜欢0
用户评论
ved.

ved. 实名认证

懒的都不写签名

积分
问答
粉丝
关注
  • RV-STAR 开发板
  • RISC-V处理器设计系列课程
  • 培养RISC-V大学土壤 共建RISC-V教育生态
RV-STAR 开发板