瀏覽代碼

ESQL: Fixed length vector builder (#99970)

This adds things like `IntVector.FixedBuilder` which is slightly simpler
to use than constructing the arrays by hand. It also measures bytes used
up front in the circuit breaker. And it'll be easier to integrate it
into framework happening over in #99931 to handle errors in topn.

This also uses it in `mv_` functions.
Nik Everett 2 年之前
父節點
當前提交
dd1cb826f7
共有 59 個文件被更改,包括 879 次插入228 次删除
  1. 21 0
      x-pack/plugin/esql/compute/build.gradle
  2. 25 24
      x-pack/plugin/esql/compute/gen/src/main/java/org/elasticsearch/compute/gen/MvEvaluatorImplementer.java
  3. 1 1
      x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/BooleanArrayVector.java
  4. 28 0
      x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/BooleanVector.java
  5. 1 1
      x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/BooleanVectorBuilder.java
  6. 61 0
      x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/BooleanVectorFixedBuilder.java
  7. 1 1
      x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/BytesRefArrayVector.java
  8. 7 0
      x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/BytesRefVector.java
  9. 1 1
      x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/BytesRefVectorBuilder.java
  10. 2 2
      x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/ConstantBooleanVector.java
  11. 3 3
      x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/ConstantBytesRefVector.java
  12. 2 2
      x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/ConstantDoubleVector.java
  13. 2 2
      x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/ConstantIntVector.java
  14. 2 2
      x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/ConstantLongVector.java
  15. 1 1
      x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/DoubleArrayVector.java
  16. 28 0
      x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/DoubleVector.java
  17. 1 1
      x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/DoubleVectorBuilder.java
  18. 61 0
      x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/DoubleVectorFixedBuilder.java
  19. 1 1
      x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/IntArrayVector.java
  20. 28 0
      x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/IntVector.java
  21. 1 1
      x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/IntVectorBuilder.java
  22. 61 0
      x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/IntVectorFixedBuilder.java
  23. 1 1
      x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/LongArrayVector.java
  24. 28 0
      x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/LongVector.java
  25. 1 1
      x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/LongVectorBuilder.java
  26. 61 0
      x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/LongVectorFixedBuilder.java
  27. 17 1
      x-pack/plugin/esql/compute/src/main/java/org/elasticsearch/compute/data/BlockFactory.java
  28. 1 1
      x-pack/plugin/esql/compute/src/main/java/org/elasticsearch/compute/data/X-ArrayVector.java.st
  29. 11 2
      x-pack/plugin/esql/compute/src/main/java/org/elasticsearch/compute/data/X-ConstantVector.java.st
  30. 40 0
      x-pack/plugin/esql/compute/src/main/java/org/elasticsearch/compute/data/X-Vector.java.st
  31. 1 1
      x-pack/plugin/esql/compute/src/main/java/org/elasticsearch/compute/data/X-VectorBuilder.java.st
  32. 61 0
      x-pack/plugin/esql/compute/src/main/java/org/elasticsearch/compute/data/X-VectorFixedBuilder.java.st
  33. 1 1
      x-pack/plugin/esql/compute/src/main/java/org/elasticsearch/compute/operator/DriverContext.java
  34. 4 0
      x-pack/plugin/esql/compute/src/test/java/org/elasticsearch/compute/data/BlockFactoryTests.java
  35. 136 0
      x-pack/plugin/esql/compute/src/test/java/org/elasticsearch/compute/data/VectorFixedBuilderTests.java
  36. 3 1
      x-pack/plugin/esql/src/internalClusterTest/java/org/elasticsearch/xpack/esql/action/EsqlDisruptionIT.java
  37. 5 5
      x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvAvgDoubleEvaluator.java
  38. 10 10
      x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvAvgIntEvaluator.java
  39. 10 10
      x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvAvgLongEvaluator.java
  40. 10 10
      x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvAvgUnsignedLongEvaluator.java
  41. 9 9
      x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvMaxBooleanEvaluator.java
  42. 9 11
      x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvMaxBytesRefEvaluator.java
  43. 9 9
      x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvMaxDoubleEvaluator.java
  44. 9 9
      x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvMaxIntEvaluator.java
  45. 9 9
      x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvMaxLongEvaluator.java
  46. 5 5
      x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvMedianDoubleEvaluator.java
  47. 9 9
      x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvMedianIntEvaluator.java
  48. 9 9
      x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvMedianLongEvaluator.java
  49. 9 9
      x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvMedianUnsignedLongEvaluator.java
  50. 9 9
      x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvMinBooleanEvaluator.java
  51. 9 11
      x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvMinBytesRefEvaluator.java
  52. 9 9
      x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvMinDoubleEvaluator.java
  53. 9 9
      x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvMinIntEvaluator.java
  54. 9 9
      x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvMinLongEvaluator.java
  55. 5 5
      x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvSumDoubleEvaluator.java
  56. 1 1
      x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvSumIntEvaluator.java
  57. 1 1
      x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvSumLongEvaluator.java
  58. 1 1
      x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvSumUnsignedLongEvaluator.java
  59. 9 7
      x-pack/plugin/esql/src/main/java/org/elasticsearch/xpack/esql/evaluator/mapper/EvaluatorMapper.java

+ 21 - 0
x-pack/plugin/esql/compute/build.gradle

@@ -343,6 +343,27 @@ tasks.named('stringTemplates').configure {
     it.inputFile =  vectorBuildersInputFile
     it.outputFile = "org/elasticsearch/compute/data/BooleanVectorBuilder.java"
   }
+  File vectorFixedBuildersInputFile = new File("${projectDir}/src/main/java/org/elasticsearch/compute/data/X-VectorFixedBuilder.java.st")
+  template {
+    it.properties = intProperties
+    it.inputFile =  vectorFixedBuildersInputFile
+    it.outputFile = "org/elasticsearch/compute/data/IntVectorFixedBuilder.java"
+  }
+  template {
+    it.properties = longProperties
+    it.inputFile =  vectorFixedBuildersInputFile
+    it.outputFile = "org/elasticsearch/compute/data/LongVectorFixedBuilder.java"
+  }
+  template {
+    it.properties = doubleProperties
+    it.inputFile =  vectorFixedBuildersInputFile
+    it.outputFile = "org/elasticsearch/compute/data/DoubleVectorFixedBuilder.java"
+  }
+  template {
+    it.properties = booleanProperties
+    it.inputFile =  vectorFixedBuildersInputFile
+    it.outputFile = "org/elasticsearch/compute/data/BooleanVectorFixedBuilder.java"
+  }
   File stateInputFile = new File("${projectDir}/src/main/java/org/elasticsearch/compute/aggregation/X-State.java.st")
   template {
     it.properties = intProperties

+ 25 - 24
x-pack/plugin/esql/compute/gen/src/main/java/org/elasticsearch/compute/gen/MvEvaluatorImplementer.java

@@ -31,17 +31,15 @@ import static org.elasticsearch.compute.gen.Methods.findMethod;
 import static org.elasticsearch.compute.gen.Methods.getMethod;
 import static org.elasticsearch.compute.gen.Types.ABSTRACT_MULTIVALUE_FUNCTION_EVALUATOR;
 import static org.elasticsearch.compute.gen.Types.ABSTRACT_NULLABLE_MULTIVALUE_FUNCTION_EVALUATOR;
-import static org.elasticsearch.compute.gen.Types.BIG_ARRAYS;
 import static org.elasticsearch.compute.gen.Types.BLOCK;
 import static org.elasticsearch.compute.gen.Types.BYTES_REF;
-import static org.elasticsearch.compute.gen.Types.BYTES_REF_ARRAY;
 import static org.elasticsearch.compute.gen.Types.DRIVER_CONTEXT;
 import static org.elasticsearch.compute.gen.Types.EXPRESSION_EVALUATOR;
 import static org.elasticsearch.compute.gen.Types.SOURCE;
 import static org.elasticsearch.compute.gen.Types.VECTOR;
 import static org.elasticsearch.compute.gen.Types.WARNINGS;
-import static org.elasticsearch.compute.gen.Types.arrayVectorType;
 import static org.elasticsearch.compute.gen.Types.blockType;
+import static org.elasticsearch.compute.gen.Types.vectorType;
 
 public class MvEvaluatorImplementer {
     private final TypeElement declarationType;
@@ -197,16 +195,25 @@ public class MvEvaluatorImplementer {
         builder.addStatement("int positionCount = v.getPositionCount()");
         if (nullable) {
             TypeName resultBlockType = blockType(resultType);
-            builder.addStatement("$T.Builder builder = $T.newBlockBuilder(positionCount)", resultBlockType, resultBlockType);
+            builder.addStatement(
+                "$T.Builder builder = $T.newBlockBuilder(positionCount, driverContext.blockFactory())",
+                resultBlockType,
+                resultBlockType
+            );
         } else if (resultType.equals(BYTES_REF)) {
+            TypeName resultVectorType = vectorType(resultType);
             builder.addStatement(
-                "$T values = new $T(positionCount, $T.NON_RECYCLING_INSTANCE)",  // TODO blocks should use recycling array
-                BYTES_REF_ARRAY,
-                BYTES_REF_ARRAY,
-                BIG_ARRAYS
+                "$T.Builder builder = $T.newVectorBuilder(positionCount, driverContext.blockFactory())",
+                resultVectorType,
+                resultVectorType
             );
         } else {
-            builder.addStatement("$T[] values = new $T[positionCount]", resultType, resultType);
+            TypeName resultVectorType = vectorType(resultType);
+            builder.addStatement(
+                "$T.FixedBuilder builder = $T.newVectorFixedBuilder(positionCount, driverContext.blockFactory())",
+                resultVectorType,
+                resultVectorType
+            );
         }
 
         if (false == workType.equals(fieldType) && workType.isPrimitive() == false) {
@@ -244,11 +251,7 @@ public class MvEvaluatorImplementer {
         }
         builder.endControlFlow();
 
-        if (nullable) {
-            builder.addStatement("return builder.build()");
-        } else {
-            builder.addStatement("return new $T(values, positionCount)", arrayVectorType(resultType));
-        }
+        builder.addStatement("return builder.build()");
         return builder.build();
     }
 
@@ -268,7 +271,7 @@ public class MvEvaluatorImplementer {
                 builder.beginControlFlow("if (valueCount == 1)");
                 fetch(builder, "value", fieldType, "first", workType.equals(fieldType) ? "firstScratch" : "valueScratch");
                 singleValueFunction.call(builder);
-                writeResult(builder, nullable);
+                writeResult(builder);
                 builder.addStatement("continue");
                 builder.endControlFlow();
             }
@@ -302,7 +305,7 @@ public class MvEvaluatorImplementer {
                 builder.endControlFlow();
                 finishFunction.call(builder, "work");
             }
-            writeResult(builder, nullable);
+            writeResult(builder);
         });
     }
 
@@ -313,7 +316,7 @@ public class MvEvaluatorImplementer {
             builder.addStatement("int first = v.getFirstValueIndex(p)");
             fetch(builder, "value", fieldType, "first", workType.equals(fieldType) ? "firstScratch" : "valueScratch");
             singleValueFunction.call(builder);
-            writeResult(builder, nullable);
+            writeResult(builder);
         });
     }
 
@@ -332,17 +335,15 @@ public class MvEvaluatorImplementer {
         return evalShell(name, false, nullable, javadoc, builder -> {}, builder -> {
             builder.addStatement("int first = v.getFirstValueIndex(p)");
             ascendingFunction.call(builder);
-            writeResult(builder, nullable);
+            writeResult(builder);
         });
     }
 
-    private void writeResult(MethodSpec.Builder builder, boolean nullable) {
-        if (nullable) {
-            builder.addStatement("builder.$L(result)", appendMethod(resultType));
-        } else if (fieldType.equals(BYTES_REF)) {
-            builder.addStatement("values.append(result)");
+    private void writeResult(MethodSpec.Builder builder) {
+        if (fieldType.equals(BYTES_REF)) {
+            builder.addStatement("builder.appendBytesRef(result)");
         } else {
-            builder.addStatement("values[p] = result");
+            builder.addStatement("builder.$L(result)", appendMethod(resultType));
         }
     }
 

+ 1 - 1
x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/BooleanArrayVector.java

@@ -17,7 +17,7 @@ import java.util.Arrays;
  */
 public final class BooleanArrayVector extends AbstractVector implements BooleanVector {
 
-    private static final long BASE_RAM_BYTES_USED = RamUsageEstimator.shallowSizeOfInstance(BooleanArrayVector.class);
+    static final long BASE_RAM_BYTES_USED = RamUsageEstimator.shallowSizeOfInstance(BooleanArrayVector.class);
 
     private final boolean[] values;
 

+ 28 - 0
x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/BooleanVector.java

@@ -106,10 +106,25 @@ public sealed interface BooleanVector extends Vector permits ConstantBooleanVect
         return newVectorBuilder(estimatedSize, BlockFactory.getNonBreakingInstance());
     }
 
+    /**
+     * Creates a builder that grows as needed. Prefer {@link #newVectorFixedBuilder}
+     * if you know the size up front because it's faster.
+     */
     static Builder newVectorBuilder(int estimatedSize, BlockFactory blockFactory) {
         return blockFactory.newBooleanVectorBuilder(estimatedSize);
     }
 
+    /**
+     * Creates a builder that never grows. Prefer this over {@link #newVectorBuilder}
+     * if you know the size up front because it's faster.
+     */
+    static FixedBuilder newVectorFixedBuilder(int size, BlockFactory blockFactory) {
+        return blockFactory.newBooleanVectorFixedBuilder(size);
+    }
+
+    /**
+     * A builder that grows as needed.
+     */
     sealed interface Builder extends Vector.Builder permits BooleanVectorBuilder {
         /**
          * Appends a boolean to the current entry.
@@ -119,4 +134,17 @@ public sealed interface BooleanVector extends Vector permits ConstantBooleanVect
         @Override
         BooleanVector build();
     }
+
+    /**
+     * A builder that never grows.
+     */
+    sealed interface FixedBuilder extends Vector.Builder permits BooleanVectorFixedBuilder {
+        /**
+         * Appends a boolean to the current entry.
+         */
+        FixedBuilder appendBoolean(boolean value);
+
+        @Override
+        BooleanVector build();
+    }
 }

+ 1 - 1
x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/BooleanVectorBuilder.java

@@ -10,7 +10,7 @@ package org.elasticsearch.compute.data;
 import java.util.Arrays;
 
 /**
- * Block build of BooleanBlocks.
+ * Builder for {@link BooleanVector}s that grows as needed.
  * This class is generated. Do not edit it.
  */
 final class BooleanVectorBuilder extends AbstractVectorBuilder implements BooleanVector.Builder {

+ 61 - 0
x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/BooleanVectorFixedBuilder.java

@@ -0,0 +1,61 @@
+/*
+ * Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
+ * or more contributor license agreements. Licensed under the Elastic License
+ * 2.0; you may not use this file except in compliance with the Elastic License
+ * 2.0.
+ */
+
+package org.elasticsearch.compute.data;
+
+import org.apache.lucene.util.RamUsageEstimator;
+
+/**
+ * Builder for {@link BooleanVector}s that never grows. Prefer this to
+ * {@link BooleanVectorBuilder} if you know the precise size up front because
+ * it's faster.
+ * This class is generated. Do not edit it.
+ */
+final class BooleanVectorFixedBuilder implements BooleanVector.FixedBuilder {
+    private final BlockFactory blockFactory;
+    private final boolean[] values;
+    /**
+     * The next value to write into. {@code -1} means the vector has already
+     * been built.
+     */
+    private int nextIndex;
+
+    BooleanVectorFixedBuilder(int size, BlockFactory blockFactory) {
+        blockFactory.adjustBreaker(ramBytesUsed(size), false);
+        this.blockFactory = blockFactory;
+        this.values = new boolean[size];
+    }
+
+    @Override
+    public BooleanVectorFixedBuilder appendBoolean(boolean value) {
+        values[nextIndex++] = value;
+        return this;
+    }
+
+    private static long ramBytesUsed(int size) {
+        return size == 1
+            ? ConstantBooleanVector.RAM_BYTES_USED
+            : BooleanArrayVector.BASE_RAM_BYTES_USED + RamUsageEstimator.alignObjectSize(
+                (long) RamUsageEstimator.NUM_BYTES_ARRAY_HEADER + size * Byte.BYTES
+            );
+    }
+
+    @Override
+    public BooleanVector build() {
+        if (nextIndex < 0) {
+            throw new IllegalStateException("already closed");
+        }
+        if (nextIndex != values.length) {
+            throw new IllegalStateException("expected to write [" + values.length + "] entries but wrote [" + nextIndex + "]");
+        }
+        nextIndex = -1;
+        if (values.length == 1) {
+            return new ConstantBooleanVector(values[0], 1, blockFactory);
+        }
+        return new BooleanArrayVector(values, values.length, blockFactory);
+    }
+}

+ 1 - 1
x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/BytesRefArrayVector.java

@@ -18,7 +18,7 @@ import org.elasticsearch.core.Releasables;
  */
 public final class BytesRefArrayVector extends AbstractVector implements BytesRefVector {
 
-    private static final long BASE_RAM_BYTES_USED = RamUsageEstimator.shallowSizeOfInstance(BytesRefArrayVector.class);
+    static final long BASE_RAM_BYTES_USED = RamUsageEstimator.shallowSizeOfInstance(BytesRefArrayVector.class);
 
     private final BytesRefArray values;
 

+ 7 - 0
x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/BytesRefVector.java

@@ -106,10 +106,16 @@ public sealed interface BytesRefVector extends Vector permits ConstantBytesRefVe
         return newVectorBuilder(estimatedSize, BlockFactory.getNonBreakingInstance());
     }
 
+    /**
+     * Creates a builder that grows as needed.
+     */
     static Builder newVectorBuilder(int estimatedSize, BlockFactory blockFactory) {
         return blockFactory.newBytesRefVectorBuilder(estimatedSize);
     }
 
+    /**
+     * A builder that grows as needed.
+     */
     sealed interface Builder extends Vector.Builder permits BytesRefVectorBuilder {
         /**
          * Appends a BytesRef to the current entry.
@@ -119,4 +125,5 @@ public sealed interface BytesRefVector extends Vector permits ConstantBytesRefVe
         @Override
         BytesRefVector build();
     }
+
 }

+ 1 - 1
x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/BytesRefVectorBuilder.java

@@ -13,7 +13,7 @@ import org.elasticsearch.common.util.BytesRefArray;
 import org.elasticsearch.core.Releasables;
 
 /**
- * Block build of BytesRefBlocks.
+ * Builder for {@link BytesRefVector}s that grows as needed.
  * This class is generated. Do not edit it.
  */
 final class BytesRefVectorBuilder extends AbstractVectorBuilder implements BytesRefVector.Builder {

+ 2 - 2
x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/ConstantBooleanVector.java

@@ -15,7 +15,7 @@ import org.apache.lucene.util.RamUsageEstimator;
  */
 public final class ConstantBooleanVector extends AbstractVector implements BooleanVector {
 
-    private static final long BASE_RAM_BYTES_USED = RamUsageEstimator.shallowSizeOfInstance(ConstantBooleanVector.class);
+    static final long RAM_BYTES_USED = RamUsageEstimator.shallowSizeOfInstance(ConstantBooleanVector.class);
 
     private final boolean value;
 
@@ -55,7 +55,7 @@ public final class ConstantBooleanVector extends AbstractVector implements Boole
 
     @Override
     public long ramBytesUsed() {
-        return BASE_RAM_BYTES_USED + RamUsageEstimator.shallowSizeOfInstance(boolean.class);
+        return RAM_BYTES_USED;
     }
 
     @Override

+ 3 - 3
x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/ConstantBytesRefVector.java

@@ -16,8 +16,8 @@ import org.apache.lucene.util.RamUsageEstimator;
  */
 public final class ConstantBytesRefVector extends AbstractVector implements BytesRefVector {
 
-    private static final long BASE_RAM_BYTES_USED = RamUsageEstimator.shallowSizeOfInstance(ConstantBytesRefVector.class);
-
+    static final long BASE_RAM_BYTES_USED = RamUsageEstimator.shallowSizeOfInstance(ConstantBytesRefVector.class) + RamUsageEstimator
+        .shallowSizeOfInstance(BytesRef.class);
     private final BytesRef value;
 
     public ConstantBytesRefVector(BytesRef value, int positionCount) {
@@ -56,7 +56,7 @@ public final class ConstantBytesRefVector extends AbstractVector implements Byte
 
     @Override
     public long ramBytesUsed() {
-        return BASE_RAM_BYTES_USED + RamUsageEstimator.shallowSizeOfInstance(BytesRef.class);
+        return BASE_RAM_BYTES_USED + RamUsageEstimator.sizeOf(value.bytes);
     }
 
     @Override

+ 2 - 2
x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/ConstantDoubleVector.java

@@ -15,7 +15,7 @@ import org.apache.lucene.util.RamUsageEstimator;
  */
 public final class ConstantDoubleVector extends AbstractVector implements DoubleVector {
 
-    private static final long BASE_RAM_BYTES_USED = RamUsageEstimator.shallowSizeOfInstance(ConstantDoubleVector.class);
+    static final long RAM_BYTES_USED = RamUsageEstimator.shallowSizeOfInstance(ConstantDoubleVector.class);
 
     private final double value;
 
@@ -55,7 +55,7 @@ public final class ConstantDoubleVector extends AbstractVector implements Double
 
     @Override
     public long ramBytesUsed() {
-        return BASE_RAM_BYTES_USED + RamUsageEstimator.shallowSizeOfInstance(double.class);
+        return RAM_BYTES_USED;
     }
 
     @Override

+ 2 - 2
x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/ConstantIntVector.java

@@ -15,7 +15,7 @@ import org.apache.lucene.util.RamUsageEstimator;
  */
 public final class ConstantIntVector extends AbstractVector implements IntVector {
 
-    private static final long BASE_RAM_BYTES_USED = RamUsageEstimator.shallowSizeOfInstance(ConstantIntVector.class);
+    static final long RAM_BYTES_USED = RamUsageEstimator.shallowSizeOfInstance(ConstantIntVector.class);
 
     private final int value;
 
@@ -55,7 +55,7 @@ public final class ConstantIntVector extends AbstractVector implements IntVector
 
     @Override
     public long ramBytesUsed() {
-        return BASE_RAM_BYTES_USED + RamUsageEstimator.shallowSizeOfInstance(int.class);
+        return RAM_BYTES_USED;
     }
 
     @Override

+ 2 - 2
x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/ConstantLongVector.java

@@ -15,7 +15,7 @@ import org.apache.lucene.util.RamUsageEstimator;
  */
 public final class ConstantLongVector extends AbstractVector implements LongVector {
 
-    private static final long BASE_RAM_BYTES_USED = RamUsageEstimator.shallowSizeOfInstance(ConstantLongVector.class);
+    static final long RAM_BYTES_USED = RamUsageEstimator.shallowSizeOfInstance(ConstantLongVector.class);
 
     private final long value;
 
@@ -55,7 +55,7 @@ public final class ConstantLongVector extends AbstractVector implements LongVect
 
     @Override
     public long ramBytesUsed() {
-        return BASE_RAM_BYTES_USED + RamUsageEstimator.shallowSizeOfInstance(long.class);
+        return RAM_BYTES_USED;
     }
 
     @Override

+ 1 - 1
x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/DoubleArrayVector.java

@@ -17,7 +17,7 @@ import java.util.Arrays;
  */
 public final class DoubleArrayVector extends AbstractVector implements DoubleVector {
 
-    private static final long BASE_RAM_BYTES_USED = RamUsageEstimator.shallowSizeOfInstance(DoubleArrayVector.class);
+    static final long BASE_RAM_BYTES_USED = RamUsageEstimator.shallowSizeOfInstance(DoubleArrayVector.class);
 
     private final double[] values;
 

+ 28 - 0
x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/DoubleVector.java

@@ -107,10 +107,25 @@ public sealed interface DoubleVector extends Vector permits ConstantDoubleVector
         return newVectorBuilder(estimatedSize, BlockFactory.getNonBreakingInstance());
     }
 
+    /**
+     * Creates a builder that grows as needed. Prefer {@link #newVectorFixedBuilder}
+     * if you know the size up front because it's faster.
+     */
     static Builder newVectorBuilder(int estimatedSize, BlockFactory blockFactory) {
         return blockFactory.newDoubleVectorBuilder(estimatedSize);
     }
 
+    /**
+     * Creates a builder that never grows. Prefer this over {@link #newVectorBuilder}
+     * if you know the size up front because it's faster.
+     */
+    static FixedBuilder newVectorFixedBuilder(int size, BlockFactory blockFactory) {
+        return blockFactory.newDoubleVectorFixedBuilder(size);
+    }
+
+    /**
+     * A builder that grows as needed.
+     */
     sealed interface Builder extends Vector.Builder permits DoubleVectorBuilder {
         /**
          * Appends a double to the current entry.
@@ -120,4 +135,17 @@ public sealed interface DoubleVector extends Vector permits ConstantDoubleVector
         @Override
         DoubleVector build();
     }
+
+    /**
+     * A builder that never grows.
+     */
+    sealed interface FixedBuilder extends Vector.Builder permits DoubleVectorFixedBuilder {
+        /**
+         * Appends a double to the current entry.
+         */
+        FixedBuilder appendDouble(double value);
+
+        @Override
+        DoubleVector build();
+    }
 }

+ 1 - 1
x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/DoubleVectorBuilder.java

@@ -10,7 +10,7 @@ package org.elasticsearch.compute.data;
 import java.util.Arrays;
 
 /**
- * Block build of DoubleBlocks.
+ * Builder for {@link DoubleVector}s that grows as needed.
  * This class is generated. Do not edit it.
  */
 final class DoubleVectorBuilder extends AbstractVectorBuilder implements DoubleVector.Builder {

+ 61 - 0
x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/DoubleVectorFixedBuilder.java

@@ -0,0 +1,61 @@
+/*
+ * Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
+ * or more contributor license agreements. Licensed under the Elastic License
+ * 2.0; you may not use this file except in compliance with the Elastic License
+ * 2.0.
+ */
+
+package org.elasticsearch.compute.data;
+
+import org.apache.lucene.util.RamUsageEstimator;
+
+/**
+ * Builder for {@link DoubleVector}s that never grows. Prefer this to
+ * {@link DoubleVectorBuilder} if you know the precise size up front because
+ * it's faster.
+ * This class is generated. Do not edit it.
+ */
+final class DoubleVectorFixedBuilder implements DoubleVector.FixedBuilder {
+    private final BlockFactory blockFactory;
+    private final double[] values;
+    /**
+     * The next value to write into. {@code -1} means the vector has already
+     * been built.
+     */
+    private int nextIndex;
+
+    DoubleVectorFixedBuilder(int size, BlockFactory blockFactory) {
+        blockFactory.adjustBreaker(ramBytesUsed(size), false);
+        this.blockFactory = blockFactory;
+        this.values = new double[size];
+    }
+
+    @Override
+    public DoubleVectorFixedBuilder appendDouble(double value) {
+        values[nextIndex++] = value;
+        return this;
+    }
+
+    private static long ramBytesUsed(int size) {
+        return size == 1
+            ? ConstantDoubleVector.RAM_BYTES_USED
+            : DoubleArrayVector.BASE_RAM_BYTES_USED + RamUsageEstimator.alignObjectSize(
+                (long) RamUsageEstimator.NUM_BYTES_ARRAY_HEADER + size * Double.BYTES
+            );
+    }
+
+    @Override
+    public DoubleVector build() {
+        if (nextIndex < 0) {
+            throw new IllegalStateException("already closed");
+        }
+        if (nextIndex != values.length) {
+            throw new IllegalStateException("expected to write [" + values.length + "] entries but wrote [" + nextIndex + "]");
+        }
+        nextIndex = -1;
+        if (values.length == 1) {
+            return new ConstantDoubleVector(values[0], 1, blockFactory);
+        }
+        return new DoubleArrayVector(values, values.length, blockFactory);
+    }
+}

+ 1 - 1
x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/IntArrayVector.java

@@ -17,7 +17,7 @@ import java.util.Arrays;
  */
 public final class IntArrayVector extends AbstractVector implements IntVector {
 
-    private static final long BASE_RAM_BYTES_USED = RamUsageEstimator.shallowSizeOfInstance(IntArrayVector.class);
+    static final long BASE_RAM_BYTES_USED = RamUsageEstimator.shallowSizeOfInstance(IntArrayVector.class);
 
     private final int[] values;
 

+ 28 - 0
x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/IntVector.java

@@ -106,10 +106,22 @@ public sealed interface IntVector extends Vector permits ConstantIntVector, Filt
         return newVectorBuilder(estimatedSize, BlockFactory.getNonBreakingInstance());
     }
 
+    /**
+     * Creates a builder that grows as needed. Prefer {@link #newVectorFixedBuilder}
+     * if you know the size up front because it's faster.
+     */
     static Builder newVectorBuilder(int estimatedSize, BlockFactory blockFactory) {
         return blockFactory.newIntVectorBuilder(estimatedSize);
     }
 
+    /**
+     * Creates a builder that never grows. Prefer this over {@link #newVectorBuilder}
+     * if you know the size up front because it's faster.
+     */
+    static FixedBuilder newVectorFixedBuilder(int size, BlockFactory blockFactory) {
+        return blockFactory.newIntVectorFixedBuilder(size);
+    }
+
     /** Create a vector for a range of ints. */
     static IntVector range(int startInclusive, int endExclusive) {
         int[] values = new int[endExclusive - startInclusive];
@@ -119,6 +131,9 @@ public sealed interface IntVector extends Vector permits ConstantIntVector, Filt
         return new IntArrayVector(values, values.length);
     }
 
+    /**
+     * A builder that grows as needed.
+     */
     sealed interface Builder extends Vector.Builder permits IntVectorBuilder {
         /**
          * Appends a int to the current entry.
@@ -128,4 +143,17 @@ public sealed interface IntVector extends Vector permits ConstantIntVector, Filt
         @Override
         IntVector build();
     }
+
+    /**
+     * A builder that never grows.
+     */
+    sealed interface FixedBuilder extends Vector.Builder permits IntVectorFixedBuilder {
+        /**
+         * Appends a int to the current entry.
+         */
+        FixedBuilder appendInt(int value);
+
+        @Override
+        IntVector build();
+    }
 }

+ 1 - 1
x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/IntVectorBuilder.java

@@ -10,7 +10,7 @@ package org.elasticsearch.compute.data;
 import java.util.Arrays;
 
 /**
- * Block build of IntBlocks.
+ * Builder for {@link IntVector}s that grows as needed.
  * This class is generated. Do not edit it.
  */
 final class IntVectorBuilder extends AbstractVectorBuilder implements IntVector.Builder {

+ 61 - 0
x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/IntVectorFixedBuilder.java

@@ -0,0 +1,61 @@
+/*
+ * Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
+ * or more contributor license agreements. Licensed under the Elastic License
+ * 2.0; you may not use this file except in compliance with the Elastic License
+ * 2.0.
+ */
+
+package org.elasticsearch.compute.data;
+
+import org.apache.lucene.util.RamUsageEstimator;
+
+/**
+ * Builder for {@link IntVector}s that never grows. Prefer this to
+ * {@link IntVectorBuilder} if you know the precise size up front because
+ * it's faster.
+ * This class is generated. Do not edit it.
+ */
+final class IntVectorFixedBuilder implements IntVector.FixedBuilder {
+    private final BlockFactory blockFactory;
+    private final int[] values;
+    /**
+     * The next value to write into. {@code -1} means the vector has already
+     * been built.
+     */
+    private int nextIndex;
+
+    IntVectorFixedBuilder(int size, BlockFactory blockFactory) {
+        blockFactory.adjustBreaker(ramBytesUsed(size), false);
+        this.blockFactory = blockFactory;
+        this.values = new int[size];
+    }
+
+    @Override
+    public IntVectorFixedBuilder appendInt(int value) {
+        values[nextIndex++] = value;
+        return this;
+    }
+
+    private static long ramBytesUsed(int size) {
+        return size == 1
+            ? ConstantIntVector.RAM_BYTES_USED
+            : IntArrayVector.BASE_RAM_BYTES_USED + RamUsageEstimator.alignObjectSize(
+                (long) RamUsageEstimator.NUM_BYTES_ARRAY_HEADER + size * Integer.BYTES
+            );
+    }
+
+    @Override
+    public IntVector build() {
+        if (nextIndex < 0) {
+            throw new IllegalStateException("already closed");
+        }
+        if (nextIndex != values.length) {
+            throw new IllegalStateException("expected to write [" + values.length + "] entries but wrote [" + nextIndex + "]");
+        }
+        nextIndex = -1;
+        if (values.length == 1) {
+            return new ConstantIntVector(values[0], 1, blockFactory);
+        }
+        return new IntArrayVector(values, values.length, blockFactory);
+    }
+}

+ 1 - 1
x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/LongArrayVector.java

@@ -17,7 +17,7 @@ import java.util.Arrays;
  */
 public final class LongArrayVector extends AbstractVector implements LongVector {
 
-    private static final long BASE_RAM_BYTES_USED = RamUsageEstimator.shallowSizeOfInstance(LongArrayVector.class);
+    static final long BASE_RAM_BYTES_USED = RamUsageEstimator.shallowSizeOfInstance(LongArrayVector.class);
 
     private final long[] values;
 

+ 28 - 0
x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/LongVector.java

@@ -107,10 +107,25 @@ public sealed interface LongVector extends Vector permits ConstantLongVector, Fi
         return newVectorBuilder(estimatedSize, BlockFactory.getNonBreakingInstance());
     }
 
+    /**
+     * Creates a builder that grows as needed. Prefer {@link #newVectorFixedBuilder}
+     * if you know the size up front because it's faster.
+     */
     static Builder newVectorBuilder(int estimatedSize, BlockFactory blockFactory) {
         return blockFactory.newLongVectorBuilder(estimatedSize);
     }
 
+    /**
+     * Creates a builder that never grows. Prefer this over {@link #newVectorBuilder}
+     * if you know the size up front because it's faster.
+     */
+    static FixedBuilder newVectorFixedBuilder(int size, BlockFactory blockFactory) {
+        return blockFactory.newLongVectorFixedBuilder(size);
+    }
+
+    /**
+     * A builder that grows as needed.
+     */
     sealed interface Builder extends Vector.Builder permits LongVectorBuilder {
         /**
          * Appends a long to the current entry.
@@ -120,4 +135,17 @@ public sealed interface LongVector extends Vector permits ConstantLongVector, Fi
         @Override
         LongVector build();
     }
+
+    /**
+     * A builder that never grows.
+     */
+    sealed interface FixedBuilder extends Vector.Builder permits LongVectorFixedBuilder {
+        /**
+         * Appends a long to the current entry.
+         */
+        FixedBuilder appendLong(long value);
+
+        @Override
+        LongVector build();
+    }
 }

+ 1 - 1
x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/LongVectorBuilder.java

@@ -10,7 +10,7 @@ package org.elasticsearch.compute.data;
 import java.util.Arrays;
 
 /**
- * Block build of LongBlocks.
+ * Builder for {@link LongVector}s that grows as needed.
  * This class is generated. Do not edit it.
  */
 final class LongVectorBuilder extends AbstractVectorBuilder implements LongVector.Builder {

+ 61 - 0
x-pack/plugin/esql/compute/src/main/generated-src/org/elasticsearch/compute/data/LongVectorFixedBuilder.java

@@ -0,0 +1,61 @@
+/*
+ * Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
+ * or more contributor license agreements. Licensed under the Elastic License
+ * 2.0; you may not use this file except in compliance with the Elastic License
+ * 2.0.
+ */
+
+package org.elasticsearch.compute.data;
+
+import org.apache.lucene.util.RamUsageEstimator;
+
+/**
+ * Builder for {@link LongVector}s that never grows. Prefer this to
+ * {@link LongVectorBuilder} if you know the precise size up front because
+ * it's faster.
+ * This class is generated. Do not edit it.
+ */
+final class LongVectorFixedBuilder implements LongVector.FixedBuilder {
+    private final BlockFactory blockFactory;
+    private final long[] values;
+    /**
+     * The next value to write into. {@code -1} means the vector has already
+     * been built.
+     */
+    private int nextIndex;
+
+    LongVectorFixedBuilder(int size, BlockFactory blockFactory) {
+        blockFactory.adjustBreaker(ramBytesUsed(size), false);
+        this.blockFactory = blockFactory;
+        this.values = new long[size];
+    }
+
+    @Override
+    public LongVectorFixedBuilder appendLong(long value) {
+        values[nextIndex++] = value;
+        return this;
+    }
+
+    private static long ramBytesUsed(int size) {
+        return size == 1
+            ? ConstantLongVector.RAM_BYTES_USED
+            : LongArrayVector.BASE_RAM_BYTES_USED + RamUsageEstimator.alignObjectSize(
+                (long) RamUsageEstimator.NUM_BYTES_ARRAY_HEADER + size * Long.BYTES
+            );
+    }
+
+    @Override
+    public LongVector build() {
+        if (nextIndex < 0) {
+            throw new IllegalStateException("already closed");
+        }
+        if (nextIndex != values.length) {
+            throw new IllegalStateException("expected to write [" + values.length + "] entries but wrote [" + nextIndex + "]");
+        }
+        nextIndex = -1;
+        if (values.length == 1) {
+            return new ConstantLongVector(values[0], 1, blockFactory);
+        }
+        return new LongArrayVector(values, values.length, blockFactory);
+    }
+}

+ 17 - 1
x-pack/plugin/esql/compute/src/main/java/org/elasticsearch/compute/data/BlockFactory.java

@@ -46,7 +46,7 @@ public class BlockFactory {
 
     private final BigArrays bigArrays;
 
-    private BlockFactory(CircuitBreaker breaker, BigArrays bigArrays) {
+    public BlockFactory(CircuitBreaker breaker, BigArrays bigArrays) {
         this.breaker = breaker;
         this.bigArrays = bigArrays;
     }
@@ -134,6 +134,10 @@ public class BlockFactory {
         return new BooleanBlockBuilder(estimatedSize, this);
     }
 
+    BooleanVector.FixedBuilder newBooleanVectorFixedBuilder(int size) {
+        return new BooleanVectorFixedBuilder(size, this);
+    }
+
     public BooleanBlock newBooleanArrayBlock(
         boolean[] values,
         int positionCount,
@@ -180,6 +184,10 @@ public class BlockFactory {
         return new IntVectorBuilder(estimatedSize, this);
     }
 
+    IntVector.FixedBuilder newIntVectorFixedBuilder(int size) {
+        return new IntVectorFixedBuilder(size, this);
+    }
+
     /**
      * Creates a new Vector with the given values and positionCount. Equivalent to:
      *   newIntArrayVector(values, positionCount, 0L); // with zero pre-adjusted bytes
@@ -225,6 +233,10 @@ public class BlockFactory {
         return new LongVectorBuilder(estimatedSize, this);
     }
 
+    LongVector.FixedBuilder newLongVectorFixedBuilder(int size) {
+        return new LongVectorFixedBuilder(size, this);
+    }
+
     public LongVector newLongArrayVector(long[] values, int positionCount) {
         return newLongArrayVector(values, positionCount, 0L);
     }
@@ -261,6 +273,10 @@ public class BlockFactory {
         return new DoubleVectorBuilder(estimatedSize, this);
     }
 
+    DoubleVector.FixedBuilder newDoubleVectorFixedBuilder(int size) {
+        return new DoubleVectorFixedBuilder(size, this);
+    }
+
     public DoubleVector newDoubleArrayVector(double[] values, int positionCount) {
         return newDoubleArrayVector(values, positionCount, 0L);
     }

+ 1 - 1
x-pack/plugin/esql/compute/src/main/java/org/elasticsearch/compute/data/X-ArrayVector.java.st

@@ -25,7 +25,7 @@ $endif$
  */
 public final class $Type$ArrayVector extends AbstractVector implements $Type$Vector {
 
-    private static final long BASE_RAM_BYTES_USED = RamUsageEstimator.shallowSizeOfInstance($Type$ArrayVector.class);
+    static final long BASE_RAM_BYTES_USED = RamUsageEstimator.shallowSizeOfInstance($Type$ArrayVector.class);
 
 $if(BytesRef)$
     private final BytesRefArray values;

+ 11 - 2
x-pack/plugin/esql/compute/src/main/java/org/elasticsearch/compute/data/X-ConstantVector.java.st

@@ -18,7 +18,12 @@ import org.apache.lucene.util.RamUsageEstimator;
  */
 public final class Constant$Type$Vector extends AbstractVector implements $Type$Vector {
 
-    private static final long BASE_RAM_BYTES_USED = RamUsageEstimator.shallowSizeOfInstance(Constant$Type$Vector.class);
+$if(BytesRef)$
+    static final long BASE_RAM_BYTES_USED = RamUsageEstimator.shallowSizeOfInstance(ConstantBytesRefVector.class) + RamUsageEstimator
+        .shallowSizeOfInstance(BytesRef.class);
+$else$
+    static final long RAM_BYTES_USED = RamUsageEstimator.shallowSizeOfInstance(Constant$Type$Vector.class);
+$endif$
 
     private final $type$ value;
 
@@ -62,7 +67,11 @@ $endif$
 
     @Override
     public long ramBytesUsed() {
-        return BASE_RAM_BYTES_USED + RamUsageEstimator.shallowSizeOfInstance($type$.class);
+$if(BytesRef)$
+        return BASE_RAM_BYTES_USED + RamUsageEstimator.sizeOf(value.bytes);
+$else$
+        return RAM_BYTES_USED;
+$endif$
     }
 
     @Override

+ 40 - 0
x-pack/plugin/esql/compute/src/main/java/org/elasticsearch/compute/data/X-Vector.java.st

@@ -148,10 +148,31 @@ $endif$
         return newVectorBuilder(estimatedSize, BlockFactory.getNonBreakingInstance());
     }
 
+$if(BytesRef)$
+    /**
+     * Creates a builder that grows as needed.
+     */
+$else$
+    /**
+     * Creates a builder that grows as needed. Prefer {@link #newVectorFixedBuilder}
+     * if you know the size up front because it's faster.
+     */
+$endif$
     static Builder newVectorBuilder(int estimatedSize, BlockFactory blockFactory) {
         return blockFactory.new$Type$VectorBuilder(estimatedSize);
     }
 
+$if(BytesRef)$
+$else$
+    /**
+     * Creates a builder that never grows. Prefer this over {@link #newVectorBuilder}
+     * if you know the size up front because it's faster.
+     */
+    static FixedBuilder newVectorFixedBuilder(int size, BlockFactory blockFactory) {
+        return blockFactory.new$Type$VectorFixedBuilder(size);
+    }
+$endif$
+
 $if(int)$
     /** Create a vector for a range of ints. */
     static IntVector range(int startInclusive, int endExclusive) {
@@ -163,6 +184,9 @@ $if(int)$
     }
 $endif$
 
+    /**
+     * A builder that grows as needed.
+     */
     sealed interface Builder extends Vector.Builder permits $Type$VectorBuilder {
         /**
          * Appends a $type$ to the current entry.
@@ -172,4 +196,20 @@ $endif$
         @Override
         $Type$Vector build();
     }
+
+$if(BytesRef)$
+$else$
+    /**
+     * A builder that never grows.
+     */
+    sealed interface FixedBuilder extends Vector.Builder permits $Type$VectorFixedBuilder {
+        /**
+         * Appends a $type$ to the current entry.
+         */
+        FixedBuilder append$Type$($type$ value);
+
+        @Override
+        $Type$Vector build();
+    }
+$endif$
 }

+ 1 - 1
x-pack/plugin/esql/compute/src/main/java/org/elasticsearch/compute/data/X-VectorBuilder.java.st

@@ -18,7 +18,7 @@ import java.util.Arrays;
 $endif$
 
 /**
- * Block build of $Type$Blocks.
+ * Builder for {@link $Type$Vector}s that grows as needed.
  * This class is generated. Do not edit it.
  */
 final class $Type$VectorBuilder extends AbstractVectorBuilder implements $Type$Vector.Builder {

+ 61 - 0
x-pack/plugin/esql/compute/src/main/java/org/elasticsearch/compute/data/X-VectorFixedBuilder.java.st

@@ -0,0 +1,61 @@
+/*
+ * Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
+ * or more contributor license agreements. Licensed under the Elastic License
+ * 2.0; you may not use this file except in compliance with the Elastic License
+ * 2.0.
+ */
+
+package org.elasticsearch.compute.data;
+
+import org.apache.lucene.util.RamUsageEstimator;
+
+/**
+ * Builder for {@link $Type$Vector}s that never grows. Prefer this to
+ * {@link $Type$VectorBuilder} if you know the precise size up front because
+ * it's faster.
+ * This class is generated. Do not edit it.
+ */
+final class $Type$VectorFixedBuilder implements $Type$Vector.FixedBuilder {
+    private final BlockFactory blockFactory;
+    private final $type$[] values;
+    /**
+     * The next value to write into. {@code -1} means the vector has already
+     * been built.
+     */
+    private int nextIndex;
+
+    $Type$VectorFixedBuilder(int size, BlockFactory blockFactory) {
+        blockFactory.adjustBreaker(ramBytesUsed(size), false);
+        this.blockFactory = blockFactory;
+        this.values = new $type$[size];
+    }
+
+    @Override
+    public $Type$VectorFixedBuilder append$Type$($type$ value) {
+        values[nextIndex++] = value;
+        return this;
+    }
+
+    private static long ramBytesUsed(int size) {
+        return size == 1
+            ? Constant$Type$Vector.RAM_BYTES_USED
+            : $Type$ArrayVector.BASE_RAM_BYTES_USED + RamUsageEstimator.alignObjectSize(
+                (long) RamUsageEstimator.NUM_BYTES_ARRAY_HEADER + size * $BYTES$
+            );
+    }
+
+    @Override
+    public $Type$Vector build() {
+        if (nextIndex < 0) {
+            throw new IllegalStateException("already closed");
+        }
+        if (nextIndex != values.length) {
+            throw new IllegalStateException("expected to write [" + values.length + "] entries but wrote [" + nextIndex + "]");
+        }
+        nextIndex = -1;
+        if (values.length == 1) {
+            return new Constant$Type$Vector(values[0], 1, blockFactory);
+        }
+        return new $Type$ArrayVector(values, values.length, blockFactory);
+    }
+}

+ 1 - 1
x-pack/plugin/esql/compute/src/main/java/org/elasticsearch/compute/operator/DriverContext.java

@@ -61,7 +61,7 @@ public class DriverContext {
      * The {@link CircuitBreaker} to use to track memory.
      */
     public CircuitBreaker breaker() {
-        return bigArrays.breakerService().getBreaker(CircuitBreaker.REQUEST);
+        return blockFactory.breaker();
     }
 
     public BlockFactory blockFactory() {

+ 4 - 0
x-pack/plugin/esql/compute/src/test/java/org/elasticsearch/compute/data/BlockFactoryTests.java

@@ -38,6 +38,10 @@ import static org.mockito.Mockito.when;
 // BlockFactory is used and effectively tested in many other places, but this class contains tests
 // more specific to the factory implementation itself (and not necessarily tested elsewhere).
 public class BlockFactoryTests extends ESTestCase {
+    public static BlockFactory blockFactory(ByteSizeValue size) {
+        BigArrays bigArrays = new MockBigArrays(PageCacheRecycler.NON_RECYCLING_INSTANCE, size).withCircuitBreaking();
+        return new BlockFactory(bigArrays.breakerService().getBreaker(CircuitBreaker.REQUEST), bigArrays);
+    }
 
     final CircuitBreaker breaker;
     final BigArrays bigArrays;

+ 136 - 0
x-pack/plugin/esql/compute/src/test/java/org/elasticsearch/compute/data/VectorFixedBuilderTests.java

@@ -0,0 +1,136 @@
+/*
+ * Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
+ * or more contributor license agreements. Licensed under the Elastic License
+ * 2.0; you may not use this file except in compliance with the Elastic License
+ * 2.0.
+ */
+
+package org.elasticsearch.compute.data;
+
+import com.carrotsearch.randomizedtesting.annotations.ParametersFactory;
+
+import org.elasticsearch.common.breaker.CircuitBreaker;
+import org.elasticsearch.common.breaker.CircuitBreakingException;
+import org.elasticsearch.common.unit.ByteSizeValue;
+import org.elasticsearch.common.util.BigArrays;
+import org.elasticsearch.common.util.MockBigArrays;
+import org.elasticsearch.common.util.PageCacheRecycler;
+import org.elasticsearch.indices.CrankyCircuitBreakerService;
+import org.elasticsearch.test.ESTestCase;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import static org.hamcrest.Matchers.equalTo;
+
+public class VectorFixedBuilderTests extends ESTestCase {
+    @ParametersFactory
+    public static List<Object[]> params() {
+        List<Object[]> params = new ArrayList<>();
+        for (ElementType elementType : ElementType.values()) {
+            if (elementType == ElementType.UNKNOWN
+                || elementType == ElementType.NULL
+                || elementType == ElementType.DOC
+                || elementType == ElementType.BYTES_REF) {
+                continue;
+            }
+            params.add(new Object[] { elementType });
+        }
+        return params;
+    }
+
+    private final ElementType elementType;
+
+    public VectorFixedBuilderTests(ElementType elementType) {
+        this.elementType = elementType;
+    }
+
+    public void testBuildSmall() {
+        testBuild(between(1, 100));
+    }
+
+    public void testBuildHuge() {
+        testBuild(between(1_000, 50_000));
+    }
+
+    public void testBuildSingle() {
+        testBuild(1);
+    }
+
+    private void testBuild(int size) {
+        BlockFactory blockFactory = BlockFactoryTests.blockFactory(ByteSizeValue.ofGb(1));
+        Vector.Builder builder = vectorBuilder(size, blockFactory);
+        BasicBlockTests.RandomBlock random = BasicBlockTests.randomBlock(elementType, size, false, 1, 1, 0, 0);
+        fill(builder, random.block().asVector());
+        try (Vector built = builder.build()) {
+            assertThat(built, equalTo(random.block().asVector()));
+            assertThat(blockFactory.breaker().getUsed(), equalTo(built.ramBytesUsed()));
+        }
+    }
+
+    public void testDoubleBuild() {
+        BlockFactory blockFactory = BlockFactoryTests.blockFactory(ByteSizeValue.ofGb(1));
+        Vector.Builder builder = vectorBuilder(10, blockFactory);
+        BasicBlockTests.RandomBlock random = BasicBlockTests.randomBlock(elementType, 10, false, 1, 1, 0, 0);
+        fill(builder, random.block().asVector());
+        try (Vector built = builder.build()) {
+            assertThat(built, equalTo(random.block().asVector()));
+        }
+        Exception e = expectThrows(IllegalStateException.class, builder::build);
+        assertThat(e.getMessage(), equalTo("already closed"));
+    }
+
+    public void testCranky() {
+        BigArrays bigArrays = new MockBigArrays(PageCacheRecycler.NON_RECYCLING_INSTANCE, new CrankyCircuitBreakerService());
+        BlockFactory blockFactory = new BlockFactory(bigArrays.breakerService().getBreaker(CircuitBreaker.REQUEST), bigArrays);
+        try {
+            Vector.Builder builder = vectorBuilder(10, blockFactory);
+            BasicBlockTests.RandomBlock random = BasicBlockTests.randomBlock(elementType, 10, false, 1, 1, 0, 0);
+            fill(builder, random.block().asVector());
+            try (Vector built = builder.build()) {
+                assertThat(built, equalTo(random.block().asVector()));
+            }
+            // If we made it this far cranky didn't fail us!
+        } catch (CircuitBreakingException e) {
+            logger.info("cranky", e);
+            assertThat(e.getMessage(), equalTo(CrankyCircuitBreakerService.ERROR_MESSAGE));
+        }
+        assertThat(blockFactory.breaker().getUsed(), equalTo(0L));
+    }
+
+    private Vector.Builder vectorBuilder(int size, BlockFactory blockFactory) {
+        return switch (elementType) {
+            case NULL, BYTES_REF, DOC, UNKNOWN -> throw new UnsupportedOperationException();
+            case BOOLEAN -> BooleanVector.newVectorFixedBuilder(size, blockFactory);
+            case DOUBLE -> DoubleVector.newVectorFixedBuilder(size, blockFactory);
+            case INT -> IntVector.newVectorFixedBuilder(size, blockFactory);
+            case LONG -> LongVector.newVectorFixedBuilder(size, blockFactory);
+        };
+    }
+
+    private void fill(Vector.Builder builder, Vector from) {
+        switch (elementType) {
+            case NULL, DOC, UNKNOWN -> throw new UnsupportedOperationException();
+            case BOOLEAN -> {
+                for (int p = 0; p < from.getPositionCount(); p++) {
+                    ((BooleanVector.FixedBuilder) builder).appendBoolean(((BooleanVector) from).getBoolean(p));
+                }
+            }
+            case DOUBLE -> {
+                for (int p = 0; p < from.getPositionCount(); p++) {
+                    ((DoubleVector.FixedBuilder) builder).appendDouble(((DoubleVector) from).getDouble(p));
+                }
+            }
+            case INT -> {
+                for (int p = 0; p < from.getPositionCount(); p++) {
+                    ((IntVector.FixedBuilder) builder).appendInt(((IntVector) from).getInt(p));
+                }
+            }
+            case LONG -> {
+                for (int p = 0; p < from.getPositionCount(); p++) {
+                    ((LongVector.FixedBuilder) builder).appendLong(((LongVector) from).getLong(p));
+                }
+            }
+        }
+    }
+}

+ 3 - 1
x-pack/plugin/esql/src/internalClusterTest/java/org/elasticsearch/xpack/esql/action/EsqlDisruptionIT.java

@@ -47,11 +47,13 @@ public class EsqlDisruptionIT extends EsqlActionIT {
 
     @Override
     protected Settings nodeSettings(int nodeOrdinal, Settings otherSettings) {
-        return Settings.builder()
+        Settings settings = Settings.builder()
             .put(super.nodeSettings(nodeOrdinal, otherSettings))
             .put(DEFAULT_SETTINGS)
             .put(ExchangeService.INACTIVE_SINKS_INTERVAL_SETTING, TimeValue.timeValueMillis(between(1000, 2000)))
             .build();
+        logger.info("settings {}", settings);
+        return settings;
     }
 
     @Override

+ 5 - 5
x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvAvgDoubleEvaluator.java

@@ -7,8 +7,8 @@ package org.elasticsearch.xpack.esql.expression.function.scalar.multivalue;
 import java.lang.Override;
 import java.lang.String;
 import org.elasticsearch.compute.data.Block;
-import org.elasticsearch.compute.data.DoubleArrayVector;
 import org.elasticsearch.compute.data.DoubleBlock;
+import org.elasticsearch.compute.data.DoubleVector;
 import org.elasticsearch.compute.data.Vector;
 import org.elasticsearch.compute.operator.DriverContext;
 import org.elasticsearch.compute.operator.EvalOperator;
@@ -38,7 +38,7 @@ public final class MvAvgDoubleEvaluator extends AbstractMultivalueFunction.Abstr
   public Block evalNullable(Block fieldVal) {
     DoubleBlock v = (DoubleBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    DoubleBlock.Builder builder = DoubleBlock.newBlockBuilder(positionCount);
+    DoubleBlock.Builder builder = DoubleBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     CompensatedSum work = new CompensatedSum();
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
@@ -65,7 +65,7 @@ public final class MvAvgDoubleEvaluator extends AbstractMultivalueFunction.Abstr
   public Vector evalNotNullable(Block fieldVal) {
     DoubleBlock v = (DoubleBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    double[] values = new double[positionCount];
+    DoubleVector.FixedBuilder builder = DoubleVector.newVectorFixedBuilder(positionCount, driverContext.blockFactory());
     CompensatedSum work = new CompensatedSum();
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
@@ -76,8 +76,8 @@ public final class MvAvgDoubleEvaluator extends AbstractMultivalueFunction.Abstr
         MvAvg.process(work, value);
       }
       double result = MvAvg.finish(work, valueCount);
-      values[p] = result;
+      builder.appendDouble(result);
     }
-    return new DoubleArrayVector(values, positionCount);
+    return builder.build();
   }
 }

+ 10 - 10
x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvAvgIntEvaluator.java

@@ -7,8 +7,8 @@ package org.elasticsearch.xpack.esql.expression.function.scalar.multivalue;
 import java.lang.Override;
 import java.lang.String;
 import org.elasticsearch.compute.data.Block;
-import org.elasticsearch.compute.data.DoubleArrayVector;
 import org.elasticsearch.compute.data.DoubleBlock;
+import org.elasticsearch.compute.data.DoubleVector;
 import org.elasticsearch.compute.data.IntBlock;
 import org.elasticsearch.compute.data.Vector;
 import org.elasticsearch.compute.operator.DriverContext;
@@ -39,7 +39,7 @@ public final class MvAvgIntEvaluator extends AbstractMultivalueFunction.Abstract
   public Block evalNullable(Block fieldVal) {
     IntBlock v = (IntBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    DoubleBlock.Builder builder = DoubleBlock.newBlockBuilder(positionCount);
+    DoubleBlock.Builder builder = DoubleBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     CompensatedSum work = new CompensatedSum();
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
@@ -72,7 +72,7 @@ public final class MvAvgIntEvaluator extends AbstractMultivalueFunction.Abstract
   public Vector evalNotNullable(Block fieldVal) {
     IntBlock v = (IntBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    double[] values = new double[positionCount];
+    DoubleVector.FixedBuilder builder = DoubleVector.newVectorFixedBuilder(positionCount, driverContext.blockFactory());
     CompensatedSum work = new CompensatedSum();
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
@@ -80,7 +80,7 @@ public final class MvAvgIntEvaluator extends AbstractMultivalueFunction.Abstract
       if (valueCount == 1) {
         int value = v.getInt(first);
         double result = MvAvg.single(value);
-        values[p] = result;
+        builder.appendDouble(result);
         continue;
       }
       int end = first + valueCount;
@@ -89,9 +89,9 @@ public final class MvAvgIntEvaluator extends AbstractMultivalueFunction.Abstract
         MvAvg.process(work, value);
       }
       double result = MvAvg.finish(work, valueCount);
-      values[p] = result;
+      builder.appendDouble(result);
     }
-    return new DoubleArrayVector(values, positionCount);
+    return builder.build();
   }
 
   /**
@@ -101,7 +101,7 @@ public final class MvAvgIntEvaluator extends AbstractMultivalueFunction.Abstract
   public Block evalSingleValuedNullable(Block fieldVal) {
     IntBlock v = (IntBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    DoubleBlock.Builder builder = DoubleBlock.newBlockBuilder(positionCount);
+    DoubleBlock.Builder builder = DoubleBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     CompensatedSum work = new CompensatedSum();
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
@@ -125,7 +125,7 @@ public final class MvAvgIntEvaluator extends AbstractMultivalueFunction.Abstract
   public Vector evalSingleValuedNotNullable(Block fieldVal) {
     IntBlock v = (IntBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    double[] values = new double[positionCount];
+    DoubleVector.FixedBuilder builder = DoubleVector.newVectorFixedBuilder(positionCount, driverContext.blockFactory());
     CompensatedSum work = new CompensatedSum();
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
@@ -133,8 +133,8 @@ public final class MvAvgIntEvaluator extends AbstractMultivalueFunction.Abstract
       int first = v.getFirstValueIndex(p);
       int value = v.getInt(first);
       double result = MvAvg.single(value);
-      values[p] = result;
+      builder.appendDouble(result);
     }
-    return new DoubleArrayVector(values, positionCount);
+    return builder.build();
   }
 }

+ 10 - 10
x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvAvgLongEvaluator.java

@@ -7,8 +7,8 @@ package org.elasticsearch.xpack.esql.expression.function.scalar.multivalue;
 import java.lang.Override;
 import java.lang.String;
 import org.elasticsearch.compute.data.Block;
-import org.elasticsearch.compute.data.DoubleArrayVector;
 import org.elasticsearch.compute.data.DoubleBlock;
+import org.elasticsearch.compute.data.DoubleVector;
 import org.elasticsearch.compute.data.LongBlock;
 import org.elasticsearch.compute.data.Vector;
 import org.elasticsearch.compute.operator.DriverContext;
@@ -39,7 +39,7 @@ public final class MvAvgLongEvaluator extends AbstractMultivalueFunction.Abstrac
   public Block evalNullable(Block fieldVal) {
     LongBlock v = (LongBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    DoubleBlock.Builder builder = DoubleBlock.newBlockBuilder(positionCount);
+    DoubleBlock.Builder builder = DoubleBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     CompensatedSum work = new CompensatedSum();
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
@@ -72,7 +72,7 @@ public final class MvAvgLongEvaluator extends AbstractMultivalueFunction.Abstrac
   public Vector evalNotNullable(Block fieldVal) {
     LongBlock v = (LongBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    double[] values = new double[positionCount];
+    DoubleVector.FixedBuilder builder = DoubleVector.newVectorFixedBuilder(positionCount, driverContext.blockFactory());
     CompensatedSum work = new CompensatedSum();
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
@@ -80,7 +80,7 @@ public final class MvAvgLongEvaluator extends AbstractMultivalueFunction.Abstrac
       if (valueCount == 1) {
         long value = v.getLong(first);
         double result = MvAvg.single(value);
-        values[p] = result;
+        builder.appendDouble(result);
         continue;
       }
       int end = first + valueCount;
@@ -89,9 +89,9 @@ public final class MvAvgLongEvaluator extends AbstractMultivalueFunction.Abstrac
         MvAvg.process(work, value);
       }
       double result = MvAvg.finish(work, valueCount);
-      values[p] = result;
+      builder.appendDouble(result);
     }
-    return new DoubleArrayVector(values, positionCount);
+    return builder.build();
   }
 
   /**
@@ -101,7 +101,7 @@ public final class MvAvgLongEvaluator extends AbstractMultivalueFunction.Abstrac
   public Block evalSingleValuedNullable(Block fieldVal) {
     LongBlock v = (LongBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    DoubleBlock.Builder builder = DoubleBlock.newBlockBuilder(positionCount);
+    DoubleBlock.Builder builder = DoubleBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     CompensatedSum work = new CompensatedSum();
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
@@ -125,7 +125,7 @@ public final class MvAvgLongEvaluator extends AbstractMultivalueFunction.Abstrac
   public Vector evalSingleValuedNotNullable(Block fieldVal) {
     LongBlock v = (LongBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    double[] values = new double[positionCount];
+    DoubleVector.FixedBuilder builder = DoubleVector.newVectorFixedBuilder(positionCount, driverContext.blockFactory());
     CompensatedSum work = new CompensatedSum();
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
@@ -133,8 +133,8 @@ public final class MvAvgLongEvaluator extends AbstractMultivalueFunction.Abstrac
       int first = v.getFirstValueIndex(p);
       long value = v.getLong(first);
       double result = MvAvg.single(value);
-      values[p] = result;
+      builder.appendDouble(result);
     }
-    return new DoubleArrayVector(values, positionCount);
+    return builder.build();
   }
 }

+ 10 - 10
x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvAvgUnsignedLongEvaluator.java

@@ -7,8 +7,8 @@ package org.elasticsearch.xpack.esql.expression.function.scalar.multivalue;
 import java.lang.Override;
 import java.lang.String;
 import org.elasticsearch.compute.data.Block;
-import org.elasticsearch.compute.data.DoubleArrayVector;
 import org.elasticsearch.compute.data.DoubleBlock;
+import org.elasticsearch.compute.data.DoubleVector;
 import org.elasticsearch.compute.data.LongBlock;
 import org.elasticsearch.compute.data.Vector;
 import org.elasticsearch.compute.operator.DriverContext;
@@ -40,7 +40,7 @@ public final class MvAvgUnsignedLongEvaluator extends AbstractMultivalueFunction
   public Block evalNullable(Block fieldVal) {
     LongBlock v = (LongBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    DoubleBlock.Builder builder = DoubleBlock.newBlockBuilder(positionCount);
+    DoubleBlock.Builder builder = DoubleBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     CompensatedSum work = new CompensatedSum();
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
@@ -73,7 +73,7 @@ public final class MvAvgUnsignedLongEvaluator extends AbstractMultivalueFunction
   public Vector evalNotNullable(Block fieldVal) {
     LongBlock v = (LongBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    double[] values = new double[positionCount];
+    DoubleVector.FixedBuilder builder = DoubleVector.newVectorFixedBuilder(positionCount, driverContext.blockFactory());
     CompensatedSum work = new CompensatedSum();
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
@@ -81,7 +81,7 @@ public final class MvAvgUnsignedLongEvaluator extends AbstractMultivalueFunction
       if (valueCount == 1) {
         long value = v.getLong(first);
         double result = MvAvg.singleUnsignedLong(value);
-        values[p] = result;
+        builder.appendDouble(result);
         continue;
       }
       int end = first + valueCount;
@@ -90,9 +90,9 @@ public final class MvAvgUnsignedLongEvaluator extends AbstractMultivalueFunction
         MvAvg.processUnsignedLong(work, value);
       }
       double result = MvAvg.finish(work, valueCount);
-      values[p] = result;
+      builder.appendDouble(result);
     }
-    return new DoubleArrayVector(values, positionCount);
+    return builder.build();
   }
 
   /**
@@ -102,7 +102,7 @@ public final class MvAvgUnsignedLongEvaluator extends AbstractMultivalueFunction
   public Block evalSingleValuedNullable(Block fieldVal) {
     LongBlock v = (LongBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    DoubleBlock.Builder builder = DoubleBlock.newBlockBuilder(positionCount);
+    DoubleBlock.Builder builder = DoubleBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     CompensatedSum work = new CompensatedSum();
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
@@ -126,7 +126,7 @@ public final class MvAvgUnsignedLongEvaluator extends AbstractMultivalueFunction
   public Vector evalSingleValuedNotNullable(Block fieldVal) {
     LongBlock v = (LongBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    double[] values = new double[positionCount];
+    DoubleVector.FixedBuilder builder = DoubleVector.newVectorFixedBuilder(positionCount, driverContext.blockFactory());
     CompensatedSum work = new CompensatedSum();
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
@@ -134,8 +134,8 @@ public final class MvAvgUnsignedLongEvaluator extends AbstractMultivalueFunction
       int first = v.getFirstValueIndex(p);
       long value = v.getLong(first);
       double result = MvAvg.singleUnsignedLong(value);
-      values[p] = result;
+      builder.appendDouble(result);
     }
-    return new DoubleArrayVector(values, positionCount);
+    return builder.build();
   }
 }

+ 9 - 9
x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvMaxBooleanEvaluator.java

@@ -7,8 +7,8 @@ package org.elasticsearch.xpack.esql.expression.function.scalar.multivalue;
 import java.lang.Override;
 import java.lang.String;
 import org.elasticsearch.compute.data.Block;
-import org.elasticsearch.compute.data.BooleanArrayVector;
 import org.elasticsearch.compute.data.BooleanBlock;
+import org.elasticsearch.compute.data.BooleanVector;
 import org.elasticsearch.compute.data.Vector;
 import org.elasticsearch.compute.operator.DriverContext;
 import org.elasticsearch.compute.operator.EvalOperator;
@@ -41,7 +41,7 @@ public final class MvMaxBooleanEvaluator extends AbstractMultivalueFunction.Abst
     }
     BooleanBlock v = (BooleanBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    BooleanBlock.Builder builder = BooleanBlock.newBlockBuilder(positionCount);
+    BooleanBlock.Builder builder = BooleanBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       if (valueCount == 0) {
@@ -71,7 +71,7 @@ public final class MvMaxBooleanEvaluator extends AbstractMultivalueFunction.Abst
     }
     BooleanBlock v = (BooleanBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    boolean[] values = new boolean[positionCount];
+    BooleanVector.FixedBuilder builder = BooleanVector.newVectorFixedBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       int first = v.getFirstValueIndex(p);
@@ -82,9 +82,9 @@ public final class MvMaxBooleanEvaluator extends AbstractMultivalueFunction.Abst
         value = MvMax.process(value, next);
       }
       boolean result = value;
-      values[p] = result;
+      builder.appendBoolean(result);
     }
-    return new BooleanArrayVector(values, positionCount);
+    return builder.build();
   }
 
   /**
@@ -93,7 +93,7 @@ public final class MvMaxBooleanEvaluator extends AbstractMultivalueFunction.Abst
   private Block evalAscendingNullable(Block fieldVal) {
     BooleanBlock v = (BooleanBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    BooleanBlock.Builder builder = BooleanBlock.newBlockBuilder(positionCount);
+    BooleanBlock.Builder builder = BooleanBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       if (valueCount == 0) {
@@ -114,14 +114,14 @@ public final class MvMaxBooleanEvaluator extends AbstractMultivalueFunction.Abst
   private Vector evalAscendingNotNullable(Block fieldVal) {
     BooleanBlock v = (BooleanBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    boolean[] values = new boolean[positionCount];
+    BooleanVector.FixedBuilder builder = BooleanVector.newVectorFixedBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       int first = v.getFirstValueIndex(p);
       int idx = MvMax.ascendingIndex(valueCount);
       boolean result = v.getBoolean(first + idx);
-      values[p] = result;
+      builder.appendBoolean(result);
     }
-    return new BooleanArrayVector(values, positionCount);
+    return builder.build();
   }
 }

+ 9 - 11
x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvMaxBytesRefEvaluator.java

@@ -7,11 +7,9 @@ package org.elasticsearch.xpack.esql.expression.function.scalar.multivalue;
 import java.lang.Override;
 import java.lang.String;
 import org.apache.lucene.util.BytesRef;
-import org.elasticsearch.common.util.BigArrays;
-import org.elasticsearch.common.util.BytesRefArray;
 import org.elasticsearch.compute.data.Block;
-import org.elasticsearch.compute.data.BytesRefArrayVector;
 import org.elasticsearch.compute.data.BytesRefBlock;
+import org.elasticsearch.compute.data.BytesRefVector;
 import org.elasticsearch.compute.data.Vector;
 import org.elasticsearch.compute.operator.DriverContext;
 import org.elasticsearch.compute.operator.EvalOperator;
@@ -44,7 +42,7 @@ public final class MvMaxBytesRefEvaluator extends AbstractMultivalueFunction.Abs
     }
     BytesRefBlock v = (BytesRefBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    BytesRefBlock.Builder builder = BytesRefBlock.newBlockBuilder(positionCount);
+    BytesRefBlock.Builder builder = BytesRefBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     BytesRef firstScratch = new BytesRef();
     BytesRef nextScratch = new BytesRef();
     for (int p = 0; p < positionCount; p++) {
@@ -76,7 +74,7 @@ public final class MvMaxBytesRefEvaluator extends AbstractMultivalueFunction.Abs
     }
     BytesRefBlock v = (BytesRefBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    BytesRefArray values = new BytesRefArray(positionCount, BigArrays.NON_RECYCLING_INSTANCE);
+    BytesRefVector.Builder builder = BytesRefVector.newVectorBuilder(positionCount, driverContext.blockFactory());
     BytesRef firstScratch = new BytesRef();
     BytesRef nextScratch = new BytesRef();
     for (int p = 0; p < positionCount; p++) {
@@ -89,9 +87,9 @@ public final class MvMaxBytesRefEvaluator extends AbstractMultivalueFunction.Abs
         MvMax.process(value, next);
       }
       BytesRef result = value;
-      values.append(result);
+      builder.appendBytesRef(result);
     }
-    return new BytesRefArrayVector(values, positionCount);
+    return builder.build();
   }
 
   /**
@@ -100,7 +98,7 @@ public final class MvMaxBytesRefEvaluator extends AbstractMultivalueFunction.Abs
   private Block evalAscendingNullable(Block fieldVal) {
     BytesRefBlock v = (BytesRefBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    BytesRefBlock.Builder builder = BytesRefBlock.newBlockBuilder(positionCount);
+    BytesRefBlock.Builder builder = BytesRefBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     BytesRef firstScratch = new BytesRef();
     BytesRef nextScratch = new BytesRef();
     for (int p = 0; p < positionCount; p++) {
@@ -123,7 +121,7 @@ public final class MvMaxBytesRefEvaluator extends AbstractMultivalueFunction.Abs
   private Vector evalAscendingNotNullable(Block fieldVal) {
     BytesRefBlock v = (BytesRefBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    BytesRefArray values = new BytesRefArray(positionCount, BigArrays.NON_RECYCLING_INSTANCE);
+    BytesRefVector.Builder builder = BytesRefVector.newVectorBuilder(positionCount, driverContext.blockFactory());
     BytesRef firstScratch = new BytesRef();
     BytesRef nextScratch = new BytesRef();
     for (int p = 0; p < positionCount; p++) {
@@ -131,8 +129,8 @@ public final class MvMaxBytesRefEvaluator extends AbstractMultivalueFunction.Abs
       int first = v.getFirstValueIndex(p);
       int idx = MvMax.ascendingIndex(valueCount);
       BytesRef result = v.getBytesRef(first + idx, firstScratch);
-      values.append(result);
+      builder.appendBytesRef(result);
     }
-    return new BytesRefArrayVector(values, positionCount);
+    return builder.build();
   }
 }

+ 9 - 9
x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvMaxDoubleEvaluator.java

@@ -7,8 +7,8 @@ package org.elasticsearch.xpack.esql.expression.function.scalar.multivalue;
 import java.lang.Override;
 import java.lang.String;
 import org.elasticsearch.compute.data.Block;
-import org.elasticsearch.compute.data.DoubleArrayVector;
 import org.elasticsearch.compute.data.DoubleBlock;
+import org.elasticsearch.compute.data.DoubleVector;
 import org.elasticsearch.compute.data.Vector;
 import org.elasticsearch.compute.operator.DriverContext;
 import org.elasticsearch.compute.operator.EvalOperator;
@@ -40,7 +40,7 @@ public final class MvMaxDoubleEvaluator extends AbstractMultivalueFunction.Abstr
     }
     DoubleBlock v = (DoubleBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    DoubleBlock.Builder builder = DoubleBlock.newBlockBuilder(positionCount);
+    DoubleBlock.Builder builder = DoubleBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       if (valueCount == 0) {
@@ -70,7 +70,7 @@ public final class MvMaxDoubleEvaluator extends AbstractMultivalueFunction.Abstr
     }
     DoubleBlock v = (DoubleBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    double[] values = new double[positionCount];
+    DoubleVector.FixedBuilder builder = DoubleVector.newVectorFixedBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       int first = v.getFirstValueIndex(p);
@@ -81,9 +81,9 @@ public final class MvMaxDoubleEvaluator extends AbstractMultivalueFunction.Abstr
         value = MvMax.process(value, next);
       }
       double result = value;
-      values[p] = result;
+      builder.appendDouble(result);
     }
-    return new DoubleArrayVector(values, positionCount);
+    return builder.build();
   }
 
   /**
@@ -92,7 +92,7 @@ public final class MvMaxDoubleEvaluator extends AbstractMultivalueFunction.Abstr
   private Block evalAscendingNullable(Block fieldVal) {
     DoubleBlock v = (DoubleBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    DoubleBlock.Builder builder = DoubleBlock.newBlockBuilder(positionCount);
+    DoubleBlock.Builder builder = DoubleBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       if (valueCount == 0) {
@@ -113,14 +113,14 @@ public final class MvMaxDoubleEvaluator extends AbstractMultivalueFunction.Abstr
   private Vector evalAscendingNotNullable(Block fieldVal) {
     DoubleBlock v = (DoubleBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    double[] values = new double[positionCount];
+    DoubleVector.FixedBuilder builder = DoubleVector.newVectorFixedBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       int first = v.getFirstValueIndex(p);
       int idx = MvMax.ascendingIndex(valueCount);
       double result = v.getDouble(first + idx);
-      values[p] = result;
+      builder.appendDouble(result);
     }
-    return new DoubleArrayVector(values, positionCount);
+    return builder.build();
   }
 }

+ 9 - 9
x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvMaxIntEvaluator.java

@@ -7,8 +7,8 @@ package org.elasticsearch.xpack.esql.expression.function.scalar.multivalue;
 import java.lang.Override;
 import java.lang.String;
 import org.elasticsearch.compute.data.Block;
-import org.elasticsearch.compute.data.IntArrayVector;
 import org.elasticsearch.compute.data.IntBlock;
+import org.elasticsearch.compute.data.IntVector;
 import org.elasticsearch.compute.data.Vector;
 import org.elasticsearch.compute.operator.DriverContext;
 import org.elasticsearch.compute.operator.EvalOperator;
@@ -40,7 +40,7 @@ public final class MvMaxIntEvaluator extends AbstractMultivalueFunction.Abstract
     }
     IntBlock v = (IntBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    IntBlock.Builder builder = IntBlock.newBlockBuilder(positionCount);
+    IntBlock.Builder builder = IntBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       if (valueCount == 0) {
@@ -70,7 +70,7 @@ public final class MvMaxIntEvaluator extends AbstractMultivalueFunction.Abstract
     }
     IntBlock v = (IntBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    int[] values = new int[positionCount];
+    IntVector.FixedBuilder builder = IntVector.newVectorFixedBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       int first = v.getFirstValueIndex(p);
@@ -81,9 +81,9 @@ public final class MvMaxIntEvaluator extends AbstractMultivalueFunction.Abstract
         value = MvMax.process(value, next);
       }
       int result = value;
-      values[p] = result;
+      builder.appendInt(result);
     }
-    return new IntArrayVector(values, positionCount);
+    return builder.build();
   }
 
   /**
@@ -92,7 +92,7 @@ public final class MvMaxIntEvaluator extends AbstractMultivalueFunction.Abstract
   private Block evalAscendingNullable(Block fieldVal) {
     IntBlock v = (IntBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    IntBlock.Builder builder = IntBlock.newBlockBuilder(positionCount);
+    IntBlock.Builder builder = IntBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       if (valueCount == 0) {
@@ -113,14 +113,14 @@ public final class MvMaxIntEvaluator extends AbstractMultivalueFunction.Abstract
   private Vector evalAscendingNotNullable(Block fieldVal) {
     IntBlock v = (IntBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    int[] values = new int[positionCount];
+    IntVector.FixedBuilder builder = IntVector.newVectorFixedBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       int first = v.getFirstValueIndex(p);
       int idx = MvMax.ascendingIndex(valueCount);
       int result = v.getInt(first + idx);
-      values[p] = result;
+      builder.appendInt(result);
     }
-    return new IntArrayVector(values, positionCount);
+    return builder.build();
   }
 }

+ 9 - 9
x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvMaxLongEvaluator.java

@@ -7,8 +7,8 @@ package org.elasticsearch.xpack.esql.expression.function.scalar.multivalue;
 import java.lang.Override;
 import java.lang.String;
 import org.elasticsearch.compute.data.Block;
-import org.elasticsearch.compute.data.LongArrayVector;
 import org.elasticsearch.compute.data.LongBlock;
+import org.elasticsearch.compute.data.LongVector;
 import org.elasticsearch.compute.data.Vector;
 import org.elasticsearch.compute.operator.DriverContext;
 import org.elasticsearch.compute.operator.EvalOperator;
@@ -40,7 +40,7 @@ public final class MvMaxLongEvaluator extends AbstractMultivalueFunction.Abstrac
     }
     LongBlock v = (LongBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    LongBlock.Builder builder = LongBlock.newBlockBuilder(positionCount);
+    LongBlock.Builder builder = LongBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       if (valueCount == 0) {
@@ -70,7 +70,7 @@ public final class MvMaxLongEvaluator extends AbstractMultivalueFunction.Abstrac
     }
     LongBlock v = (LongBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    long[] values = new long[positionCount];
+    LongVector.FixedBuilder builder = LongVector.newVectorFixedBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       int first = v.getFirstValueIndex(p);
@@ -81,9 +81,9 @@ public final class MvMaxLongEvaluator extends AbstractMultivalueFunction.Abstrac
         value = MvMax.process(value, next);
       }
       long result = value;
-      values[p] = result;
+      builder.appendLong(result);
     }
-    return new LongArrayVector(values, positionCount);
+    return builder.build();
   }
 
   /**
@@ -92,7 +92,7 @@ public final class MvMaxLongEvaluator extends AbstractMultivalueFunction.Abstrac
   private Block evalAscendingNullable(Block fieldVal) {
     LongBlock v = (LongBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    LongBlock.Builder builder = LongBlock.newBlockBuilder(positionCount);
+    LongBlock.Builder builder = LongBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       if (valueCount == 0) {
@@ -113,14 +113,14 @@ public final class MvMaxLongEvaluator extends AbstractMultivalueFunction.Abstrac
   private Vector evalAscendingNotNullable(Block fieldVal) {
     LongBlock v = (LongBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    long[] values = new long[positionCount];
+    LongVector.FixedBuilder builder = LongVector.newVectorFixedBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       int first = v.getFirstValueIndex(p);
       int idx = MvMax.ascendingIndex(valueCount);
       long result = v.getLong(first + idx);
-      values[p] = result;
+      builder.appendLong(result);
     }
-    return new LongArrayVector(values, positionCount);
+    return builder.build();
   }
 }

+ 5 - 5
x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvMedianDoubleEvaluator.java

@@ -7,8 +7,8 @@ package org.elasticsearch.xpack.esql.expression.function.scalar.multivalue;
 import java.lang.Override;
 import java.lang.String;
 import org.elasticsearch.compute.data.Block;
-import org.elasticsearch.compute.data.DoubleArrayVector;
 import org.elasticsearch.compute.data.DoubleBlock;
+import org.elasticsearch.compute.data.DoubleVector;
 import org.elasticsearch.compute.data.Vector;
 import org.elasticsearch.compute.operator.DriverContext;
 import org.elasticsearch.compute.operator.EvalOperator;
@@ -38,7 +38,7 @@ public final class MvMedianDoubleEvaluator extends AbstractMultivalueFunction.Ab
   public Block evalNullable(Block fieldVal) {
     DoubleBlock v = (DoubleBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    DoubleBlock.Builder builder = DoubleBlock.newBlockBuilder(positionCount);
+    DoubleBlock.Builder builder = DoubleBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     MvMedian.Doubles work = new MvMedian.Doubles();
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
@@ -65,7 +65,7 @@ public final class MvMedianDoubleEvaluator extends AbstractMultivalueFunction.Ab
   public Vector evalNotNullable(Block fieldVal) {
     DoubleBlock v = (DoubleBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    double[] values = new double[positionCount];
+    DoubleVector.FixedBuilder builder = DoubleVector.newVectorFixedBuilder(positionCount, driverContext.blockFactory());
     MvMedian.Doubles work = new MvMedian.Doubles();
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
@@ -76,8 +76,8 @@ public final class MvMedianDoubleEvaluator extends AbstractMultivalueFunction.Ab
         MvMedian.process(work, value);
       }
       double result = MvMedian.finish(work);
-      values[p] = result;
+      builder.appendDouble(result);
     }
-    return new DoubleArrayVector(values, positionCount);
+    return builder.build();
   }
 }

+ 9 - 9
x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvMedianIntEvaluator.java

@@ -7,8 +7,8 @@ package org.elasticsearch.xpack.esql.expression.function.scalar.multivalue;
 import java.lang.Override;
 import java.lang.String;
 import org.elasticsearch.compute.data.Block;
-import org.elasticsearch.compute.data.IntArrayVector;
 import org.elasticsearch.compute.data.IntBlock;
+import org.elasticsearch.compute.data.IntVector;
 import org.elasticsearch.compute.data.Vector;
 import org.elasticsearch.compute.operator.DriverContext;
 import org.elasticsearch.compute.operator.EvalOperator;
@@ -40,7 +40,7 @@ public final class MvMedianIntEvaluator extends AbstractMultivalueFunction.Abstr
     }
     IntBlock v = (IntBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    IntBlock.Builder builder = IntBlock.newBlockBuilder(positionCount);
+    IntBlock.Builder builder = IntBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     MvMedian.Ints work = new MvMedian.Ints();
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
@@ -70,7 +70,7 @@ public final class MvMedianIntEvaluator extends AbstractMultivalueFunction.Abstr
     }
     IntBlock v = (IntBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    int[] values = new int[positionCount];
+    IntVector.FixedBuilder builder = IntVector.newVectorFixedBuilder(positionCount, driverContext.blockFactory());
     MvMedian.Ints work = new MvMedian.Ints();
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
@@ -81,9 +81,9 @@ public final class MvMedianIntEvaluator extends AbstractMultivalueFunction.Abstr
         MvMedian.process(work, value);
       }
       int result = MvMedian.finish(work);
-      values[p] = result;
+      builder.appendInt(result);
     }
-    return new IntArrayVector(values, positionCount);
+    return builder.build();
   }
 
   /**
@@ -92,7 +92,7 @@ public final class MvMedianIntEvaluator extends AbstractMultivalueFunction.Abstr
   private Block evalAscendingNullable(Block fieldVal) {
     IntBlock v = (IntBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    IntBlock.Builder builder = IntBlock.newBlockBuilder(positionCount);
+    IntBlock.Builder builder = IntBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     MvMedian.Ints work = new MvMedian.Ints();
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
@@ -113,14 +113,14 @@ public final class MvMedianIntEvaluator extends AbstractMultivalueFunction.Abstr
   private Vector evalAscendingNotNullable(Block fieldVal) {
     IntBlock v = (IntBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    int[] values = new int[positionCount];
+    IntVector.FixedBuilder builder = IntVector.newVectorFixedBuilder(positionCount, driverContext.blockFactory());
     MvMedian.Ints work = new MvMedian.Ints();
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       int first = v.getFirstValueIndex(p);
       int result = MvMedian.ascending(v, first, valueCount);
-      values[p] = result;
+      builder.appendInt(result);
     }
-    return new IntArrayVector(values, positionCount);
+    return builder.build();
   }
 }

+ 9 - 9
x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvMedianLongEvaluator.java

@@ -7,8 +7,8 @@ package org.elasticsearch.xpack.esql.expression.function.scalar.multivalue;
 import java.lang.Override;
 import java.lang.String;
 import org.elasticsearch.compute.data.Block;
-import org.elasticsearch.compute.data.LongArrayVector;
 import org.elasticsearch.compute.data.LongBlock;
+import org.elasticsearch.compute.data.LongVector;
 import org.elasticsearch.compute.data.Vector;
 import org.elasticsearch.compute.operator.DriverContext;
 import org.elasticsearch.compute.operator.EvalOperator;
@@ -41,7 +41,7 @@ public final class MvMedianLongEvaluator extends AbstractMultivalueFunction.Abst
     }
     LongBlock v = (LongBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    LongBlock.Builder builder = LongBlock.newBlockBuilder(positionCount);
+    LongBlock.Builder builder = LongBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     MvMedian.Longs work = new MvMedian.Longs();
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
@@ -71,7 +71,7 @@ public final class MvMedianLongEvaluator extends AbstractMultivalueFunction.Abst
     }
     LongBlock v = (LongBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    long[] values = new long[positionCount];
+    LongVector.FixedBuilder builder = LongVector.newVectorFixedBuilder(positionCount, driverContext.blockFactory());
     MvMedian.Longs work = new MvMedian.Longs();
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
@@ -82,9 +82,9 @@ public final class MvMedianLongEvaluator extends AbstractMultivalueFunction.Abst
         MvMedian.process(work, value);
       }
       long result = MvMedian.finish(work);
-      values[p] = result;
+      builder.appendLong(result);
     }
-    return new LongArrayVector(values, positionCount);
+    return builder.build();
   }
 
   /**
@@ -93,7 +93,7 @@ public final class MvMedianLongEvaluator extends AbstractMultivalueFunction.Abst
   private Block evalAscendingNullable(Block fieldVal) {
     LongBlock v = (LongBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    LongBlock.Builder builder = LongBlock.newBlockBuilder(positionCount);
+    LongBlock.Builder builder = LongBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     MvMedian.Longs work = new MvMedian.Longs();
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
@@ -114,14 +114,14 @@ public final class MvMedianLongEvaluator extends AbstractMultivalueFunction.Abst
   private Vector evalAscendingNotNullable(Block fieldVal) {
     LongBlock v = (LongBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    long[] values = new long[positionCount];
+    LongVector.FixedBuilder builder = LongVector.newVectorFixedBuilder(positionCount, driverContext.blockFactory());
     MvMedian.Longs work = new MvMedian.Longs();
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       int first = v.getFirstValueIndex(p);
       long result = MvMedian.ascending(v, first, valueCount);
-      values[p] = result;
+      builder.appendLong(result);
     }
-    return new LongArrayVector(values, positionCount);
+    return builder.build();
   }
 }

+ 9 - 9
x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvMedianUnsignedLongEvaluator.java

@@ -7,8 +7,8 @@ package org.elasticsearch.xpack.esql.expression.function.scalar.multivalue;
 import java.lang.Override;
 import java.lang.String;
 import org.elasticsearch.compute.data.Block;
-import org.elasticsearch.compute.data.LongArrayVector;
 import org.elasticsearch.compute.data.LongBlock;
+import org.elasticsearch.compute.data.LongVector;
 import org.elasticsearch.compute.data.Vector;
 import org.elasticsearch.compute.operator.DriverContext;
 import org.elasticsearch.compute.operator.EvalOperator;
@@ -41,7 +41,7 @@ public final class MvMedianUnsignedLongEvaluator extends AbstractMultivalueFunct
     }
     LongBlock v = (LongBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    LongBlock.Builder builder = LongBlock.newBlockBuilder(positionCount);
+    LongBlock.Builder builder = LongBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     MvMedian.Longs work = new MvMedian.Longs();
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
@@ -71,7 +71,7 @@ public final class MvMedianUnsignedLongEvaluator extends AbstractMultivalueFunct
     }
     LongBlock v = (LongBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    long[] values = new long[positionCount];
+    LongVector.FixedBuilder builder = LongVector.newVectorFixedBuilder(positionCount, driverContext.blockFactory());
     MvMedian.Longs work = new MvMedian.Longs();
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
@@ -82,9 +82,9 @@ public final class MvMedianUnsignedLongEvaluator extends AbstractMultivalueFunct
         MvMedian.processUnsignedLong(work, value);
       }
       long result = MvMedian.finishUnsignedLong(work);
-      values[p] = result;
+      builder.appendLong(result);
     }
-    return new LongArrayVector(values, positionCount);
+    return builder.build();
   }
 
   /**
@@ -93,7 +93,7 @@ public final class MvMedianUnsignedLongEvaluator extends AbstractMultivalueFunct
   private Block evalAscendingNullable(Block fieldVal) {
     LongBlock v = (LongBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    LongBlock.Builder builder = LongBlock.newBlockBuilder(positionCount);
+    LongBlock.Builder builder = LongBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     MvMedian.Longs work = new MvMedian.Longs();
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
@@ -114,14 +114,14 @@ public final class MvMedianUnsignedLongEvaluator extends AbstractMultivalueFunct
   private Vector evalAscendingNotNullable(Block fieldVal) {
     LongBlock v = (LongBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    long[] values = new long[positionCount];
+    LongVector.FixedBuilder builder = LongVector.newVectorFixedBuilder(positionCount, driverContext.blockFactory());
     MvMedian.Longs work = new MvMedian.Longs();
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       int first = v.getFirstValueIndex(p);
       long result = MvMedian.ascendingUnsignedLong(v, first, valueCount);
-      values[p] = result;
+      builder.appendLong(result);
     }
-    return new LongArrayVector(values, positionCount);
+    return builder.build();
   }
 }

+ 9 - 9
x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvMinBooleanEvaluator.java

@@ -7,8 +7,8 @@ package org.elasticsearch.xpack.esql.expression.function.scalar.multivalue;
 import java.lang.Override;
 import java.lang.String;
 import org.elasticsearch.compute.data.Block;
-import org.elasticsearch.compute.data.BooleanArrayVector;
 import org.elasticsearch.compute.data.BooleanBlock;
+import org.elasticsearch.compute.data.BooleanVector;
 import org.elasticsearch.compute.data.Vector;
 import org.elasticsearch.compute.operator.DriverContext;
 import org.elasticsearch.compute.operator.EvalOperator;
@@ -41,7 +41,7 @@ public final class MvMinBooleanEvaluator extends AbstractMultivalueFunction.Abst
     }
     BooleanBlock v = (BooleanBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    BooleanBlock.Builder builder = BooleanBlock.newBlockBuilder(positionCount);
+    BooleanBlock.Builder builder = BooleanBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       if (valueCount == 0) {
@@ -71,7 +71,7 @@ public final class MvMinBooleanEvaluator extends AbstractMultivalueFunction.Abst
     }
     BooleanBlock v = (BooleanBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    boolean[] values = new boolean[positionCount];
+    BooleanVector.FixedBuilder builder = BooleanVector.newVectorFixedBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       int first = v.getFirstValueIndex(p);
@@ -82,9 +82,9 @@ public final class MvMinBooleanEvaluator extends AbstractMultivalueFunction.Abst
         value = MvMin.process(value, next);
       }
       boolean result = value;
-      values[p] = result;
+      builder.appendBoolean(result);
     }
-    return new BooleanArrayVector(values, positionCount);
+    return builder.build();
   }
 
   /**
@@ -93,7 +93,7 @@ public final class MvMinBooleanEvaluator extends AbstractMultivalueFunction.Abst
   private Block evalAscendingNullable(Block fieldVal) {
     BooleanBlock v = (BooleanBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    BooleanBlock.Builder builder = BooleanBlock.newBlockBuilder(positionCount);
+    BooleanBlock.Builder builder = BooleanBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       if (valueCount == 0) {
@@ -114,14 +114,14 @@ public final class MvMinBooleanEvaluator extends AbstractMultivalueFunction.Abst
   private Vector evalAscendingNotNullable(Block fieldVal) {
     BooleanBlock v = (BooleanBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    boolean[] values = new boolean[positionCount];
+    BooleanVector.FixedBuilder builder = BooleanVector.newVectorFixedBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       int first = v.getFirstValueIndex(p);
       int idx = MvMin.ascendingIndex(valueCount);
       boolean result = v.getBoolean(first + idx);
-      values[p] = result;
+      builder.appendBoolean(result);
     }
-    return new BooleanArrayVector(values, positionCount);
+    return builder.build();
   }
 }

+ 9 - 11
x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvMinBytesRefEvaluator.java

@@ -7,11 +7,9 @@ package org.elasticsearch.xpack.esql.expression.function.scalar.multivalue;
 import java.lang.Override;
 import java.lang.String;
 import org.apache.lucene.util.BytesRef;
-import org.elasticsearch.common.util.BigArrays;
-import org.elasticsearch.common.util.BytesRefArray;
 import org.elasticsearch.compute.data.Block;
-import org.elasticsearch.compute.data.BytesRefArrayVector;
 import org.elasticsearch.compute.data.BytesRefBlock;
+import org.elasticsearch.compute.data.BytesRefVector;
 import org.elasticsearch.compute.data.Vector;
 import org.elasticsearch.compute.operator.DriverContext;
 import org.elasticsearch.compute.operator.EvalOperator;
@@ -44,7 +42,7 @@ public final class MvMinBytesRefEvaluator extends AbstractMultivalueFunction.Abs
     }
     BytesRefBlock v = (BytesRefBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    BytesRefBlock.Builder builder = BytesRefBlock.newBlockBuilder(positionCount);
+    BytesRefBlock.Builder builder = BytesRefBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     BytesRef firstScratch = new BytesRef();
     BytesRef nextScratch = new BytesRef();
     for (int p = 0; p < positionCount; p++) {
@@ -76,7 +74,7 @@ public final class MvMinBytesRefEvaluator extends AbstractMultivalueFunction.Abs
     }
     BytesRefBlock v = (BytesRefBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    BytesRefArray values = new BytesRefArray(positionCount, BigArrays.NON_RECYCLING_INSTANCE);
+    BytesRefVector.Builder builder = BytesRefVector.newVectorBuilder(positionCount, driverContext.blockFactory());
     BytesRef firstScratch = new BytesRef();
     BytesRef nextScratch = new BytesRef();
     for (int p = 0; p < positionCount; p++) {
@@ -89,9 +87,9 @@ public final class MvMinBytesRefEvaluator extends AbstractMultivalueFunction.Abs
         MvMin.process(value, next);
       }
       BytesRef result = value;
-      values.append(result);
+      builder.appendBytesRef(result);
     }
-    return new BytesRefArrayVector(values, positionCount);
+    return builder.build();
   }
 
   /**
@@ -100,7 +98,7 @@ public final class MvMinBytesRefEvaluator extends AbstractMultivalueFunction.Abs
   private Block evalAscendingNullable(Block fieldVal) {
     BytesRefBlock v = (BytesRefBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    BytesRefBlock.Builder builder = BytesRefBlock.newBlockBuilder(positionCount);
+    BytesRefBlock.Builder builder = BytesRefBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     BytesRef firstScratch = new BytesRef();
     BytesRef nextScratch = new BytesRef();
     for (int p = 0; p < positionCount; p++) {
@@ -123,7 +121,7 @@ public final class MvMinBytesRefEvaluator extends AbstractMultivalueFunction.Abs
   private Vector evalAscendingNotNullable(Block fieldVal) {
     BytesRefBlock v = (BytesRefBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    BytesRefArray values = new BytesRefArray(positionCount, BigArrays.NON_RECYCLING_INSTANCE);
+    BytesRefVector.Builder builder = BytesRefVector.newVectorBuilder(positionCount, driverContext.blockFactory());
     BytesRef firstScratch = new BytesRef();
     BytesRef nextScratch = new BytesRef();
     for (int p = 0; p < positionCount; p++) {
@@ -131,8 +129,8 @@ public final class MvMinBytesRefEvaluator extends AbstractMultivalueFunction.Abs
       int first = v.getFirstValueIndex(p);
       int idx = MvMin.ascendingIndex(valueCount);
       BytesRef result = v.getBytesRef(first + idx, firstScratch);
-      values.append(result);
+      builder.appendBytesRef(result);
     }
-    return new BytesRefArrayVector(values, positionCount);
+    return builder.build();
   }
 }

+ 9 - 9
x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvMinDoubleEvaluator.java

@@ -7,8 +7,8 @@ package org.elasticsearch.xpack.esql.expression.function.scalar.multivalue;
 import java.lang.Override;
 import java.lang.String;
 import org.elasticsearch.compute.data.Block;
-import org.elasticsearch.compute.data.DoubleArrayVector;
 import org.elasticsearch.compute.data.DoubleBlock;
+import org.elasticsearch.compute.data.DoubleVector;
 import org.elasticsearch.compute.data.Vector;
 import org.elasticsearch.compute.operator.DriverContext;
 import org.elasticsearch.compute.operator.EvalOperator;
@@ -40,7 +40,7 @@ public final class MvMinDoubleEvaluator extends AbstractMultivalueFunction.Abstr
     }
     DoubleBlock v = (DoubleBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    DoubleBlock.Builder builder = DoubleBlock.newBlockBuilder(positionCount);
+    DoubleBlock.Builder builder = DoubleBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       if (valueCount == 0) {
@@ -70,7 +70,7 @@ public final class MvMinDoubleEvaluator extends AbstractMultivalueFunction.Abstr
     }
     DoubleBlock v = (DoubleBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    double[] values = new double[positionCount];
+    DoubleVector.FixedBuilder builder = DoubleVector.newVectorFixedBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       int first = v.getFirstValueIndex(p);
@@ -81,9 +81,9 @@ public final class MvMinDoubleEvaluator extends AbstractMultivalueFunction.Abstr
         value = MvMin.process(value, next);
       }
       double result = value;
-      values[p] = result;
+      builder.appendDouble(result);
     }
-    return new DoubleArrayVector(values, positionCount);
+    return builder.build();
   }
 
   /**
@@ -92,7 +92,7 @@ public final class MvMinDoubleEvaluator extends AbstractMultivalueFunction.Abstr
   private Block evalAscendingNullable(Block fieldVal) {
     DoubleBlock v = (DoubleBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    DoubleBlock.Builder builder = DoubleBlock.newBlockBuilder(positionCount);
+    DoubleBlock.Builder builder = DoubleBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       if (valueCount == 0) {
@@ -113,14 +113,14 @@ public final class MvMinDoubleEvaluator extends AbstractMultivalueFunction.Abstr
   private Vector evalAscendingNotNullable(Block fieldVal) {
     DoubleBlock v = (DoubleBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    double[] values = new double[positionCount];
+    DoubleVector.FixedBuilder builder = DoubleVector.newVectorFixedBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       int first = v.getFirstValueIndex(p);
       int idx = MvMin.ascendingIndex(valueCount);
       double result = v.getDouble(first + idx);
-      values[p] = result;
+      builder.appendDouble(result);
     }
-    return new DoubleArrayVector(values, positionCount);
+    return builder.build();
   }
 }

+ 9 - 9
x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvMinIntEvaluator.java

@@ -7,8 +7,8 @@ package org.elasticsearch.xpack.esql.expression.function.scalar.multivalue;
 import java.lang.Override;
 import java.lang.String;
 import org.elasticsearch.compute.data.Block;
-import org.elasticsearch.compute.data.IntArrayVector;
 import org.elasticsearch.compute.data.IntBlock;
+import org.elasticsearch.compute.data.IntVector;
 import org.elasticsearch.compute.data.Vector;
 import org.elasticsearch.compute.operator.DriverContext;
 import org.elasticsearch.compute.operator.EvalOperator;
@@ -40,7 +40,7 @@ public final class MvMinIntEvaluator extends AbstractMultivalueFunction.Abstract
     }
     IntBlock v = (IntBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    IntBlock.Builder builder = IntBlock.newBlockBuilder(positionCount);
+    IntBlock.Builder builder = IntBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       if (valueCount == 0) {
@@ -70,7 +70,7 @@ public final class MvMinIntEvaluator extends AbstractMultivalueFunction.Abstract
     }
     IntBlock v = (IntBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    int[] values = new int[positionCount];
+    IntVector.FixedBuilder builder = IntVector.newVectorFixedBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       int first = v.getFirstValueIndex(p);
@@ -81,9 +81,9 @@ public final class MvMinIntEvaluator extends AbstractMultivalueFunction.Abstract
         value = MvMin.process(value, next);
       }
       int result = value;
-      values[p] = result;
+      builder.appendInt(result);
     }
-    return new IntArrayVector(values, positionCount);
+    return builder.build();
   }
 
   /**
@@ -92,7 +92,7 @@ public final class MvMinIntEvaluator extends AbstractMultivalueFunction.Abstract
   private Block evalAscendingNullable(Block fieldVal) {
     IntBlock v = (IntBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    IntBlock.Builder builder = IntBlock.newBlockBuilder(positionCount);
+    IntBlock.Builder builder = IntBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       if (valueCount == 0) {
@@ -113,14 +113,14 @@ public final class MvMinIntEvaluator extends AbstractMultivalueFunction.Abstract
   private Vector evalAscendingNotNullable(Block fieldVal) {
     IntBlock v = (IntBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    int[] values = new int[positionCount];
+    IntVector.FixedBuilder builder = IntVector.newVectorFixedBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       int first = v.getFirstValueIndex(p);
       int idx = MvMin.ascendingIndex(valueCount);
       int result = v.getInt(first + idx);
-      values[p] = result;
+      builder.appendInt(result);
     }
-    return new IntArrayVector(values, positionCount);
+    return builder.build();
   }
 }

+ 9 - 9
x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvMinLongEvaluator.java

@@ -7,8 +7,8 @@ package org.elasticsearch.xpack.esql.expression.function.scalar.multivalue;
 import java.lang.Override;
 import java.lang.String;
 import org.elasticsearch.compute.data.Block;
-import org.elasticsearch.compute.data.LongArrayVector;
 import org.elasticsearch.compute.data.LongBlock;
+import org.elasticsearch.compute.data.LongVector;
 import org.elasticsearch.compute.data.Vector;
 import org.elasticsearch.compute.operator.DriverContext;
 import org.elasticsearch.compute.operator.EvalOperator;
@@ -40,7 +40,7 @@ public final class MvMinLongEvaluator extends AbstractMultivalueFunction.Abstrac
     }
     LongBlock v = (LongBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    LongBlock.Builder builder = LongBlock.newBlockBuilder(positionCount);
+    LongBlock.Builder builder = LongBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       if (valueCount == 0) {
@@ -70,7 +70,7 @@ public final class MvMinLongEvaluator extends AbstractMultivalueFunction.Abstrac
     }
     LongBlock v = (LongBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    long[] values = new long[positionCount];
+    LongVector.FixedBuilder builder = LongVector.newVectorFixedBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       int first = v.getFirstValueIndex(p);
@@ -81,9 +81,9 @@ public final class MvMinLongEvaluator extends AbstractMultivalueFunction.Abstrac
         value = MvMin.process(value, next);
       }
       long result = value;
-      values[p] = result;
+      builder.appendLong(result);
     }
-    return new LongArrayVector(values, positionCount);
+    return builder.build();
   }
 
   /**
@@ -92,7 +92,7 @@ public final class MvMinLongEvaluator extends AbstractMultivalueFunction.Abstrac
   private Block evalAscendingNullable(Block fieldVal) {
     LongBlock v = (LongBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    LongBlock.Builder builder = LongBlock.newBlockBuilder(positionCount);
+    LongBlock.Builder builder = LongBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       if (valueCount == 0) {
@@ -113,14 +113,14 @@ public final class MvMinLongEvaluator extends AbstractMultivalueFunction.Abstrac
   private Vector evalAscendingNotNullable(Block fieldVal) {
     LongBlock v = (LongBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    long[] values = new long[positionCount];
+    LongVector.FixedBuilder builder = LongVector.newVectorFixedBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       int first = v.getFirstValueIndex(p);
       int idx = MvMin.ascendingIndex(valueCount);
       long result = v.getLong(first + idx);
-      values[p] = result;
+      builder.appendLong(result);
     }
-    return new LongArrayVector(values, positionCount);
+    return builder.build();
   }
 }

+ 5 - 5
x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvSumDoubleEvaluator.java

@@ -7,8 +7,8 @@ package org.elasticsearch.xpack.esql.expression.function.scalar.multivalue;
 import java.lang.Override;
 import java.lang.String;
 import org.elasticsearch.compute.data.Block;
-import org.elasticsearch.compute.data.DoubleArrayVector;
 import org.elasticsearch.compute.data.DoubleBlock;
+import org.elasticsearch.compute.data.DoubleVector;
 import org.elasticsearch.compute.data.Vector;
 import org.elasticsearch.compute.operator.DriverContext;
 import org.elasticsearch.compute.operator.EvalOperator;
@@ -38,7 +38,7 @@ public final class MvSumDoubleEvaluator extends AbstractMultivalueFunction.Abstr
   public Block evalNullable(Block fieldVal) {
     DoubleBlock v = (DoubleBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    DoubleBlock.Builder builder = DoubleBlock.newBlockBuilder(positionCount);
+    DoubleBlock.Builder builder = DoubleBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     CompensatedSum work = new CompensatedSum();
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
@@ -65,7 +65,7 @@ public final class MvSumDoubleEvaluator extends AbstractMultivalueFunction.Abstr
   public Vector evalNotNullable(Block fieldVal) {
     DoubleBlock v = (DoubleBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    double[] values = new double[positionCount];
+    DoubleVector.FixedBuilder builder = DoubleVector.newVectorFixedBuilder(positionCount, driverContext.blockFactory());
     CompensatedSum work = new CompensatedSum();
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
@@ -76,8 +76,8 @@ public final class MvSumDoubleEvaluator extends AbstractMultivalueFunction.Abstr
         MvSum.process(work, value);
       }
       double result = MvSum.finish(work);
-      values[p] = result;
+      builder.appendDouble(result);
     }
-    return new DoubleArrayVector(values, positionCount);
+    return builder.build();
   }
 }

+ 1 - 1
x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvSumIntEvaluator.java

@@ -42,7 +42,7 @@ public final class MvSumIntEvaluator extends AbstractMultivalueFunction.Abstract
   public Block evalNullable(Block fieldVal) {
     IntBlock v = (IntBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    IntBlock.Builder builder = IntBlock.newBlockBuilder(positionCount);
+    IntBlock.Builder builder = IntBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       if (valueCount == 0) {

+ 1 - 1
x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvSumLongEvaluator.java

@@ -42,7 +42,7 @@ public final class MvSumLongEvaluator extends AbstractMultivalueFunction.Abstrac
   public Block evalNullable(Block fieldVal) {
     LongBlock v = (LongBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    LongBlock.Builder builder = LongBlock.newBlockBuilder(positionCount);
+    LongBlock.Builder builder = LongBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       if (valueCount == 0) {

+ 1 - 1
x-pack/plugin/esql/src/main/java/generated/org/elasticsearch/xpack/esql/expression/function/scalar/multivalue/MvSumUnsignedLongEvaluator.java

@@ -42,7 +42,7 @@ public final class MvSumUnsignedLongEvaluator extends AbstractMultivalueFunction
   public Block evalNullable(Block fieldVal) {
     LongBlock v = (LongBlock) fieldVal;
     int positionCount = v.getPositionCount();
-    LongBlock.Builder builder = LongBlock.newBlockBuilder(positionCount);
+    LongBlock.Builder builder = LongBlock.newBlockBuilder(positionCount, driverContext.blockFactory());
     for (int p = 0; p < positionCount; p++) {
       int valueCount = v.getValueCount(p);
       if (valueCount == 0) {

+ 9 - 7
x-pack/plugin/esql/src/main/java/org/elasticsearch/xpack/esql/evaluator/mapper/EvaluatorMapper.java

@@ -9,10 +9,12 @@ package org.elasticsearch.xpack.esql.evaluator.mapper;
 
 import org.elasticsearch.common.breaker.CircuitBreaker;
 import org.elasticsearch.common.breaker.NoopCircuitBreaker;
+import org.elasticsearch.common.util.BigArrays;
 import org.elasticsearch.compute.data.Block;
+import org.elasticsearch.compute.data.BlockFactory;
 import org.elasticsearch.compute.data.Page;
+import org.elasticsearch.compute.operator.DriverContext;
 import org.elasticsearch.compute.operator.EvalOperator.ExpressionEvaluator;
-import org.elasticsearch.compute.operator.ThrowingDriverContext;
 import org.elasticsearch.xpack.ql.expression.Expression;
 
 import java.util.function.Function;
@@ -41,12 +43,12 @@ public interface EvaluatorMapper {
 
             @Override
             public void close() {}
-        }).get(new ThrowingDriverContext() {
-            @Override
-            public CircuitBreaker breaker() {
+        }).get(
+            new DriverContext(
+                BigArrays.NON_RECYCLING_INSTANCE,
                 // TODO maybe this should have a small fixed limit?
-                return new NoopCircuitBreaker(CircuitBreaker.REQUEST);
-            }
-        }).eval(new Page(1)), 0);
+                new BlockFactory(new NoopCircuitBreaker(CircuitBreaker.REQUEST), BigArrays.NON_RECYCLING_INSTANCE)
+            )
+        ).eval(new Page(1)), 0);
     }
 }