<p dir="ltr">Yes, but where does it say that #4 is valid and under what conditions? Presumably in this example, shared is read somewhere else as well (different method perhaps) - else why are we calling it shared? Only writers? That's uninteresting.</p>

<p dir="ltr">Sent from my phone</p>
<div class="gmail_quot<blockquote class=" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">
  
    
  
  <div bgcolor="#FFFFFF" text="#000000">
    Yes.<br>
    <br>
    1. Unroll the loop.<br>
    2. Reorder non-volatile accesses to go ahead of volatile stores<br>
    3. Now all volatile stores from all iterations are one after the
    other<br>
    4. Multiple stores to the same location can be fused, even if they
    are volatile stores<br>
    <br>
    If you want a store in every iteration, need a volatile load
    somewhere between the stores.<br>
    <br>
    Alex<br>
    <br>
    <br>
    <div>On 17/04/2013 18:01, Vitaly Davidovich
      wrote:<br>
    </div>
    <blockquote type="cite">
      <p dir="ltr">Are you sure about fusion if shared is volatile?
        Maybe theoretically it's possible but the analysis (and risk)
        the JVM would have to do to make that transform is probably
        impractical.  Intuitively, if I mark something volatile, I
        expect almost verbatim code to execute.</p>
      <p dir="ltr">By instructions, I mean loads and stores since that's
        what actually matters for these scenarios.</p>
      <div class="gmail_quote">On Apr 17, 2013 12:55 PM, "oleksandr
        otenko" <<a href="mailto:oleksandr.otenko@oracle.com" target="_blank">oleksandr.otenko@oracle.com</a>>
        wrote:<br type="attribution">
        <blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">
          <div bgcolor="#FFFFFF" text="#000000"> Yes, but not any
            instructions - only those that have temporal relationship.<br>
            <br>
            So, for example, in this case even if shared is volatile,
            then volatile stores can still be moved out of the loop and
            fused into a single volatile store.<br>
            <br>
            Alex<br>
            <br>
            <br>
            <div>On 17/04/2013 17:43, Vitaly Davidovich wrote:<br>
            </div>
            <blockquote type="cite">
              <p dir="ltr">Immediate means store is made globally
                visible before subsequent instructions complete/retire.</p>
              <div class="gmail_quote">On Apr 17, 2013 12:26 PM,
                "oleksandr otenko" <<a href="mailto:oleksandr.otenko@oracle.com" target="_blank">oleksandr.otenko@oracle.com</a>>
                wrote:<br type="attribution">
                <blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">
                  <div bgcolor="#FFFFFF" text="#000000"> <font face="Helvetica, Arial, sans-serif">What is this
                      "immediate" anyway?<br>
                      <br>
                      It is actually "before anything else in this
                      thread that's temporal"<br>
                      <br>
                      Alex<br>
                      <br>
                      <br>
                    </font>
                    <div>On 17/04/2013 16:44, Vitaly Davidovich wrote:<br>
                    </div>
                    <blockquote type="cite">
                      <p dir="ltr">I actually expect that the optimizer
                        *would* do this transformation on plain fields
                        (provided it doesn't break intra-thread
                        semantics, of course) because it's a perf gain.</p>
                      <p dir="ltr">Don't know how much JIT can see
                        through println as it ultimately calls into
                        runtime and OS functions, so I'd guess it
                        doesn't know enough or simply plays conservative
                        here.  However, Nathan's point is still valid
                        even if example isn't necessarily the best one. 
                        If you had "pure" java code instead of an I/O
                        call that took significant time to execute, the
                        write would be delayed.  I'm not sure why that
                        matters though for benign data races.  Clearly
                        if you need immediate visibility, you code for
                        that specifically.</p>
                      <div class="gmail_quote">On Apr 17, 2013 11:32 AM,
                        "Zhong Yu" <<a href="mailto:zhong.j.yu@gmail.com" target="_blank">zhong.j.yu@gmail.com</a>>
                        wrote:<br type="attribution">
                        <blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex"> On Wed, Apr 17, 2013
                          at 1:38 AM, Nathan Reynolds<br>
                          <<a href="mailto:nathan.reynolds@oracle.com" target="_blank">nathan.reynolds@oracle.com</a>>

                          wrote:<br>
                          > Couldn't JIT hoist the non-volatile
                          writes out of the loop?<br>
                          <br>
                          Certainly, sorry if my statement sounds too
                          absolute.<br>
                          <br>
                          > For example, the following code...<br>
                          <br>
                          But, is this a valid example? Can JMM really
                          reorder around<br>
                          System.out.println()?<br>
                          <br>
                          > for (i = 0; i < 1_000_000_000; i++)<br>
                          > {<br>
                          >     System.out.println(i);<br>
                          >     shared = 2 * i;<br>
                          > }<br>
                          ><br>
                          > ... could be transformed into ...<br>
                          ><br>
                          > for (i = 0; i < 1_000_000_000; i++)<br>
                          > {<br>
                          >     System.out.println(i);<br>
                          > }<br>
                          ><br>
                          > shared = 2 * 1_000_000_000;<br>
                          ><br>
                          > ... If so, then the non-volatile write
                          may not happen for a very long time.<br>
                          ><br>
                          > Nathan Reynolds | Architect | <a href="tel:602.333.9091" value="+16023339091" target="_blank">602.333.9091</a><br>
                          > Oracle PSR Engineering | Server
                          Technology<br>
                          > On 4/16/2013 10:27 PM, Zhong Yu wrote:<br>
                          ><br>
                          > On Tue, Apr 16, 2013 at 8:51 PM,
                          thurstonn <<a href="mailto:thurston@nomagicsoftware.com" target="_blank">thurston@nomagicsoftware.com</a>><br>
                          > wrote:<br>
                          ><br>
                          > Vitaly Davidovich wrote<br>
                          ><br>
                          > The code works as-is.<br>
                          ><br>
                          > Absolutely.  volatile is not needed for
                          correctness<br>
                          ><br>
                          > Vitaly Davidovich wrote<br>
                          ><br>
                          > Why?<br>
                          ><br>
                          > Well, for performance reasons given the
                          'undefined/indefinite' visibility of<br>
                          > #hash to other threads.<br>
                          > At least according to the JMM (which has
                          nothing to say about CPU cache<br>
                          > coherency), it is *possible* that each
                          distinct thread that invoked<br>
                          > #hashCode() *could* result in a
                          recalculation of the hash.<br>
                          ><br>
                          > In practice though, application threads
                          contain very frequent<br>
                          > synchronization actions, or other
                          operations that force VM to<br>
                          > flush/reload. So it won't take very long
                          for any non-volatile write in<br>
                          > one thread to become visible to other
                          threads.<br>
                          ><br>
                          > Imagine a long-lived Map<String,
                          ?>; and many threads accessing the map's<br>
                          > keyset and for some unknown reason
                          invoking #hashCode() on each key.<br>
                          > If #hash was declared volatile, although
                          there is no guarantee that #hash<br>
                          > would only be calculated once, it is
                          guaranteed that once a write to main<br>
                          > memory was completed, every *subsequent*
                          (here meaning after the write to<br>
                          ><br>
                          > In JMM though, we cannot even express
                          this guarantee. Say we have<br>
                          > threads T1...Tn, each thread Ti burns `i`
                          seconds CPU time first, then<br>
                          > volatile-reads #hash, and if it's 0,
                          calculates and volatile-writes<br>
                          > #hash which takes 100 ns. We can find no
                          guarantee from JMM that<br>
                          > there's only one write; it's legal that
                          every thread sees 0 from the<br>
                          > volatile read.<br>
                          ><br>
                          > Zhong Yu<br>
                          ><br>
                          > main memory) read no matter from which
                          thread would see #hash != 0 and<br>
                          > therefore skip the calculation.<br>
                          ><br>
                          ><br>
                          ><br>
                          > Vitaly Davidovich wrote<br>
                          ><br>
                          > String is too high profile (especially<br>
                          > hashing it) to do the "naive" thing.<br>
                          ><br>
                          > Nothing wrong with being naive; naive can
                          be charming.<br>
                          ><br>
                          ><br>
                          > Vitaly Davidovich wrote<br>
                          ><br>
                          > Also, some architectures pay a<br>
                          > penalty for volatile loads and you'd
                          incur that each time.<br>
                          ><br>
                          > Fair point; the JDK authors only get one
                          shot and they can't assume that<br>
                          > volatile reads are cheap<br>
                          ><br>
                          ><br>
                          ><br>
                          ><br>
                          ><br>
                          > --<br>
                          > View this message in context:<br>
                          > <a href="http://jsr166-concurrency.10961.n7.nabble.com/On-A-Formal-Definition-of-Data-Race-tp9408p9466.html" target="_blank">http://jsr166-concurrency.10961.n7.nabble.com/On-A-Formal-Definition-of-Data-Race-tp9408p9466.html</a><br>

                          > Sent from the JSR166 Concurrency mailing
                          list archive at Nabble.com.<br>
                          >
                          _______________________________________________<br>
                          > Concurrency-interest mailing list<br>
                          > <a href="mailto:Concurrency-interest@cs.oswego.edu" target="_blank">Concurrency-interest@cs.oswego.edu</a><br>
                          > <a href="http://cs.oswego.edu/mailman/listinfo/concurrency-interest" target="_blank">http://cs.oswego.edu/mailman/listinfo/concurrency-interest</a><br>
                          ><br>
                          >
                          _______________________________________________<br>
                          > Concurrency-interest mailing list<br>
                          > <a href="mailto:Concurrency-interest@cs.oswego.edu" target="_blank">Concurrency-interest@cs.oswego.edu</a><br>
                          > <a href="http://cs.oswego.edu/mailman/listinfo/concurrency-interest" target="_blank">http://cs.oswego.edu/mailman/listinfo/concurrency-interest</a><br>
                          ><br>
                          ><br>
                          ><br>
                          ><br>
                          >
                          _______________________________________________<br>
                          > Concurrency-interest mailing list<br>
                          > <a href="mailto:Concurrency-interest@cs.oswego.edu" target="_blank">Concurrency-interest@cs.oswego.edu</a><br>
                          > <a href="http://cs.oswego.edu/mailman/listinfo/concurrency-interest" target="_blank">http://cs.oswego.edu/mailman/listinfo/concurrency-interest</a><br>
                          ><br>
_______________________________________________<br>
                          Concurrency-interest mailing list<br>
                          <a href="mailto:Concurrency-interest@cs.oswego.edu" target="_blank">Concurrency-interest@cs.oswego.edu</a><br>
                          <a href="http://cs.oswego.edu/mailman/listinfo/concurrency-interest" target="_blank">http://cs.oswego.edu/mailman/listinfo/concurrency-interest</a><br>
                        </blockquote>
                      </div>
                      <br>
                      <fieldset></fieldset>
                      <br>
                      <pre>_______________________________________________
Concurrency-interest mailing list
<a href="mailto:Concurrency-interest@cs.oswego.edu" target="_blank">Concurrency-interest@cs.oswego.edu</a>
<a href="http://cs.oswego.edu/mailman/listinfo/concurrency-interest" target="_blank">http://cs.oswego.edu/mailman/listinfo/concurrency-interest</a>
</pre>
                    </blockquote>
                    <br>
                  </div>
                  <br>
                  _______________________________________________<br>
                  Concurrency-interest mailing list<br>
                  <a href="mailto:Concurrency-interest@cs.oswego.edu" target="_blank">Concurrency-interest@cs.oswego.edu</a><br>
                  <a href="http://cs.oswego.edu/mailman/listinfo/concurrency-interest" target="_blank">http://cs.oswego.edu/mailman/listinfo/concurrency-interest</a><br>
                  <br>
                </blockquote>
              </div>
            </blockquote>
            <br>
          </div>
          <br>
          _______________________________________________<br>
          Concurrency-interest mailing list<br>
          <a href="mailto:Concurrency-interest@cs.oswego.edu" target="_blank">Concurrency-interest@cs.oswego.edu</a><br>
          <a href="http://cs.oswego.edu/mailman/listinfo/concurrency-interest" target="_blank">http://cs.oswego.edu/mailman/listinfo/concurrency-interest</a><br>
          <br>
        </blockquote>
      </div>
    </blockquote>
    <br>
  </div>

<br>_______________________________________________<br>
Concurrency-interest mailing list<br>
<a href="mailto:Concurrency-interest@cs.oswego.edu">Concurrency-interest@cs.oswego.edu</a><br>
<a href="http://cs.oswego.edu/mailman/listinfo/concurrency-interest" target="_blank">http://cs.oswego.edu/mailman/listinfo/concurrency-interest</a><br>
<br></div>