访问寄存器谁的号码存储在另一个寄存器中
Access register who's number is stored in another register
我正在为我的 类 之一开发一个项目,该项目涉及将 C 代码转换为 MIPS 程序集。我在翻译这段代码时遇到问题:
r[extract(ir,15,11)] = aluout;
基本上,r[] 是一个数组,表示 C 中的寄存器。如您所见,它根据 extract
函数的结果来确定访问哪个寄存器。 MIPS中有这样的东西吗?我能想到的唯一方法是获取我将从 extract 子例程中返回的值,并根据所有寄存器号检查它。它的 C 表示形式如下:
regNum = extract(ir, 15, 11);
if (regNum == 1) {
r[1] = aluout;
} else if (regNum == 2) {
r[2] = aluout;
} else if (regNum == 3) {
r[3] = aluout;
} ...
有什么想法吗?这是解决问题的唯一方法吗?
你应该使用自修改代码吗?例如将寄存器号放入即将 运行?
的指令中
这个问题更类似于在 C 中有多个命名变量(var1
、var2
等)并且必须 return var i
中的值.如果 i
是编译时常量,您可以使用预处理器来完成:
#define expandvar(x) var ## x // two step process to macro-expand x before concat
#define var(x) expandvar(x)
#define wantvar 4
int foo(void) { return var(wantvar); }
// int foo(constexpr int i) { ... } // nope
否则你需要一个 switch()
,你可以随心所欲地实现它(跳转 table、分支树或其他。)
寄存器没有间接级别,除非您将它们全部存储到内存中,然后在该数组中使用变量偏移量。
实现这一点的一种方法是计算跳转,而不是 table 跳转地址。你会有一系列
# calculate $t0 = set_r0 + reg_num * 8. (probably using PC as the starting point, rather than actually referencing the address of set_r0)
j $t0 # jump to one of the pairs.
set_r0:
move $r0, src
j end
move $r1, src
j end
...
如果您想检索一个寄存器的值,但破坏所有其他寄存器,
move $r30, $r31
move $r29, $r30
move $r28, $r29
...
move $r0, $r1
在您想要的 reg 被读取的地方跳到这里。
我正在为我的 类 之一开发一个项目,该项目涉及将 C 代码转换为 MIPS 程序集。我在翻译这段代码时遇到问题:
r[extract(ir,15,11)] = aluout;
基本上,r[] 是一个数组,表示 C 中的寄存器。如您所见,它根据 extract
函数的结果来确定访问哪个寄存器。 MIPS中有这样的东西吗?我能想到的唯一方法是获取我将从 extract 子例程中返回的值,并根据所有寄存器号检查它。它的 C 表示形式如下:
regNum = extract(ir, 15, 11);
if (regNum == 1) {
r[1] = aluout;
} else if (regNum == 2) {
r[2] = aluout;
} else if (regNum == 3) {
r[3] = aluout;
} ...
有什么想法吗?这是解决问题的唯一方法吗?
你应该使用自修改代码吗?例如将寄存器号放入即将 运行?
的指令中这个问题更类似于在 C 中有多个命名变量(var1
、var2
等)并且必须 return var i
中的值.如果 i
是编译时常量,您可以使用预处理器来完成:
#define expandvar(x) var ## x // two step process to macro-expand x before concat
#define var(x) expandvar(x)
#define wantvar 4
int foo(void) { return var(wantvar); }
// int foo(constexpr int i) { ... } // nope
否则你需要一个 switch()
,你可以随心所欲地实现它(跳转 table、分支树或其他。)
寄存器没有间接级别,除非您将它们全部存储到内存中,然后在该数组中使用变量偏移量。
实现这一点的一种方法是计算跳转,而不是 table 跳转地址。你会有一系列
# calculate $t0 = set_r0 + reg_num * 8. (probably using PC as the starting point, rather than actually referencing the address of set_r0)
j $t0 # jump to one of the pairs.
set_r0:
move $r0, src
j end
move $r1, src
j end
...
如果您想检索一个寄存器的值,但破坏所有其他寄存器,
move $r30, $r31
move $r29, $r30
move $r28, $r29
...
move $r0, $r1
在您想要的 reg 被读取的地方跳到这里。