prestodb/presto · error · IllegalArgumentException

arrayOffset is negative

Error message

arrayOffset is negative

What it means

The package-private VariableWidthBlock constructor validates its invariants up front. arrayOffset is the starting index into the offsets array for this block's view; a negative value means a malformed slice view was constructed and the library throws IllegalArgumentException to fail fast rather than produce corrupt blocks.

Source

Thrown at presto-common/src/main/java/com/facebook/presto/common/block/VariableWidthBlock.java:71

    private final int arrayOffset;
    private final int positionCount;
    private final Slice slice;
    private final int[] offsets;
    @Nullable
    private final boolean[] valueIsNull;

    private final long retainedSizeInBytes;
    private final long sizeInBytes;

    public VariableWidthBlock(int positionCount, Slice slice, int[] offsets, Optional<boolean[]> valueIsNull)
    {
        this(0, positionCount, slice, offsets, valueIsNull.orElse(null));
    }

    VariableWidthBlock(int arrayOffset, int positionCount, Slice slice, int[] offsets, boolean[] valueIsNull)
    {
        if (arrayOffset < 0) {
            throw new IllegalArgumentException("arrayOffset is negative");
        }
        this.arrayOffset = arrayOffset;
        if (positionCount < 0) {
            throw new IllegalArgumentException("positionCount is negative");
        }
        this.positionCount = positionCount;

        if (slice == null) {
            throw new IllegalArgumentException("slice is null");
        }
        this.slice = slice;

        if (offsets.length - arrayOffset < (positionCount + 1)) {
            throw new IllegalArgumentException("offsets length is less than positionCount");
        }
        this.offsets = offsets;

        if (valueIsNull != null && valueIsNull.length - arrayOffset < positionCount) {

View on GitHub (pinned to 55bb57d202)

Solutions

  1. Fix the offset computation that produces the negative arrayOffset before constructing the block.
  2. Clamp/validate offsets at the source of the region/slice calculation.
  3. If using public APIs, ensure positionCount/offsets derive from a valid parent block region.

Example fix

// before
new VariableWidthBlock(parentOffset - delta, count, slice, offsets, null); // negative
// after
int arrayOffset = Math.max(0, parentOffset - delta);
new VariableWidthBlock(arrayOffset, count, slice, offsets, null);
Defensive patterns

Strategy: validation

Validate before calling

checkArgument(arrayOffset >= 0, "arrayOffset must be >= 0, got %s", arrayOffset);

Try / catch

try {
    new VariableWidthBlock(arrayOffset, positionCount, slice, offsets, valueIsNull);
} catch (IllegalArgumentException e) {
    // fix region-offset math upstream
}

Prevention

When it happens

Trigger: Constructing VariableWidthBlock (public constructor delegates to this one) with a negative arrayOffset, typically from a region() / sliced-view factory computing an offset from bad position math.

Common situations: Custom Block implementations or slice-view code computing region offsets incorrectly; off-by-one or negative position arithmetic when creating sub-block views.

Related errors


AI-assisted analysis of prestodb/presto@55bb57d202 (2026-09-04). Data as JSON: /api/errors/38dded6e12d0bbea. Report an issue: GitHub.