What's the purpose of the LEA instruction?

assembly, x86, x86-16, x86-64

Solution

As others have pointed out, LEA (load effective address) is often used as a "trick" to do certain computations, but that's not its primary purpose. The x86 instruction set was designed to support high-level languages like Pascal and C, where arrays—especially arrays of ints or small structs—are common. Consider, for example, a struct representing (x, y) coordinates:

struct Point
{
     int xcoord;
     int ycoord;
};

Now imagine a statement like:

int y = points[i].ycoord;

where `points[]` is an array of `Point`. Assuming the base of the array is already in `EBX`, and variable `i` is in `EAX`, and `xcoord` and `ycoord` are each 32 bits (so `ycoord` is at offset 4 bytes in the struct), this statement can be compiled to:

MOV EDX, [EBX + 8*EAX + 4]    ; right side is "effective address"

which will land `y` in `EDX`. The scale factor of 8 is because each `Point` is 8 bytes in size. Now consider the same expression used with the "address of" operator &:

int *p = &points[i].ycoord;

In this case, you don't want the value of `ycoord`, but its address. That's where `LEA` (load effective address) comes in. Instead of a `MOV`, the compiler can generate

LEA ESI, [EBX + 8*EAX + 4]

which will load the address in `ESI`.

Problem

For me, it just seems like a funky MOV. What's its purpose and when should I use it?

Original source

Related problems