Skip to content

Commit

Permalink
add padding between the write counter and array buffer
Browse files Browse the repository at this point in the history
  • Loading branch information
ben-manes committed Oct 29, 2023
1 parent ea0b0e1 commit 4e6c4a1
Showing 1 changed file with 46 additions and 27 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -54,8 +54,9 @@ protected Buffer<E> create(E e) {
return new RingBuffer<>(e);
}

static final class RingBuffer<E> extends BBHeader.ReadAndWriteCounterRef implements Buffer<E> {
static final VarHandle BUFFER = MethodHandles.arrayElementVarHandle(Object[].class);
/** Enforces a memory layout to avoid false sharing by padding the fields. */
static final class RingBuffer<E> extends BBHeader.PadRingBuffer implements Buffer<E> {
static final VarHandle READ, WRITE, BUFFER;

final Object[] buffer;

Expand Down Expand Up @@ -113,6 +114,29 @@ public long reads() {
public long writes() {
return writeCounter;
}

void setReadCounterOpaque(long count) {
READ.setOpaque(this, count);
}

long writeCounterOpaque() {
return (long) WRITE.getOpaque(this);
}

boolean casWriteCounter(long expect, long update) {
return WRITE.weakCompareAndSet(this, expect, update);
}

static {
var lookup = MethodHandles.lookup();
try {
BUFFER = MethodHandles.arrayElementVarHandle(Object[].class);
READ = lookup.findVarHandle(RingBuffer.class, "readCounter", long.class);
WRITE = lookup.findVarHandle(RingBuffer.class, "writeCounter", long.class);
} catch (ReflectiveOperationException e) {
throw new ExceptionInInitializerError(e);
}
}
}
}

Expand Down Expand Up @@ -161,32 +185,27 @@ abstract static class PadWriteCounter extends ReadCounterRef {
byte p232, p233, p234, p235, p236, p237, p238, p239;
}

/** Enforces a memory layout to avoid false sharing by padding the write counter. */
abstract static class ReadAndWriteCounterRef extends PadWriteCounter {
static final VarHandle READ, WRITE;

/** Enforces a memory layout to avoid false sharing by padding the read count. */
abstract static class WriteCounterRef extends PadWriteCounter {
volatile long writeCounter;
}

void setReadCounterOpaque(long count) {
READ.setOpaque(this, count);
}

long writeCounterOpaque() {
return (long) WRITE.getOpaque(this);
}

boolean casWriteCounter(long expect, long update) {
return WRITE.weakCompareAndSet(this, expect, update);
}

static {
var lookup = MethodHandles.lookup();
try {
READ = lookup.findVarHandle(ReadCounterRef.class, "readCounter", long.class);
WRITE = lookup.findVarHandle(ReadAndWriteCounterRef.class, "writeCounter", long.class);
} catch (ReflectiveOperationException e) {
throw new ExceptionInInitializerError(e);
}
}
@SuppressWarnings("PMD.AbstractClassWithoutAbstractMethod")
abstract static class PadRingBuffer extends WriteCounterRef {
byte p240, p241, p242, p243, p244, p245, p246, p247;
byte p248, p249, p250, p251, p252, p253, p254, p255;
byte p256, p257, p258, p259, p260, p261, p262, p263;
byte p264, p265, p266, p267, p268, p269, p270, p271;
byte p272, p273, p274, p275, p276, p277, p278, p279;
byte p280, p281, p282, p283, p284, p285, p286, p287;
byte p288, p289, p290, p291, p292, p293, p294, p295;
byte p296, p297, p298, p299, p300, p301, p302, p303;
byte p304, p305, p306, p307, p308, p309, p310, p311;
byte p312, p313, p314, p315, p316, p317, p318, p319;
byte p320, p321, p322, p323, p324, p325, p326, p327;
byte p328, p329, p330, p331, p332, p333, p334, p335;
byte p336, p337, p338, p339, p340, p341, p342, p343;
byte p344, p345, p346, p347, p348, p349, p350, p351;
byte p352, p353, p354, p355, p356, p357, p358, p359;
}
}

0 comments on commit 4e6c4a1

Please sign in to comment.