ViewVC Help
View File | Revision Log | Show Annotations | Download File | Root Listing
root/jsr166/jsr166/src/jsr166e/ConcurrentHashMapV8.java
Revision: 1.14
Committed: Tue Sep 6 00:26:27 2011 UTC (12 years, 8 months ago) by dl
Branch: MAIN
Changes since 1.13: +718 -632 lines
Log Message:
Refactor iterators; various other improvements

File Contents

# User Rev Content
1 dl 1.1 /*
2     * Written by Doug Lea with assistance from members of JCP JSR-166
3     * Expert Group and released to the public domain, as explained at
4     * http://creativecommons.org/publicdomain/zero/1.0/
5     */
6    
7     package jsr166e;
8     import jsr166e.LongAdder;
9     import java.util.Map;
10     import java.util.Set;
11     import java.util.Collection;
12     import java.util.AbstractMap;
13     import java.util.AbstractSet;
14     import java.util.AbstractCollection;
15     import java.util.Hashtable;
16     import java.util.HashMap;
17     import java.util.Iterator;
18     import java.util.Enumeration;
19     import java.util.ConcurrentModificationException;
20     import java.util.NoSuchElementException;
21     import java.util.concurrent.ConcurrentMap;
22     import java.io.Serializable;
23    
24     /**
25     * A hash table supporting full concurrency of retrievals and
26     * high expected concurrency for updates. This class obeys the
27     * same functional specification as {@link java.util.Hashtable}, and
28     * includes versions of methods corresponding to each method of
29     * {@code Hashtable}. However, even though all operations are
30     * thread-safe, retrieval operations do <em>not</em> entail locking,
31     * and there is <em>not</em> any support for locking the entire table
32     * in a way that prevents all access. This class is fully
33     * interoperable with {@code Hashtable} in programs that rely on its
34     * thread safety but not on its synchronization details.
35     *
36     * <p> Retrieval operations (including {@code get}) generally do not
37     * block, so may overlap with update operations (including {@code put}
38     * and {@code remove}). Retrievals reflect the results of the most
39     * recently <em>completed</em> update operations holding upon their
40     * onset. For aggregate operations such as {@code putAll} and {@code
41     * clear}, concurrent retrievals may reflect insertion or removal of
42     * only some entries. Similarly, Iterators and Enumerations return
43     * elements reflecting the state of the hash table at some point at or
44     * since the creation of the iterator/enumeration. They do
45     * <em>not</em> throw {@link ConcurrentModificationException}.
46     * However, iterators are designed to be used by only one thread at a
47     * time. Bear in mind that the results of aggregate status methods
48     * including {@code size}, {@code isEmpty}, and {@code containsValue}
49     * are typically useful only when a map is not undergoing concurrent
50     * updates in other threads. Otherwise the results of these methods
51     * reflect transient states that may be adequate for monitoring
52     * purposes, but not for program control.
53     *
54     * <p> Resizing this or any other kind of hash table is a relatively
55     * slow operation, so, when possible, it is a good idea to provide
56     * estimates of expected table sizes in constructors. Also, for
57 jsr166 1.7 * compatibility with previous versions of this class, constructors
58 dl 1.1 * may optionally specify an expected {@code concurrencyLevel} as an
59     * additional hint for internal sizing.
60     *
61     * <p>This class and its views and iterators implement all of the
62     * <em>optional</em> methods of the {@link Map} and {@link Iterator}
63     * interfaces.
64     *
65     * <p> Like {@link Hashtable} but unlike {@link HashMap}, this class
66     * does <em>not</em> allow {@code null} to be used as a key or value.
67     *
68     * <p>This class is a member of the
69     * <a href="{@docRoot}/../technotes/guides/collections/index.html">
70     * Java Collections Framework</a>.
71     *
72     * <p><em>jsr166e note: This class is a candidate replacement for
73     * java.util.concurrent.ConcurrentHashMap.<em>
74     *
75     * @since 1.5
76     * @author Doug Lea
77     * @param <K> the type of keys maintained by this map
78     * @param <V> the type of mapped values
79     */
80     public class ConcurrentHashMapV8<K, V>
81     implements ConcurrentMap<K, V>, Serializable {
82     private static final long serialVersionUID = 7249069246763182397L;
83    
84     /**
85     * A function computing a mapping from the given key to a value,
86 jsr166 1.8 * or {@code null} if there is no mapping. This is a place-holder
87     * for an upcoming JDK8 interface.
88 dl 1.1 */
89     public static interface MappingFunction<K, V> {
90     /**
91     * Returns a value for the given key, or null if there is no
92     * mapping. If this function throws an (unchecked) exception,
93     * the exception is rethrown to its caller, and no mapping is
94     * recorded. Because this function is invoked within
95     * atomicity control, the computation should be short and
96     * simple. The most common usage is to construct a new object
97     * serving as an initial mapped value.
98     *
99     * @param key the (non-null) key
100     * @return a value, or null if none
101     */
102     V map(K key);
103     }
104    
105     /*
106     * Overview:
107     *
108     * The primary design goal of this hash table is to maintain
109     * concurrent readability (typically method get(), but also
110     * iterators and related methods) while minimizing update
111     * contention.
112     *
113     * Each key-value mapping is held in a Node. Because Node fields
114     * can contain special values, they are defined using plain Object
115     * types. Similarly in turn, all internal methods that use them
116 dl 1.14 * work off Object types. And similarly, so do the internal
117     * methods of auxiliary iterator and view classes. All public
118     * generic typed methods relay in/out of these internal methods,
119     * supplying null-checks and casts as needed.
120 dl 1.1 *
121     * The table is lazily initialized to a power-of-two size upon the
122 dl 1.14 * first insertion. Each bin in the table contains a list of
123     * Nodes (most often, zero or one Node). Table accesses require
124     * volatile/atomic reads, writes, and CASes. Because there is no
125     * other way to arrange this without adding further indirections,
126     * we use intrinsics (sun.misc.Unsafe) operations. The lists of
127     * nodes within bins are always accurately traversable under
128     * volatile reads, so long as lookups check hash code and
129     * non-nullness of value before checking key equality. (All valid
130     * hash codes are nonnegative. Negative values are reserved for
131     * special forwarding nodes; see below.)
132     *
133     * Insertion (via put or putIfAbsent) of the first node in an
134     * empty bin is performed by just CASing it to the bin. This is
135     * on average by far the most common case for put operations.
136     * Other update operations (insert, delete, and replace) require
137     * locks. We do not want to waste the space required to associate
138     * a distinct lock object with each bin, so instead use the first
139     * node of a bin list itself as a lock, using plain "synchronized"
140     * locks. These save space and we can live with block-structured
141     * lock/unlock operations. Using the first node of a list as a
142     * lock does not by itself suffice though: When a node is locked,
143     * any update must first validate that it is still the first node,
144     * and retry if not. Because new nodes are always appended to
145     * lists, once a node is first in a bin, it remains first until
146     * deleted or the bin becomes invalidated. However, operations
147     * that only conditionally update can and sometimes do inspect
148     * nodes until the point of update. This is a converse of sorts to
149     * the lazy locking technique described by Herlihy & Shavit.
150     *
151     * The main disadvantage of this approach is that most update
152     * operations on other nodes in a bin list protected by the same
153     * lock can stall, for example when user equals() or mapping
154     * functions take a long time. However, statistically, this is
155     * not a common enough problem to outweigh the time/space overhead
156     * of alternatives: Under random hash codes, the frequency of
157     * nodes in bins follows a Poisson distribution
158     * (http://en.wikipedia.org/wiki/Poisson_distribution) with a
159 dl 1.5 * parameter of 0.5 on average under the default loadFactor of
160 dl 1.14 * 0.75. The expected number of locks covering different elements
161 dl 1.5 * (i.e., bins with 2 or more nodes) is approximately 10% at
162 dl 1.14 * steady state. Lock contention probability for two threads
163     * accessing distinct elements is roughly 1 / (8 * #elements).
164     * Function "spread" performs hashCode randomization that improves
165     * the likelihood that these assumptions hold unless users define
166     * exactly the same value for too many hashCodes.
167 dl 1.1 *
168     * The table is resized when occupancy exceeds a threshold. Only
169     * a single thread performs the resize (using field "resizing", to
170     * arrange exclusion), but the table otherwise remains usable for
171 dl 1.14 * reads and updates. Resizing proceeds by transferring bins, one
172     * by one, from the table to the next table. Upon transfer, the
173     * old table bin contains only a special forwarding node (with
174     * negative hash field) that contains the next table as its
175     * key. On encountering a forwarding node, access and update
176 dl 1.1 * operations restart, using the new table. To ensure concurrent
177     * readability of traversals, transfers must proceed from the last
178 dl 1.14 * bin (table.length - 1) up towards the first. Upon seeing a
179     * forwarding node, traversals (see class InternalIterator)
180     * arrange to move to the new table for the rest of the traversal
181     * without revisiting nodes. This constrains bin transfers to a
182     * particular order, and so can block indefinitely waiting for the
183     * next lock, and other threads cannot help with the transfer.
184     * However, expected stalls are infrequent enough to not warrant
185     * the additional overhead of access and iteration schemes that
186     * could admit out-of-order or concurrent bin transfers.
187     *
188     * This traversal scheme also applies to partial traversals of
189     * ranges of bins (via an alternate InternalIterator constructor)
190     * to support partitioned aggregate operations (that are not
191     * otherwise implemented yet). Also, read-only operations give up
192     * if ever forwarded to a null table, which provides support for
193     * shutdown-style clearing, which is also not currently
194     * implemented.
195     *
196     * Lazy table initialization minimizes footprint until first use,
197     * and also avoids resizings when the first operation is from a
198     * putAll, constructor with map argument, or deserialization.
199     * These cases attempt to override the targetCapacity used in
200     * growTable (which may harmlessly fail to take effect in cases of
201     * races with other ongoing resizings).
202 dl 1.1 *
203     * The element count is maintained using a LongAdder, which avoids
204     * contention on updates but can encounter cache thrashing if read
205 dl 1.14 * too frequently during concurrent access. To avoid reading so
206 dl 1.2 * often, resizing is normally attempted only upon adding to a bin
207 dl 1.14 * already holding two or more nodes. Under the default load
208     * factor and uniform hash distributions, the probability of this
209 dl 1.1 * occurring at threshold is around 13%, meaning that only about 1
210     * in 8 puts check threshold (and after resizing, many fewer do
211 dl 1.2 * so). But this approximation has high variance for small table
212     * sizes, so we check on any collision for sizes <= 64. Further,
213 dl 1.14 * to increase the probability that a resize occurs soon enough,
214     * we offset the threshold (see THRESHOLD_OFFSET) by the expected
215 dl 1.2 * number of puts between checks. This is currently set to 8, in
216 dl 1.14 * accord with the default load factor. In practice, this default
217     * is rarely overridden, and in any case is close enough to other
218 jsr166 1.7 * plausible values not to waste dynamic probability computation
219 dl 1.14 * for the sake of more precision.
220     *
221     * Maintaining API and serialization compatibility with previous
222     * versions of this class introduces several oddities. Mainly: We
223     * leave untouched but unused constructor arguments refering to
224     * concurrencyLevel. We also declare an unused "Segment" class
225     * that is instantiated in minimal form only when serializing.
226 dl 1.1 */
227    
228     /* ---------------- Constants -------------- */
229    
230     /**
231     * The largest allowed table capacity. Must be a power of 2, at
232 dl 1.14 * most 1<<30 to stay within Java array size limits.
233 dl 1.1 */
234 dl 1.14 private static final int MAXIMUM_CAPACITY = 1 << 30;
235 dl 1.1
236     /**
237 dl 1.14 * The default initial table capacity. Must be a power of 2
238     * (i.e., at least 1) and at most MAXIMUM_CAPACITY.
239 dl 1.1 */
240 dl 1.14 private static final int DEFAULT_CAPACITY = 16;
241 dl 1.1
242     /**
243     * The default load factor for this table, used when not otherwise
244     * specified in a constructor.
245     */
246 dl 1.14 private static final float DEFAULT_LOAD_FACTOR = 0.75f;
247 dl 1.1
248     /**
249     * The default concurrency level for this table. Unused, but
250     * defined for compatibility with previous versions of this class.
251     */
252 dl 1.14 private static final int DEFAULT_CONCURRENCY_LEVEL = 16;
253 dl 1.1
254     /**
255 jsr166 1.7 * The count value to offset thresholds to compensate for checking
256 dl 1.14 * for the need to resize only when inserting into bins with two
257     * or more elements. See above for explanation.
258 dl 1.1 */
259 dl 1.14 private static final int THRESHOLD_OFFSET = 8;
260    
261     /* ---------------- Nodes -------------- */
262 dl 1.1
263     /**
264 dl 1.14 * Key-value entry. Note that this is never exported out as a
265     * user-visible Map.Entry. Nodes with a negative hash field are
266     * special, and do not contain user keys or values. Otherwise,
267     * keys are never null, and null val fields indicate that a node
268     * is in the process of being deleted or created. For purposes of
269     * read-only, access, a key may be read before a val, but can only
270     * be used after checking val. (For an update operation, when a
271     * lock is held on a node, order doesn't matter.)
272 dl 1.1 */
273 dl 1.14 static final class Node {
274     final int hash;
275     final Object key;
276     volatile Object val;
277     volatile Node next;
278    
279     Node(int hash, Object key, Object val, Node next) {
280     this.hash = hash;
281     this.key = key;
282     this.val = val;
283     this.next = next;
284     }
285     }
286    
287     /**
288     * Sign bit of node hash value indicating to use table in node.key.
289     */
290     private static final int SIGN_BIT = 0x80000000;
291 dl 1.1
292     /* ---------------- Fields -------------- */
293    
294     /**
295     * The array of bins. Lazily initialized upon first insertion.
296 dl 1.14 * Size is always a power of two. Accessed directly by iterators.
297 dl 1.1 */
298     transient volatile Node[] table;
299    
300     /** The counter maintaining number of elements. */
301     private transient final LongAdder counter;
302     /** Nonzero when table is being initialized or resized. Updated via CAS. */
303     private transient volatile int resizing;
304     /** The next element count value upon which to resize the table. */
305     private transient int threshold;
306 dl 1.14 /** The target capacity; volatile to cover initialization races. */
307     private transient volatile int targetCapacity;
308     /** The target load factor for the table */
309     private transient final float loadFactor;
310 dl 1.1
311     // views
312 dl 1.14 private transient KeySet<K,V> keySet;
313     private transient Values<K,V> values;
314     private transient EntrySet<K,V> entrySet;
315 dl 1.1
316 jsr166 1.7 /** For serialization compatibility. Null unless serialized; see below */
317 dl 1.14 private Segment<K,V>[] segments;
318 dl 1.1
319 dl 1.14 /* ---------------- Table element access -------------- */
320 dl 1.1
321     /*
322 jsr166 1.7 * Volatile access methods are used for table elements as well as
323 dl 1.14 * elements of in-progress next table while resizing. Uses are
324     * null checked by callers, and implicitly bounds-checked, relying
325     * on the invariants that tab arrays have non-zero size, and all
326     * indices are masked with (tab.length - 1) which is never
327     * negative and always less than length. Note that, to be correct
328     * wrt arbitrary concurrency errors by users, bounds checks must
329     * operate on local variables, which accounts for some odd-looking
330     * inline assignments below.
331 dl 1.1 */
332    
333 dl 1.14 static final Node tabAt(Node[] tab, int i) { // used by InternalIterator
334 dl 1.1 return (Node)UNSAFE.getObjectVolatile(tab, ((long)i<<ASHIFT)+ABASE);
335     }
336    
337     private static final boolean casTabAt(Node[] tab, int i, Node c, Node v) {
338     return UNSAFE.compareAndSwapObject(tab, ((long)i<<ASHIFT)+ABASE, c, v);
339     }
340    
341     private static final void setTabAt(Node[] tab, int i, Node v) {
342     UNSAFE.putObjectVolatile(tab, ((long)i<<ASHIFT)+ABASE, v);
343     }
344    
345 dl 1.14 /* ----------------Table Initialization and Resizing -------------- */
346    
347     /**
348     * Returns a power of two table size for the given desired capacity.
349     * See Hackers Delight, sec 3.2
350     */
351     private static final int tableSizeFor(int c) {
352     int n = c - 1;
353     n |= n >>> 1;
354     n |= n >>> 2;
355     n |= n >>> 4;
356     n |= n >>> 8;
357     n |= n >>> 16;
358     return (n < 0) ? 1 : (n >= MAXIMUM_CAPACITY) ? MAXIMUM_CAPACITY : n + 1;
359 dl 1.2 }
360    
361 dl 1.14 /**
362     * If not already resizing, initializes or creates next table and
363     * transfers bins. Initial table size uses the capacity recorded
364     * in targetCapacity. Rechecks occupancy after a transfer to see
365     * if another resize is already needed because resizings are
366     * lagging additions.
367     *
368     * @return current table
369     */
370     private final Node[] growTable() {
371     if (resizing == 0 &&
372     UNSAFE.compareAndSwapInt(this, resizingOffset, 0, 1)) {
373     try {
374     for (;;) {
375     Node[] tab = table;
376     int n, c;
377     if (tab == null)
378     n = (c = targetCapacity) > 0 ? c : DEFAULT_CAPACITY;
379     else if ((n = tab.length) < MAXIMUM_CAPACITY &&
380     counter.sum() >= threshold)
381     n <<= 1;
382     else
383     break;
384     Node[] nextTab = new Node[n];
385     threshold = (int)(n * loadFactor) - THRESHOLD_OFFSET;
386     if (tab != null)
387     transfer(tab, nextTab,
388     new Node(SIGN_BIT, nextTab, null, null));
389     table = nextTab;
390     if (tab == null)
391     break;
392     }
393     } finally {
394     resizing = 0;
395     }
396     }
397     else if (table == null)
398     Thread.yield(); // lost initialization race; just spin
399     return table;
400     }
401    
402     /*
403     * Reclassifies nodes in each bin to new table. Because we are
404     * using power-of-two expansion, the elements from each bin must
405     * either stay at same index, or move with a power of two
406     * offset. We eliminate unnecessary node creation by catching
407     * cases where old nodes can be reused because their next fields
408     * won't change. Statistically, at the default loadFactor, only
409     * about one-sixth of them need cloning when a table doubles. The
410     * nodes they replace will be garbage collectable as soon as they
411     * are no longer referenced by any reader thread that may be in
412     * the midst of concurrently traversing table.
413     *
414     * Transfers are done from the bottom up to preserve iterator
415     * traversability. On each step, the old bin is locked,
416     * moved/copied, and then replaced with a forwarding node.
417     */
418     private static final void transfer(Node[] tab, Node[] nextTab, Node fwd) {
419     int n = tab.length;
420     Node ignore = nextTab[n + n - 1]; // force bounds check
421     for (int i = n - 1; i >= 0; --i) {
422     for (Node e;;) {
423     if ((e = tabAt(tab, i)) != null) {
424     boolean validated = false;
425     synchronized (e) {
426     if (tabAt(tab, i) == e) {
427     validated = true;
428     Node lo = null, hi = null, lastRun = e;
429     int runBit = e.hash & n;
430     for (Node p = e.next; p != null; p = p.next) {
431     int b = p.hash & n;
432     if (b != runBit) {
433     runBit = b;
434     lastRun = p;
435     }
436     }
437     if (runBit == 0)
438     lo = lastRun;
439     else
440     hi = lastRun;
441     for (Node p = e; p != lastRun; p = p.next) {
442     int ph = p.hash;
443     Object pk = p.key, pv = p.val;
444     if ((ph & n) == 0)
445     lo = new Node(ph, pk, pv, lo);
446     else
447     hi = new Node(ph, pk, pv, hi);
448     }
449     setTabAt(nextTab, i, lo);
450     setTabAt(nextTab, i + n, hi);
451     setTabAt(tab, i, fwd);
452     }
453     }
454     if (validated)
455     break;
456     }
457     else if (casTabAt(tab, i, e, fwd))
458     break;
459     }
460     }
461 dl 1.2 }
462    
463 dl 1.14 /* ---------------- Internal access and update methods -------------- */
464    
465     /**
466     * Applies a supplemental hash function to a given hashCode, which
467     * defends against poor quality hash functions. The result must
468     * be non-negative, and for reasonable performance must have good
469     * avalanche properties; i.e., that each bit of the argument
470     * affects each bit (except sign bit) of the result.
471     */
472     private static final int spread(int h) {
473     // Apply base step of MurmurHash; see http://code.google.com/p/smhasher/
474     h ^= h >>> 16;
475     h *= 0x85ebca6b;
476     h ^= h >>> 13;
477     h *= 0xc2b2ae35;
478     return (h >>> 16) ^ (h & 0x7fffffff); // mask out sign bit
479     }
480 dl 1.1
481 dl 1.14 /** Implementation for get and containsKey */
482 jsr166 1.4 private final Object internalGet(Object k) {
483 dl 1.1 int h = spread(k.hashCode());
484 dl 1.14 retry: for (Node[] tab = table; tab != null;) {
485     Node e; Object ek, ev; int eh; // locals to read fields once
486     for (e = tabAt(tab, (tab.length - 1) & h); e != null; e = e.next) {
487     if ((eh = e.hash) == h) {
488     if ((ev = e.val) != null &&
489     ((ek = e.key) == k || k.equals(ek)))
490 dl 1.1 return ev;
491     }
492 dl 1.14 else if (eh < 0) { // sign bit set
493     tab = (Node[])e.key; // bin was moved during resize
494 dl 1.1 continue retry;
495     }
496     }
497     break;
498     }
499     return null;
500     }
501    
502 dl 1.10 /** Implementation for put and putIfAbsent */
503 dl 1.1 private final Object internalPut(Object k, Object v, boolean replace) {
504     int h = spread(k.hashCode());
505 dl 1.14 Object oldVal = null; // previous value or null if none
506     for (Node[] tab = table;;) {
507     Node e; int i; Object ek, ev;
508 dl 1.1 if (tab == null)
509 dl 1.14 tab = growTable();
510 dl 1.1 else if ((e = tabAt(tab, i = (tab.length - 1) & h)) == null) {
511 dl 1.2 if (casTabAt(tab, i, null, new Node(h, k, v, null)))
512 dl 1.14 break; // no lock when adding to empty bin
513     }
514     else if (e.hash < 0) // resized -- restart with new table
515     tab = (Node[])e.key;
516     else if (!replace && e.hash == h && (ev = e.val) != null &&
517     ((ek = e.key) == k || k.equals(ek))) {
518     if (tabAt(tab, i) == e) { // inspect and validate 1st node
519     oldVal = ev; // without lock for putIfAbsent
520 dl 1.1 break;
521 dl 1.14 }
522 dl 1.1 }
523     else {
524     boolean validated = false;
525     boolean checkSize = false;
526 dl 1.14 synchronized (e) { // lock the 1st node of bin list
527 dl 1.10 if (tabAt(tab, i) == e) {
528 dl 1.14 validated = true; // retry if 1st already deleted
529 dl 1.10 for (Node first = e;;) {
530 jsr166 1.11 if (e.hash == h &&
531 dl 1.14 ((ek = e.key) == k || k.equals(ek)) &&
532     (ev = e.val) != null) {
533 dl 1.1 oldVal = ev;
534     if (replace)
535     e.val = v;
536 dl 1.10 break;
537 dl 1.1 }
538 dl 1.10 Node last = e;
539     if ((e = e.next) == null) {
540 dl 1.2 last.next = new Node(h, k, v, null);
541     if (last != first || tab.length <= 64)
542 dl 1.1 checkSize = true;
543 dl 1.10 break;
544 dl 1.1 }
545     }
546     }
547     }
548     if (validated) {
549     if (checkSize && tab.length < MAXIMUM_CAPACITY &&
550     resizing == 0 && counter.sum() >= threshold)
551 dl 1.14 growTable();
552 dl 1.1 break;
553     }
554     }
555     }
556     if (oldVal == null)
557 dl 1.14 counter.increment(); // update counter outside of locks
558 dl 1.1 return oldVal;
559     }
560    
561     /**
562 dl 1.10 * Implementation for the four public remove/replace methods:
563     * Replaces node value with v, conditional upon match of cv if
564     * non-null. If resulting value is null, delete.
565 dl 1.1 */
566     private final Object internalReplace(Object k, Object v, Object cv) {
567     int h = spread(k.hashCode());
568 dl 1.14 for (Node[] tab = table;;) {
569     Node e; int i;
570     if (tab == null ||
571     (e = tabAt(tab, i = (tab.length - 1) & h)) == null)
572     return null;
573     else if (e.hash < 0)
574 dl 1.1 tab = (Node[])e.key;
575     else {
576 dl 1.14 Object oldVal = null;
577 dl 1.1 boolean validated = false;
578     boolean deleted = false;
579 jsr166 1.4 synchronized (e) {
580 dl 1.10 if (tabAt(tab, i) == e) {
581     validated = true;
582     Node pred = null;
583     do {
584     Object ek, ev;
585     if (e.hash == h &&
586 dl 1.14 ((ek = e.key) == k || k.equals(ek)) &&
587     ((ev = e.val) != null)) {
588 dl 1.1 if (cv == null || cv == ev || cv.equals(ev)) {
589     oldVal = ev;
590     if ((e.val = v) == null) {
591     deleted = true;
592     Node en = e.next;
593     if (pred != null)
594     pred.next = en;
595     else
596     setTabAt(tab, i, en);
597     }
598     }
599 dl 1.10 break;
600 dl 1.1 }
601 dl 1.14 } while ((e = (pred = e).next) != null);
602 dl 1.1 }
603     }
604     if (validated) {
605     if (deleted)
606     counter.decrement();
607 dl 1.14 return oldVal;
608 dl 1.1 }
609     }
610     }
611     }
612    
613 dl 1.14 /** Implementation for computeIfAbsent and compute. Like put, but messier. */
614 dl 1.1 @SuppressWarnings("unchecked")
615 dl 1.2 private final V internalCompute(K k,
616     MappingFunction<? super K, ? extends V> f,
617     boolean replace) {
618 dl 1.1 int h = spread(k.hashCode());
619     V val = null;
620     boolean added = false;
621     Node[] tab = table;
622 dl 1.14 outer:for (;;) {
623     Node e; int i; Object ek, ev;
624 dl 1.1 if (tab == null)
625 dl 1.14 tab = growTable();
626 dl 1.1 else if ((e = tabAt(tab, i = (tab.length - 1) & h)) == null) {
627 dl 1.2 Node node = new Node(h, k, null, null);
628 dl 1.10 boolean validated = false;
629 dl 1.14 synchronized (node) { // must lock while computing value
630 dl 1.1 if (casTabAt(tab, i, null, node)) {
631     validated = true;
632     try {
633     val = f.map(k);
634     if (val != null) {
635     node.val = val;
636     added = true;
637     }
638     } finally {
639     if (!added)
640     setTabAt(tab, i, null);
641     }
642     }
643     }
644 dl 1.10 if (validated)
645     break;
646 dl 1.1 }
647     else if (e.hash < 0)
648     tab = (Node[])e.key;
649 dl 1.14 else if (!replace && e.hash == h && (ev = e.val) != null &&
650     ((ek = e.key) == k || k.equals(ek))) {
651     if (tabAt(tab, i) == e) {
652     val = (V)ev;
653     break;
654     }
655     }
656 dl 1.5 else if (Thread.holdsLock(e))
657     throw new IllegalStateException("Recursive map computation");
658 dl 1.1 else {
659 dl 1.10 boolean validated = false;
660 dl 1.1 boolean checkSize = false;
661 jsr166 1.4 synchronized (e) {
662 dl 1.10 if (tabAt(tab, i) == e) {
663     validated = true;
664     for (Node first = e;;) {
665     if (e.hash == h &&
666 dl 1.14 ((ek = e.key) == k || k.equals(ek)) &&
667     ((ev = e.val) != null)) {
668     Object fv;
669 dl 1.10 if (replace && (fv = f.map(k)) != null)
670     ev = e.val = fv;
671 dl 1.1 val = (V)ev;
672 dl 1.10 break;
673 dl 1.1 }
674 dl 1.10 Node last = e;
675     if ((e = e.next) == null) {
676 dl 1.1 if ((val = f.map(k)) != null) {
677 dl 1.2 last.next = new Node(h, k, val, null);
678     added = true;
679     if (last != first || tab.length <= 64)
680 dl 1.1 checkSize = true;
681     }
682 dl 1.10 break;
683 dl 1.1 }
684     }
685     }
686     }
687 dl 1.10 if (validated) {
688     if (checkSize && tab.length < MAXIMUM_CAPACITY &&
689     resizing == 0 && counter.sum() >= threshold)
690 dl 1.14 growTable();
691 dl 1.10 break;
692     }
693 dl 1.1 }
694 dl 1.10 }
695 dl 1.1 if (added)
696     counter.increment();
697     return val;
698     }
699    
700     /**
701 dl 1.2 * Implementation for clear. Steps through each bin, removing all nodes.
702 dl 1.1 */
703     private final void internalClear() {
704 dl 1.14 long delta = 0L; // negative number of deletions
705 dl 1.1 int i = 0;
706     Node[] tab = table;
707     while (tab != null && i < tab.length) {
708     Node e = tabAt(tab, i);
709     if (e == null)
710     ++i;
711     else if (e.hash < 0)
712     tab = (Node[])e.key;
713     else {
714     boolean validated = false;
715 jsr166 1.4 synchronized (e) {
716 dl 1.1 if (tabAt(tab, i) == e) {
717     validated = true;
718 dl 1.14 Node en;
719 dl 1.1 do {
720 dl 1.14 en = e.next;
721     if (e.val != null) { // currently always true
722 dl 1.1 e.val = null;
723 dl 1.14 --delta;
724 dl 1.1 }
725 dl 1.14 } while ((e = en) != null);
726 dl 1.1 setTabAt(tab, i, null);
727     }
728     }
729 dl 1.14 if (validated)
730 dl 1.1 ++i;
731     }
732     }
733 dl 1.14 counter.add(delta);
734 dl 1.1 }
735    
736 dl 1.14 /* ----------------Table Traversal -------------- */
737    
738 dl 1.1 /**
739 dl 1.14 * Encapsulates traversal for methods such as containsValue; also
740     * serves as a base class for other iterators.
741     *
742     * At each step, the iterator snapshots the key ("nextKey") and
743     * value ("nextVal") of a valid node (i.e., one that, at point of
744     * snapshot, has a nonnull user value). Because val fields can
745     * change (including to null, indicating deletion), field nextVal
746     * might not be accurate at point of use, but still maintains the
747     * weak consistency property of holding a value that was once
748     * valid.
749     *
750     * Internal traversals directly access these fields, as in:
751     * {@code while (it.next != null) { process(nextKey); it.advance(); }}
752     *
753     * Exported iterators (subclasses of ViewIterator) extract key,
754     * value, or key-value pairs as return values of Iterator.next(),
755     * and encapulate the it.next check as hasNext();
756     *
757     * The iterator visits each valid node that was reachable upon
758     * iterator construction once. It might miss some that were added
759     * to a bin after the bin was visited, which is OK wrt consistency
760     * guarantees. Maintaining this property in the face of possible
761     * ongoing resizes requires a fair amount of bookkeeping state
762     * that is difficult to optimize away amidst volatile accesses.
763     * Even so, traversal maintains reasonable throughput.
764     *
765     * Normally, iteration proceeds bin-by-bin traversing lists.
766     * However, if the table has been resized, then all future steps
767     * must traverse both the bin at the current index as well as at
768     * (index + baseSize); and so on for further resizings. To
769     * paranoically cope with potential sharing by users of iterators
770     * across threads, iteration terminates if a bounds checks fails
771     * for a table read.
772     *
773     * The range-based constructor enables creation of parallel
774     * range-splitting traversals. (Not yet implemented.)
775     */
776     static class InternalIterator {
777     Node next; // the next entry to use
778     Node last; // the last entry used
779     Object nextKey; // cached key field of next
780     Object nextVal; // cached val field of next
781     Node[] tab; // current table; updated if resized
782     int index; // index of bin to use next
783     int baseIndex; // current index of initial table
784     final int baseLimit; // index bound for initial table
785     final int baseSize; // initial table size
786    
787     /** Creates iterator for all entries in the table. */
788     InternalIterator(Node[] tab) {
789     this.tab = tab;
790     baseLimit = baseSize = (tab == null) ? 0 : tab.length;
791     index = baseIndex = 0;
792     next = null;
793     advance();
794     }
795    
796     /** Creates iterator for the given range of the table */
797     InternalIterator(Node[] tab, int lo, int hi) {
798     this.tab = tab;
799     baseSize = (tab == null) ? 0 : tab.length;
800     baseLimit = (hi <= baseSize)? hi : baseSize;
801     index = baseIndex = lo;
802     next = null;
803     advance();
804     }
805    
806     /** Advances next. See above for explanation. */
807     final void advance() {
808     Node e = last = next;
809     outer: do {
810     if (e != null) // pass used or skipped node
811 dl 1.1 e = e.next;
812 dl 1.14 while (e == null) { // get to next non-null bin
813     Node[] t; int b, i, n; // checks must use locals
814     if ((b = baseIndex) >= baseLimit || (i = index) < 0 ||
815     (t = tab) == null || i >= (n = t.length))
816     break outer;
817     else if ((e = tabAt(t, i)) != null && e.hash < 0)
818     tab = (Node[])e.key; // restarts due to null val
819     else // visit upper slots if present
820     index = (i += baseSize) < n ? i : (baseIndex = b + 1);
821 dl 1.1 }
822 dl 1.14 nextKey = e.key;
823     } while ((nextVal = e.val) == null); // skip deleted or special nodes
824     next = e;
825 dl 1.1 }
826     }
827    
828     /* ---------------- Public operations -------------- */
829    
830     /**
831     * Creates a new, empty map with the specified initial
832     * capacity, load factor and concurrency level.
833     *
834     * @param initialCapacity the initial capacity. The implementation
835     * performs internal sizing to accommodate this many elements.
836     * @param loadFactor the load factor threshold, used to control resizing.
837     * Resizing may be performed when the average number of elements per
838     * bin exceeds this threshold.
839     * @param concurrencyLevel the estimated number of concurrently
840     * updating threads. The implementation may use this value as
841     * a sizing hint.
842     * @throws IllegalArgumentException if the initial capacity is
843     * negative or the load factor or concurrencyLevel are
844     * nonpositive.
845     */
846     public ConcurrentHashMapV8(int initialCapacity,
847 jsr166 1.9 float loadFactor, int concurrencyLevel) {
848 dl 1.14 if (!(loadFactor > 0.0f) || initialCapacity < 0 || concurrencyLevel <= 0)
849 dl 1.1 throw new IllegalArgumentException();
850 dl 1.14 int cap = tableSizeFor(initialCapacity);
851     this.counter = new LongAdder();
852 dl 1.1 this.loadFactor = loadFactor;
853 dl 1.14 this.targetCapacity = cap;
854 dl 1.1 }
855    
856     /**
857     * Creates a new, empty map with the specified initial capacity
858     * and load factor and with the default concurrencyLevel (16).
859     *
860     * @param initialCapacity The implementation performs internal
861     * sizing to accommodate this many elements.
862     * @param loadFactor the load factor threshold, used to control resizing.
863     * Resizing may be performed when the average number of elements per
864     * bin exceeds this threshold.
865     * @throws IllegalArgumentException if the initial capacity of
866     * elements is negative or the load factor is nonpositive
867     *
868     * @since 1.6
869     */
870     public ConcurrentHashMapV8(int initialCapacity, float loadFactor) {
871     this(initialCapacity, loadFactor, DEFAULT_CONCURRENCY_LEVEL);
872     }
873    
874     /**
875     * Creates a new, empty map with the specified initial capacity,
876     * and with default load factor (0.75) and concurrencyLevel (16).
877     *
878     * @param initialCapacity the initial capacity. The implementation
879     * performs internal sizing to accommodate this many elements.
880     * @throws IllegalArgumentException if the initial capacity of
881     * elements is negative.
882     */
883     public ConcurrentHashMapV8(int initialCapacity) {
884     this(initialCapacity, DEFAULT_LOAD_FACTOR, DEFAULT_CONCURRENCY_LEVEL);
885     }
886    
887     /**
888     * Creates a new, empty map with a default initial capacity (16),
889     * load factor (0.75) and concurrencyLevel (16).
890     */
891     public ConcurrentHashMapV8() {
892     this(DEFAULT_CAPACITY, DEFAULT_LOAD_FACTOR, DEFAULT_CONCURRENCY_LEVEL);
893     }
894    
895     /**
896     * Creates a new map with the same mappings as the given map.
897     * The map is created with a capacity of 1.5 times the number
898     * of mappings in the given map or 16 (whichever is greater),
899     * and a default load factor (0.75) and concurrencyLevel (16).
900     *
901     * @param m the map
902     */
903     public ConcurrentHashMapV8(Map<? extends K, ? extends V> m) {
904     this(DEFAULT_CAPACITY, DEFAULT_LOAD_FACTOR, DEFAULT_CONCURRENCY_LEVEL);
905 dl 1.14 putAll(m);
906 dl 1.1 }
907    
908     /**
909 dl 1.14 * {@inheritDoc}
910 dl 1.1 */
911     public boolean isEmpty() {
912 dl 1.2 return counter.sum() <= 0L; // ignore transient negative values
913 dl 1.1 }
914    
915     /**
916 dl 1.14 * {@inheritDoc}
917 dl 1.1 */
918     public int size() {
919     long n = counter.sum();
920 dl 1.14 return ((n < 0L)? 0 :
921     (n > (long)Integer.MAX_VALUE)? Integer.MAX_VALUE :
922     (int)n);
923 dl 1.1 }
924    
925     /**
926     * Returns the value to which the specified key is mapped,
927     * or {@code null} if this map contains no mapping for the key.
928     *
929     * <p>More formally, if this map contains a mapping from a key
930     * {@code k} to a value {@code v} such that {@code key.equals(k)},
931     * then this method returns {@code v}; otherwise it returns
932     * {@code null}. (There can be at most one such mapping.)
933     *
934     * @throws NullPointerException if the specified key is null
935     */
936     @SuppressWarnings("unchecked")
937     public V get(Object key) {
938     if (key == null)
939     throw new NullPointerException();
940     return (V)internalGet(key);
941     }
942    
943     /**
944     * Tests if the specified object is a key in this table.
945     *
946     * @param key possible key
947     * @return {@code true} if and only if the specified object
948     * is a key in this table, as determined by the
949     * {@code equals} method; {@code false} otherwise.
950     * @throws NullPointerException if the specified key is null
951     */
952     public boolean containsKey(Object key) {
953     if (key == null)
954     throw new NullPointerException();
955     return internalGet(key) != null;
956     }
957    
958     /**
959     * Returns {@code true} if this map maps one or more keys to the
960 dl 1.14 * specified value. Note: This method may require a full traversal
961     * of the map, and is much slower than method {@code containsKey}.
962 dl 1.1 *
963     * @param value value whose presence in this map is to be tested
964     * @return {@code true} if this map maps one or more keys to the
965     * specified value
966     * @throws NullPointerException if the specified value is null
967     */
968     public boolean containsValue(Object value) {
969     if (value == null)
970     throw new NullPointerException();
971 dl 1.14 Object v;
972     InternalIterator it = new InternalIterator(table);
973     while (it.next != null) {
974     if ((v = it.nextVal) == value || value.equals(v))
975     return true;
976     it.advance();
977     }
978     return false;
979 dl 1.1 }
980    
981     /**
982     * Legacy method testing if some key maps into the specified value
983     * in this table. This method is identical in functionality to
984     * {@link #containsValue}, and exists solely to ensure
985     * full compatibility with class {@link java.util.Hashtable},
986     * which supported this method prior to introduction of the
987     * Java Collections framework.
988     *
989     * @param value a value to search for
990     * @return {@code true} if and only if some key maps to the
991     * {@code value} argument in this table as
992     * determined by the {@code equals} method;
993     * {@code false} otherwise
994     * @throws NullPointerException if the specified value is null
995     */
996     public boolean contains(Object value) {
997     return containsValue(value);
998     }
999    
1000     /**
1001     * Maps the specified key to the specified value in this table.
1002     * Neither the key nor the value can be null.
1003     *
1004     * <p> The value can be retrieved by calling the {@code get} method
1005     * with a key that is equal to the original key.
1006     *
1007     * @param key key with which the specified value is to be associated
1008     * @param value value to be associated with the specified key
1009     * @return the previous value associated with {@code key}, or
1010     * {@code null} if there was no mapping for {@code key}
1011     * @throws NullPointerException if the specified key or value is null
1012     */
1013     @SuppressWarnings("unchecked")
1014     public V put(K key, V value) {
1015     if (key == null || value == null)
1016     throw new NullPointerException();
1017     return (V)internalPut(key, value, true);
1018     }
1019    
1020     /**
1021     * {@inheritDoc}
1022     *
1023     * @return the previous value associated with the specified key,
1024     * or {@code null} if there was no mapping for the key
1025     * @throws NullPointerException if the specified key or value is null
1026     */
1027     @SuppressWarnings("unchecked")
1028     public V putIfAbsent(K key, V value) {
1029     if (key == null || value == null)
1030     throw new NullPointerException();
1031     return (V)internalPut(key, value, false);
1032     }
1033    
1034     /**
1035     * Copies all of the mappings from the specified map to this one.
1036     * These mappings replace any mappings that this map had for any of the
1037     * keys currently in the specified map.
1038     *
1039     * @param m mappings to be stored in this map
1040     */
1041     public void putAll(Map<? extends K, ? extends V> m) {
1042     if (m == null)
1043     throw new NullPointerException();
1044 dl 1.14 /*
1045     * If uninitialized, try to adjust targetCapacity to
1046     * accommodate the given number of elements.
1047     */
1048     if (table == null) {
1049     int size = m.size();
1050     int cap = (size >= (MAXIMUM_CAPACITY >>> 1)) ? MAXIMUM_CAPACITY :
1051     tableSizeFor(size + (size >>> 1));
1052     if (cap > targetCapacity)
1053     targetCapacity = cap;
1054     }
1055     for (Map.Entry<? extends K, ? extends V> e : m.entrySet())
1056     put(e.getKey(), e.getValue());
1057 dl 1.1 }
1058    
1059     /**
1060     * If the specified key is not already associated with a value,
1061     * computes its value using the given mappingFunction, and if
1062     * non-null, enters it into the map. This is equivalent to
1063 jsr166 1.13 * <pre> {@code
1064     * if (map.containsKey(key))
1065     * return map.get(key);
1066     * value = mappingFunction.map(key);
1067     * if (value != null)
1068     * map.put(key, value);
1069     * return value;}</pre>
1070 dl 1.1 *
1071     * except that the action is performed atomically. Some attempted
1072 dl 1.5 * update operations on this map by other threads may be blocked
1073     * while computation is in progress, so the computation should be
1074     * short and simple, and must not attempt to update any other
1075     * mappings of this Map. The most appropriate usage is to
1076     * construct a new object serving as an initial mapped value, or
1077     * memoized result, as in:
1078 jsr166 1.13 * <pre> {@code
1079 dl 1.5 * map.computeIfAbsent(key, new MappingFunction<K, V>() {
1080 jsr166 1.13 * public V map(K k) { return new Value(f(k)); }});}</pre>
1081 dl 1.1 *
1082     * @param key key with which the specified value is to be associated
1083     * @param mappingFunction the function to compute a value
1084     * @return the current (existing or computed) value associated with
1085     * the specified key, or {@code null} if the computation
1086     * returned {@code null}.
1087     * @throws NullPointerException if the specified key or mappingFunction
1088     * is null,
1089 dl 1.5 * @throws IllegalStateException if the computation detectably
1090     * attempts a recursive update to this map that would
1091     * otherwise never complete.
1092 dl 1.1 * @throws RuntimeException or Error if the mappingFunction does so,
1093     * in which case the mapping is left unestablished.
1094     */
1095     public V computeIfAbsent(K key, MappingFunction<? super K, ? extends V> mappingFunction) {
1096     if (key == null || mappingFunction == null)
1097     throw new NullPointerException();
1098 dl 1.2 return internalCompute(key, mappingFunction, false);
1099     }
1100    
1101     /**
1102 dl 1.5 * Computes the value associated with the given key using the given
1103 dl 1.2 * mappingFunction, and if non-null, enters it into the map. This
1104     * is equivalent to
1105 jsr166 1.13 * <pre> {@code
1106     * value = mappingFunction.map(key);
1107     * if (value != null)
1108     * map.put(key, value);
1109     * else
1110     * value = map.get(key);
1111     * return value;}</pre>
1112 dl 1.2 *
1113     * except that the action is performed atomically. Some attempted
1114 dl 1.5 * update operations on this map by other threads may be blocked
1115     * while computation is in progress, so the computation should be
1116     * short and simple, and must not attempt to update any other
1117     * mappings of this Map.
1118 dl 1.2 *
1119     * @param key key with which the specified value is to be associated
1120     * @param mappingFunction the function to compute a value
1121     * @return the current value associated with
1122     * the specified key, or {@code null} if the computation
1123     * returned {@code null} and the value was not otherwise present.
1124     * @throws NullPointerException if the specified key or mappingFunction
1125     * is null,
1126 dl 1.5 * @throws IllegalStateException if the computation detectably
1127     * attempts a recursive update to this map that would
1128     * otherwise never complete.
1129 dl 1.2 * @throws RuntimeException or Error if the mappingFunction does so,
1130     * in which case the mapping is unchanged.
1131     */
1132     public V compute(K key, MappingFunction<? super K, ? extends V> mappingFunction) {
1133     if (key == null || mappingFunction == null)
1134     throw new NullPointerException();
1135     return internalCompute(key, mappingFunction, true);
1136 dl 1.1 }
1137    
1138     /**
1139     * Removes the key (and its corresponding value) from this map.
1140     * This method does nothing if the key is not in the map.
1141     *
1142     * @param key the key that needs to be removed
1143     * @return the previous value associated with {@code key}, or
1144     * {@code null} if there was no mapping for {@code key}
1145     * @throws NullPointerException if the specified key is null
1146     */
1147     @SuppressWarnings("unchecked")
1148     public V remove(Object key) {
1149     if (key == null)
1150     throw new NullPointerException();
1151 jsr166 1.3 return (V)internalReplace(key, null, null);
1152 dl 1.1 }
1153    
1154     /**
1155     * {@inheritDoc}
1156     *
1157     * @throws NullPointerException if the specified key is null
1158     */
1159     public boolean remove(Object key, Object value) {
1160     if (key == null)
1161     throw new NullPointerException();
1162     if (value == null)
1163     return false;
1164     return internalReplace(key, null, value) != null;
1165     }
1166    
1167     /**
1168     * {@inheritDoc}
1169     *
1170     * @throws NullPointerException if any of the arguments are null
1171     */
1172     public boolean replace(K key, V oldValue, V newValue) {
1173     if (key == null || oldValue == null || newValue == null)
1174     throw new NullPointerException();
1175 jsr166 1.3 return internalReplace(key, newValue, oldValue) != null;
1176 dl 1.1 }
1177    
1178     /**
1179     * {@inheritDoc}
1180     *
1181     * @return the previous value associated with the specified key,
1182     * or {@code null} if there was no mapping for the key
1183     * @throws NullPointerException if the specified key or value is null
1184     */
1185     @SuppressWarnings("unchecked")
1186     public V replace(K key, V value) {
1187     if (key == null || value == null)
1188     throw new NullPointerException();
1189 jsr166 1.3 return (V)internalReplace(key, value, null);
1190 dl 1.1 }
1191    
1192     /**
1193     * Removes all of the mappings from this map.
1194     */
1195     public void clear() {
1196     internalClear();
1197     }
1198    
1199     /**
1200     * Returns a {@link Set} view of the keys contained in this map.
1201     * The set is backed by the map, so changes to the map are
1202     * reflected in the set, and vice-versa. The set supports element
1203     * removal, which removes the corresponding mapping from this map,
1204     * via the {@code Iterator.remove}, {@code Set.remove},
1205     * {@code removeAll}, {@code retainAll}, and {@code clear}
1206     * operations. It does not support the {@code add} or
1207     * {@code addAll} operations.
1208     *
1209     * <p>The view's {@code iterator} is a "weakly consistent" iterator
1210     * that will never throw {@link ConcurrentModificationException},
1211     * and guarantees to traverse elements as they existed upon
1212     * construction of the iterator, and may (but is not guaranteed to)
1213     * reflect any modifications subsequent to construction.
1214     */
1215     public Set<K> keySet() {
1216 dl 1.14 KeySet<K,V> ks = keySet;
1217     return (ks != null) ? ks : (keySet = new KeySet<K,V>(this));
1218 dl 1.1 }
1219    
1220     /**
1221     * Returns a {@link Collection} view of the values contained in this map.
1222     * The collection is backed by the map, so changes to the map are
1223     * reflected in the collection, and vice-versa. The collection
1224     * supports element removal, which removes the corresponding
1225     * mapping from this map, via the {@code Iterator.remove},
1226     * {@code Collection.remove}, {@code removeAll},
1227     * {@code retainAll}, and {@code clear} operations. It does not
1228     * support the {@code add} or {@code addAll} operations.
1229     *
1230     * <p>The view's {@code iterator} is a "weakly consistent" iterator
1231     * that will never throw {@link ConcurrentModificationException},
1232     * and guarantees to traverse elements as they existed upon
1233     * construction of the iterator, and may (but is not guaranteed to)
1234     * reflect any modifications subsequent to construction.
1235     */
1236     public Collection<V> values() {
1237 dl 1.14 Values<K,V> vs = values;
1238     return (vs != null) ? vs : (values = new Values<K,V>(this));
1239 dl 1.1 }
1240    
1241     /**
1242     * Returns a {@link Set} view of the mappings contained in this map.
1243     * The set is backed by the map, so changes to the map are
1244     * reflected in the set, and vice-versa. The set supports element
1245     * removal, which removes the corresponding mapping from the map,
1246     * via the {@code Iterator.remove}, {@code Set.remove},
1247     * {@code removeAll}, {@code retainAll}, and {@code clear}
1248     * operations. It does not support the {@code add} or
1249     * {@code addAll} operations.
1250     *
1251     * <p>The view's {@code iterator} is a "weakly consistent" iterator
1252     * that will never throw {@link ConcurrentModificationException},
1253     * and guarantees to traverse elements as they existed upon
1254     * construction of the iterator, and may (but is not guaranteed to)
1255     * reflect any modifications subsequent to construction.
1256     */
1257     public Set<Map.Entry<K,V>> entrySet() {
1258 dl 1.14 EntrySet<K,V> es = entrySet;
1259     return (es != null) ? es : (entrySet = new EntrySet<K,V>(this));
1260 dl 1.1 }
1261    
1262     /**
1263     * Returns an enumeration of the keys in this table.
1264     *
1265     * @return an enumeration of the keys in this table
1266     * @see #keySet()
1267     */
1268     public Enumeration<K> keys() {
1269 dl 1.14 return new KeyIterator<K,V>(this);
1270 dl 1.1 }
1271    
1272     /**
1273     * Returns an enumeration of the values in this table.
1274     *
1275     * @return an enumeration of the values in this table
1276     * @see #values()
1277     */
1278     public Enumeration<V> elements() {
1279 dl 1.14 return new ValueIterator<K,V>(this);
1280 dl 1.1 }
1281    
1282     /**
1283 dl 1.2 * Returns the hash code value for this {@link Map}, i.e.,
1284     * the sum of, for each key-value pair in the map,
1285     * {@code key.hashCode() ^ value.hashCode()}.
1286     *
1287     * @return the hash code value for this map
1288 dl 1.1 */
1289     public int hashCode() {
1290 dl 1.14 int h = 0;
1291     InternalIterator it = new InternalIterator(table);
1292     while (it.next != null) {
1293     h += it.nextKey.hashCode() ^ it.nextVal.hashCode();
1294     it.advance();
1295     }
1296     return h;
1297 dl 1.1 }
1298    
1299     /**
1300 dl 1.2 * Returns a string representation of this map. The string
1301     * representation consists of a list of key-value mappings (in no
1302     * particular order) enclosed in braces ("{@code {}}"). Adjacent
1303     * mappings are separated by the characters {@code ", "} (comma
1304     * and space). Each key-value mapping is rendered as the key
1305     * followed by an equals sign ("{@code =}") followed by the
1306     * associated value.
1307     *
1308     * @return a string representation of this map
1309 dl 1.1 */
1310     public String toString() {
1311 dl 1.14 InternalIterator it = new InternalIterator(table);
1312     StringBuilder sb = new StringBuilder();
1313     sb.append('{');
1314     if (it.next != null) {
1315     for (;;) {
1316     Object k = it.nextKey, v = it.nextVal;
1317     sb.append(k == this ? "(this Map)" : k);
1318     sb.append('=');
1319     sb.append(v == this ? "(this Map)" : v);
1320     it.advance();
1321     if (it.next == null)
1322     break;
1323     sb.append(',').append(' ');
1324     }
1325     }
1326     return sb.append('}').toString();
1327 dl 1.1 }
1328    
1329     /**
1330 dl 1.2 * Compares the specified object with this map for equality.
1331     * Returns {@code true} if the given object is a map with the same
1332     * mappings as this map. This operation may return misleading
1333     * results if either map is concurrently modified during execution
1334     * of this method.
1335     *
1336     * @param o object to be compared for equality with this map
1337     * @return {@code true} if the specified object is equal to this map
1338 dl 1.1 */
1339     public boolean equals(Object o) {
1340 dl 1.14 if (o != this) {
1341     if (!(o instanceof Map))
1342     return false;
1343     Map<?,?> m = (Map<?,?>) o;
1344     InternalIterator it = new InternalIterator(table);
1345     while (it.next != null) {
1346     Object val = it.nextVal;
1347     Object v = m.get(it.nextKey);
1348     if (v == null || (v != val && !v.equals(val)))
1349 dl 1.1 return false;
1350 dl 1.14 it.advance();
1351     }
1352 dl 1.1 for (Map.Entry<?,?> e : m.entrySet()) {
1353 dl 1.14 Object mk, mv, v;
1354     if ((mk = e.getKey()) == null ||
1355     (mv = e.getValue()) == null ||
1356     (v = internalGet(mk)) == null ||
1357     (mv != v && !mv.equals(v)))
1358 dl 1.1 return false;
1359     }
1360 dl 1.14 }
1361     return true;
1362     }
1363    
1364     /* ----------------Iterators -------------- */
1365    
1366     /**
1367     * Base class for key, value, and entry iterators. Adds a map
1368     * reference to InternalIterator to support Iterator.remove.
1369     */
1370     static abstract class ViewIterator<K,V> extends InternalIterator {
1371     final ConcurrentHashMapV8<K, V> map;
1372     ViewIterator(ConcurrentHashMapV8<K, V> map) {
1373     super(map.table);
1374     this.map = map;
1375     }
1376    
1377     public final void remove() {
1378     if (last == null)
1379     throw new IllegalStateException();
1380     map.remove(last.key);
1381     last = null;
1382     }
1383    
1384     public final boolean hasNext() { return next != null; }
1385     public final boolean hasMoreElements() { return next != null; }
1386     }
1387    
1388     static final class KeyIterator<K,V> extends ViewIterator<K,V>
1389     implements Iterator<K>, Enumeration<K> {
1390     KeyIterator(ConcurrentHashMapV8<K, V> map) { super(map); }
1391    
1392     @SuppressWarnings("unchecked")
1393     public final K next() {
1394     if (next == null)
1395     throw new NoSuchElementException();
1396     Object k = nextKey;
1397     advance();
1398     return (K)k;
1399     }
1400    
1401     public final K nextElement() { return next(); }
1402     }
1403    
1404     static final class ValueIterator<K,V> extends ViewIterator<K,V>
1405     implements Iterator<V>, Enumeration<V> {
1406     ValueIterator(ConcurrentHashMapV8<K, V> map) { super(map); }
1407    
1408     @SuppressWarnings("unchecked")
1409     public final V next() {
1410     if (next == null)
1411     throw new NoSuchElementException();
1412     Object v = nextVal;
1413     advance();
1414     return (V)v;
1415     }
1416    
1417     public final V nextElement() { return next(); }
1418     }
1419    
1420     static final class EntryIterator<K,V> extends ViewIterator<K,V>
1421     implements Iterator<Map.Entry<K,V>> {
1422     EntryIterator(ConcurrentHashMapV8<K, V> map) { super(map); }
1423    
1424     @SuppressWarnings("unchecked")
1425     public final Map.Entry<K,V> next() {
1426     if (next == null)
1427     throw new NoSuchElementException();
1428     Object k = nextKey;
1429     Object v = nextVal;
1430     advance();
1431     return new WriteThroughEntry<K,V>(map, (K)k, (V)v);
1432 dl 1.1 }
1433     }
1434    
1435     /**
1436     * Custom Entry class used by EntryIterator.next(), that relays
1437     * setValue changes to the underlying map.
1438     */
1439 dl 1.14 static final class WriteThroughEntry<K,V> implements Map.Entry<K, V> {
1440     final ConcurrentHashMapV8<K, V> map;
1441     final K key; // non-null
1442     V val; // non-null
1443     WriteThroughEntry(ConcurrentHashMapV8<K, V> map, K key, V val) {
1444     this.map = map; this.key = key; this.val = val;
1445     }
1446    
1447     public final K getKey() { return key; }
1448     public final V getValue() { return val; }
1449     public final int hashCode() { return key.hashCode() ^ val.hashCode(); }
1450     public final String toString(){ return key + "=" + val; }
1451    
1452     public final boolean equals(Object o) {
1453     Object k, v; Map.Entry<?,?> e;
1454     return ((o instanceof Map.Entry) &&
1455     (k = (e = (Map.Entry<?,?>)o).getKey()) != null &&
1456     (v = e.getValue()) != null &&
1457     (k == key || k.equals(key)) &&
1458     (v == val || v.equals(val)));
1459 dl 1.1 }
1460    
1461     /**
1462     * Sets our entry's value and writes through to the map. The
1463     * value to return is somewhat arbitrary here. Since a
1464     * WriteThroughEntry does not necessarily track asynchronous
1465     * changes, the most recent "previous" value could be
1466     * different from what we return (or could even have been
1467     * removed in which case the put will re-establish). We do not
1468     * and cannot guarantee more.
1469     */
1470 dl 1.14 public final V setValue(V value) {
1471 dl 1.1 if (value == null) throw new NullPointerException();
1472 dl 1.14 V v = val;
1473     val = value;
1474     map.put(key, value);
1475 dl 1.1 return v;
1476     }
1477     }
1478    
1479 dl 1.14 /* ----------------Views -------------- */
1480 dl 1.1
1481 dl 1.14 /*
1482     * These currently just extend java.util.AbstractX classes, but
1483     * may need a new custom base to support partitioned traversal.
1484     */
1485 dl 1.1
1486 dl 1.14 static final class KeySet<K,V> extends AbstractSet<K> {
1487     final ConcurrentHashMapV8<K, V> map;
1488     KeySet(ConcurrentHashMapV8<K, V> map) { this.map = map; }
1489 dl 1.1
1490 dl 1.14 public final int size() { return map.size(); }
1491     public final boolean isEmpty() { return map.isEmpty(); }
1492     public final void clear() { map.clear(); }
1493     public final boolean contains(Object o) { return map.containsKey(o); }
1494     public final boolean remove(Object o) { return map.remove(o) != null; }
1495     public final Iterator<K> iterator() {
1496     return new KeyIterator<K,V>(map);
1497 dl 1.1 }
1498     }
1499    
1500 dl 1.14 static final class Values<K,V> extends AbstractCollection<V> {
1501     final ConcurrentHashMapV8<K, V> map;
1502     Values(ConcurrentHashMapV8<K, V> map) { this.map = map; }
1503    
1504     public final int size() { return map.size(); }
1505     public final boolean isEmpty() { return map.isEmpty(); }
1506     public final void clear() { map.clear(); }
1507     public final boolean contains(Object o) { return map.containsValue(o); }
1508     public final Iterator<V> iterator() {
1509     return new ValueIterator<K,V>(map);
1510 dl 1.1 }
1511     }
1512    
1513 dl 1.14 static final class EntrySet<K,V> extends AbstractSet<Map.Entry<K,V>> {
1514     final ConcurrentHashMapV8<K, V> map;
1515     EntrySet(ConcurrentHashMapV8<K, V> map) { this.map = map; }
1516    
1517     public final int size() { return map.size(); }
1518     public final boolean isEmpty() { return map.isEmpty(); }
1519     public final void clear() { map.clear(); }
1520     public final Iterator<Map.Entry<K,V>> iterator() {
1521     return new EntryIterator<K,V>(map);
1522 dl 1.1 }
1523 dl 1.14
1524     public final boolean contains(Object o) {
1525     Object k, v, r; Map.Entry<?,?> e;
1526     return ((o instanceof Map.Entry) &&
1527     (k = (e = (Map.Entry<?,?>)o).getKey()) != null &&
1528     (r = map.get(k)) != null &&
1529     (v = e.getValue()) != null &&
1530     (v == r || v.equals(r)));
1531 dl 1.1 }
1532 dl 1.14
1533     public final boolean remove(Object o) {
1534     Object k, v; Map.Entry<?,?> e;
1535     return ((o instanceof Map.Entry) &&
1536     (k = (e = (Map.Entry<?,?>)o).getKey()) != null &&
1537     (v = e.getValue()) != null &&
1538     map.remove(k, v));
1539 dl 1.1 }
1540     }
1541    
1542     /* ---------------- Serialization Support -------------- */
1543    
1544     /**
1545 dl 1.14 * Stripped-down version of helper class used in previous version,
1546     * declared for the sake of serialization compatibility
1547 dl 1.1 */
1548 dl 1.14 static class Segment<K,V> implements Serializable {
1549 dl 1.1 private static final long serialVersionUID = 2249069246763182397L;
1550     final float loadFactor;
1551     Segment(float lf) { this.loadFactor = lf; }
1552     }
1553    
1554     /**
1555     * Saves the state of the {@code ConcurrentHashMapV8} instance to a
1556     * stream (i.e., serializes it).
1557     * @param s the stream
1558     * @serialData
1559     * the key (Object) and value (Object)
1560     * for each key-value mapping, followed by a null pair.
1561     * The key-value mappings are emitted in no particular order.
1562     */
1563     @SuppressWarnings("unchecked")
1564     private void writeObject(java.io.ObjectOutputStream s)
1565     throws java.io.IOException {
1566     if (segments == null) { // for serialization compatibility
1567     segments = (Segment<K,V>[])
1568     new Segment<?,?>[DEFAULT_CONCURRENCY_LEVEL];
1569     for (int i = 0; i < segments.length; ++i)
1570 dl 1.14 segments[i] = new Segment<K,V>(DEFAULT_LOAD_FACTOR);
1571 dl 1.1 }
1572     s.defaultWriteObject();
1573 dl 1.14 InternalIterator it = new InternalIterator(table);
1574     while (it.next != null) {
1575     s.writeObject(it.nextKey);
1576     s.writeObject(it.nextVal);
1577     it.advance();
1578     }
1579 dl 1.1 s.writeObject(null);
1580     s.writeObject(null);
1581     segments = null; // throw away
1582     }
1583    
1584     /**
1585 jsr166 1.9 * Reconstitutes the instance from a stream (that is, deserializes it).
1586 dl 1.1 * @param s the stream
1587     */
1588     @SuppressWarnings("unchecked")
1589     private void readObject(java.io.ObjectInputStream s)
1590     throws java.io.IOException, ClassNotFoundException {
1591     s.defaultReadObject();
1592     this.segments = null; // unneeded
1593 dl 1.14 // initalize transient final fields
1594     UNSAFE.putObjectVolatile(this, counterOffset, new LongAdder());
1595     UNSAFE.putFloatVolatile(this, loadFactorOffset, DEFAULT_LOAD_FACTOR);
1596     this.targetCapacity = DEFAULT_CAPACITY;
1597    
1598     // Create all nodes, then place in table once size is known
1599     long size = 0L;
1600     Node p = null;
1601 dl 1.1 for (;;) {
1602 dl 1.14 K k = (K) s.readObject();
1603     V v = (V) s.readObject();
1604     if (k != null && v != null) {
1605     p = new Node(spread(k.hashCode()), k, v, p);
1606     ++size;
1607     }
1608     else
1609 dl 1.1 break;
1610 dl 1.14 }
1611     if (p != null) {
1612     boolean init = false;
1613     if (resizing == 0 &&
1614     UNSAFE.compareAndSwapInt(this, resizingOffset, 0, 1)) {
1615     try {
1616     if (table == null) {
1617     init = true;
1618     int n;
1619     if (size >= (long)(MAXIMUM_CAPACITY >>> 1))
1620     n = MAXIMUM_CAPACITY;
1621     else {
1622     int sz = (int)size;
1623     n = tableSizeFor(sz + (sz >>> 1));
1624     }
1625     threshold = (n - (n >>> 2)) - THRESHOLD_OFFSET;
1626     Node[] tab = new Node[n];
1627     int mask = n - 1;
1628     while (p != null) {
1629     int j = p.hash & mask;
1630     Node next = p.next;
1631     p.next = tabAt(tab, j);
1632     setTabAt(tab, j, p);
1633     p = next;
1634     }
1635     table = tab;
1636     counter.add(size);
1637     }
1638     } finally {
1639     resizing = 0;
1640     }
1641     }
1642     if (!init) { // Can only happen if unsafely published.
1643     while (p != null) {
1644     internalPut(p.key, p.val, true);
1645     p = p.next;
1646     }
1647     }
1648 dl 1.1 }
1649     }
1650    
1651     // Unsafe mechanics
1652     private static final sun.misc.Unsafe UNSAFE;
1653     private static final long counterOffset;
1654 dl 1.14 private static final long loadFactorOffset;
1655 dl 1.1 private static final long resizingOffset;
1656     private static final long ABASE;
1657     private static final int ASHIFT;
1658    
1659     static {
1660     int ss;
1661     try {
1662     UNSAFE = getUnsafe();
1663     Class<?> k = ConcurrentHashMapV8.class;
1664     counterOffset = UNSAFE.objectFieldOffset
1665     (k.getDeclaredField("counter"));
1666 dl 1.14 loadFactorOffset = UNSAFE.objectFieldOffset
1667     (k.getDeclaredField("loadFactor"));
1668 dl 1.1 resizingOffset = UNSAFE.objectFieldOffset
1669     (k.getDeclaredField("resizing"));
1670     Class<?> sc = Node[].class;
1671     ABASE = UNSAFE.arrayBaseOffset(sc);
1672     ss = UNSAFE.arrayIndexScale(sc);
1673     } catch (Exception e) {
1674     throw new Error(e);
1675     }
1676     if ((ss & (ss-1)) != 0)
1677     throw new Error("data type scale not a power of two");
1678     ASHIFT = 31 - Integer.numberOfLeadingZeros(ss);
1679     }
1680    
1681     /**
1682     * Returns a sun.misc.Unsafe. Suitable for use in a 3rd party package.
1683     * Replace with a simple call to Unsafe.getUnsafe when integrating
1684     * into a jdk.
1685     *
1686     * @return a sun.misc.Unsafe
1687     */
1688     private static sun.misc.Unsafe getUnsafe() {
1689     try {
1690     return sun.misc.Unsafe.getUnsafe();
1691     } catch (SecurityException se) {
1692     try {
1693     return java.security.AccessController.doPrivileged
1694     (new java.security
1695     .PrivilegedExceptionAction<sun.misc.Unsafe>() {
1696     public sun.misc.Unsafe run() throws Exception {
1697     java.lang.reflect.Field f = sun.misc
1698     .Unsafe.class.getDeclaredField("theUnsafe");
1699     f.setAccessible(true);
1700     return (sun.misc.Unsafe) f.get(null);
1701     }});
1702     } catch (java.security.PrivilegedActionException e) {
1703     throw new RuntimeException("Could not initialize intrinsics",
1704     e.getCause());
1705     }
1706     }
1707     }
1708    
1709     }