Reduce write lock scope as much as possible in relocation and remove operations

This commit is contained in:
leventov
2016-02-26 20:55:47 +07:00
parent ed4589a1f4
commit e37de00202
2 changed files with 8 additions and 6 deletions
@@ -131,12 +131,13 @@ public abstract class HashQuery<K> implements SetEntry<K> {
checkOnEachPublicOperation.checkOnEachPublicOperation();
s.innerUpdateLock.lock();
if (ks.searchStatePresent()) {
// TODO optimize: if shift-deletion is trivial, updateLock.lock()
s.innerWriteLock.lock();
hashLookupSearch.remove();
entry.innerRemoveEntryExceptHashLookupUpdate();
ks.setSearchState(ABSENT);
initPresenceOfEntry(EntryPresence.ABSENT);
// write lock scope is reduced as much as possible
s.innerWriteLock.lock();
hashLookupSearch.remove();
} else {
throw new IllegalStateException("Entry is absent when doRemove() is called");
}
@@ -184,7 +184,6 @@ public abstract class MapEntryStages<K, V> extends HashEntryStages<K>
}
protected void relocation(Data<V> newValue, long newSizeOfEverythingBeforeValue) {
s.innerWriteLock.lock();
long entrySize = innerEntrySize(newSizeOfEverythingBeforeValue, newValue.size());
// need to copy, because in initEntryAndKeyCopying(), in alloc(), nextTier() called ->
// hashLookupPos cleared, as a dependant
@@ -207,8 +206,10 @@ public abstract class MapEntryStages<K, V> extends HashEntryStages<K>
CompactOffHeapLinearHashTable hl = hh.h().hashLookup;
long hashLookupKey = hl.key(hl.readEntry(oldHashLookupAddr, oldHashLookupPos));
hl.checkValueForPut(pos);
// volatile not needed, because we are in write lock context
hl.writeEntry(s.tierBaseAddr, hlp.hashLookupPos, hl.entry(hashLookupKey, pos));
hl.writeEntryVolatile(s.tierBaseAddr, hlp.hashLookupPos, hashLookupKey, pos);
// write lock is needed anyway (see testPutShouldBeWriteLocked()) but the scope is reduced
// as much as possible
s.innerWriteLock.lock();
if (tierHasChanged)
hl.remove(oldHashLookupAddr, oldHashLookupPos);
}