问题
I'm trying to figure out a reason for the scale factor not being present in the x86 16-bit addressing modes (MASM assembly). While the 32-bit and 64-bit addressing modes have a scale factor. Is there an actual reasoning behind this or it doesn't need it? I would appreciate it if you could explain.
All possible ways different components can be combined to create an effective address:
Differences between 16- and 32-bit addressing modes
回答1:
16-bit addressing modes only allow a single ModRM byte to encode the register (3 bits), mode (2 bits) and the register/memory operand (3 bits), so there's no room to encode a scale factor, or even to let arbitrary registers be bases or indices. NASM x86 16-bit addressing modes lists them all, it's not a long list! Just subsets of (BP|BX) + (DI|SI) + disp0/8/16
. Remember that in an instruction like add cx, [bx+si]
, the register destination needs the 3 bit /r
field in ModRM to encode which of the 8 GP registers.
(The 2-bit "mode" signals whether it's a register or memory, e.g. add bx, cx
vs. add [bx], cx
, and how many immediate displacement bytes there are: disp8 / disp16 or no displacement.)
In 32/64-bit addressing modes, the r/m field in ModRM can be an escape code that signals the presence of a SIB byte (Scale/Index/Base), which gives room to encode scaled-index addressing modes with a 2-bit shift count.
And also enough coding space to let us use any register as a base, and any register (except ESP) as an index. So 32-bit addressing modes make the registers more orthogonal. See rbp not allowed as SIB base? for the details on the escape sequences, e.g. [esp]
always needs a SIB byte because the encoding that would mean base=ESP is the escape code for the presence of a SIB byte.
See https://wiki.osdev.org/X86-64_Instruction_Encoding#32.2F64-bit_addressing_2 or the ModRM/SIB tables in Intel's manuals for more details.
来源:https://stackoverflow.com/questions/55657904/why-dont-x86-16-bit-addressing-modes-have-a-scale-factor-while-the-32-bit-vers