5

I have read the following in the book Programming from the Ground Up:

Processors have a number of different ways of accessing data, known as addressing modes. The simplest mode is immediate mode, in which the data to access is embedded in the instruction itself. For example, if we want to initialize a register to 0, instead of giving the computer an address to read the 0 from, we would specify immediate mode, and give it the number 0.

In the register addressing mode, the instruction contains a register to access, rather than a memory location. The rest of the modes will deal with addresses.

Does that mean that for example the instruction mov eax, 123 is in both immediate mode and register addressing mode?

user8240761
  • 975
  • 1
  • 10
  • 15
  • 1
    What is on the right of the comma determines the addressing mode. So immediate here. Compare to mov eax,ebx, that's register addressing mode. – Hans Passant Jul 01 '17 at 16:50
  • @Hans Passant So *Peter Cordes*'s answer is wrong? – user8240761 Jul 01 '17 at 19:58
  • 2
    @HansPassant: What about `mov [eax+ecx], 123`? I think it just doesn't make sense to talk about the whole instruction having one addressing mode. Each operand has its own addressing mode. – Peter Cordes Jul 02 '17 at 08:41

2 Answers2

8

It's not the whole instruction that has a certain addressing mode, it's each operand separately. In your mov eax, 123 example, you'd say that the source is an immediate operand, and the destination is a register operand.

Or you could say that the machine code for that instruction will use the mov r, imm32 encoding of mov, if you want to talk about the form the whole instruction takes. (There's also a mov r/m, imm32 form of mov, but it's longer so a good assembler will only pick that if the destination actually is memory).

However, when one of the operands is a register, you could for convenience and brevity say "the instruction uses a [base+index] addressing mode" if you want. But really it's the memory operand that you're talking about, not really the whole instruction. Especially if you count register and immediate as "addressing modes", even though there is no memory address involved.


Moreover, usually when people say "addressing mode", they're talking about a memory address. Technically in x86, most instructions have one register and one register/memory operand, so the difference between add eax, ecx and add eax, [ecx] is only I think 1 bit in the mod/rm byte (which follows the opcode).

Some instructions have two memory operands. For example, push qword [rdi + rax*8] explicitly loads from [rdi + rax*8] and implicitly stores to [rsp]. Another example are the string instructions movs and cmps, which use [rdi] and [rsi] implicitly.

But no instruction has two general r/m operands that let you use an arbitrary choice of the normal addressing modes. So an x86 instruction has at most one mod/rm byte.


It's debatable whether an immediate operand should be called an "addressing mode", because the data doesn't come from anywhere. It's part of the instruction. Also, the immediate-operand form of an instruction has a different opcode from the reg, reg/mem form.

Also note that most integer instructions that can have a memory source or memory destination have two opcodes: one for op r/m, r and one for op r, r/m. (e.g., see the ref manual entry for and, and more links to docs in the tag wiki.) Anyway, and eax, ecx can be encoded with either of the two opcodes, and it's up to the assembler to pick. The choice makes no difference for performance.

Peter Cordes
  • 328,167
  • 45
  • 605
  • 847
  • *Hans Passant* says in his comment on my question: *"What is on the right of the comma determines the addressing mode. So immediate here. Compare to mov eax,ebx, that's register addressing mode."*. So I don't know if your answer is correct or his answer is correct! – user8240761 Jul 02 '17 at 08:34
  • @user8240761: Don't worry too much about terminology. Different books / people use different terms to describe the same thing. But notice that nothing in the text you quoted from PGU says that the whole instruction has an addressing mode. (I have skimmed parts of PGU, and recommend it. The author seems to think about computers and asm in a sensible way from what I've seen.) – Peter Cordes Jul 02 '17 at 08:43
2

Processors have a number of different ways of accessing data, known as addressing modes.

This sentence talks about "processors" in general, not about a certain processor type.

I think this is too generalized because you'll always find an exception to sentences like this. Indeed when looking on modern CPUs you'll find more exceptions than CPUs that follow this rule.

Indeed for "simple" CPUs like the 6800 or the 6502 the instruction itself has one addressing mode:

lda $3A

... for example uses "zero-page" or "direct" addressing mode.

Other CPUs indeed definitely had two different addressing modes in one instruction. The "move" instruction of the 68000 for example:

move.w ($123).w, (a3, $4567)

For the x86 CPU it is even more difficult to say:

In the 6800, the instruction that can be compared to mov al, bl is named tba (with no arguments) while mov al, [0x123] was named lda $123.

So you could argue that mov al, bl is an instruction without argument (addressing mode implied - because the instruction is written as movblal without any operands on other CPUs) and mov al, [0x123] is an instruction with one memory address argument (absolute addressing mode - because the instruction is written as ldal 0x123 with one operand on other CPUs).

(The only instructions of the original 8086 not allowing you to argue like this seem to be the instructions having m8, imm8 and m16, imm16 addressing modes such as mov word ptr [123], 567 or add byte ptr [123], 45.)

Of course you may also argue that the instruction is mov and that al and bl are two arguments of the mov al, bl instruction.

So it depends on your argumentation if the instruction mov al, bl is an instruction with the addressing mode "implied" (= no operands) or "register-to-register".

Martin Rosenau
  • 17,897
  • 3
  • 19
  • 38
  • Your m68k example is equivalent to x86 `mov r/m16, imm16`, i.e. a memory dest operand and an immediate source operand. If you want a really exotic example, VAX instructions can have arbitrary addressing modes for each operand, so e.g. both operands can be memory, probably with post-increment addressing or something. (In x86, some instructions have two memory operands, but at least one of them is implicit. None take two `[base + idx*scale + displacement]` operands.) – Peter Cordes Jul 02 '17 at 15:02
  • I'm not sure [which form of `mov`](http://felixcloutier.com/x86/MOV.html) you're talking about with `mov byte ptr`, or what your point is in that paragraph. Most 8086 ALU instructions have a `op [mem], immediate` form (using an `op r/m, imm8` or `...imm16` opcode with the mod/rm byte encoding a memory addressing mode instead of register). – Peter Cordes Jul 02 '17 at 15:08
  • @PeterCordes I wanted to write "implied" (= no arguments). I corrected that. – Martin Rosenau Jul 02 '17 at 16:35
  • @PeterCordes The m68k instruction is equivalent to `mov word ptr [ecx+0x4567], word ptr [0x123]` which would be `mov m16, m16` and not `mov m16, imm16`. I don't know about amd64 but i386 did not have such an instruction (with the exception of `movsw`). – Martin Rosenau Jul 02 '17 at 16:43
  • Ah right, `()` parens in m68k are a dereference, sorry. I forgot that m68k had a flexible memory-to-memory move, so I just assumed that must be the syntax for an immediate >.<. x86's [`movsw` is implicitly `movsw [es:edi], [esi]`](http://felixcloutier.com/x86/MOVS:MOVSB:MOVSW:MOVSD:MOVSQ.html), with no choice of addressing mode for either operand (except for segment overrides for `esi`). And no, AMD64 didn't introduce any more-CISC instructions. – Peter Cordes Jul 03 '17 at 01:29
  • I'm still [not clear on the 2nd-last paragraph](https://stackoverflow.com/questions/44861768/can-an-instruction-be-in-two-addressing-modes-at-the-same-time/44869390?noredirect=1#comment76722908_44869390). What do you mean by `mov word ptr`? – Peter Cordes Jul 03 '17 at 01:33