<html>
  <head>
    <meta content="text/html; charset=utf-8" http-equiv="Content-Type">
  </head>
  <body style="background-color: rgb(255, 255, 255); color: rgb(0, 0,
    0);" bgcolor="#FFFFFF" text="#000000">
    Hi Gil,<br>
    <br>
    The algorithm complexity has been on my mind too and I've been
    thinking of how to maintain a key (or it's address) -> ephemeron
    mapping most efficiently. As I have written in a reply to Mandy, if
    we say that individual phase2 of processing of the normal References
    has complexity O(N) where N is the number of discovered references,
    then the equivalent phase2 processing of Ephemerons has comparable
    complexity O(N*d) where N is the number of discovered Ephemerons and
    d is the maximum number of "hops" in object graph where a "hop" is
    defined as a point in chain where the value of some ephemeron refers
    directly or indirectly to the key of some other ephemeron and the
    value of that other ephemeron continues the chain. Let's hope that
    in practical data structures, d is not large. The maximum value of d
    is N, as in one of the tests. The algorithm in the prototype tries
    to reduce the number of outer iterations to much less than 'd' in
    many situations by alternating the direction of scanning in each
    pass. The value(ephemeronX) -> key(ephemeronY) links could be
    arranged in a zig-zag pattern relative to the order of discovered
    references in the list though which would be the worst case for the
    algorithm, but I think the chances of that happening in a real-world
    data structure are low. But we have to think of possible
    denial-of-service attacks too, so I agree that worst-case scenario
    has to be improved.<br>
    <br>
    Presently, Reference objects are discovered and hooked on
    single-linked _discoveredXXX lists (using Reference.discovered field
    to point to the next in list). Each reference type has it's own set
    of lists. Multiple lists in a set enable parallel (concurrent?)
    discovery without contention (a list per thread).<br>
    <br>
    So I was thinking that one possibility would be for ephemerons to
    have a bigger table of discovered lists - not just one per discovery
    thread, but quite bigger and that the index of a list to which
    discovered ephemeron is added would be computed from the ephemeron's
    key. A classical hash-table with buckets. Big enough table would
    minimize contention when discovery is parallelized and enable the
    following algorithm (which could also be parallelized):<br>
    <br>
    Let each bucket (each head of the list) have 2 boolean flags:
    include & pending.<br>
    At the start, set include flags of all buckets to true and then
    enter the loop:<br>
    do {<br>
        reset pending flags of all buckets to false;<br>
        for each bucket with (include == true), do {<br>
            scan the ephemerons and for those with live keys, mark value
    and transitive closure as live. <br>
            while marking the value and transitive closure as live, for
    each object that was newly marked alive,<br>
            compute the index into the ephemeron buckets as though such
    object was ephemeron's key<br>
            and set the pending flag of that bucket.<br>
        }<br>
        set the include flags of all buckets from the pending flags of
    the buckets and count # of pending buckets<br>
    } while (# of pending buckets > 0);<br>
    <br>
    <br>
    Hm, ....<br>
    <br>
    <br>
    Regards, Peter<br>
    <br>
    <div class="moz-cite-prefix">On 01/24/2016 06:43 PM, Gil Tene wrote:<br>
    </div>
    <blockquote cite="mid:5AFD362E-43AD-4234-8D6E-158AB1BA5340@azul.com"
      type="cite"><!--[if !IE]><DIV style="border-left: 2px solid #009900; border-right: 2px solid #009900;  padding: 0px 15px; margin: 2px 0px;"><![endif]-->
      <meta http-equiv="Content-Type" content="text/html; charset=utf-8">
      A note on implementation possibilities:
      <div class=""><br class="">
      </div>
      <div class="">If I read the implementation correctly, a "weakness"
        of the current implementation approach for making sure
        value-referents (and their transitively reachable) objects are
        kept alive if key referents are alive is that it requires
        multiple passes through the discovered Ephemeron list, with the
        passes terminating when the list stabilizes. While I think that
        this is sound (in the sense that it will work), it carries a
        potentially high cost when large sets of Ephemerons exist in the
        heap. E.g. if the Ephemerons are linked in a k-v list (where the
        value referent of one ephemeron is the key of another, in a
        chain), as in your code example, there is an N^2 scanning thing
        going on. And e.g. if a large set of ephemeron keys become
        weakly reachable in a single cycle (e.g. a large cache was
        discarded) while other ephemeron participate in some linked list
        relationship, the entire list of [stably] weak-keyed ephemerons
        has to be traversed in each pass (in case one of them has become
        live in a previous pass). I'd worry that these computational
        complexity issues could become prohibitive enough in GC cost
        that you there would be significant resistance to their
        adoption.</div>
      <div class=""><br class="">
      </div>
      <div class="">Note that in comparison (to my understanding),
        current ref processing work involved in GC handling
        soft/weak/final/phantom refs remains linear to the number of
        refs, and does not have an O(N^2) component.</div>
      <div class=""><br class="">
      </div>
      <div class="">I believe that there is a relatively simple way to
        bring Ephemeron processing to O(N) by establishing reverse
        mapping during the scan (the below description assumes STW
        during the scan):</div>
      <div class=""><br class="">
      </div>
      <div class="">1. Start ref processing with no reverse mapping
        table established.</div>
      <div class=""><br class="">
      </div>
      <div class="">2. During ref processing, establish an
        EphemeronKeyReverseMapping table (logically a Map<Address,
        List<Ephemerons>>) which would map individual heap
        addresses to ephemerons who's key referent points to those
        addresses.</div>
      <div class=""><br class="">
      </div>
      <div class="">3. Note that since each heap address can show up in
        multiple key referents, the map needs to return a (potentially
        empty) list of Ephemerons who's keys refer to the address.</div>
      <div class=""><br class="">
      </div>
      <div class="">4. Specifically, starting with an empty list, and
        for each discovered Ephemeron, add a reverse-mapping entry to
        the EphemeronKeyReverseMapping, mapping from the key referent
        address to the Ephemeron.</div>
      <div class=""><br class="">
      </div>
      <div class="">5. During Ephemeron processing (under the case where
        the referent is found to be alive and the ephemeron then needs
        to keep the value referent alive) mark down the value referent
        path using a special ephemeron_keep_alive OopClosure (or a mode
        flag that affects the normal keep_alive behavior) which, when
        reaching a not-yet-marked-live object [in addition to marking it
        live and traversing it as keep_alive would normally do] would
        look up the object's address in the EphemeronKeyReverseMapping
        to get a list of Ephemerons to traverse, and traverse each of
        the mapped Ephemerons' value referent with the
        same ephemeron_keep_alive closure. </div>
      <div class="">Note: doing reverse-mapping lookups on each
        not-yet-marked object in a keep_alive closure will add cost,
        which is why this ephemeron_keep_alive pass should probably be
        done after regular keep_alive passes have had their chance to
        mark objects live. This way only paths that become newly-live
        via ephemeron processing are subject to the extra
        reverse-mapping-lookip cost.</div>
      <div class=""><br class="">
      </div>
      <div class="">While I haven't been poking at this too long to see
        if it has holes, I think it can produce a reliable result, and
        is O(N) on the count of Ephemerons.</div>
      <div class=""><br class="">
      </div>
      <div class="">— Gil.</div>
      <div class=""><br class="">
      </div>
      <div class=""><br class="">
        <div>
          <blockquote type="cite" class=""><!--[if !IE]><DIV style="border-left: 2px solid #009900; border-right: 2px solid #009900;  padding: 0px 15px; margin: 2px 0px;"><![endif]-->
            <div class="">On Jan 24, 2016, at 2:52 AM, Peter Levart <<a
                moz-do-not-send="true"
                href="mailto:peter.levart@gmail.com" class=""><a class="moz-txt-link-abbreviated" href="mailto:peter.levart@gmail.com">peter.levart@gmail.com</a></a>>
              wrote:</div>
            <br class="Apple-interchange-newline">
            <div class="">
              <meta http-equiv="Content-Type" content="text/html;
                charset=utf-8" class="">
              <div style="background-color: rgb(255, 255, 255);"
                bgcolor="#FFFFFF" text="#000000" class=""> Hi Gil,<br
                  class="">
                <br class="">
                I totally agree with your assessment. We should not
                introduce another way of reviving the almost collectable
                objects and I fully support tightening the specification
                so that soft and weak references to the same referent
                and to other referents from which this referent is
                reachable are required to be cleared together
                atomically.<br class="">
                <br class="">
                I modified the prototype to (hopefully) adhere to this
                new Ephemeron specification that Gil and I agreed upon.
                Anyone interested in experimenting can find it here:<br
                  class="">
                <br class="">
                <a moz-do-not-send="true" class="moz-txt-link-freetext"
href="http://cr.openjdk.java.net/%7Eplevart/misc/Ephemeron/webrev.jdk.02/">http://cr.openjdk.java.net/~plevart/misc/Ephemeron/webrev.jdk.02/</a><br
                  class="">
                <a moz-do-not-send="true" class="moz-txt-link-freetext"
href="http://cr.openjdk.java.net/%7Eplevart/misc/Ephemeron/webrev.hotspot.02/">http://cr.openjdk.java.net/~plevart/misc/Ephemeron/webrev.hotspot.02/</a><br
                  class="">
                <br class="">
                It is rebased to current tip of jdk9-dev repositories
                (after the bulk of merges for jdk-9+102), but still
                contains the change to remove the Cleaner reference type
                as it has not yet managed to get in...<br class="">
                <br class="">
                I have also added a test that is a start for verifying
                the functionality.<br class="">
                <br class="">
                Regards, Peter<br class="">
                <br class="">
                <div class="moz-cite-prefix">On 01/23/2016 07:25 PM, Gil
                  Tene wrote:<br class="">
                </div>
                <blockquote
                  cite="mid:8154B857-931F-4BED-872A-36892E050CCF@azul.com"
                  type="cite" class=""><!--[if !IE]><DIV style="border-left: 2px solid #009900; border-right: 2px solid #009900;  padding: 0px 15px; margin: 2px 0px;"><![endif]--><!--[if !IE]><DIV style="border-left: 2px solid #009900; border-right: 2px solid #009900;  padding: 0px 15px; margin: 2px 0px;"><![endif]-->
                  <br class="">
                  <div class="">
                    <blockquote type="cite" class=""><!--[if !IE]><DIV style="border-left: 2px solid #009900; border-right: 2px solid #009900;  padding: 0px 15px; margin: 2px 0px;"><![endif]--><!--[if !IE]><DIV style="border-left: 2px solid #009900; border-right: 2px solid #009900;  padding: 0px 15px; margin: 2px 0px;"><![endif]-->
                      <div class="">On Jan 23, 2016, at 5:14 AM, Peter
                        Levart <<a moz-do-not-send="true"
                          class="moz-txt-link-abbreviated"
                          href="mailto:peter.levart@gmail.com">peter.levart@gmail.com</a>>

                        wrote:</div>
                      <br class="Apple-interchange-newline">
                      <div class="">
                        <div style="background-color: rgb(255, 255,
                          255);" bgcolor="#FFFFFF" text="#000000"
                          class=""> Hi Gil, it's good to have this
                          discussion. See comments inline...<br class="">
                          <br class="">
                          <div class="moz-cite-prefix">On 01/23/2016
                            05:13 AM, Gil Tene wrote:<br class="">
                          </div>
                          ....<br class="">
                          <blockquote
                            cite="mid:C295F49E-ABAB-4085-9490-C29C700F1274@azul.com"
                            type="cite" class=""><!--[if !IE]><DIV style="border-left: 2px solid #009900; border-right: 2px solid #009900;  padding: 0px 15px; margin: 2px 0px;"><![endif]--><!--[if !IE]><DIV style="border-left: 2px solid #009900; border-right: 2px solid #009900;  padding: 0px 15px; margin: 2px 0px;"><![endif]--><!--[if !IE]><DIV style="border-left: 2px solid #009900; border-right: 2px solid #009900;  padding: 0px 15px; margin: 2px 0px;"><![endif]-->
                            <div class="">
                              <blockquote type="cite" class=""><!--[if !IE]><DIV style="border-left: 2px solid #009900; border-right: 2px solid #009900;  padding: 0px 15px; margin: 2px 0px;"><![endif]--><!--[if !IE]><DIV style="border-left: 2px solid #009900; border-right: 2px solid #009900;  padding: 0px 15px; margin: 2px 0px;"><![endif]--><!--[if !IE]><DIV style="border-left: 2px solid #009900; border-right: 2px solid #009900;  padding: 0px 15px; margin: 2px 0px;"><![endif]-->
                                <div class="">On Jan 22, 2016, at 2:49
                                  PM, Peter Levart <<a
                                    moz-do-not-send="true"
                                    class="moz-txt-link-abbreviated"
                                    href="mailto:peter.levart@gmail.com"><a class="moz-txt-link-abbreviated" href="mailto:peter.levart@gmail.com">peter.levart@gmail.com</a></a>>


                                  wrote:</div>
                                <br class="Apple-interchange-newline">
                                <div class="">
                                  <div style="background-color: rgb(255,
                                    255, 255);" bgcolor="#FFFFFF"
                                    text="#000000" class=""> Ephemeron
                                    always touches definitions of at
                                    least two consecutive strengths of
                                    reachabilities. The prototype says:<br
                                      class="">
                                    <br class="">
                                     * <li> An object is
                                    <em>weakly
                                    reachable</em> if it is
                                    neither<br class="">
                                     * strongly nor softly reachable but
                                    can be reached by traversing a<br
                                      class="">
                                     * weak reference or by traversing
                                    an ephemeron through it's value
                                    while<br class="">
                                     * the ephemeron's key is at least
                                    weakly reachable.<br class="">
                                    <br class="">
                                     * <li> An object is
                                    <em>ephemerally
                                    reachable</em> if it is
                                    neither<br class="">
                                     * strongly, softly nor weakly
                                    reachable but can be reached by
                                    traversing an<br class="">
                                     * ephemeron through it's key or by
                                    traversing an ephemeron through it's
                                    value<br class="">
                                     * while it's key is at most
                                    ephemerally reachable. When the
                                    ephemerons that<br class="">
                                     * refer to ephemerally reachable
                                    key object are cleared, the key
                                    object becomes<br class="">
                                     * eligible for finalization.<br
                                      class="">
                                  </div>
                                </div>
                                <!--[if !IE]></DIV><![endif]--><!--[if !IE]></DIV><![endif]--><!--[if !IE]></DIV><![endif]--></blockquote>
                              <div class=""><br class="">
                              </div>
                              <div class="">Looking into this a bit
                                more, I don't think the above is quite
                                right. Specifically, If an ephemeron's
                                key is either strongly of softly
                                reachable, you want the value to remain
                                appropriately strongly/softly reachable.
                                Without this quality, Ephemeron value
                                referents can (and will) be prematurely
                                collected and finalized while the keys
                                are not. This (IMO) needed quality not
                                provided by the behavior you specify…</div>
                            </div>
                            <!--[if !IE]></DIV><![endif]--><!--[if !IE]></DIV><![endif]--><!--[if !IE]></DIV><![endif]--></blockquote>
                          <br class="">
                          This is not quite true. While ephemeron's
                          value is weakly or even ephemerally-reachable,
                          it is not finalizable, because
                          ephemeraly-reachable is stronger than
                          finaly-reachable. After ephemeron's key
                          becomes ephemeraly-reachable, the ephemeron is
                          cleared by GC which sets it's key *and* value
                          to null atomically. The life of key and value
                          at that moment becomes untangled. Either of
                          them can have a finalizer or not and both of
                          them will eventually be collected if not
                          revived by their finalize() methods. But it
                          can never happen that ephemeron's value is
                          finalized or collected while it's key is still
                          reachable through the ephemeron (while the
                          ephemeron is not cleared yet).</div>
                      </div>
                      <!--[if !IE]></DIV><![endif]--><!--[if !IE]></DIV><![endif]--></blockquote>
                    <blockquote type="cite" class=""><!--[if !IE]><DIV style="border-left: 2px solid #009900; border-right: 2px solid #009900;  padding: 0px 15px; margin: 2px 0px;"><![endif]--><!--[if !IE]><DIV style="border-left: 2px solid #009900; border-right: 2px solid #009900;  padding: 0px 15px; margin: 2px 0px;"><![endif]-->
                      <div class="">
                        <div style="background-color: rgb(255, 255,
                          255);" bgcolor="#FFFFFF" text="#000000"
                          class=""> <br class="">
                          But I agree that it would be desirable for
                          ephemeron's value to follow the reachability
                          of it's key. In above specification, if the
                          key is strongly reachable, the value is weakly
                          reachable, so any WeakReferences or
                          SoftReferences pointing at the Ephemeron's
                          value can already be cleared while the key is
                          still strongly reachable. This is arguably no
                          different than current specification of Soft
                          vs. Weak references. A SoftReference can
                          already be cleared while its referent is still
                          reachable through a WeakReference, </div>
                      </div>
                      <!--[if !IE]></DIV><![endif]--><!--[if !IE]></DIV><![endif]--></blockquote>
                    <div class=""><br class="">
                    </div>
                    <div class="">
                      <div class="">We seem to agree about the cleaner
                        behavior specification (in both of our texts
                        below), so the these next paragraphs are really
                        about arguing for why this is an important
                        design choice if/when adding Ephemerons to
                        Java: </div>
                    </div>
                    <div class=""><br class="">
                    </div>
                    <div class="">It is true the [current] spec allows
                      for soft references to an object to be cleared
                      while weak references to the same object are not:
                      the "determines" in "Suppose that the garbage
                      collector determines at a certain point in
                      time hat an object is RRRR reachable..." part
                      [for RRRR = {soft, weak}] does not have to happen
                      at the same "certain point in time". </div>
                    <div class=""><br class="">
                    </div>
                    <div class="">However, to my knowledge all current
                      implementations present as if this determination
                      is happening at the same "point in time" for all
                      weakly and softly reachable objects combined.
                      Specifically [in implementations]: if soft
                      reachability is determined for an object at some
                      point in time, then weak reachability for that
                      object is determined at the same point in time.
                      And the weak reachability determination for an
                      object depends on whether the collector chose to
                      clear existing soft references to that object at
                      that same point in time, with the appearance of
                      the choice to clear (or not to clear) soft
                      references to a given object atomically affecting
                      the determination of it's weak reachability. Since
                      the collector is *required* to act on a weak
                      determination when it is made, while it *may* act
                      on a soft determination when it is made, making
                      the combined determination at the same "point in
                      time" eliminates an obviously confusing situation
                      that is not prohibited by the spec: if the
                      determination for weak and soft reachability was
                      not done at the same point in time, then an object
                      that was softly reachable and had it's soft
                      references cleared and queued could later become
                      strongly reachable, and even softly reachable
                      again. When reference processing is done as a STW
                      thing, this "combined determination" effect is a
                      trivial side-effect of STW. When it is done
                      concurrently (or incrementally?), implementations
                      still work to maintain the appearance of combined
                      atomic determination of soft and weak
                      reachability. I know ours does. In our case, we do
                      it because we had no desire to be the ones to
                      argue "I know that all implementations did this
                      atomically because they were STW, but the spec
                      allows us to add this bug to your program…".</div>
                    <div class=""><br class="">
                    </div>
                    <div class="">So in actual implementations (to my
                      knowledge), finalization is currently the only
                      mechanism that can create this "strange situation"
                      where an object was no longer strongly reachable,
                      had actions triggered as a result from loss of
                      strong reachability (i.e. actually observed by the
                      program as "known to not be strongly reachable"),
                      and later became strongly reachable again. E.g. a
                      finalizer can propagate a strong reference to a
                      previously non-strongly reachable object ('this'
                      in the finalizer, or anything that 'this'
                      transitively refers and was not otherwise
                      reachable when the finalizer was called).. This is
                      one of those "undesired" things that the
                      introduction of Reference types was meant to deal
                      with (Reference types were introduced in 1.2,
                      after finalization was unfortunately already
                      included and spec'ed. And phantom refs were meant
                      to allow for a cleaner form that could replace
                      finalization). And while the specifications of
                      SoftReference and WeakReference do not prohibit
                      it, implementations are not required to allow it,
                      and in practice non of them do (I think), as doing
                      so would most likely expose some "interesting"
                      spec-allowed-but-extremely-surprising things/bugs
                      that none of us want to have to defend...</div>
                    <div class=""><br class="">
                    </div>
                    <div class="">In this context, it would be a "highly
                      undesirable" design choice to introduce Ephemerons
                      in a way that would them to return a strong
                      reference to an object that has previously been
                      determined to no longer be strongly reachable.
                      Structuring the spec to prohibit this is a better
                      design choice.</div>
                    <div class=""><br class="">
                    </div>
                    <div class="">To highlight the design choice here,
                      let me describe a specific problem scenario for
                      which the previous (above) spec would cause
                      "re-strengthening" behavior that would break
                      assumptions that are allowed under the current
                      spec: in the above/previously specified behavior
                      an object V that is known to have no finalizers,
                      but has e.g. 3 WeakReference objects that refer to
                      it, can become weakly reachable while both a key
                      referent object K in some ephemeron E with a value
                      referent of V remain strongly reachable. At such a
                      point (V is weakly reachable, K and E are strongly
                      reachable), the collector may determine weak
                      reachability for V, [atomically] clear all weak
                      references to V, and enqueue those weak reference
                      objects on their respective queues. While V is
                      still ephemerally reachable under your previous
                      definition, there are no references to it anywhere
                      other than in ephemeron value referent fields, and
                      weak references that did refer to it have been
                      cleared and queued. Since the ephemeron is still
                      there, and the key is still there, and the
                      ephemeron has not been cleared, an
                      Ephemeron.getValue() call would create a strong
                      reference to an object that was previously
                      determined to not be weakly reachable. Re-creating
                      a strong reference to V after the point where weak
                      references to V were cleared and the weak refs to
                      it were enqueued would be "surprising" to current
                      weak reference based code (the only thing that
                      could cause this under the current spec would be a
                      finalizer), so allowing that (jn the spec) is
                      likely to break all kinds of logic that depends on
                      currently spec'ed weak reference behaviors.</div>
                    <div class=""><br class="">
                    </div>
                    <div class="">The spec'ed behavior we seem to be
                      agreeing on (below) would prohibit this loophole
                      and would [I think] maintain any
                      reachability-based expectations that current
                      weak-ref based logic can make under the current
                      spec. Maintaining this continuity is an important
                      design choice for adding Ephemerons into the
                      current set of Reference behaviors.</div>
                    <div class=""><br class="">
                    </div>
                    <div class="">And since I suspect that all
                      implementations will continue to choose to do the
                      "determination" of soft and weak reachability at
                      the same "point in time", this will fit well with
                      how people would build this stuff anyway.</div>
                    <div class=""><br class="">
                    </div>
                    <div class="">Separate note: It would be separately
                      interesting to consider narrowing the SoftRef spec
                      to require JVM implementations to atomically clear
                      all soft *and* weak references to an object at the
                      same time. I.e. if the garbage collector chooses
                      to clear a soft reference to an object that would
                      become weakly reachable as a result, then all weak
                      references to that object must be [atomically]
                      cleared at the same time. Since I suspect that all
                      current JVM implementations actually adhere to
                      this stronger requirement already, this would not
                      "hurt" anything or require extra work to comply
                      with. [Anyone from Metronome or some other non-STW
                      reference processing implementations want to chime
                      in?].</div>
                    <div class=""><br class="">
                    </div>
                    <blockquote type="cite" class=""><!--[if !IE]><DIV style="border-left: 2px solid #009900; border-right: 2px solid #009900;  padding: 0px 15px; margin: 2px 0px;"><![endif]--><!--[if !IE]><DIV style="border-left: 2px solid #009900; border-right: 2px solid #009900;  padding: 0px 15px; margin: 2px 0px;"><![endif]-->
                      <div class="">
                        <div style="background-color: rgb(255, 255,
                          255);" bgcolor="#FFFFFF" text="#000000"
                          class="">but for Ephemeron's value this might
                          be confusing. The easier to understand
                          conceptual model for Ephemerons might be a
                          pair of (WeakReference<K>,
                          WeakReference<V>) where the key has a
                          virtual strong reference to the value. And
                          this is what we get if we say that
                          reachability of the value follows reachability
                          of the key.<br class="">
                          <br class="">
                          <blockquote
                            cite="mid:C295F49E-ABAB-4085-9490-C29C700F1274@azul.com"
                            type="cite" class=""><!--[if !IE]><DIV style="border-left: 2px solid #009900; border-right: 2px solid #009900;  padding: 0px 15px; margin: 2px 0px;"><![endif]--><!--[if !IE]><DIV style="border-left: 2px solid #009900; border-right: 2px solid #009900;  padding: 0px 15px; margin: 2px 0px;"><![endif]--><!--[if !IE]><DIV style="border-left: 2px solid #009900; border-right: 2px solid #009900;  padding: 0px 15px; margin: 2px 0px;"><![endif]-->
                            <div class="">
                              <div class=""> </div>
                              <div class=""><br class="">
                              </div>
                              <div class="">For a correctly specified
                                behavior, I think all strengths (from
                                strong down) need to be affected by
                                key/value Ephemeron relationships, but
                                without adding an "ephemerally
                                reachable" strength. E.g. I think you
                                fundamentally need something like this:</div>
                              <div class=""><br class="">
                              </div>
                              <div class="">- "An object is
                                <em>strongly reachable</em>
                                if it can be reached by (a) some thread
                                without traversing any reference
                                objects, or by (b) traversing the value
                                of an Ephemeron whose key is strongly
                                reachable. A newly-created object is
                                strongly reachable by the thread that
                                created it"</div>
                              <div class=""><br class="">
                              </div>
                              <div class="">- "An object is
                                <em>softly reachable</em> if
                                it is not strongly reachable but can be
                                reached by (a) traversing a soft
                                reference or by (b) traversing the value
                                of an Ephemeron whose key is softly
                                reachable.</div>
                              <div class=""><br class="">
                              </div>
                              <div class="">
                                <div class="">- "An object is
                                  <em>weakly reachable</em>
                                  if it is neither strongly nor softly
                                  reachable but can be reached by (a)
                                  traversing a weak reference or by (b)
                                  traversing the value of an ephemeron
                                  whose key is weakly reachable.</div>
                              </div>
                            </div>
                            <!--[if !IE]></DIV><![endif]--><!--[if !IE]></DIV><![endif]--><!--[if !IE]></DIV><![endif]--></blockquote>
                          <br class="">
                          ...and that's where we stop, because when we
                          make Ephemeron just a special kind of
                          WeakReference, the next thing that happens is:<br
                            class="">
                          <br class="">
                           * <p> Suppose that the garbage
                          collector determines at a certain point in
                          time<br class="">
                           * that an object is <a
                          href="package-summary.html#reachability">weakly<br
                            class="">
                           * reachable</a>.  At that time it will
                          atomically clear all weak references to<br
                            class="">
                           * that object and all weak references to any
                          other weakly-reachable objects<br class="">
                           * from which that object is reachable through
                          a chain of strong and soft<br class="">
                           * references.  At the same time it will
                          declare all of the formerly<br class="">
                           * weakly-reachable objects to be
                          finalizable.  At the same time or at some<br
                            class="">
                           * later time it will enqueue those
                          newly-cleared weak references that are<br
                            class="">
                           * registered with reference queues.<br
                            class="">
                          <br class="">
                          ...where "clearing of the WeakReference" means
                          reseting the key *and* value to null in case
                          it is an Ephemeron; and<br class="">
                          "all weak references to some object" means
                          Ephemerons that have that object as a key (but
                          not those that only have it as a value!) in
                          case of ephemerons<br class="">
                          <br class="">
                          ...<br class="">
                          <blockquote
                            cite="mid:C295F49E-ABAB-4085-9490-C29C700F1274@azul.com"
                            type="cite" class=""><!--[if !IE]><DIV style="border-left: 2px solid #009900; border-right: 2px solid #009900;  padding: 0px 15px; margin: 2px 0px;"><![endif]--><!--[if !IE]><DIV style="border-left: 2px solid #009900; border-right: 2px solid #009900;  padding: 0px 15px; margin: 2px 0px;"><![endif]--><!--[if !IE]><DIV style="border-left: 2px solid #009900; border-right: 2px solid #009900;  padding: 0px 15px; margin: 2px 0px;"><![endif]-->
                            <div class="">I still think that
                              Ephemeron<K, V> should extend
                              WeakReference<K>, since that places
                              already established rules and expectation
                              on (a) when it will be enqueued, (b) when
                              the collector will clear it (when the the
                              collector encounters the <K> key
                              being weakly reachable), and (c) that
                              clearing of all Ephemeron *and*
                              WeakReference instances who share an
                              identical key value is done atomically,
                              along with (d) all weak references to to
                              any other weakly-reachable objects from
                              which that object is reachable through a
                              chain of strong and soft references. These
                              last (c, d) parts are critically captured
                              since an Ephemeron *is a* WeakReference,
                              and the statement in WeakReference that
                              says that "… it will atomically clear all
                              weak references to that object and all
                              weak references to any other
                              weakly-reachable objects from which that
                              object is reachable through a chain of
                              strong and soft references." has a clear
                              application.</div>
                            <div class=""><br class="">
                            </div>
                            <div class="">Here are some suggested edits
                              to the JavaDoc to go with this suggested
                              spec'ed behavior:</div>
                            <div class="">
                              <div class="">/**</div>
                              <div class="">  * Ephemeron<K, V>
                                objects are a special kind of
                                WeakReference<K> objects, which</div>
                              <div class="">  * hold two referents (a
                                key referent and a value referent) and
                                do not prevent their</div>
                              <div class="">  * referents from being
                                made finalizable, finalized, and then
                                reclaimed.</div>
                            </div>
                            <!--[if !IE]></DIV><![endif]--><!--[if !IE]></DIV><![endif]--><!--[if !IE]></DIV><![endif]--></blockquote>
                          <blockquote
                            cite="mid:C295F49E-ABAB-4085-9490-C29C700F1274@azul.com"
                            type="cite" class=""><!--[if !IE]><DIV style="border-left: 2px solid #009900; border-right: 2px solid #009900;  padding: 0px 15px; margin: 2px 0px;"><![endif]--><!--[if !IE]><DIV style="border-left: 2px solid #009900; border-right: 2px solid #009900;  padding: 0px 15px; margin: 2px 0px;"><![endif]--><!--[if !IE]><DIV style="border-left: 2px solid #009900; border-right: 2px solid #009900;  padding: 0px 15px; margin: 2px 0px;"><![endif]-->
                            <div class="">
                              <div class="">  * In addition to the key
                                referent, which adheres to the referent
                                behavior of a</div>
                              <div class="">  * WeakReference<K>,
                                an ephemeron also holds a value referent
                                whose reachabiliy</div>
                              <div class="">  * strength is affected by
                                the reachability strength of the key
                                referent: </div>
                              <div class="">  * The value referent of an
                                Ephemeron instance is considered:</div>
                              <div class="">  * (a) strongly reachable
                                if the key referent of the same
                                Ephemeron</div>
                              <div class="">  * object
                                is strongly reachable, or if the value
                                referent is otherwise strongly
                                reachable.</div>
                              <div class="">
                                <div class="">  * (b) softly reachable
                                  if it is not strongly reachable, and
                                  (i) the key referent of</div>
                                <div class="">  * the same Ephemeron
                                  object is softly reachable, or (ii)
                                  if the value referent is otherwise</div>
                                <div class="">  * softly reachable.</div>
                              </div>
                              <div class="">
                                <div class="">  * (c) weakly reachable
                                  if it is not strongly or softly
                                  reachable, and (i) the key referent of</div>
                                <div class="">  * the same Ephemeron
                                  object is weakly reachable, or (ii)
                                  if the value referent is otherwise</div>
                                <div class="">  * weakly reachable.</div>
                              </div>
                              <div class="">  * <p> When the
                                collector clears an Ephemeron object
                                instance (according to the rules</div>
                            </div>
                            <div class="">
                              <div class="">  * expressed for clearing
                                WeakReference object instances), the
                                Ephemeron instance's</div>
                              <div class="">  * key referent value
                                referent are simultaneously and
                                atomically cleared.</div>
                              <div class="">  * <p> By
                                convenience, the Ephemeron's referent is
                                also called the key, and can be</div>
                              <div class="">  * obtained either by
                                invoking {@link #get} or {@link #getKey}
                                while the value</div>
                              <div class="">  * can be obtained by
                                invoking {@link #getValue} method.</div>
                              <div class="">  *...</div>
                            </div>
                            <!--[if !IE]></DIV><![endif]--><!--[if !IE]></DIV><![endif]--><!--[if !IE]></DIV><![endif]--></blockquote>
                          <br class="">
                          <br class="">
                          Thanks, this is very nice. I do like this
                          behavior more.<br class="">
                          <br class="">
                          Let me see what it takes to implement this
                          strategy...<br class="">
                          <br class="">
                          Regards, Peter<br class="">
                          <br class="">
                        </div>
                      </div>
                      <!--[if !IE]></DIV><![endif]--><!--[if !IE]></DIV><![endif]--></blockquote>
                  </div>
                  <br class="">
                  <!--[if !IE]></DIV><![endif]--><!--[if !IE]></DIV><![endif]--></blockquote>
                <br class="">
              </div>
            </div>
            <!--[if !IE]></DIV><![endif]--></blockquote>
        </div>
        <br class="">
      </div>
      <!--[if !IE]></DIV><![endif]--></blockquote>
    <br>
  </body>
</html>