From e928cbfe900c3e4d0a0194a9dc583e9220855966 Mon Sep 17 00:00:00 2001 From: leventov Date: Mon, 14 Dec 2015 16:13:35 +0300 Subject: [PATCH] Fix a bug in VanillaChronicleMap.putValue() -- avoid allocation of overlapping areas --- .../net/openhft/chronicle/map/ReplicatedChronicleMap.java | 5 ++--- .../net/openhft/chronicle/map/VanillaChronicleMap.java | 8 +++++--- 2 files changed, 7 insertions(+), 6 deletions(-) diff --git a/src/main/java/net/openhft/chronicle/map/ReplicatedChronicleMap.java b/src/main/java/net/openhft/chronicle/map/ReplicatedChronicleMap.java index c31e87159..205297a7b 100644 --- a/src/main/java/net/openhft/chronicle/map/ReplicatedChronicleMap.java +++ b/src/main/java/net/openhft/chronicle/map/ReplicatedChronicleMap.java @@ -1476,9 +1476,8 @@ final class ReplicatedChronicleMap assertion fails. diff --git a/src/main/java/net/openhft/chronicle/map/VanillaChronicleMap.java b/src/main/java/net/openhft/chronicle/map/VanillaChronicleMap.java index 826021649..f35d2af9d 100755 --- a/src/main/java/net/openhft/chronicle/map/VanillaChronicleMap.java +++ b/src/main/java/net/openhft/chronicle/map/VanillaChronicleMap.java @@ -2376,10 +2376,10 @@ class VanillaChronicleMap, prevValueInstance = readValue(copies, entry, null, prevValueSize); } - entry.positionAddr(valueAddr); boolean doPutValue; boolean hasValueChanged = false; if (eventListener != null) { + entry.positionAddr(valueAddr); hasValueChanged = prevValueSize != valueSize || !metaValueInterop.startsWith(valueInterop, entry, value); doPutValue = hasValueChanged; @@ -2783,10 +2783,10 @@ class VanillaChronicleMap, MVBI metaValueInterop = getNewValueInterops.getMetaValueInterop( copies, valueInterop, newValue); long newValueSize = metaValueInterop.size(valueInterop, newValue); - entry.positionAddr(valueAddr); boolean doPutValue; boolean hasValueChanged = false; if (eventListener != null) { + entry.positionAddr(valueAddr); hasValueChanged = valueSize != newValueSize || !metaValueInterop.startsWith(valueInterop, entry, newValue); doPutValue = hasValueChanged; @@ -2856,11 +2856,13 @@ class VanillaChronicleMap, if (realloc(pos, oldSizeInChunks, newSizeInChunks)) break newValueDoesNotFit; // RELOCATION - free(pos, oldSizeInChunks); onRelocation(this, pos); int allocatedChunks = inChunks(innerEntrySize(sizeOfEverythingBeforeValue, newElemSize)); long newPos = alloc(allocatedChunks); + // free after new alloc, to avoid overlapping allocation => undef. behaviour + // on unsafe.copyMemory + free(pos, oldSizeInChunks); // putValue() is called from put() and replace() // after successful search by key searchedHashLookup.replacePrevPos(segmentState.searchState, newPos,