On Tue, Sep 15, 2015 at 1:09 PM, Mark Thomas <ma...@apache.org> wrote:
> On 15/09/2015 20:42, Caldarale, Charles R wrote: > >> From: Mark Thomas [mailto:ma...@apache.org] > >> Subject: Re: RV-Predict bugs > > > >> Putting it into my own words to check my understanding: > > > >> - The two reads in T2 may be re-ordered because, in T2, there is nothing > >> that requires a happens-before relationship between the two reads > > > > Depends on what was really meant by the ??? notation. If it were > another reference to st_200, then the example ignores the potential write > to st_200. > > > >> - If T2 was executing in isolation the order of the reads wouldn't > >> matter > > > > Correct, assuming there is no write in T2's control flow. > > > >> - However, T1 is writing. > > > >> So if the writes > > > > I'll assume you meant "reads" there. > > I'd did. Thanks. > > >> in T2 are re-ordered and the write from T1 takes place between them the > T2 > >> read for the line 'st_200 == null' could return a non-null value for > st_200 > >> (the value after the write from T1) while the read for the line 'return > >> st_200;' could return null (the value from before the write in T1). > > > > No - that would violate program order (intra-thread semantics). The > compiler cannot legally move the read for "return st_200" to a point before > the potential write to st_200. The CPU can speculatively read for the > return value, but must discard such speculation if a write were to occur > (or use store forwarding to update the read). > > Thanks for sticking with me on this. I'm finding it hugely helpful. I > think I need a few more references to make things clearer so I'm going > to restate the problem. > > st_200 is non-volatile > > L1 if (st_200 == null ) { > L2 st_200 = sm.getString("sc.200"); > L3 } > L4 return st_200; > > Ln=Line n > Tx=Thread x > Rn=Read at line n > Wn=Write at line n > > So T2 has two reads, T2R1 and T2R4. > Depending on the value read for T2R1 there may be a write at T2W2. > If there is a write there is a happens before relationship between T2R1 > and T2R4. > > Consider the following sequence > > T2R4 (out of order read returns null) > T1R1 (returns null) > T1W2 (writes non-null value) > T1R4 (reads new non-null value) > T2R1 (reads new non-null value) > > Because T2R1 reads a non-null value there is no write in T2. > Therefore there is no happens-before relationship between T2R1 and T2R4 > because there is no intervening write in that thread (the write happens > in T1). > Therefore the re-ordering is allowed to happen. > And we get the unexpected result. > > Or > > The write at T1W2 is sufficient to enforce the happens before > relationship between T2R1 and T2R4. In which case what is the point of > volatile? What do I gain by using it? > Again, as I mentioned in my previous message, I am afraid this is not the correct way to use HB relationship. To make things more clear, I steal this transformation from Jeremy Manson's article I sent before: r1 = hash; if (hash == 0) { r1 = hash = // calculate hash } return r1; This is a legal transformation w.r.t JMM (though really impractical) and it is easy to see that this method can return 0 under certain interleaving. Yilong > A still slightly confused, > > Mark > > > --------------------------------------------------------------------- > To unsubscribe, e-mail: dev-unsubscr...@tomcat.apache.org > For additional commands, e-mail: dev-h...@tomcat.apache.org > >