<!DOCTYPE html><html><head><title></title></head><body><div><span class="color" style="color:rgb(10, 10, 10);">A more honest comparison would be using a Executors.newCachedThreadPool() so it is also unlimited connections, or using a Semaphore with 4 permits around the virtual</span></div><div><br></div><div><span class="color" style="color:rgb(10, 10, 10);">Regards</span><br></div><div><br></div><div>On Wed, Nov 26, 2025, at 11:32, David wrote:</div><blockquote type="cite" id="qt" style=""><div dir="ltr"><div>Hi, </div><div><br></div><div><div>There seems to be a limit causing a 12-30 second delay after establishing ~8K connections too quickly. 10K platform threads do not see or reach this limit. </div><div><br></div><div>The simplest workaround I found was adding System.out.println("1"); right before making each request. The synchronized lock is probably doing the heavy lifting here. This makes the platform and virtual threads perform about the same. </div><div><br></div><div>Increasing the server-side Tomcat settings also resolves the stalling:</div><ul><li>server.tomcat.accept-count=10000</li><li>server.tomcat.max-connections=20000</li><li>server.tomcat.threads.max=500</li><li>server.tomcat.threads.min-spare=50</li></ul><div>However, with these higher server limits, I'm seeing different throughput characteristics:</div><ul><li>Platform threads: 2.3 ops/s</li><li>Virtual threads: 0.9 ops/s (about half the speed)</li></ul><div><br></div><blockquote class="qt-gmail_quote" style="margin-top:0px;margin-right:0px;margin-bottom:0px;margin-left:0.8ex;border-left-width:1px;border-left-style:solid;border-left-color:rgb(204, 204, 204);padding-left:1ex;"><div>I assume it also benefits from being able to use HTTP persistent<span class="qt-gmail-Apple-converted-space"> </span></div><div>connections.</div></blockquote><div><br></div><div>Just trying to understand, does that mean that virtual threads don't have this? Because running Socket Statistics in the background showing 17K established connections while running virtual threads vs 140 when using platform threads.</div><div><br></div><div>At this point I am just trying to understand where this delay is coming from and why virtual threads trigger this.</div><div><br></div><div>Thanks in advance!</div><div><br></div><div>Kind regards,</div><div>David</div><div><br></div><div><br></div></div></div><div><br></div><div class="qt-gmail_quote qt-gmail_quote_container"><div dir="ltr" class="qt-gmail_attr">On Wed, 26 Nov 2025 at 10:33, Alan Bateman <<a href="mailto:alan.bateman@oracle.com">alan.bateman@oracle.com</a>> wrote:</div><blockquote class="qt-gmail_quote" style="margin-top:0px;margin-right:0px;margin-bottom:0px;margin-left:0.8ex;border-left-width:1px;border-left-style:solid;border-left-color:rgb(204, 204, 204);padding-left:1ex;"><div><br></div><div><br></div><div>On 26/11/2025 00:25, Robert Engels wrote:</div><div> > Your platform test is limiting to at most 4 outstanding requests.</div><div> <br></div><div> I assume it also benefits from being able to use HTTP persistent </div><div> connections.</div><div> <br></div><div> The benchmark using virtual threads is very different, it tries to </div><div> establish 10k connections in a burst. Do you know what connection </div><div> backlog is used by Tomcat? It may require adjusting net.core.somaxconn </div><div> (kern.ipc.somaxconn on macOS) and other settings. ~8100 may be 8k and </div><div> maybe there is something in the Tomcat or Spring connection that </div><div> controls this.</div><div> <br></div><div> -Alan</div></blockquote></div></blockquote><div><br></div></body></html>