summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorTahg <tahgtahv@gmail.com>2011-03-07 13:43:26 -0500
committerTahg <tahgtahv@gmail.com>2011-03-10 13:04:59 -0500
commit67cf10656c4328164331a2411286f5045ec6f6d9 (patch)
treefb500345e5f34e61e2ae0c5ec8b3af6d3be8af46
parent54a05f3ce2a06b5700b7d08aa24bad20dc114ac5 (diff)
downloadcraftbukkit-67cf10656c4328164331a2411286f5045ec6f6d9.tar
craftbukkit-67cf10656c4328164331a2411286f5045ec6f6d9.tar.gz
craftbukkit-67cf10656c4328164331a2411286f5045ec6f6d9.tar.lz
craftbukkit-67cf10656c4328164331a2411286f5045ec6f6d9.tar.xz
craftbukkit-67cf10656c4328164331a2411286f5045ec6f6d9.zip
Add locks to Hashset
-rw-r--r--src/main/java/org/bukkit/craftbukkit/util/LongHashset.java191
1 files changed, 128 insertions, 63 deletions
diff --git a/src/main/java/org/bukkit/craftbukkit/util/LongHashset.java b/src/main/java/org/bukkit/craftbukkit/util/LongHashset.java
index 2f8c2ccb..4422ec07 100644
--- a/src/main/java/org/bukkit/craftbukkit/util/LongHashset.java
+++ b/src/main/java/org/bukkit/craftbukkit/util/LongHashset.java
@@ -1,14 +1,27 @@
package org.bukkit.craftbukkit.util;
+
import static org.bukkit.craftbukkit.util.Java15Compat.Arrays_copyOf;
+import java.util.concurrent.locks.ReentrantReadWriteLock;
+import java.util.concurrent.locks.ReentrantReadWriteLock.ReadLock;
+import java.util.concurrent.locks.ReentrantReadWriteLock.WriteLock;
-public class LongHashset extends LongHash {
+public class LongHashset extends LongHash
+{
long values[][][] = new long[256][][];
int count = 0;
-
+ ReentrantReadWriteLock rwl = new ReentrantReadWriteLock();
+ ReadLock rl = rwl.readLock();
+ WriteLock wl = rwl.writeLock();
+
public boolean isEmpty() {
- return count == 0;
+ rl.lock();
+ try {
+ return count == 0;
+ } finally {
+ rl.unlock();
+ }
}
-
+
public void add(int msw, int lsw) {
add(toLong(msw, lsw));
}
@@ -16,90 +29,142 @@ public class LongHashset extends LongHash {
public void add(long key) {
int mainIdx = (int) (key & 255);
int outerIdx = (int) ((key >> 32) & 255);
- long outer[][] = values[mainIdx], inner[];
- if(outer == null) values[mainIdx] = outer = new long[256][];
- inner = outer[outerIdx];
- if(inner == null) {
- outer[outerIdx] = inner = new long[1];
- inner[0] = key;
- count++;
- }
- else {
- int i;
- for(i = 0; i < inner.length; i++) {
- if(inner[i] == key) {
- return;
+ rl.lock();
+ try {
+ wl.lock();
+ try {
+ long outer[][] = values[mainIdx], inner[];
+ if (outer == null)
+ values[mainIdx] = outer = new long[256][];
+ inner = outer[outerIdx];
+ if (inner == null) {
+ synchronized (this) {
+ outer[outerIdx] = inner = new long[1];
+ inner[0] = key;
+ count++;
+ }
+ } else {
+ int i;
+ for (i = 0; i < inner.length; i++) {
+ if (inner[i] == key) {
+ return;
+ }
+ }
+ inner = Arrays_copyOf(inner, i + 1);
+ outer[outerIdx] = inner;
+ inner[i] = key;
+ count++;
}
+ } finally {
+ wl.unlock();
}
- outer[outerIdx] = inner = Arrays_copyOf(inner, i+1);
- inner[i] = key;
- count++;
+ } finally {
+ rl.unlock();
}
}
-
+
public boolean containsKey(long key) {
int mainIdx = (int) (key & 255);
int outerIdx = (int) ((key >> 32) & 255);
- long outer[][] = values[mainIdx], inner[];
- if(outer == null) return false;
- inner = outer[outerIdx];
- if(inner == null) return false;
- else {
- for(long entry : inner) {
- if(entry == key) return true;
+ rl.lock();
+ try {
+ long outer[][] = values[mainIdx], inner[];
+ if (outer == null)
+ return false;
+ inner = outer[outerIdx];
+ if (inner == null)
+ return false;
+ else {
+ for (long entry : inner) {
+ if (entry == key)
+ return true;
+ }
+ return false;
}
- return false;
+ } finally {
+ rl.unlock();
}
}
-
+
public void remove(long key) {
- long[][] outer = this.values[(int) (key & 255)];
- if (outer == null) return;
+ rl.lock();
+ try {
+ long[][] outer = this.values[(int) (key & 255)];
+ if (outer == null)
+ return;
- long[] inner = outer[(int) ((key >> 32) & 255)];
- if (inner == null) return;
-
- int max = inner.length - 1;
- for(int i = 0; i <= max; i++) {
- if(inner[i] == key) {
- count--;
- if(i != max) {
- inner[i] = inner[max];
- }
- outer[(int) ((key >> 32) & 255)] = (max == 0 ? null : Arrays_copyOf(inner, max));
+ long[] inner = outer[(int) ((key >> 32) & 255)];
+ if (inner == null)
return;
+
+ int max = inner.length - 1;
+ for (int i = 0; i <= max; i++) {
+ if (inner[i] == key) {
+ wl.lock();
+ try {
+ count--;
+ if (i != max) {
+ inner[i] = inner[max];
+ }
+ outer[(int) ((key >> 32) & 255)] = (max == 0 ? null : Arrays_copyOf(inner, max));
+ } finally {
+ wl.unlock();
+ }
+ return;
+ }
}
+ } finally {
+ rl.unlock();
}
}
-
+
public long popFirst() {
- for(long[][] outer : values) {
- if(outer == null) continue;
- for(int i = 0; i < outer.length ; i++) {
- long[] inner = outer[i];
- if(inner == null || inner.length == 0) continue;
- count--;
- long ret = inner[inner.length - 1];
- outer[i] = Arrays_copyOf(inner, inner.length - 1);
- return ret;
-
+ rl.lock();
+ try {
+ for (long[][] outer : values) {
+ if (outer == null)
+ continue;
+ for (int i = 0; i < outer.length; i++) {
+ long[] inner = outer[i];
+ if (inner == null || inner.length == 0)
+ continue;
+ wl.lock();
+ try {
+ count--;
+ long ret = inner[inner.length - 1];
+ outer[i] = Arrays_copyOf(inner, inner.length - 1);
+ return ret;
+ } finally {
+ wl.unlock();
+ }
+
+ }
}
+ } finally {
+ rl.unlock();
}
return 0;
}
-
+
public long[] keys() {
int index = 0;
- long ret[] = new long[count];
- for(long[][] outer : values) {
- if(outer == null) continue;
- for(long[] inner : outer) {
- if(inner == null) continue;
- for(long entry : inner) {
- ret[index++] = entry;
+ rl.lock();
+ try {
+ long ret[] = new long[count];
+ for (long[][] outer : values) {
+ if (outer == null)
+ continue;
+ for (long[] inner : outer) {
+ if (inner == null)
+ continue;
+ for (long entry : inner) {
+ ret[index++] = entry;
+ }
}
}
+ return ret;
+ } finally {
+ rl.unlock();
}
- return ret;
}
} \ No newline at end of file