From d30ff782c1c046a28939278b2e50d012d945f362 Mon Sep 17 00:00:00 2001
From: Valery Kharseko <vharseko@3a-systems.ru>
Date: Fri, 25 Sep 2026 09:44:49 +0000
Subject: [PATCH] [#1096] Copy a value into Persistit once rather than twice, and write the large values of PDBStorageTest through a small buffer pool (#1097)
---
opendj-server-legacy/src/main/java/org/opends/server/backends/pdb/PDBStorage.java | 18 ++++++++++++++++--
1 files changed, 16 insertions(+), 2 deletions(-)
diff --git a/opendj-server-legacy/src/main/java/org/opends/server/backends/pdb/PDBStorage.java b/opendj-server-legacy/src/main/java/org/opends/server/backends/pdb/PDBStorage.java
index d0ea8de..cdcccf8 100644
--- a/opendj-server-legacy/src/main/java/org/opends/server/backends/pdb/PDBStorage.java
+++ b/opendj-server-legacy/src/main/java/org/opends/server/backends/pdb/PDBStorage.java
@@ -139,6 +139,8 @@
private static final String JOURNAL_NAME = VOLUME_NAME + "_journal";
/** The buffer / page size used by the PersistIt storage. */
private static final int BUFFER_SIZE = 16 * 1024;
+ /** Encoded by {@link #bytesToValue(Value, ByteSequence)} for the header Persistit puts before a byte array. */
+ private static final byte[] EMPTY_BYTES = new byte[0];
/** PersistIt implementation of the {@link Cursor} interface. */
private final class CursorImpl implements Cursor<ByteString, ByteString>
@@ -578,7 +580,7 @@
}
else
{
- ex.getValue().clear().putByteArray(newValue.toByteArray());
+ bytesToValue(ex.getValue(), newValue);
ex.store();
}
return true;
@@ -1542,9 +1544,21 @@
return key.clear().appendByteArray(tmp, 0, tmp.length);
}
+ /**
+ * Encodes the bytes as a byte array value, copying them once, straight into the encoded bytes of the value.
+ * {@code putByteArray(bytes.toByteArray())} would copy them twice, and for a value of 63 MB the extra copy is
+ * one more humongous array live next to the source and the value buffer. Persistit encodes a byte array as a
+ * header followed by the bytes as they are, so the header is taken from Persistit itself - by encoding an empty
+ * array - and the bytes are appended behind it.
+ */
private static Value bytesToValue(final Value value, final ByteSequence bytes)
{
- value.clear().putByteArray(bytes.toByteArray());
+ value.clear().putByteArray(EMPTY_BYTES);
+ final int headerSize = value.getEncodedSize();
+ value.ensureFit(bytes.length());
+ // ensureFit() may have replaced the encoded bytes, so they are read only after it
+ bytes.copyTo(value.getEncodedBytes(), headerSize);
+ value.setEncodedSize(headerSize + bytes.length());
return value;
}
--
Gitblit v1.10.0