Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

VirtualThreadPool blocks all carrier threads #12651

Open
CLandsberg opened this issue Dec 18, 2024 · 8 comments
Open

VirtualThreadPool blocks all carrier threads #12651

CLandsberg opened this issue Dec 18, 2024 · 8 comments
Labels
Bug For general bugs on Jetty side

Comments

@CLandsberg
Copy link

CLandsberg commented Dec 18, 2024

Jetty version(s)
12.0.15 & 12.0.16

Jetty Environment
ee10

Java version/vendor (use: java -version)
Corretto-23.0.1.8.1

OS type/version
Linux 6.12.4-arch1-1 x86_64

Description
I am unable to start any (!!) virtual thread after no virtual thread (ANY virtual thread -> no link to jetty) is used for ~ 30 seconds after using org.eclipse.jetty.util.thread.VirtualThreadPool.
Using

//        VirtualThreadPool virtualThreadPool = new VirtualThreadPool(); //this blocks carrier threads
        QueuedThreadPool virtualThreadPool = new QueuedThreadPool(Integer.MAX_VALUE, 0, 0);
        virtualThreadPool.setVirtualThreadsExecutor(Executors.newVirtualThreadPerTaskExecutor());

        server = new Server(virtualThreadPool);

works fine. Using Java 24 EA works fine as well with VirtualThreadPool.

I inserted

            var l = new AtomicLong(0);
            Executors.newSingleThreadScheduledExecutor().scheduleAtFixedRate(() -> {
                var i = l.getAndIncrement();
                LOG.info("Tick {}", i);
                Thread.ofVirtual().start(() -> LOG.info("Tack {}", i));
            }, 1, 1, TimeUnit.MINUTES);

as a Test in the first line of the application. The Problem is when using the VirtualThreadPool class:

  • If TimeUnit.SECONDS is used i get both Tick and Tack logs.
  • If MINUTES is used no virtual threads can be started anymore. Only Tick is logged.

The last block i get before this happens is

o.eclipse.jetty.io.ManagedSelector -- Selector sun.nio.ch.EPollSelectorImpl@1aedf2b7 woken up from select, 1/1/1 selected
o.eclipse.jetty.io.ManagedSelector -- Selector sun.nio.ch.EPollSelectorImpl@1aedf2b7 processing 1 keys, 0 updates
o.eclipse.jetty.io.ManagedSelector -- selected 1 channel=java.nio.channels.SocketChannel[connected local=/127.0.0.1:8042 remote=/127.0.0.1:41452], selector=sun.nio.ch.EPollSelectorImpl@1aedf2b7, interestOps=1, readyOps=1 SocketChannelEndPoint@5d1778d5[{l=/127.0.0.1:8042,r=/127.0.0.1:41452,OPEN,fill=FI,flush=-,to=29788/30000}{io=1/1,kio=1,kro=1}]->[HttpConnection@7d92426a[p=HttpParser{s=START,0 of -1},g=HttpGenerator@b3b62be{s=START}]=>HttpChannelState@78ab3c22{handling=null, handled=false, send=SENDING, completed=false, request=null}] 
o.e.j.io.SelectableChannelEndPoint -- onSelected 1->0 r=true w=false for SocketChannelEndPoint@5d1778d5[{l=/127.0.0.1:8042,r=/127.0.0.1:41452,OPEN,fill=FI,flush=-,to=29788/30000}{io=1/0,kio=1,kro=1}]->[HttpConnection@7d92426a[p=HttpParser{s=START,0 of -1},g=HttpGenerator@b3b62be{s=START}]=>HttpChannelState@78ab3c22{handling=null, handled=false, send=SENDING, completed=false, request=null}]
o.e.j.io.SelectableChannelEndPoint -- task SocketChannelEndPoint@5d1778d5[{l=/127.0.0.1:8042,r=/127.0.0.1:41452,OPEN,fill=FI,flush=-,to=29788/30000}{io=1/0,kio=1,kro=1}]->[HttpConnection@7d92426a[p=HttpParser{s=START,0 of -1},g=HttpGenerator@b3b62be{s=START}]=>HttpChannelState@78ab3c22{handling=null, handled=false, send=SENDING, completed=false, request=null}]:runFillable:BLOCKING
o.e.j.u.t.s.AdaptiveExecutionStrategy -- consumeTask ss=EXECUTE_PRODUCE_CONSUME/false/BLOCKING t=SocketChannelEndPoint@5d1778d5[{l=/127.0.0.1:8042,r=/127.0.0.1:41452,OPEN,fill=FI,flush=-,to=29788/30000}{io=1/0,kio=1,kro=1}]->[HttpConnection@7d92426a[p=HttpParser{s=START,0 of -1},g=HttpGenerator@b3b62be{s=START}]=>HttpChannelState@78ab3c22{handling=null, handled=false, send=SENDING, completed=false, request=null}]:runFillable:BLOCKING AdaptiveExecutionStrategy@79135a38/SelectorProducer@77fceac6/IDLE/p=1/oejut.VirtualThreadPool@4b1ec694{STARTED}[pc=0,pic=0,pec=0,epc=1]@2024-12-18T11:54:36.002538642+01:00
org.eclipse.jetty.io.FillInterest -- fillable FillInterest@17c5b04f{ReadCallback@19377083{HttpConnection@7d92426a::SocketChannelEndPoint@5d1778d5[{l=/127.0.0.1:8042,r=/127.0.0.1:41452,OPEN,fill=FI,flush=-,to=29789/30000}{io=1/0,kio=1,kro=1}]->[HttpConnection@7d92426a[p=HttpParser{s=START,0 of -1},g=HttpGenerator@b3b62be{s=START}]=>HttpChannelState@78ab3c22{handling=null, handled=false, send=SENDING, completed=false, request=null}]}}
o.e.j.server.internal.HttpConnection -- onFillable enter HttpChannelState@78ab3c22{handling=null, handled=false, send=SENDING, completed=false, request=null} null HttpConnection@7d92426a::SocketChannelEndPoint@5d1778d5[{l=/127.0.0.1:8042,r=/127.0.0.1:41452,OPEN,fill=-,flush=-,to=29789/30000}{io=1/0,kio=1,kro=1}]->[HttpConnection@7d92426a[p=HttpParser{s=START,0 of -1},g=HttpGenerator@b3b62be{s=START}]=>HttpChannelState@78ab3c22{handling=null, handled=false, send=SENDING, completed=false, request=null}]
o.e.j.u.t.s.AdaptiveExecutionStrategy -- AdaptiveExecutionStrategy@79135a38/SelectorProducer@77fceac6/IDLE/p=1/oejut.VirtualThreadPool@4b1ec694{STARTED}[pc=0,pic=0,pec=0,epc=2]@2024-12-18T11:54:36.002792301+01:00 tryProduce true
o.eclipse.jetty.io.ManagedSelector -- updateable 0
o.eclipse.jetty.io.ManagedSelector -- updates 0
o.eclipse.jetty.util.ConcurrentPool -- returning entry ConcurrentEntry@25408306{terminated=false,multiplex=1,pooled=Buffer@4dc0b76a[rc=0,DirectByteBuffer@dacb89c[p=0,l=0,c=8192,r=0]={<<<>>>\x00\x00\x00\x00\x00\x00\x00\x00\x00...\x00\x00\x00\x00\x00\x00\x00}]} for ConcurrentPool@46531ff9[strategy=THREAD_ID,inUse=1,size=6,max=256,leaked=0,terminated=false]
o.e.j.io.SelectableChannelEndPoint -- Key interests updated 1 -> 0 on SocketChannelEndPoint@5d1778d5[{l=/127.0.0.1:8042,r=/127.0.0.1:41452,OPEN,fill=-,flush=-,to=29789/30000}{io=0/0,kio=0,kro=1}]->[HttpConnection@7d92426a[p=HttpParser{s=START,0 of -1},g=HttpGenerator@b3b62be{s=START}]=>HttpChannelState@78ab3c22{handling=null, handled=false, send=SENDING, completed=false, request=null}]
o.e.j.server.internal.HttpConnection -- request buffer acquired Buffer@4dc0b76a[rc=1,DirectByteBuffer@dacb89c[p=0,l=0,c=8192,r=0]={<<<>>>\x00\x00\x00\x00\x00\x00\x00\x00\x00...\x00\x00\x00\x00\x00\x00\x00}] HttpConnection@7d92426a::SocketChannelEndPoint@5d1778d5[{l=/127.0.0.1:8042,r=/127.0.0.1:41452,OPEN,fill=-,flush=-,to=29789/30000}{io=0/0,kio=0,kro=1}]->[HttpConnection@7d92426a[p=HttpParser{s=START,0 of -1},g=HttpGenerator@b3b62be{s=START}]=>HttpChannelState@78ab3c22{handling=?, handled=?, send=?, completed=?, request=?}]
o.eclipse.jetty.io.ManagedSelector -- Selector sun.nio.ch.EPollSelectorImpl@1aedf2b7 waiting with 1 keys
o.eclipse.jetty.io.AbstractEndPoint -- shutdownInput SocketChannelEndPoint@5d1778d5[{l=/127.0.0.1:8042,r=/127.0.0.1:41452,OPEN,fill=-,flush=-,to=29789/30000}{io=0/0,kio=0,kro=1}]->[HttpConnection@7d92426a[p=HttpParser{s=START,0 of -1},g=HttpGenerator@b3b62be{s=START}]=>HttpChannelState@78ab3c22{handling=null, handled=false, send=SENDING, completed=false, request=null}]
o.e.jetty.io.SocketChannelEndPoint -- filled -1 DirectByteBuffer@dacb89c[p=0,l=0,c=8192,r=0]={<<<>>>\x00\x00\x00\x00\x00\x00\x00\x00\x00...\x00\x00\x00\x00\x00\x00\x00}
o.e.j.server.internal.HttpConnection -- filled -1 Buffer@4dc0b76a[rc=1,DirectByteBuffer@dacb89c[p=0,l=0,c=8192,r=0]={<<<>>>\x00\x00\x00\x00\x00\x00\x00\x00\x00...\x00\x00\x00\x00\x00\x00\x00}] HttpConnection@7d92426a::SocketChannelEndPoint@5d1778d5[{l=/127.0.0.1:8042,r=/127.0.0.1:41452,ISHUT,fill=-,flush=-,to=29789/30000}{io=0/0,kio=0,kro=1}]->[HttpConnection@7d92426a[p=HttpParser{s=START,0 of -1},g=HttpGenerator@b3b62be{s=START}]=>HttpChannelState@78ab3c22{handling=null, handled=false, send=SENDING, completed=false, request=null}]
org.eclipse.jetty.http.HttpParser -- atEOF HttpParser{s=START,0 of -1}
o.e.j.server.internal.HttpConnection -- onFillable filled -1 HttpChannelState@78ab3c22{handling=null, handled=false, send=SENDING, completed=false, request=null} Buffer@4dc0b76a[rc=1,DirectByteBuffer@dacb89c[p=0,l=0,c=8192,r=0]={<<<>>>\x00\x00\x00\x00\x00\x00\x00\x00\x00...\x00\x00\x00\x00\x00\x00\x00}] HttpConnection@7d92426a::SocketChannelEndPoint@5d1778d5[{l=/127.0.0.1:8042,r=/127.0.0.1:41452,ISHUT,fill=-,flush=-,to=29789/30000}{io=0/0,kio=0,kro=1}]->[HttpConnection@7d92426a[p=HttpParser{s=START,0 of -1},g=HttpGenerator@b3b62be{s=START}]=>HttpChannelState@78ab3c22{handling=null, handled=false, send=SENDING, completed=false, request=null}]
o.e.j.server.internal.HttpConnection -- parse Buffer@4dc0b76a[rc=1,DirectByteBuffer@dacb89c[p=0,l=0,c=8192,r=0]={<<<>>>\x00\x00\x00\x00\x00\x00\x00\x00\x00...\x00\x00\x00\x00\x00\x00\x00}] HttpConnection@7d92426a::SocketChannelEndPoint@5d1778d5[{l=/127.0.0.1:8042,r=/127.0.0.1:41452,ISHUT,fill=-,flush=-,to=29790/30000}{io=0/0,kio=0,kro=1}]->[HttpConnection@7d92426a[p=HttpParser{s=START,0 of -1},g=HttpGenerator@b3b62be{s=START}]=>HttpChannelState@78ab3c22{handling=null, handled=false, send=SENDING, completed=false, request=null}]
org.eclipse.jetty.http.HttpParser -- parseNext s=START DirectByteBuffer@dacb89c[p=0,l=0,c=8192,r=0]={<<<>>>\x00\x00\x00\x00\x00\x00\x00\x00\x00...\x00\x00\x00\x00\x00\x00\x00}
org.eclipse.jetty.http.HttpParser -- START --> CLOSED
o.e.j.server.internal.HttpConnection -- early EOF HttpConnection@7d92426a::SocketChannelEndPoint@5d1778d5[{l=/127.0.0.1:8042,r=/127.0.0.1:41452,ISHUT,fill=-,flush=-,to=29790/30000}{io=0/0,kio=0,kro=1}]->[HttpConnection@7d92426a[p=HttpParser{s=CLOSED,0 of -1},g=HttpGenerator@b3b62be{s=START}]=>HttpChannelState@78ab3c22{handling=null, handled=false, send=SENDING, completed=false, request=null}]
o.e.j.server.internal.HttpConnection -- parsed false HttpParser{s=CLOSED,0 of -1} Buffer@4dc0b76a[rc=1,DirectByteBuffer@dacb89c[p=0,l=0,c=8192,r=0]={<<<>>>\x00\x00\x00\x00\x00\x00\x00\x00\x00...\x00\x00\x00\x00\x00\x00\x00}] HttpConnection@7d92426a::SocketChannelEndPoint@5d1778d5[{l=/127.0.0.1:8042,r=/127.0.0.1:41452,ISHUT,fill=-,flush=-,to=29790/30000}{io=0/0,kio=0,kro=1}]->[HttpConnection@7d92426a[p=HttpParser{s=CLOSED,0 of -1},g=HttpGenerator@b3b62be{s=START}]=>HttpChannelState@78ab3c22{handling=null, handled=false, send=SENDING, completed=false, request=null}]
o.e.j.server.internal.HttpConnection -- releasing request buffer Buffer@4dc0b76a[rc=1,DirectByteBuffer@dacb89c[p=0,l=0,c=8192,r=0]={<<<>>>\x00\x00\x00\x00\x00\x00\x00\x00\x00...\x00\x00\x00\x00\x00\x00\x00}] HttpConnection@7d92426a::SocketChannelEndPoint@5d1778d5[{l=/127.0.0.1:8042,r=/127.0.0.1:41452,ISHUT,fill=-,flush=-,to=29790/30000}{io=0/0,kio=0,kro=1}]->[HttpConnection@7d92426a[p=HttpParser{s=CLOSED,0 of -1},g=HttpGenerator@b3b62be{s=START}]=>HttpChannelState@78ab3c22{handling=null, handled=false, send=SENDING, completed=false, request=null}]
o.eclipse.jetty.util.ConcurrentPool -- released true ConcurrentEntry@25408306{terminated=false,multiplex=0,pooled=Buffer@4dc0b76a[rc=0,DirectByteBuffer@dacb89c[p=0,l=0,c=8192,r=0]={<<<>>>\x00\x00\x00\x00\x00\x00\x00\x00\x00...\x00\x00\x00\x00\x00\x00\x00}]} for ConcurrentPool@46531ff9[strategy=THREAD_ID,inUse=0,size=6,max=256,leaked=0,terminated=false]
o.eclipse.jetty.io.AbstractEndPoint -- shutdownOutput SocketChannelEndPoint@5d1778d5[{l=/127.0.0.1:8042,r=/127.0.0.1:41452,ISHUT,fill=-,flush=-,to=29790/30000}{io=0/0,kio=0,kro=1}]->[HttpConnection@7d92426a[p=HttpParser{s=CLOSED,0 of -1},g=HttpGenerator@b3b62be{s=START}]=>HttpChannelState@78ab3c22{handling=null, handled=false, send=SENDING, completed=false, request=null}]
o.e.j.io.SelectableChannelEndPoint -- doClose SocketChannelEndPoint@5d1778d5[{l=/127.0.0.1:8042,r=/127.0.0.1:41452,CLOSED,fill=-,flush=-,to=29790/30000}{io=0/0,kio=0,kro=1}]->[HttpConnection@7d92426a[p=HttpParser{s=CLOSED,0 of -1},g=HttpGenerator@b3b62be{s=START}]=>HttpChannelState@78ab3c22{handling=null, handled=false, send=SENDING, completed=false, request=null}]
org.eclipse.jetty.io.FillInterest -- onClose FillInterest@17c5b04f{null}
o.eclipse.jetty.io.ManagedSelector -- Wakeup oeji.ManagedSelector@563c3aca{STARTED}[id=10 keys=1 selected=0 updates=0 selection:tot=2/avg=1,00/max=1]
o.eclipse.jetty.io.ManagedSelector -- Selector sun.nio.ch.EPollSelectorImpl@1aedf2b7 woken with none selected
o.eclipse.jetty.io.ManagedSelector -- Selector sun.nio.ch.EPollSelectorImpl@1aedf2b7 woken up from select, 0/0/0 selected
o.eclipse.jetty.io.ManagedSelector -- Selector sun.nio.ch.EPollSelectorImpl@1aedf2b7 processing 0 keys, 0 updates
o.eclipse.jetty.io.ManagedSelector -- updateable 0
o.eclipse.jetty.io.ManagedSelector -- updates 0
o.eclipse.jetty.io.ManagedSelector -- Selector sun.nio.ch.EPollSelectorImpl@1aedf2b7 waiting with 0 keys
o.eclipse.jetty.io.ManagedSelector -- Destroyed SocketChannelEndPoint@5d1778d5[{l=null,r=null,CLOSED,fill=-,flush=-,to=29791/30000}{io=0/0,kio=-1,kro=-1}]->[HttpConnection@7d92426a[p=HttpParser{s=CLOSED,0 of -1},g=HttpGenerator@b3b62be{s=START}]=>HttpChannelState@78ab3c22{handling=null, handled=false, send=SENDING, completed=false, request=null}]
o.e.j.server.internal.HttpConnection -- onFillable exit HttpChannelState@78ab3c22{handling=null, handled=false, send=SENDING, completed=false, request=null} null HttpConnection@7d92426a::SocketChannelEndPoint@5d1778d5[{l=null,r=null,CLOSED,fill=-,flush=-,to=29791/30000}{io=0/0,kio=-1,kro=-1}]->[HttpConnection@7d92426a[p=HttpParser{s=CLOSED,0 of -1},g=HttpGenerator@b3b62be{s=START}]=>HttpChannelState@78ab3c22{handling=null, handled=false, send=SENDING, completed=false, request=null}]
o.e.jetty.io.AbstractConnection -- onClose HttpConnection@7d92426a::SocketChannelEndPoint@5d1778d5[{l=null,r=null,CLOSED,fill=-,flush=-,to=29791/30000}{io=0/0,kio=-1,kro=-1}]->[HttpConnection@7d92426a[p=HttpParser{s=CLOSED,0 of -1},g=HttpGenerator@b3b62be{s=START}]=>HttpChannelState@78ab3c22{handling=null, handled=false, send=SENDING, completed=false, request=null}]

It looks like the virtual threads scheduled but never executed. The thread dump looks a bit like described here https://netflixtechblog.com/java-21-virtual-threads-dude-wheres-my-lock-3052540e231d but i do not see the threads waiting for any locks

@CLandsberg CLandsberg added the Bug For general bugs on Jetty side label Dec 18, 2024
@sbordet
Copy link
Contributor

sbordet commented Dec 18, 2024

Sorry but it's not clear what you are doing, and the logs do not report any indication of the thread name, so we can't really try to figure things out from them.

Please have a read at this section:
https://jetty.org/docs/jetty/12/programming-guide/arch/threads.html#thread-pool-virtual-threads-virtual

The important part is that the select() operation pins the carrier, so you have to play with the number of selectors to avoid that all carriers are pinned.

@CLandsberg
Copy link
Author

I produced a minimal example of this:

https://github.com/CLandsberg/JettyBug/blob/master/src/main/java/Main.java

The Helloworld example freezes after some time.

The key for this is adding two ServerConnectors it seems

@CLandsberg
Copy link
Author

Example output:

14:28:48.002 [main] INFO  Main -- Server started on port 8080
14:28:48.003 [platform] INFO  Main -- Tick 0
14:28:48.004 [virtual-157] INFO  Main -- Tack 0
14:29:48.003 [platform] INFO  Main -- Tick 1
14:30:48.003 [platform] INFO  Main -- Tick 2

All requests timeout afterwards.

@sbordet
Copy link
Contributor

sbordet commented Dec 19, 2024

@CLandsberg sorry but with virtual threads it is of extreme importance to know how many cores (and therefore carrier threads) you have, and whether you override or not the number of carriers via system property.

If the number of carriers is the same (or less) than the number of selectors of all ServerConnectors, then you will have a problem, otherwise you won't.

Your example will run differently on my machine with M cores than on your machine with N cores.

@CLandsberg
Copy link
Author

CLandsberg commented Dec 20, 2024

I use default parameters without any system property or other configuration.

What i fail to understand is how the starting of complete independent Virtual Threads (changing the Timeunit to seconds here) prevent the blocking of carrier threads. It might be coincidental, but this could also be a symptom of a major issue.

@joakime
Copy link
Contributor

joakime commented Dec 20, 2024

@CLandsberg the behaviors are machine specific as @sbordet pointed out.

For example, on my machine, your demo never hangs.

(I changed the iteration to once every 5 seconds, just to see it operate. If I leave it at the original once every 1 minute, the behavior is the same, no hang, just less output)

2024-12-20 08:56:32.948:INFO :oejs.Server:main: jetty-12.0.16; built: 2024-12-09T21:02:54.535Z; git: c3f88bafb4e393f23204dc14dc57b042e84debc7; jvm 21.0.3+9-LTS
2024-12-20 08:56:32.970:INFO :oejsh.ContextHandler:main: Started oeje10s.ServletContextHandler@1da51a35{ROOT,/,b=null,a=AVAILABLE,h=oeje10s.ServletHandler@16022d9d{STARTED}}
2024-12-20 08:56:32.975:INFO :oejes.ServletContextHandler:main: Started oeje10s.ServletContextHandler@1da51a35{ROOT,/,b=null,a=AVAILABLE,h=oeje10s.ServletHandler@16022d9d{STARTED}}
2024-12-20 08:56:32.998:INFO :oejs.AbstractConnector:main: Started ServerConnector@76329302{HTTP/1.1, (http/1.1)}{0.0.0.0:8080}
2024-12-20 08:56:33.024:INFO :oejs.AbstractConnector:main: Started ServerConnector@4df828d7{HTTP/1.1, (http/1.1)}{0.0.0.0:8081}
2024-12-20 08:56:33.035:INFO :oejs.Server:main: Started oejs.Server@436e852b{STARTING}[12.0.16,sto=0] @473ms
2024-12-20 08:56:33.035:INFO :Main:main: Server started on port 8080
2024-12-20 08:56:33.037:INFO :Main:platform: Tick 0
2024-12-20 08:56:33.038:INFO :Main:: Tack 0
2024-12-20 08:56:38.036:INFO :Main:platform: Tick 1
2024-12-20 08:56:38.036:INFO :Main:: Tack 1
2024-12-20 08:56:43.036:INFO :Main:platform: Tick 2
2024-12-20 08:56:43.036:INFO :Main:: Tack 2
2024-12-20 08:56:48.036:INFO :Main:platform: Tick 3
2024-12-20 08:56:48.036:INFO :Main:: Tack 3
2024-12-20 08:56:53.036:INFO :Main:platform: Tick 4
2024-12-20 08:56:53.036:INFO :Main:: Tack 4
2024-12-20 08:56:58.036:INFO :Main:platform: Tick 5
2024-12-20 08:56:58.036:INFO :Main:: Tack 5
2024-12-20 08:57:03.036:INFO :Main:platform: Tick 6
2024-12-20 08:57:03.036:INFO :Main:: Tack 6
2024-12-20 08:57:04.372:INFO :Main:: Servlet called
2024-12-20 08:57:04.489:INFO :Main:: Servlet called
2024-12-20 08:57:04.831:INFO :Main:: Servlet called
2024-12-20 08:57:05.044:INFO :Main:: Servlet called
2024-12-20 08:57:05.259:INFO :Main:: Servlet called
2024-12-20 08:57:05.497:INFO :Main:: Servlet called
2024-12-20 08:57:05.716:INFO :Main:: Servlet called
2024-12-20 08:57:05.932:INFO :Main:: Servlet called
2024-12-20 08:57:06.170:INFO :Main:: Servlet called
2024-12-20 08:57:06.403:INFO :Main:: Servlet called
2024-12-20 08:57:06.623:INFO :Main:: Servlet called
2024-12-20 08:57:06.840:INFO :Main:: Servlet called
2024-12-20 08:57:07.057:INFO :Main:: Servlet called
2024-12-20 08:57:07.271:INFO :Main:: Servlet called
2024-12-20 08:57:07.487:INFO :Main:: Servlet called
2024-12-20 08:57:07.705:INFO :Main:: Servlet called
2024-12-20 08:57:07.915:INFO :Main:: Servlet called
2024-12-20 08:57:08.036:INFO :Main:platform: Tick 7
2024-12-20 08:57:08.037:INFO :Main:: Tack 7
2024-12-20 08:57:08.125:INFO :Main:: Servlet called
2024-12-20 08:57:08.333:INFO :Main:: Servlet called
2024-12-20 08:57:08.541:INFO :Main:: Servlet called
2024-12-20 08:57:08.752:INFO :Main:: Servlet called
2024-12-20 08:57:08.962:INFO :Main:: Servlet called
2024-12-20 08:57:09.183:INFO :Main:: Servlet called
2024-12-20 08:57:09.403:INFO :Main:: Servlet called
2024-12-20 08:57:09.608:INFO :Main:: Servlet called
2024-12-20 08:57:09.816:INFO :Main:: Servlet called
2024-12-20 08:57:10.042:INFO :Main:: Servlet called
2024-12-20 08:57:10.270:INFO :Main:: Servlet called
2024-12-20 08:57:10.500:INFO :Main:: Servlet called
2024-12-20 08:57:10.705:INFO :Main:: Servlet called
2024-12-20 08:57:10.926:INFO :Main:: Servlet called
2024-12-20 08:57:11.149:INFO :Main:: Servlet called
2024-12-20 08:57:11.369:INFO :Main:: Servlet called
2024-12-20 08:57:11.574:INFO :Main:: Servlet called
2024-12-20 08:57:11.798:INFO :Main:: Servlet called
2024-12-20 08:57:12.002:INFO :Main:: Servlet called
2024-12-20 08:57:12.218:INFO :Main:: Servlet called
2024-12-20 08:57:12.448:INFO :Main:: Servlet called
2024-12-20 08:57:12.675:INFO :Main:: Servlet called
2024-12-20 08:57:12.885:INFO :Main:: Servlet called
2024-12-20 08:57:13.036:INFO :Main:platform: Tick 8
2024-12-20 08:57:13.037:INFO :Main:: Tack 8
2024-12-20 08:57:13.094:INFO :Main:: Servlet called
2024-12-20 08:57:13.301:INFO :Main:: Servlet called
2024-12-20 08:57:13.498:INFO :Main:: Servlet called
2024-12-20 08:57:13.709:INFO :Main:: Servlet called
2024-12-20 08:57:13.933:INFO :Main:: Servlet called
2024-12-20 08:57:14.153:INFO :Main:: Servlet called
2024-12-20 08:57:14.378:INFO :Main:: Servlet called
2024-12-20 08:57:14.599:INFO :Main:: Servlet called
2024-12-20 08:57:14.798:INFO :Main:: Servlet called
2024-12-20 08:57:14.993:INFO :Main:: Servlet called
2024-12-20 08:57:15.222:INFO :Main:: Servlet called
2024-12-20 08:57:15.430:INFO :Main:: Servlet called
2024-12-20 08:57:15.618:INFO :Main:: Servlet called
2024-12-20 08:57:16.175:INFO :Main:: Servlet called
2024-12-20 08:57:18.036:INFO :Main:platform: Tick 9
2024-12-20 08:57:18.036:INFO :Main:: Tack 9

@CLandsberg
Copy link
Author

@sbordet @joakime Does it make sense to you starting a virtual thread every second should prevents the blocking on my System while changing it to every minute blocks it right away?

And doesn't the QueuedThreadPool also use the same number of virtual threads for selectors? I would expect them to behave the same.

@sbordet
Copy link
Contributor

sbordet commented Dec 23, 2024

@CLandsberg it is not clear what you're trying to do.

You do not want to configure virtual threads, but then have to add workarounds such as starting a virtual thread every second to avoid carrier pinning.

Using QueuedThreadPool with setVirtualThreadExecutor() works (as you report), so that is your best solution.

Virtual threads have a number of surprises and gotchas, but we arranged to get the minimum surprises and still use them with the QueuedThreadPool with setVirtualThreadExecutor() combination, so I'd recommend you stick with that.

VirtualThreadPool is to be used when you know exactly your environment (in particular the number of cores), and you are willing to accept the limitations of virtual threads.

For practically all purposes, QueuedThreadPool with setVirtualThreadExecutor() is likely a better configuration.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Bug For general bugs on Jetty side
Projects
None yet
Development

No branches or pull requests

3 participants