Skip to content

Commit

Permalink
Fixes ehcache#1291 : Ensure single element chains are moved correctly…
Browse files Browse the repository at this point in the history
… during compaction
  • Loading branch information
chrisdennis committed Jul 7, 2016
1 parent 48971f1 commit 6285961
Show file tree
Hide file tree
Showing 3 changed files with 48 additions and 6 deletions.
Expand Up @@ -53,8 +53,12 @@ public OffHeapChainMap(PageSource source, Portability<? super K> keyPortability,
public void evicting(Callable<Map.Entry<K, InternalChain>> callable) {
try {
Map.Entry<K, InternalChain> entry = callable.call();
if (evictionListener != null) {
evictionListener.onEviction(entry.getKey());
try {
if (evictionListener != null) {
evictionListener.onEviction(entry.getKey());
}
} finally {
entry.getValue().close();
}
} catch (Exception e) {
throw new AssertionError(e);
Expand Down
Expand Up @@ -465,7 +465,7 @@ private Long createAttachedChain(ByteBuffer keyBuffer, int hash, ByteBuffer elem
int keySize = keyBuffer.remaining();
storage.writeInt(chain + CHAIN_HEADER_KEY_HASH_OFFSET, hash);
storage.writeInt(chain + CHAIN_HEADER_KEY_LENGTH_OFFSET, Integer.MIN_VALUE | keySize);
storage.writeBuffer(chain + CHAIN_HEADER_SIZE + ELEMENT_HEADER_SIZE + elemBuffer.remaining(), keyBuffer);
storage.writeBuffer(chain + CHAIN_HEADER_SIZE + ELEMENT_HEADER_SIZE + elemBuffer.remaining(), keyBuffer.duplicate());
long element = chain + CHAIN_HEADER_SIZE;
writeElement(element, elemBuffer);
storage.writeLong(element + ELEMENT_HEADER_NEXT_OFFSET, chain);
Expand Down Expand Up @@ -538,6 +538,10 @@ public boolean moved(long from, long to) {
return false;
} else {
long tail = storage.readLong(to + CHAIN_HEADER_TAIL_OFFSET);
if (tail == from + CHAIN_HEADER_SIZE) {
tail = to + CHAIN_HEADER_SIZE;
storage.writeLong(to + CHAIN_HEADER_TAIL_OFFSET, tail);
}
storage.writeLong(tail + ELEMENT_HEADER_NEXT_OFFSET, to);
for (AttachedInternalChain activeChain : activeChains) {
activeChain.moved(from, to);
Expand Down
Expand Up @@ -16,6 +16,7 @@
package org.ehcache.clustered.server.offheap;

import java.nio.ByteBuffer;
import java.util.Random;

import org.ehcache.clustered.common.internal.store.Chain;
import org.ehcache.clustered.common.internal.store.Element;
Expand All @@ -30,18 +31,51 @@
import org.terracotta.offheapstore.buffersource.OffHeapBufferSource;
import org.terracotta.offheapstore.exceptions.OversizeMappingException;
import org.terracotta.offheapstore.paging.UnlimitedPageSource;
import org.terracotta.offheapstore.paging.UpfrontAllocatingPageSource;

import static org.terracotta.offheapstore.util.MemoryUnit.MEGABYTES;

import static org.mockito.Matchers.anyLong;
import static org.mockito.Mockito.spy;
import static org.mockito.Mockito.when;
import static org.hamcrest.MatcherAssert.assertThat;
import static org.hamcrest.core.Is.is;
import static org.mockito.Matchers.any;
import static org.mockito.Matchers.anyLong;
import static org.mockito.Mockito.doThrow;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.spy;
import static org.mockito.Mockito.when;

public class OffHeapServerStoreTest extends ServerStoreTest {

@Test
public void testCrossSegmentShrinking() throws Throwable {
OffHeapServerStore store = new OffHeapServerStore(new UpfrontAllocatingPageSource(new OffHeapBufferSource(), MEGABYTES.toBytes(1L), MEGABYTES.toBytes(1)), 16);

long seed = System.nanoTime();
System.out.println("Seed : " + seed);
final Random random = new Random(seed);
final int n = 500;

ByteBuffer smallValue = ByteBuffer.allocate(1024);

for (int i = 0; i < 10000; i++) {
try {
store.getAndAppend(random.nextInt(n), smallValue.duplicate());
} catch (OversizeMappingException e) {
//ignore
}
}

ByteBuffer largeValue = ByteBuffer.allocate(100 * 1024);

for (int i = 0; i < 10000; i++) {
try {
store.getAndAppend(random.nextInt(n), largeValue.duplicate());
} catch (OversizeMappingException e) {
//ignore
}
}
}

@Override
public ServerStore newStore() {
return new OffHeapServerStore(new UnlimitedPageSource(new OffHeapBufferSource()), 16);
Expand Down

0 comments on commit 6285961

Please sign in to comment.