寄存器中存储的数字有多大
How large numbers are stored in registers
这是一个基本问题,但假设我想将寄存器 $t2、$t3 和 $t4 中的 3 个数字相乘。假设地说,假设每个寄存器只能容纳 8 位,当我们将三个数字相乘时,结果可能大于 8 位。如果大于8位,如果每个寄存器只能容纳8位,结果如何存储在寄存器$t0中?
在那种特定情况下,算术单元将设置 overflow flag
不行。这就是众所周知的算术溢出.
有时您可以更改运算符的顺序来避免此类溢出。 F.e。相反 if (a + b > INT_MAX) ...
你可以写 if (a > INT_MAX - b) ...
等等。
有时您应该使用 int64
而不是 int32
,或者 double
而不是 float
。
有时你应该使用像 GMP 这样的大数库。
通常 CPU 有某种指令将两个寄存器相乘并给出两倍大的结果,分布在多个寄存器中。这是实现扩展精度算法所必需的。
例如,在 amd64 上,要将两个 64 位数字相乘并得到 128 位结果,您可以这样做:
mov rax, qword ptr [t2]
mul qword ptr [t3]
; the result is now in rdx : rax
mov qword ptr [result], rax
mov qword ptr [result + 8], rdx
要将三个 64 位数字相乘并得到 192 位结果,您必须通过将上述相关部分相乘并将它们相加来实现扩展精度乘法。
这是一个基本问题,但假设我想将寄存器 $t2、$t3 和 $t4 中的 3 个数字相乘。假设地说,假设每个寄存器只能容纳 8 位,当我们将三个数字相乘时,结果可能大于 8 位。如果大于8位,如果每个寄存器只能容纳8位,结果如何存储在寄存器$t0中?
在那种特定情况下,算术单元将设置 overflow flag
不行。这就是众所周知的算术溢出.
有时您可以更改运算符的顺序来避免此类溢出。 F.e。相反 if (a + b > INT_MAX) ...
你可以写 if (a > INT_MAX - b) ...
等等。
有时您应该使用 int64
而不是 int32
,或者 double
而不是 float
。
有时你应该使用像 GMP 这样的大数库。
通常 CPU 有某种指令将两个寄存器相乘并给出两倍大的结果,分布在多个寄存器中。这是实现扩展精度算法所必需的。
例如,在 amd64 上,要将两个 64 位数字相乘并得到 128 位结果,您可以这样做:
mov rax, qword ptr [t2]
mul qword ptr [t3]
; the result is now in rdx : rax
mov qword ptr [result], rax
mov qword ptr [result + 8], rdx
要将三个 64 位数字相乘并得到 192 位结果,您必须通过将上述相关部分相乘并将它们相加来实现扩展精度乘法。