<html>
  <head>
    <meta content="text/html; charset=utf-8" http-equiv="Content-Type">
  </head>
  <body bgcolor="#FFFFFF" text="#000000">
    <div class="moz-cite-prefix">On 02/13/2015 03:54 AM, David Holmes
      wrote:<br>
    </div>
    <blockquote cite="mid:54DD677F.10101@oracle.com" type="cite">Hi Tom,
      <br>
      <br>
      If you are potentially messing with the (identity) hash of all
      Java objects in the 32-bit case then this needs a broader
      discussion eg on core-libs-dev (cc'd) as this will impact end-user
      code the most!
      <br>
      <br>
      The rest seems okay but I'm still mulling over it. :)
      <br>
      <br>
      Thanks,
      <br>
      David H.
      <br>
    </blockquote>
    <br>
    Hi,<br>
    <br>
    As I understand, this will make identity hashCode have 2^24 instead
    of 2^25 distinct values on 32 bit architectures, right? This will
    mostly affect java.util.IdentityHashMap performance (and any use of
    objects that don't override hashCode in other hashCode-based Maps).
    IHM has a maximum capacity of 2^29 (key, value) slots. Performance
    will start to degrade sooner - at sizes > 2^24 / 1.5 (~10M)
    instead of 2^25 / 1.5 (~20M) entries.<br>
    <br>
    IHM has the following hashCode -> array slot index mapping
    function:<br>
    <br>
    <meta http-equiv="content-type" content="text/html; charset=utf-8">
        /**<br>
         * Returns index for Object x.<br>
         */<br>
        private static int hash(Object x, int length) {<br>
            int h = System.identityHashCode(x);<br>
            // Multiply by -127, and left-shift to use least bit as part
    of hash<br>
            return ((h << 1) - (h << 8)) & (length - 1);<br>
        }<br>
    <br>
    Left-shift is added because keys are located at even indexes and
    associated values are at odd indexes in the same array. So the
    function to map hashCode to ordinal key index is actually:<br>
    <br>
        (h - (h << 7)) & (capacity - 1)<br>
    <br>
    where capacity is a power of two <= 2^29, which means that it is
    necessary that 24 hash bits from Object header be mapped to lower 24
    bits of Object.hashCode(). Object.hashCode() in range 0..2^24-1
    should still be enough to address the whole range of 2^29 capacity
    table given the above mapping function.<br>
    <br>
    So the question is, how frequent are IdentityHashMap(s) with >
    10M entries or any other HashMaps with keys that don't override
    Object.hashCode().<br>
    <br>
    Here's an JMH (<a class="moz-txt-link-freetext" href="http://openjdk.java.net/projects/code-tools/jmh/">http://openjdk.java.net/projects/code-tools/jmh/</a>)
    micro-benchmark you can use to measure the impact of change on
    IdentityHashMap:<br>
    <br>
        <a class="moz-txt-link-freetext" href="http://cr.openjdk.java.net/~plevart/misc/IHMBench/IHMBench.java">http://cr.openjdk.java.net/~plevart/misc/IHMBench/IHMBench.java</a><br>
    <br>
    by default it creates an IdentityHashMap with size of 2^24 entries.
    This is where the performance difference is expected to start to be
    different between 24bit vs. 25bit hash codes. You can also try to
    use larger (up to 28) 'log2size' parameter, but you might want to
    increate -Xmx too in this case.<br>
    <br>
    Regards, Peter<br>
    <br>
    <blockquote cite="mid:54DD677F.10101@oracle.com" type="cite">On
      13/02/2015 6:14 AM, Tom Benson wrote:
      <br>
      <blockquote type="cite">Hi,
        <br>
        I need reviewers and a commit sponsor for changes for bug
        6764713, which
        <br>
        will increase the size of the age field in an object header from
        4 bits
        <br>
        to 5. This will allow a maximum MaxTenuringThreshold of 31,
        though the
        <br>
        default will remain at the current value of 15.
        <br>
        <br>
        This includes the same change to the 32-bit version, which would
        close
        <br>
        bug 6719225 as well.  In that case, the hash field in the header
        is
        <br>
        affected, losing one bit (25 bits -> 24), so I have asked for
        review
        <br>
        from hotspot-runtime-dev as well as gc-dev.
        <br>
        <br>
        Webrev: <a class="moz-txt-link-freetext" href="http://cr.openjdk.java.net/~jprovino/6764713/webrev.00">http://cr.openjdk.java.net/~jprovino/6764713/webrev.00</a>
        <br>
        JBS bug: <a class="moz-txt-link-freetext" href="https://bugs.openjdk.java.net/browse/JDK-6764713">https://bugs.openjdk.java.net/browse/JDK-6764713</a>
        <br>
        Testing:  JPRT and reference server performance tests
        <br>
        <br>
        Notes:
        <br>
        Contrary to what earlier notes in the JBS entry said, this does
        not
        <br>
        require stronger alignment for the JavaThread structure for when
        biased
        <br>
        locking stores that pointer in the header.   The JavaThread* was
        already
        <br>
        being aligned 1 power of 2 more strongly than it needed to be,
        so there
        <br>
        was an unused bit that could be stolen.
        <br>
        <br>
        In the 32-bit version, it does require taking one bit from the
        hash
        <br>
        field, which goes from 25 to 24 bits.  This is something I'd
        especially
        <br>
        like feedback on.  Running reference server performance tests, I
        saw no
        <br>
        impact from this change.  We *could* make this change
        64-bit-only, and
        <br>
        leave the age field at 4 bits for the 32-bit version.  If we did
        so, we
        <br>
        could also decrease the alignment required for the JavaThread*
        to 512
        <br>
        from the current 1024.
        <br>
        <br>
        The comment changes imply that the bits available for the
        JavaThread*
        <br>
        have been reduced by 1, and that the alignment is now stronger,
        but
        <br>
        neither is true.  The comments have been corrected to match the
        <br>
        alignment that was already enforced.
        <br>
        <br>
        Three tests needed to be corrected to match the new limits. 
        These check
        <br>
        the maximum valid values, what value represents NeverTenure, and
        so on.
        <br>
        <br>
        Thanks,
        <br>
        Tom
        <br>
        <br>
      </blockquote>
    </blockquote>
    <br>
  </body>
</html>