0

如何在 16 位数据路径上移动 32 位数字

这是一个计算机体系结构问题。


我的数据路径只有 16 位宽,这意味着我的 ALU 一次只能处理 16 位操作数。我的寄存器为 32 位宽,可在低 16 位和高 16 位部分寻址。

每次我读取寄存器的下半部分时,我还会额外读取一点,告诉我天气上半部分根本包含任何 1(参考 1)。


到目前为止,我实现了逻辑左移。( sll rd, rs1, rs2 )

  • 读取 rs1 寄存器的下半部分,并将其移位在下 rs2 寄存器中指定的量
  • 我从这 16 位中移出的位存储在 alu 内部的一个临时 16 位寄存器中
  • 移位后的值将被写回低 rd 寄存器并设置状态位(参见参考文献 1)

现在,如果没有数据写入更高的 rs1 寄存器(参见参考文献 1)并且 temp alu 寄存器中的位都是 0,那么我的移位操作就完成了。

否则上半部分需要第二个循环

  • 读取高位 rs1 寄存器并将其移位存储在低位 rs2 寄存器中的数量
  • 但现在用存储在 alu 临时寄存器中的值填充 rs1(不是第一个周期中的 0)
  • 移出 16 位空间的位将被丢弃
  • 结果写回较高的 rd 寄存器,并设置 rd 状态位(参见参考文献 1)

示例 1:假设 rs1 为 0x00001234,rs2 为 0x00000002(执行左移 2)

  • 首先,我读取了 rs1 和 rs2 的低 16 位,呈现 0x1234 和 0x0002。但是通过阅读我也得到了两个寄存器的状态位,在这种情况下,rs1 为 0,rs2 为 0,因为两个寄存器的高 16 位都是 0。使用给定的数据,我可以执行左移 2 . 导致0x48D0。由于没有 1 从 sll 中移出,我可以将结果存储在较低的 rd 中并将其状态位设置为 0。(这一切都在一个周期内完成)

示例 2:假设 rs1 为 0x0000D234,rs2 为 0x00000005(执行左移 5)

  • 首先我读取 rs1 和 rs2 的低 16 位,显示 0xD234 和 0x0005。但是通过阅读我也得到了两个寄存器的状态位,在这种情况下,rs1 为 0,rs2 为 0,因为两个寄存器的高 16 位都是 0。使用给定的数据,我可以执行左移 5 . 导致0x4680。但现在我将 11010 (0x1A) 移出 16 位空间。该值存储在 Alu 临时寄存器中,由于它包含 1,我必须执行另一个循环。
  • 在第二个循环中,我读取了上 rs1 和下 rs2,呈现 0x0000 和 0x0005。我再次左移 5,但现在 Alu 临时寄存器用于填充移位值。0x0000 -> 0x00__ -> 0x001A。然后将该结果写回上 rd。因此在两个 16 位周期内完成我的 32 位 sll。

示例 3:假设 rs1 为 0x01231234,rs2 为 0x00000002(执行左移 2)

  • 首先,我读取了 rs1 和 rs2 的低 16 位,呈现 0x1234 和 0x0002。但是通过阅读我也得到了两个寄存器的状态位,在这种情况下,rs1 为 1,rs2 为 0,因为 rs1 的高 16 位非零。由于 rs1 的状态位非零,即使没有 1 从低 16 位移出,我也必须执行第二个周期(参见示例 2)。从现在开始,它遵循示例 2,通过写回 rd 并为高位执行第二个周期。

我希望这些例子能提供更好的见解。



现在我想实现一个右移操作(算术和逻辑)。但是如何在最多 2 个周期内做到这一点,如果我必须先读取较低的 rs1 寄存器(包括状态位)?


谢谢阅读; 这是我在这里的第一个问题,所以请不要对我苛刻:D

4

1 回答 1

1

从阅读较高的部分开始。第一个周期您将阅读高位部分。进行右移,移出的位将出现在 tmp 寄存器的高位,并且移位的结果将被写回。第二个周期,你读取低部分,你做一个移位和一个或结果出现在 tmp 寄存器中。那么这部分的结果将被写回。

于 2020-12-05T15:31:35.647 回答