On Thu, Mar 04, 2021 at 09:26:31AM +0800, Boqun Feng wrote: > On Wed, Mar 03, 2021 at 03:22:46PM -0500, Alan Stern wrote: > > Which brings us back to the case of the > > > > dep ; rfi > > > > dependency relation, where the accesses in the middle are plain and > > non-racy. Should the LKMM be changed to allow this? > > > > For this particular question, do we need to consider code as the follow? > > r1 = READ_ONCE(x); // f > if (r == 1) { > local_v = &y; // g > do_something_a(); > } > else { > local_v = &y; > do_something_b(); > } > > r2 = READ_ONCE(*local_v); // e > > , do we have the guarantee that the first READ_ONCE() happens before the > second one? Can compiler optimize the code as: > > r2 = READ_ONCE(y); > r1 = READ_ONCE(x); Well, it can't do that because the compiler isn't allowed to reorder volatile accesses (which includes READ_ONCE). But the compiler could do: r1 = READ_ONCE(x); r2 = READ_ONCE(y); > if (r == 1) { > do_something_a(); > } > else { > do_something_b(); > } > > ? Although we have: > > f ->dep g ->rfi ->addr e This would be an example of a problem Paul has described on several occasions, where both arms of an "if" statement store the same value (in this case to local_v). This problem arises even when local variables are not involved. For example: if (READ_ONCE(x) == 0) { WRITE_ONCE(y, 1); do_a(); } else { WRITE_ONCE(y, 1); do_b(); } The compiler can change this to: r = READ_ONCE(x); WRITE_ONCE(y, 1); if (r == 0) do_a(); else do_b(); thus allowing the marked accesses to be reordered by the CPU and breaking the apparent control dependency. So the answer to your question is: No, we don't have this guarantee, but the reason is because of doing the same store in both arms, not because of the use of local variables. Alan