quarkusio/quarkus · error · IllegalArgumentException
buffer hasn't backing byte array
Error message
buffer hasn't backing byte array
What it means
QuarkusHttpPostBodyUtil.SeekAheadOptimize is a fast-path optimization that requires the ByteBuf to have a backing JVM byte array. If buffer.hasArray() is false (e.g. direct or composite buffers), it throws IllegalArgumentException.
Source
Thrown at independent-projects/resteasy-reactive/client/runtime/src/main/java/org/jboss/resteasy/reactive/client/impl/multipart/QuarkusHttpPostBodyUtil.java:99
/**
* This class intends to decrease the CPU in seeking ahead some bytes in
* HttpPostRequestDecoder
*/
static class SeekAheadOptimize {
byte[] bytes;
int readerIndex;
int pos;
int origPos;
int limit;
ByteBuf buffer;
/**
* @param buffer buffer with a backing byte array
*/
SeekAheadOptimize(ByteBuf buffer) {
if (!buffer.hasArray()) {
throw new IllegalArgumentException("buffer hasn't backing byte array");
}
this.buffer = buffer;
bytes = buffer.array();
readerIndex = buffer.readerIndex();
origPos = pos = buffer.arrayOffset() + readerIndex;
limit = buffer.arrayOffset() + buffer.writerIndex();
}
/**
*
* @param minus this value will be used as (currentPos - minus) to set
* the current readerIndex in the buffer.
*/
void setReadPosition(int minus) {
pos -= minus;
readerIndex = getReadPosition(pos);
buffer.readerIndex(readerIndex);
}View on GitHub (pinned to e1c734241f)
Solutions
- Use the fallback seek-ahead-disabled parsing path (parsing directly on the ByteBuf) when the buffer has no array
- Force heap-buffer allocation for multipart request bodies (e.g. -Dio.netty.maxDirectMemory=0)
- Copy the buffer into a heap buffer (Unpooled.copiedBuffer / alloc.ioBuffer) before constructing SeekAheadOptimize
Example fix
// before SeekAheadOptimize sao = new SeekAheadOptimize(buffer); // after SeekAheadOptimize sao = buffer.hasArray() ? new SeekAheadOptimize(buffer) : null; // fall back to non-optimized path
Defensive patterns
Strategy: validation
Validate before calling
if (!buffer.hasArray()) { /* use the non-optimized parsing path */ } Type guard
null
Try / catch
try { sao = new SeekAheadOptimize(buffer); } catch (IllegalArgumentException e) { sao = null; /* seek-ahead disabled */ } Prevention
- Check buffer.hasArray() before heap-optimizing paths
- Run with -Dio.netty.maxDirectMemory=0 if heap buffers are required
- Be aware direct/composite buffers depend on Netty allocation settings and versions
When it happens
Trigger: Constructing SeekAheadOptimize with a direct (off-heap) ByteBuf or a composite/unpooled buffer without a backing array.
Common situations: Netty allocating direct buffers (default with io.netty.maxDirectMemory enabled) for multipart bodies; pooling configurations changed by flags or Netty version upgrades.
Understand the failure class
Background: UnsupportedOperationException and "is not supported" errors: when a library deliberately refuses a call — this error's family across 30 libraries.
Related errors
- Unsupported multipart message element type. Expected FileAtt
- Unsupported multipart response element type: " + httpData.ge
- setting content of MultiByteHttpData is not supported
- adding content to MultiByteHttpData is not supported
- getting all the contents of a MultiByteHttpData is not suppo
AI-assisted analysis of quarkusio/quarkus@e1c734241f (2026-09-05).
Data as JSON: /api/errors/b424f38dc18a9998.
Report an issue: GitHub.