BigSegmentHeader: try deregister wait on try-upgrade-update-to-write procedure, if it sees unexpected state (update lock is not held)

This commit is contained in:
leventov
2016-01-18 17:34:14 +03:00
parent 7e32081111
commit 0ead764edf
@@ -427,7 +427,7 @@ public final class BigSegmentHeader implements SegmentHeader {
long end = System.nanoTime() + timeInNanos;
registerWait(address);
do {
if (LOCK.tryUpgradeUpdateToWriteLockAndDeregisterWait(A, null, address + LOCK_OFFSET))
if (tryUpgradeUpdateToWriteLockAndDeregisterWait0(address))
return true;
detectInterruptionAndDeregisterWait(address, interruptible);
} while (System.nanoTime() <= end);
@@ -443,7 +443,7 @@ public final class BigSegmentHeader implements SegmentHeader {
long lastTime = System.currentTimeMillis();
registerWait(address);
do {
if (LOCK.tryUpgradeUpdateToWriteLockAndDeregisterWait(A, null, address + LOCK_OFFSET))
if (tryUpgradeUpdateToWriteLockAndDeregisterWait0(address))
return true;
detectInterruptionAndDeregisterWait(address, interruptible);
long now = System.currentTimeMillis();
@@ -456,6 +456,22 @@ public final class BigSegmentHeader implements SegmentHeader {
return false;
}
private static boolean tryUpgradeUpdateToWriteLockAndDeregisterWait0(long address) {
try {
if (LOCK.tryUpgradeUpdateToWriteLockAndDeregisterWait(A, null, address + LOCK_OFFSET)) {
return true;
}
} catch (IllegalMonitorStateException e) {
try {
deregisterWait(address);
} catch (Throwable suppressed) {
e.addSuppressed(suppressed);
}
throw e;
}
return false;
}
@Override
public void readUnlock(long address) {
LOCK.readUnlock(A, null, address + LOCK_OFFSET);