Richard Earnshaw wrote:
Consider a non-load/store machine that has a floating-point operation that
can add a value in memory to another register:
fadd Rd, Rs, (mem) // Rd = Rs + (mem)
Now if (mem) is volatile and the value returned is a signalling NaN then
the trap handler has no way to recover that value except by
dereferencing (mem) again. That means we access (mem) twice.
Or consider any type of 3-operand instruction where both source operands
come from memory. If the first access is volatile and the second not
(but it page-faults) then, unless the machine has some way to cache the
first access, it will have to be repeated when the page fault handler
returns.
The above cases simply do not occur on any common machine, so perhaps
you would have to do strange things in those cases, but nothing like
the drastic generalization you first gave. Generally even on machines
with these kind of instructions it is better to do separate loads
anyway.
Finally, but probably less likely, consider a machine instruction that
can read multiple values from memory (ARM has one -- ldm). If an
address in the list is volatile and the list crosses a page boundary,
the instruction may trap part way through execution. In that case the
OS may have to unwind part of the instruction and retry it -- it can't
safely do that if there is a volatile access in the list.
Well don't use this instruction if one of the addresses is volatile.
That seems right in any case (it seems wrong to do other than generate
a single load/store for volatile anyway, this seems like improper
combining).
R.