David Mollitor created SPARK-59558:
--------------------------------------

             Summary: Use ArrayDeque instead of LinkedList for the whole-stage 
codegen row buffer
                 Key: SPARK-59558
                 URL: https://issues.apache.org/jira/browse/SPARK-59558
             Project: Spark
          Issue Type: Improvement
          Components: SQL
    Affects Versions: 4.1.0
            Reporter: David Mollitor


h2. Summary

{{BufferedRowIterator.currentRows}} is the output buffer for whole-stage 
codegen: every generated iterator ({{GeneratedIteratorForCodegenStageN extends 
BufferedRowIterator}}) pushes its output rows into it. It is declared as a 
{{java.util.LinkedList<InternalRow>}} and used purely as a FIFO queue:

* {{append(row)}} -> {{currentRows.add(row)}}
* {{next()}} -> {{currentRows.remove()}}
* {{hasNext()}} / {{shouldStop()}} -> {{currentRows.isEmpty()}}

Because {{shouldStop()}} returns as soon as the buffer is non-empty, the 
steady-state pattern is "append one row, poll one row" per output row, so 
{{LinkedList}} allocates and discards one {{LinkedList$Node}} for every row 
every codegen pipeline emits.

This changes the field to a {{java.util.ArrayDeque}} (referenced through the 
{{Queue}}
interface). {{ArrayDeque}} allocates its backing array once and reuses it 
across add/remove, eliminating the per-row node allocation, with better cache 
locality. Its JavaDoc notes it is "likely to be faster than {{LinkedList}} when 
used as a queue."

h2. Why

JFR allocation profiling of {{JoinBenchmark}} showed 
{{java.util.LinkedList.linkLast}} as a significant allocation site on the 
codegen output path -- ~25% of sampled allocation across the full suite 
(amplified by high-fan-out operators), and ~4.8% in a focused duplicated 
broadcast-hash-join case. This is per-row garbage on the path shared by 
essentially every query that uses whole-stage codegen, so removing it reduces 
GC pressure fleet-wide.



--
This message was sent by Atlassian Jira
(v8.20.10#820010)

---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]

Reply via email to