0

I was reading about lock; prefix in assembly

In short, it makes sure the instruction is done without any interruptions.

But my question is why we need lock at all? what may interrupt instruction in the middle? Even when the cpu does context switch it doesn't do so when it's in the middle of an instruction. So what really is this used for?

rolen
  • 47
  • 7
  • 1
    That reasoning about interrupts makes sense, see for example [this other question](https://stackoverflow.com/q/53687178/555045), but interrupts are not the only thing to consider. – harold Aug 25 '21 at 20:47
  • For SMP machines, or for atomicity wrt. DMA or other bus-mastering by non-CPU devices. (That's why it existed in 8086, long before SMP x86 systems). – Peter Cordes Aug 25 '21 at 20:57
  • 1
    @harold interrupts are handled BETWEEN instructions – rolen Aug 26 '21 at 21:52
  • Yes, that's why harold said your reasoning is correct that atomicity wrt. interrupts is *not* the reason for using the `lock` prefix. [Taking a semaphore must be atomic. Is Pintos's sema\_down safe?](https://stackoverflow.com/q/39358761) would maybe be a better Q&A link to go into detail about interrupts vs. instruction boundaries and atomicity. (Since it does link to more about atomicity including wrt. other cores on SMP systems). But anyway, the linked duplicate is directly about what the `lock` prefix does and why it's necessary. – Peter Cordes Aug 27 '21 at 04:39

1 Answers1

4

Think about some kind of read-modify-write operation. For example, imagine we want to clear a bit. Now imagine another core is setting a bit in the same memory location at the same time. Without a LOCK prefix, the following could happen:

  1. Core A reads the memory location.
  2. Core B reads the same memory location.
  3. Core A sets a bit.
  4. Core B clears a different bit.
  5. Core A writes the result to the memory location.
  6. Core B writes the result to the same memory location.

Oops, the bit set done by core A was lost.

The LOCK prefix ensures that core B's read of the memory location cannot take place between core A's read and core A's write.

In the bad old days, the LOCK prefix pretty much locked the entire bus. This would ensure that the memory location wasn't read, but it would also ensure every other memory location wasn't read either! On modern CPUs, it just locks the cache line, allowing other cores to do all kinds of other operations, just not access that memory location (or any memory location that shares a cache line with it).

David Schwartz
  • 179,497
  • 17
  • 214
  • 278
  • Thanks, but I was interested in cases where we have exactly 1 Core, in which scenario we need to use lock; and what can really stop the instruction in the middle (as I explained above nothing seems to be able to do that). – rolen Aug 30 '21 at 06:43
  • @rolen Interrupts can stop an instruction in the middle. See [here](https://stackoverflow.com/questions/53687178/interrupting-instruction-in-the-middle-of-execution) for more. Also, it makes no difference how many cores you actually have because generally most code doesn't know how many cores it's going to execute on and *can't* be designed under the assumption that there will only be one. – David Schwartz Aug 31 '21 at 02:00