ar db "Defference $"
What's the difference between
mov dx,offset ar
and
lea dx,ar
I think both are doing same work, but what is the difference between these two
ar db "Defference $"
What's the difference between
mov dx,offset ar
and
lea dx,ar
I think both are doing same work, but what is the difference between these two
In this use-case LEA and MOV do the same thing. LEA is more powerful than MOV if you want to calculate an address in a more complex way.
Lets for example say you want to get the address of the n'th character in your array, and the n is stored in bx. With MOV you have to write the following two instructions:
Mov dx, offset ar
add dx, bx
With lea you can do it with just one instruction:
lea dx, [ar + bx]
Another thing to consider here: the add dx,bx
instruction will change the status flags of the CPU. The addition done inside the lea dx, [ar + bx]
instruction on the other hand does not change the flags in any way because it is not considered an arithmetic instruction.
This is sometimes helpful if you want to preserve the flags while doing some simple calculations (address calculations are very common). Storing and restoring the flag-register is doable but a slow operation.
offset ar
- is immediate value which is calculated during translation. And lea
- is actual processor instruction "Load Effective Address" with second operand which references to memmory. –
Akins lea
is just a shift-and-add instruction. It never actually loads from memory, it just uses the addressing-mode syntax and binary encoding. In the OP's case, with lea
on an absolute address, the disp16
is the same as the imm16
for the mov
, both calculated the same way at assemble time (actually at link time when the final address is known). –
Sena lea
loads anything (reference is just a reference). I said that it is a real x86 instruction. If you do calculatons that can be done during translation you can use mov
. –
Akins lea
is the syntax used by compilers and debuggers. lea ax, [addr]
for me is something like "do something with the contents of addr
and put the result into ax
, which is not the case. –
Accountable offset
or lea
interchangeably most of the time, but working with memory models other than tiny
would cause a lot of problems since offset
is relative to the segment base address where the data is defined. –
Accountable lea dx, [ar]
. It's one byte longer than mov
, and no faster. For a static address with no register index, you only ever want LEA on x86-64, for RIP-relative (position-independent) 64-bit addressing. Otherwise, always use mov-immediate if you need a plain static address in a register. (On x86-64 in position-dependent code, mov edi, offset mydata
is still optimal, e.g. on Linux where static data is in the low 32 bits of virtual address space, so 32-bit absolute addresses can be used for efficiency.) –
Sena Quote from Assembly Language for x86 Processors, 7e, KIP R. IRVINE
It is not possible to use OFFSET to get the address of a stack parameter because OFFSET only works with addresses known at compile time. The following statement would not assemble:
mov esi,OFFSET [ebp-30] ; error
You can use them to do the same thing but, LEA
will always be better if the address is a little complex.
consider that you have the following array of chars:
ASC_TBL DB '0','1','2','3','4','5','6','7','8','9','A','B','C','D','E','F'
if you want to get the 6th element '5' you would do something like this using offset
:
mov ax, offset ASC_TBL
add ax, 5h; flags [PF] will be affected
On the other hand, if you are using the LEA
instruction you can simply use one instruction like this:
LEA ax, [ASC_TBL + 5h]; no flags are affected
Notice that:
Although using LEA
proved that it has an advantage over using offset
, it's more efficient to use offset
if the address isn't very complex to write or both of them will do the same thing with the same number of instructions.
The reason is that offset ASC_TBL
is calculated during translation - like being be preprocessed- but, LEA
is an actual processor instruction.
you can't use the offset
instruction to get the addresses that aren't known before the compilation time.
mov ax, offset ASC_TBL + 5
is legal, and shorter (3 bytes for mov ax, imm16
vs. 4 bytes for LEA: opcode + modrm + disp16). Either way the absolute address is calculated by the assembler (or linker) and embedded into the machine code. ASC_TBL+5
is a link-time constant just like ASC_TBL
; there's no +5
being done at runtime. Symbols don't really exist at runtime, except as debug metadata in the executable. The CPU isn't searching for them when running instructions that reference them. –
Sena +5
is being done at runtime, I said that the full LEA
instruction is an actual processor instruction –
Expressage mov ax, offset ASC_TBL + 5
. Well, you can. :P The assembler (and linker if you're not making a flat binary) handle it with an identical mechanism to what they use to fill in [disp16]
field in the lea
operand. The mov reg, imm16
encoding also just needs an absolute address in the machine code. LEA is worse for code-size and should never be used for this, except in 64-bit code with RIP-relative addressing to get position-independence or instead of 64-bit absolute addresses. –
Sena © 2022 - 2024 — McMap. All rights reserved.
lea
is an instruction andoffset
is not – Tellurize