Hi, I read an example in the Documentation/memory-barriers.txt, which says
(*) On any given CPU, dependent memory accesses will be issued in order, with respect to itself. This means that for: Q = READ_ONCE(P); D = READ_ONCE(*Q); the CPU will issue the following memory operations: Q = LOAD P, D = LOAD *Q and always in that order. However, on DEC Alpha, READ_ONCE() also emits a memory-barrier instruction, so that a DEC Alpha CPU will instead issue the following memory operations: Q = LOAD P, MEMORY_BARRIER, D = LOAD *Q, MEMORY_BARRIER
As far as I understand it, linux kernel memory model (LKMM) guarantee two read operations execute in order. And if the CPU architecture offer an looser memory ordering (like Alpha), then the compiler must help to add a memory barrier after the load instruction to fufill the LKMM's standard.
However i did a test using klitmus like this
P0(int *x, int *y)
{
WRITE_ONCE(*x, 1);
smp_wmb();
WRITE_ONCE(*y, 1);
}
P1(int *x, int *y)
{
int r0;
int r1;
r0 = READ_ONCE(*y);
r1 = READ_ONCE(*x);
}
exists (1:r0=1 /\ 1:r1=0)
I run this test in an aarch64 machine, and get the result
Histogram (4 states)
1292209 :>1:r0=0; 1:r1=0;
1585 *>1:r0=1; 1:r1=0;
221437 :>1:r0=0; 1:r1=1;
484769 :>1:r0=1; 1:r1=1;
Ok
Witnesses
Positive: 1585, Negative: 1998415
It seems that these two READ_ONCE()s can be executed in any order. But if I run this test in a x86 machine, which has a more strict memory model, result 1:r0=1; 1:r1=0; disappears. So the order depends on the memory model provided by the CPU architecture? Isn't this contradicted with memory-barrier.txt?
_______________________________________________ Kernelnewbies mailing list Kernelnewbies@xxxxxxxxxxxxxxxxx https://lists.kernelnewbies.org/mailman/listinfo/kernelnewbies