JDK-8202307 : Getting a java.lang.OutOfMemoryError: Java heap space when calling Stream.iterator().next() on a stream which uses an infinite/very big Stream in flatMap.
  • Type: Bug
  • Component: core-libs
  • Sub-Component: java.util.stream
  • Affected Version: 10,11
  • Priority: P4
  • Status: Closed
  • Resolution: Won't Fix
  • OS: windows_10
  • CPU: x86_64
  • Submitted: 2018-04-25
  • Updated: 2018-04-26
  • Resolved: 2018-04-26
Related Reports
Relates :  
Description
A DESCRIPTION OF THE PROBLEM :
Getting a java.lang.OutOfMemoryError: Java heap space when calling Stream.iterator().next() on a stream which uses an infinite/very big Stream in flatMap.

As far as I understand this is related to the bug JDK-8196106 .

STEPS TO FOLLOW TO REPRODUCE THE PROBLEM :
Run code below

EXPECTED VERSUS ACTUAL BEHAVIOR :
EXPECTED -
Termination without output
ACTUAL -
Exception in thread "main" java.lang.OutOfMemoryError: Java heap space
	at java.base/java.util.stream.SpinedBuffer$OfInt.newArray(SpinedBuffer.java:750)
	at java.base/java.util.stream.SpinedBuffer$OfInt.newArray(SpinedBuffer.java:723)
	at java.base/java.util.stream.SpinedBuffer$OfPrimitive.ensureCapacity(SpinedBuffer.java:508)
	at java.base/java.util.stream.SpinedBuffer$OfPrimitive.increaseCapacity(SpinedBuffer.java:516)
	at java.base/java.util.stream.SpinedBuffer$OfPrimitive.preAccept(SpinedBuffer.java:569)
	at java.base/java.util.stream.SpinedBuffer$OfInt.accept(SpinedBuffer.java:768)
	at java.base/java.util.stream.StreamSpliterators$IntWrappingSpliterator$$Lambda$3/940060004.accept(Unknown Source)
	at java.base/java.util.stream.ReferencePipeline$8$1$$Lambda$4/998351292.accept(Unknown Source)
	at java.base/java.util.stream.Streams$RangeIntSpliterator.tryAdvance(Streams.java:82)
	at java.base/java.util.stream.ReferencePipeline$8$1.accept(ReferencePipeline.java:326)
	at java.base/java.util.stream.Streams$StreamBuilderImpl.tryAdvance(Streams.java:397)
	at java.base/java.util.stream.StreamSpliterators$IntWrappingSpliterator.lambda$initPartialTraversalState$0(StreamSpliterators.java:347)
	at java.base/java.util.stream.StreamSpliterators$IntWrappingSpliterator$$Lambda$5/335471116.getAsBoolean(Unknown Source)
	at java.base/java.util.stream.StreamSpliterators$AbstractWrappingSpliterator.fillBuffer(StreamSpliterators.java:206)
	at java.base/java.util.stream.StreamSpliterators$AbstractWrappingSpliterator.doAdvance(StreamSpliterators.java:161)
	at java.base/java.util.stream.StreamSpliterators$IntWrappingSpliterator.tryAdvance(StreamSpliterators.java:358)
	at java.base/java.util.Spliterators$2Adapter.hasNext(Spliterators.java:726)
	at java.base/java.util.Spliterators$2Adapter.nextInt(Spliterators.java:732)
	at BugReport.main(BugReport.java:18)

---------- BEGIN SOURCE ----------
import java.util.function.Function;
import java.util.stream.IntStream;
import java.util.stream.Stream;

public class BugReport
{
    public static void main(String[] args)
    {
        Stream
            .of(IntStream.range(0, Integer.MAX_VALUE))
            .flatMapToInt(Function.identity())
            .iterator()
            .nextInt();
    }
}

---------- END SOURCE ----------

FREQUENCY : always



Comments
The iterator() and spliterator() methods are "escape hatches" to be used when it's not possible to use other operations. They have some limitations because they turn what is a push model of the stream implementation into a pull model. Such a transition requires buffering in certain cases, such as when an element is (flat) mapped to two or more elements. It would significantly complicate the stream implementation, likely at the expense of common cases, to support a notion of back-pressure to communicate how many elements to pull through nested layers of element production.
26-04-2018

To reproduce the issue, run the attached test case. JDK 10.0.1 + 10 - Fail JDK 11-ea+10 - Fail Exception in thread "main" java.lang.OutOfMemoryError: Java heap space at java.base/java.util.stream.SpinedBuffer$OfInt.newArray(SpinedBuffer.java:750) at java.base/java.util.stream.SpinedBuffer$OfInt.newArray(SpinedBuffer.java:723) at java.base/java.util.stream.SpinedBuffer$OfPrimitive.ensureCapacity(SpinedBuffer.java:508) at java.base/java.util.stream.SpinedBuffer$OfPrimitive.increaseCapacity(SpinedBuffer.java:516) at java.base/java.util.stream.SpinedBuffer$OfPrimitive.preAccept(SpinedBuffer.java:569) at java.base/java.util.stream.SpinedBuffer$OfInt.accept(SpinedBuffer.java:768) at java.base/java.util.stream.StreamSpliterators$IntWrappingSpliterator$$Lambda$3/0x00000007c0067040.accept(Unknown Source) at java.base/java.util.stream.ReferencePipeline$8$1$$Lambda$4/0x00000007c0066840.accept(Unknown Source) at java.base/java.util.stream.Streams$RangeIntSpliterator.tryAdvance(Streams.java:82) at java.base/java.util.stream.ReferencePipeline$8$1.accept(ReferencePipeline.java:326) at java.base/java.util.stream.Streams$StreamBuilderImpl.tryAdvance(Streams.java:397) at java.base/java.util.stream.StreamSpliterators$IntWrappingSpliterator.lambda$initPartialTraversalState$0(StreamSpliterators.java:347) at java.base/java.util.stream.StreamSpliterators$IntWrappingSpliterator$$Lambda$5/0x00000007c0066c40.getAsBoolean(Unknown Source) at java.base/java.util.stream.StreamSpliterators$AbstractWrappingSpliterator.fillBuffer(StreamSpliterators.java:206) at java.base/java.util.stream.StreamSpliterators$AbstractWrappingSpliterator.doAdvance(StreamSpliterators.java:161) at java.base/java.util.stream.StreamSpliterators$IntWrappingSpliterator.tryAdvance(StreamSpliterators.java:358) at java.base/java.util.Spliterators$2Adapter.hasNext(Spliterators.java:726) at java.base/java.util.Spliterators$2Adapter.nextInt(Spliterators.java:732) at JI9053536.main(JI9053536.java:12)
26-04-2018