Assembly 用于分支的机器代码

Assembly 用于分支的机器代码,assembly,branch,mips,memory-address,machine-code,Assembly,Branch,Mips,Memory Address,Machine Code,对于分支指令如何转换为机器代码,我有点困惑。我在书中读到,分支if equal指令是B型指令,其格式如下: 操作码reg1 reg2地址+偏移量 65516 在我的教科书中,有一个问题,我看到一个程序,我被告知该程序加载在0x4321ABC8,如下所示: L1: sw $t0,3000($t1) addi $s1,$t1,-6 beq $t0,$t1,L1 如您所见,第三行代码是分支(如果相等) 我正在尝试将这个程序转换成二进制(或十六进制)在分支if equal指令中,

对于分支指令如何转换为机器代码,我有点困惑。我在书中读到,分支if equal指令是B型指令,其格式如下:

操作码reg1 reg2地址+偏移量 65516

在我的教科书中,有一个问题,我看到一个程序,我被告知该程序加载在0x4321ABC8,如下所示:

L1:   sw   $t0,3000($t1)

  addi $s1,$t1,-6

  beq  $t0,$t1,L1
如您所见,第三行代码是分支(如果相等)

我正在尝试将这个程序转换成二进制(或十六进制)在分支if equal指令中,我不太清楚应该在地址+偏移量字段中输入什么。

首先我想答案是

基址(0x4321ABC8), 加上程序计数器所在基址指令数的4倍(4*2=8),
然后,偏移量减去4,即原始基址0x4321ABC8

问题是0x4321ABC8太大,无法放入指令的16位偏移量空间

然后我想答案应该是只包含偏移量(应该是-8),但是如果是这样的话,我不知道为什么书中的问题会告诉我程序是在0x4321ABC8加载的


任何帮助都将不胜感激

偏移量实际上编码为字数(或指令,如果您愿意),因此不需要乘以字数(4字节)。此外,此偏移量与已更新的
PC
,即以下指令的地址有关。因此,偏移量是
-3

但这并不是故事的全部。MIPS确实有分支延迟槽,但它们通常对程序员隐藏。如果汇编程序可以在不改变代码含义的情况下填充这些代码,那么它可能会尝试填充这些代码。如果将示例输入到真实的汇编程序中(在本例中为
gas
),它会将
addi$s1,$t1,-6
移动到分支的延迟槽中,因为该指令的结果未在以下情况下使用:

00000000 <L1>:
   0:   ad280bb8        sw      t0,3000(t1)
   4:   1109fffe        beq     t0,t1,0 <L1>
   8:   2131fffa        addi    s1,t1,-6
00000000:
0:ad280bb8 sw T03000(t1)
4:1109fffe beq t0,t1,0
8:2131FFA附加s1,t1,-6
在此交换顺序中,编码偏移量为
-2
,您也可以从
fffe
值中看到

PS:如果您使用的是
SPIM
请注意,它已经知道了偏移量编码的一个问题。也就是说,它使用当前指令的地址,而不是下一条指令的地址


附言2:仅仅因为他们给了你一些额外的信息,并不意味着你必须使用它。这是一种常见的迷惑贫困学生的伎俩;)

偏移量实际上编码为字数(或指令,如果您愿意),因此不需要乘以字数(4字节)。此外,此偏移量与已更新的
PC
,即以下指令的地址有关。因此,偏移量是
-3

但这并不是故事的全部。MIPS确实有分支延迟槽,但它们通常对程序员隐藏。如果汇编程序可以在不改变代码含义的情况下填充这些代码,那么它可能会尝试填充这些代码。如果将示例输入到真实的汇编程序中(在本例中为
gas
),它会将
addi$s1,$t1,-6
移动到分支的延迟槽中,因为该指令的结果未在以下情况下使用:

00000000 <L1>:
   0:   ad280bb8        sw      t0,3000(t1)
   4:   1109fffe        beq     t0,t1,0 <L1>
   8:   2131fffa        addi    s1,t1,-6
00000000:
0:ad280bb8 sw T03000(t1)
4:1109fffe beq t0,t1,0
8:2131FFA附加s1,t1,-6
在此交换顺序中,编码偏移量为
-2
,您也可以从
fffe
值中看到

PS:如果您使用的是
SPIM
请注意,它已经知道了偏移量编码的一个问题。也就是说,它使用当前指令的地址,而不是下一条指令的地址


附言2:仅仅因为他们给了你一些额外的信息,并不意味着你必须使用它。这是一种常见的迷惑贫困学生的伎俩;)

偏移量实际上编码为字数(或指令,如果您愿意),因此不需要乘以字数(4字节)。此外,此偏移量与已更新的
PC
,即以下指令的地址有关。因此,偏移量是
-3

但这并不是故事的全部。MIPS确实有分支延迟槽,但它们通常对程序员隐藏。如果汇编程序可以在不改变代码含义的情况下填充这些代码,那么它可能会尝试填充这些代码。如果将示例输入到真实的汇编程序中(在本例中为
gas
),它会将
addi$s1,$t1,-6
移动到分支的延迟槽中,因为该指令的结果未在以下情况下使用:

00000000 <L1>:
   0:   ad280bb8        sw      t0,3000(t1)
   4:   1109fffe        beq     t0,t1,0 <L1>
   8:   2131fffa        addi    s1,t1,-6
00000000:
0:ad280bb8 sw T03000(t1)
4:1109fffe beq t0,t1,0
8:2131FFA附加s1,t1,-6
在此交换顺序中,编码偏移量为
-2
,您也可以从
fffe
值中看到

PS:如果您使用的是
SPIM
请注意,它已经知道了偏移量编码的一个问题。也就是说,它使用当前指令的地址,而不是下一条指令的地址


附言2:仅仅因为他们给了你一些额外的信息,并不意味着你必须使用它。这是一种常见的迷惑贫困学生的伎俩;)

偏移量实际上编码为字数(或指令,如果您愿意),因此不需要乘以字数(4字节)。此外,此偏移量与已更新的
PC
,即以下指令的地址有关。因此,偏移量是
-3

但这并不是故事的全部。MIPS确实有分支延迟槽,但它们通常对程序员隐藏。如果汇编程序能够在不改变其含义的情况下填充这些内容,那么它可能会尝试填充这些内容