Pooling allocator cleanups and checkstyle fixes

This commit is contained in:
Chris Vest 2021-05-17 16:22:33 +02:00
parent 12b38234e5
commit 03743fca0d
7 changed files with 33 additions and 54 deletions

View File

@ -17,7 +17,6 @@ package io.netty.buffer.api.pool;
import io.netty.buffer.api.AllocatorControl; import io.netty.buffer.api.AllocatorControl;
import io.netty.buffer.api.Buffer; import io.netty.buffer.api.Buffer;
import io.netty.buffer.api.BufferAllocator;
import io.netty.buffer.api.MemoryManager; import io.netty.buffer.api.MemoryManager;
import io.netty.buffer.api.internal.Statics; import io.netty.buffer.api.internal.Statics;
import io.netty.util.internal.StringUtil; import io.netty.util.internal.StringUtil;
@ -110,10 +109,6 @@ class PoolArena extends SizeClasses implements PoolArenaMetric, AllocatorControl
return new PoolSubpage[size]; return new PoolSubpage[size];
} }
boolean isDirect() {
return manager.isNative();
}
UntetheredMemory allocate(PooledAllocatorControl control, PoolThreadCache cache, int size) { UntetheredMemory allocate(PooledAllocatorControl control, PoolThreadCache cache, int size) {
final int sizeIdx = size2SizeIdx(size); final int sizeIdx = size2SizeIdx(size);
@ -164,7 +159,8 @@ class PoolArena extends SizeClasses implements PoolArenaMetric, AllocatorControl
return memory; return memory;
} }
private UntetheredMemory tcacheAllocateNormal(PooledAllocatorControl control, PoolThreadCache cache, int size, int sizeIdx) { private UntetheredMemory tcacheAllocateNormal(
PooledAllocatorControl control, PoolThreadCache cache, int size, int sizeIdx) {
UntetheredMemory memory = cache.allocateNormal(this, control, size, sizeIdx); UntetheredMemory memory = cache.allocateNormal(this, control, size, sizeIdx);
if (memory != null) { if (memory != null) {
// was able to allocate out of the cache so move on // was able to allocate out of the cache so move on
@ -178,7 +174,8 @@ class PoolArena extends SizeClasses implements PoolArenaMetric, AllocatorControl
} }
// Method must be called inside synchronized(this) { ... } block // Method must be called inside synchronized(this) { ... } block
private UntetheredMemory allocateNormal(int size, int sizeIdx, PoolThreadCache threadCache, PooledAllocatorControl control) { private UntetheredMemory allocateNormal(
int size, int sizeIdx, PoolThreadCache threadCache, PooledAllocatorControl control) {
UntetheredMemory memory = q050.allocate(size, sizeIdx, threadCache, control); UntetheredMemory memory = q050.allocate(size, sizeIdx, threadCache, control);
if (memory != null) { if (memory != null) {
return memory; return memory;
@ -215,7 +212,7 @@ class PoolArena extends SizeClasses implements PoolArenaMetric, AllocatorControl
private UntetheredMemory allocateHuge(int size) { private UntetheredMemory allocateHuge(int size) {
activeBytesHuge.add(size); activeBytesHuge.add(size);
allocationsHuge.increment(); allocationsHuge.increment();
return new UnpooledUnthetheredMemory(manager, size); return new UnpooledUnthetheredMemory(parent, manager, size);
} }
void free(PoolChunk chunk, long handle, int normCapacity, PoolThreadCache cache) { void free(PoolChunk chunk, long handle, int normCapacity, PoolThreadCache cache) {
@ -234,15 +231,12 @@ class PoolArena extends SizeClasses implements PoolArenaMetric, AllocatorControl
void freeChunk(PoolChunk chunk, long handle, int normCapacity, SizeClass sizeClass) { void freeChunk(PoolChunk chunk, long handle, int normCapacity, SizeClass sizeClass) {
final boolean destroyChunk; final boolean destroyChunk;
synchronized (this) { synchronized (this) {
switch (sizeClass) { if (sizeClass == SizeClass.Normal) {
case Normal: ++deallocationsNormal;
++deallocationsNormal; } else if (sizeClass == SizeClass.Small) {
break; ++deallocationsSmall;
case Small: } else {
++deallocationsSmall; throw new AssertionError("Unexpected size class: " + sizeClass);
break;
default:
throw new Error();
} }
destroyChunk = !chunk.parent.free(chunk, handle, normCapacity); destroyChunk = !chunk.parent.free(chunk, handle, normCapacity);
} }

View File

@ -515,14 +515,15 @@ final class PoolChunk implements PoolChunkMetric {
| (long) inUsed << IS_USED_SHIFT; | (long) inUsed << IS_USED_SHIFT;
} }
UntetheredMemory allocateBuffer(long handle, int size, PoolThreadCache threadCache, PooledAllocatorControl control) { UntetheredMemory allocateBuffer(long handle, int size, PoolThreadCache threadCache,
PooledAllocatorControl control) {
if (isRun(handle)) { if (isRun(handle)) {
int offset = runOffset(handle) << pageShifts; int offset = runOffset(handle) << pageShifts;
int maxLength = runSize(pageShifts, handle); int maxLength = runSize(pageShifts, handle);
PoolThreadCache poolThreadCache = arena.parent.threadCache(); PoolThreadCache poolThreadCache = arena.parent.threadCache();
initAllocatorControl(control, poolThreadCache, handle, maxLength); initAllocatorControl(control, poolThreadCache, handle, maxLength);
return new UntetheredChunkAllocation( return new UntetheredChunkAllocation(
memory, control, this, poolThreadCache, handle, maxLength, offset, size); memory, this, poolThreadCache, handle, maxLength, offset, size);
} else { } else {
return allocateBufferWithSubpage(handle, size, threadCache, control); return allocateBufferWithSubpage(handle, size, threadCache, control);
} }
@ -539,13 +540,12 @@ final class PoolChunk implements PoolChunkMetric {
int offset = (runOffset << pageShifts) + bitmapIdx * s.elemSize; int offset = (runOffset << pageShifts) + bitmapIdx * s.elemSize;
initAllocatorControl(control, threadCache, handle, s.elemSize); initAllocatorControl(control, threadCache, handle, s.elemSize);
return new UntetheredChunkAllocation(memory, control, this, threadCache, handle, s.elemSize, offset, size); return new UntetheredChunkAllocation(memory, this, threadCache, handle, s.elemSize, offset, size);
} }
@SuppressWarnings("unchecked") @SuppressWarnings("unchecked")
private static class UntetheredChunkAllocation implements UntetheredMemory { private static final class UntetheredChunkAllocation implements UntetheredMemory {
private final Object memory; private final Object memory;
private final PooledAllocatorControl control;
private final PoolChunk chunk; private final PoolChunk chunk;
private final PoolThreadCache threadCache; private final PoolThreadCache threadCache;
private final long handle; private final long handle;
@ -554,10 +554,9 @@ final class PoolChunk implements PoolChunkMetric {
private final int size; private final int size;
private UntetheredChunkAllocation( private UntetheredChunkAllocation(
Object memory, PooledAllocatorControl control, PoolChunk chunk, PoolThreadCache threadCache, Object memory, PoolChunk chunk, PoolThreadCache threadCache,
long handle, int maxLength, int offset, int size) { long handle, int maxLength, int offset, int size) {
this.memory = memory; this.memory = memory;
this.control = control;
this.chunk = chunk; this.chunk = chunk;
this.threadCache = threadCache; this.threadCache = threadCache;
this.handle = handle; this.handle = handle;
@ -573,7 +572,7 @@ final class PoolChunk implements PoolChunkMetric {
@Override @Override
public <BufferType extends Buffer> Drop<BufferType> drop() { public <BufferType extends Buffer> Drop<BufferType> drop() {
return (Drop<BufferType>) new PooledDrop(control, chunk.arena, chunk, threadCache, handle, maxLength); return (Drop<BufferType>) new PooledDrop(chunk.arena, chunk, threadCache, handle, maxLength);
} }
} }
@ -584,7 +583,6 @@ final class PoolChunk implements PoolChunkMetric {
control.threadCache = threadCache; control.threadCache = threadCache;
control.handle = handle; control.handle = handle;
control.normSize = normSize; control.normSize = normSize;
control.updates++;
} }
@Override @Override

View File

@ -288,8 +288,8 @@ final class PoolThreadCache {
/** /**
* Allocate a new {@link UntetheredMemory} using the provided chunk and handle with the capacity restrictions. * Allocate a new {@link UntetheredMemory} using the provided chunk and handle with the capacity restrictions.
*/ */
protected abstract UntetheredMemory allocBuf(PoolChunk chunk, long handle, int size, PoolThreadCache threadCache, protected abstract UntetheredMemory allocBuf(
PooledAllocatorControl control); PoolChunk chunk, long handle, int size, PoolThreadCache threadCache, PooledAllocatorControl control);
/** /**
* Add to cache if not already full. * Add to cache if not already full.

View File

@ -19,16 +19,16 @@ import io.netty.buffer.api.AllocatorControl;
import io.netty.buffer.api.Buffer; import io.netty.buffer.api.Buffer;
class PooledAllocatorControl implements AllocatorControl { class PooledAllocatorControl implements AllocatorControl {
public PooledBufferAllocator parent;
public PoolArena arena; public PoolArena arena;
public PoolChunk chunk; public PoolChunk chunk;
public PoolThreadCache threadCache; public PoolThreadCache threadCache;
public long handle; public long handle;
public int normSize; public int normSize;
public int updates;
@Override @Override
public UntetheredMemory allocateUntethered(Buffer originator, int size) { public UntetheredMemory allocateUntethered(Buffer originator, int size) {
return arena.parent.allocate(this, size); return parent.allocate(this, size);
} }
@Override @Override

View File

@ -289,6 +289,7 @@ public class PooledBufferAllocator implements BufferAllocator, BufferAllocatorMe
throw new IllegalArgumentException("Allocation size must be positive, but was " + size + '.'); throw new IllegalArgumentException("Allocation size must be positive, but was " + size + '.');
} }
PooledAllocatorControl control = new PooledAllocatorControl(); PooledAllocatorControl control = new PooledAllocatorControl();
control.parent = this;
UntetheredMemory memory = allocate(control, size); UntetheredMemory memory = allocate(control, size);
Buffer buffer = manager.recoverMemory(control, memory.memory(), memory.drop()); Buffer buffer = manager.recoverMemory(control, memory.memory(), memory.drop());
return buffer.fill((byte) 0).order(ByteOrder.nativeOrder()); return buffer.fill((byte) 0).order(ByteOrder.nativeOrder());
@ -305,7 +306,7 @@ public class PooledBufferAllocator implements BufferAllocator, BufferAllocatorMe
} }
private UntetheredMemory allocateUnpooled(int size) { private UntetheredMemory allocateUnpooled(int size) {
return new UnpooledUnthetheredMemory(manager, size); return new UnpooledUnthetheredMemory(this, manager, size);
} }
@Override @Override
@ -423,7 +424,7 @@ public class PooledBufferAllocator implements BufferAllocator, BufferAllocatorMe
threadCache.free(); threadCache.free();
} }
private PoolArena leastUsedArena(PoolArena[] arenas) { private static PoolArena leastUsedArena(PoolArena[] arenas) {
if (arenas == null || arenas.length == 0) { if (arenas == null || arenas.length == 0) {
return null; return null;
} }

View File

@ -19,16 +19,13 @@ import io.netty.buffer.api.Buffer;
import io.netty.buffer.api.Drop; import io.netty.buffer.api.Drop;
class PooledDrop implements Drop<Buffer> { class PooledDrop implements Drop<Buffer> {
private final PooledAllocatorControl control; private final PoolArena arena;
private PoolArena arena; private final PoolChunk chunk;
private PoolChunk chunk; private final PoolThreadCache threadCache;
private PoolThreadCache threadCache; private final long handle;
private long handle; private final int normSize;
private int normSize;
PooledDrop(PooledAllocatorControl control, PoolArena arena, PoolChunk chunk, PoolThreadCache threadCache, PooledDrop(PoolArena arena, PoolChunk chunk, PoolThreadCache threadCache, long handle, int normSize) {
long handle, int normSize) {
this.control = control;
this.arena = arena; this.arena = arena;
this.chunk = chunk; this.chunk = chunk;
this.threadCache = threadCache; this.threadCache = threadCache;
@ -40,16 +37,4 @@ class PooledDrop implements Drop<Buffer> {
public void drop(Buffer obj) { public void drop(Buffer obj) {
arena.free(chunk, handle, normSize, threadCache); arena.free(chunk, handle, normSize, threadCache);
} }
@Override
public void attach(Buffer obj) {
if (control.updates > 0) {
arena = control.arena;
chunk = control.chunk;
threadCache = control.threadCache;
handle = control.handle;
normSize = control.normSize;
control.updates = 0;
}
}
} }

View File

@ -26,9 +26,10 @@ class UnpooledUnthetheredMemory implements AllocatorControl.UntetheredMemory {
private final MemoryManager manager; private final MemoryManager manager;
private final Buffer buffer; private final Buffer buffer;
UnpooledUnthetheredMemory(MemoryManager manager, int size) { UnpooledUnthetheredMemory(PooledBufferAllocator allocator, MemoryManager manager, int size) {
this.manager = manager; this.manager = manager;
PooledAllocatorControl allocatorControl = new PooledAllocatorControl(); PooledAllocatorControl allocatorControl = new PooledAllocatorControl();
allocatorControl.parent = allocator;
buffer = manager.allocateShared(allocatorControl, size, manager.drop(), Statics.CLEANER); buffer = manager.allocateShared(allocatorControl, size, manager.drop(), Statics.CLEANER);
} }