符号扩展
当 32 位有符号整数为负时,其最高位等于 1。 当此 32 位有符号整数强制转换为 64 位数字时,可将高位设置为零 (保留数字) 的无符号整数和十六进制值,或者可将高位设置为 1 (保留数字) 的有符号值。 后一种情况称为 符号扩展。
调试器在 MASM 表达式、C++ 表达式中和显示数字时遵循不同的签名扩展规则。
MASM 表达式中的签名扩展
在某些情况下,MASM 表达式计算器会自动对数字进行 签名 。 符号扩展只能影响从0x80000000到0xFFFFFFFF的数字。 也就是说,符号扩展仅影响可在 32 位中写入且高位等于 1 的数字。
当调试器将其视为 64 位数字时,该数字0x12345678始终保持0x00000000 12345678。 另一方面,当0x890ABCDE被视为 64 位值时,它可能仍0x00000000'890ABCDE,或者 MASM 表达式计算器可能会签署扩展它以0xFFFFFFFF'890ABCDE。
从 0x80000000 到 0xFFFFFFFF 的数字根据以下条件进行符号扩展:
数字常量永远不会在用户模式下进行签名扩展。 在内核模式下,数字常量是符号扩展的,除非它在低字节之前包含重音 ( ` ) 。 例如,在内核模式下,十六进制数 EEAA1122 和 00000000EEAA1122 是符号扩展,但 0000000'EEAA1122 和 0'EEAA1122 不是。
在两种模式下,32 位寄存器都是扩展的签名。
伪寄存器始终存储为 64 位值。 在评估它们时,它们不是符号扩展。 为伪寄存器 分配 值时,将根据标准 C++ 条件计算所使用的表达式。
表达式中的单个数字和寄存器可以进行符号扩展,但在表达式计算过程中没有其他计算是符号扩展。 因此,可以使用以下语法屏蔽数字的高位或寄存器。
( 0x0`FFFFFFFF & expression )
C++ 表达式中的签名扩展
当调试器计算 C++ 表达式时,以下规则适用:
寄存器和伪寄存器永远不会进行签名扩展。
所有其他值的处理方式与 C++ 处理其类型的值完全相同。
显示 Sign-Extended 和 64 位数字
除 32 位和 16 位寄存器外,所有数字都以 64 位值的形式存储在调试器内部。 但是,当数字满足特定条件时,调试器会在命令输出中将其显示为 32 位数字。
调试器使用以下条件来确定如何显示数字:
如果数字的高 32 位都是零 (也就是说,如果该数字从 0x00000000'00000000 到 0x00000000'FFFFFFFFFF) ,则调试器会将该数字显示为 32 位数字。
如果数字的高 32 位都是 32 位,并且低 32 位的最高位也是一个 (即,如果该数字从 0xFFFFFFFF'80000000 到 0xFFFFFFFF'FFFFFFFF) ,则调试器假定该数字是一个符号扩展的 32 位数字,并将其显示为 32 位数字。
如果前两个条件不适用 (即,如果数字从 0x00000001'00000000 到 0xFFFFFFFF'7FFFFFFF) 则调试器会将该数字显示为 64 位数字。
由于这些显示规则,当数字显示为从 0x80000000 到 0xFFFFFFFF 的 32 位数字时,无法确认高 32 位是全部为 1 还是全部为零。 若要区分这两种情况,必须对数字 (执行额外的计算,例如屏蔽一个或多个高位,) 显示结果。