comparison src/os/solaris/vm/os_solaris.cpp @ 499:8a25d96bcf08

6784100: getTimeNanos - CAS reduction Summary: Get rid of the CAS loop in getTimeNanos to reduce coherence traffic on Solaris. Reviewed-by: acorn, kvn, ysr
author xlu
date Fri, 19 Dec 2008 14:40:28 -0800
parents 24fda36852ce
children 773234c55e8c
comparison
equal deleted inserted replaced
498:c6065343356f 499:8a25d96bcf08
1636 } 1636 }
1637 // gethrtime can move backwards if read from one cpu and then a different cpu 1637 // gethrtime can move backwards if read from one cpu and then a different cpu
1638 // getTimeNanos is guaranteed to not move backward on Solaris 1638 // getTimeNanos is guaranteed to not move backward on Solaris
1639 inline hrtime_t getTimeNanos() { 1639 inline hrtime_t getTimeNanos() {
1640 if (VM_Version::supports_cx8()) { 1640 if (VM_Version::supports_cx8()) {
1641 bool retry = false; 1641 const hrtime_t now = gethrtime();
1642 hrtime_t newtime = gethrtime(); 1642 const hrtime_t prev = max_hrtime;
1643 hrtime_t oldmaxtime = max_hrtime; 1643 if (now <= prev) return prev; // same or retrograde time;
1644 hrtime_t retmaxtime = oldmaxtime; 1644 const hrtime_t obsv = Atomic::cmpxchg(now, (volatile jlong*)&max_hrtime, prev);
1645 while ((newtime > retmaxtime) && (retry == false || retmaxtime != oldmaxtime)) { 1645 assert(obsv >= prev, "invariant"); // Monotonicity
1646 oldmaxtime = retmaxtime; 1646 // If the CAS succeeded then we're done and return "now".
1647 retmaxtime = Atomic::cmpxchg(newtime, (volatile jlong *)&max_hrtime, oldmaxtime); 1647 // If the CAS failed and the observed value "obs" is >= now then
1648 retry = true; 1648 // we should return "obs". If the CAS failed and now > obs > prv then
1649 } 1649 // some other thread raced this thread and installed a new value, in which case
1650 return (newtime > retmaxtime) ? newtime : retmaxtime; 1650 // we could either (a) retry the entire operation, (b) retry trying to install now
1651 // or (c) just return obs. We use (c). No loop is required although in some cases
1652 // we might discard a higher "now" value in deference to a slightly lower but freshly
1653 // installed obs value. That's entirely benign -- it admits no new orderings compared
1654 // to (a) or (b) -- and greatly reduces coherence traffic.
1655 // We might also condition (c) on the magnitude of the delta between obs and now.
1656 // Avoiding excessive CAS operations to hot RW locations is critical.
1657 // See http://blogs.sun.com/dave/entry/cas_and_cache_trivia_invalidate
1658 return (prev == obsv) ? now : obsv ;
1651 } else { 1659 } else {
1652 return oldgetTimeNanos(); 1660 return oldgetTimeNanos();
1653 } 1661 }
1654 } 1662 }
1655 1663