Synchronize ModificationIterator acquisition with globalMutableStateLock, add a bit set identifying already initialized modification bit sets, not to clear them twice in ModificationIterator constructor

This commit is contained in:
leventov
2016-01-03 01:27:24 +03:00
parent 9b782c4ec2
commit 7847675f6f
2 changed files with 20 additions and 6 deletions
@@ -315,14 +315,18 @@ public class ReplicatedChronicleMap<K, V, R> extends VanillaChronicleMap<K, V, R
if (modificationIterator != null)
return modificationIterator;
//noinspection SynchronizeOnNonFinalField
synchronized (modificationIterators) {
globalMutableStateLock();
try {
modificationIterator = modificationIterators.get(remoteIdentifier);
if (modificationIterator != null)
return modificationIterator;
final ModificationIterator modIter = new ModificationIterator(remoteIdentifier);
boolean modificationIteratorInit =
globalMutableState().getModificationIteratorInitAt(remoteIdentifier);
final ModificationIterator modIter =
new ModificationIterator(remoteIdentifier, modificationIteratorInit);
globalMutableState().setModificationIteratorInitAt(remoteIdentifier, true);
//noinspection unchecked
assignedModificationIterators = Stream
.concat(Arrays.stream(assignedModificationIterators), Stream.of(modIter))
@@ -330,6 +334,8 @@ public class ReplicatedChronicleMap<K, V, R> extends VanillaChronicleMap<K, V, R
.toArray(ReplicatedChronicleMap.ModificationIterator[]::new);
modificationIterators.set(remoteIdentifier, modIter);
return modIter;
} finally {
globalMutableStateUnlock();
}
}
@@ -629,12 +635,14 @@ public class ReplicatedChronicleMap<K, V, R> extends VanillaChronicleMap<K, V, R
*/
private long tierBitSetAddr;
public ModificationIterator(byte remoteIdentifier) {
public ModificationIterator(byte remoteIdentifier, boolean sharedMemoryInit) {
this.remoteIdentifier = remoteIdentifier;
segmentBitSetsAddr = bsAddress() + startOfModificationIterators +
remoteIdentifier * segmentModIterBitSetsForIdentifierOuterSize;
nativeAccess().zeroOut(null, segmentBitSetsAddr,
segmentModIterBitSetsForIdentifierOuterSize);
if (!sharedMemoryInit) {
nativeAccess().zeroOut(null, segmentBitSetsAddr,
segmentModIterBitSetsForIdentifierOuterSize);
}
offsetToBitSetsWithinATierBulk =
remoteIdentifier * tierBulkModIterBitSetsForIdentifierOuterSize;
@@ -17,6 +17,7 @@
package net.openhft.chronicle.map;
import net.openhft.chronicle.hash.VanillaGlobalMutableState;
import net.openhft.chronicle.values.Array;
import net.openhft.chronicle.values.Group;
interface ReplicatedGlobalMutableState extends VanillaGlobalMutableState {
@@ -24,4 +25,9 @@ interface ReplicatedGlobalMutableState extends VanillaGlobalMutableState {
@Group(5)
int getCurrentCleanupSegmentIndex();
void setCurrentCleanupSegmentIndex(int currentCleanupSegmentIndex);
@Group(6)
@Array(length = 128)
boolean getModificationIteratorInitAt(int index);
void setModificationIteratorInitAt(int index, boolean init);
}