Loom me up Scotty!  Project Loom - What's in it for Me?
Loom
Haim Yadid @ Next Insurance
Loom me up Scotty!
Haim Yadid @ Next Insurance
Loom me up Scotty!
Project Loom - What's in it for Me?
Haim Yadid @ Next Insurance
Loom me up Scotty!
Project Loom - What's in it for Me?
Haim Yadid @ Next Insurance
Dall E - Star Trek spaceship Enterprise flying inside a loom, Van gogh style
Loom me up Scotty!  Project Loom - What's in it for Me?
Loom me up Scotty!  Project Loom - What's in it for Me?
Loom me up Scotty!  Project Loom - What's in it for Me?
Loom me up Scotty!  Project Loom - What's in it for Me?
@lifeyx
Pro t L o es . 2017
JE -425
JE -428
JE -429
Loom me up Scotty!  Project Loom - What's in it for Me?
CONCURRENCY
request (task)
getBid(user)
getBid(user)
Start End
Duration
Running Blocked
getBid(user)
resolve user country Query bidding service 1
for user country
Query bidding service 2
for user country
Example - Single Threaded
val country = userClient.
findUserByEmail(userEmail).country
t1
https://github.com/lifey/loom-playground
Example - Single Threaded
val country = userClient.
findUserByEmail(userEmail).country
val resultA = serverA.getBid(country)
val resultB = serverB.getBid(country)
t1
Example - Single Threaded
val country = userClient.
findUserByEmail(userEmail).country
val resultA = serverA.getBid(country)
val resultB = serverB.getBid(country)
val lowestBid = if (resultA.price < resultB.price)
resultA
else
resultB
t1
getBid
resolve user country
Query bidding service 1
for user country
Query bidding service 2
for user country fan out is 3
getBid(John)
getBid(Robb)
CONCURRENCY
CONCURRENCY
CONCURRENCY CONCURRENCY
CONCURRENCY
threads
Immutability
Deadlocks
synchronization
Thread pools
race conditions
contention
shared mutable state
message passing
channels
Cache Coherence
callbacks
semaphores
Concurrency
is
Hard
Java and Concurrency / Parallelism
Java 1.0-1.1
(1995)
Threads
wait /notify
synchronized
Java and Concurrency / Parallelism
Java 1.0-1.1
(1995)
Threads
wait /notify
synchronized
Java 1.4
(2002)
Non blocking IO
SocketChannel
Selector
Java and Concurrency / Parallelism
Java 1.0-1.1
(1995)
Threads
wait /notify
synchronized
Java 1.4
(2002)
Non blocking IO
SocketChannel
Selector
Java 1.5
(2004)
j.u.c
Executors
Future
Reentrant Locks
Semaphores
Latches
Java and Concurrency / Parallelism
Java 1.0-1.1
(1995)
Threads
wait /notify
synchronized
Java 1.4
(2002)
Non blocking IO
SocketChannel
Selector
Java 1.5
(2004)
j.u.c
Executors
Future
Reentrant Locks
Semaphores
Latches
Java 1.7
(2011)
ForkJoin Pool
Java 1.8
(2014)
ParallelStreams
CompletableFuture
Java and Concurrency / Parallelism
Java 1.0-1.1
(1995)
Threads
wait /notify
synchronized
Java 1.4
(2002)
Non blocking IO
SocketChannel
Selector
Java 1.5
(2004)
j.u.c
Executors
Future
Reentrant Locks
Semaphores
Latches
Java 1.7
(2011)
ForkJoin Pool
Java 1.8
(2014)
ParallelStreams
CompletableFuture
Java 19
Loom
(2022)
VirtualThreads
Structured Concurrency
traditional Java Concurrency Model
● Thread per request (task) style
● Java thread is a wrapper of OS thread
● 1 or more thread to serve the request using Futures
● Executors and thread pools to control concurrency level
getBid
resolve user country
Query bidding service 1
for user country
Query bidding service 2
for user country fan out is 3
Example (Kotlin)
val userCountry =
userClient.findUserByEmail(userEmail).country
t1
Example (Kotlin)
val userCountry =
userClient.findUserByEmail(userEmail).country
executor.invokeAny (listOf(
))
t1
Example (Kotlin)
val userCountry =
userClient.findUserByEmail(userEmail).country
executor.invokeAny (listOf(
Callable { clientA.getBid(userCountry) } ,
Callable { clientB.getBid(userCountry) }
))
t1
t2
t3
Example (Kotlin)
val userCountry =
userClient.findUserByEmail(userEmail).country
val price = executor.invokeAny (listOf(
Callable { clientA.getBid(userCountry) } ,
Callable { clientB.getBid(userCountry) }
))
.price
t1
t2
t3
SCALABILITY &
HARDWARE UTILIZATION
So How much concurrency ? Little’s Law
● λ - throughput (arrival rate)
● L - average concurrency
● W- average latency /duration
L= λ * W
E= M * C2
getBid(user)
resolve user country Query bidding service 1
for user country
Query bidding service 2
for user country
50% 50%
32 CPU cores
64 (32*2) concurrent tasks
5
%
99%
32 CPU cores
3200 (32*100) concurrent tasks
5
%
99.9 %
32 CPU cores
32000 (32*1000) concurrent tasks
getBid
resolve user country
Query bidding service 1
for user country
Query bidding service 2
for user country fan out is 3
5
%
99.9 %
32 CPU cores
Fan out of 5
150K (32*1000*5) concurrent tasks
C1M Problem
What is needed for a server to hold
1M concurrent connections
So what is the Problem With OS Threads
● stack: ~1 MB
● scheduling >1µs
● launch a new thread ~0.1ms
● context switch involves kernel meaning returning from future
~5µs
● Usually Linux OS can support thousands of threads
Asynchronous Programming Style,
Callback / Non Blocking / Async Model
Event Loop
Event Loop
Asynchronous Programming Style,
Callback / Non Blocking / Async Model
#
of
cores
Async
● Less readable (for most developers )
● Callback hell anyone ?
a diagram from Ron Pressler’s presentation
CompletableFuture.supplyAsync(info::getUrl, pool)
.thenCompose(url -> getBodyAsync(url,
HttpResponse.BodyHandlers.ofString()))
.thenApply(info::findImage)
.thenCompose(url -> getBodyAsync(url,
HttpResponse.BodyHandlers.ofByteArray()))
.thenApply(info::setImageData)
.thenAccept(this::process)
.exceptionally(t -> { t.printStackTrace(); return null; });
Async is Tooling - Nightmare!
● Where is my call stack ?
● debug
● profile
● troubleshoot
● understanding number of actively
running task
●
a slide from Ron Pressler’s presentation
Project Loom is
about
Developer Productivity (& Sanity)
VIRTUAL THREADS
JEP-425 (preview)
Virtual Thread is:
A unit of execution (a task) which can run on
on carrier Platform(OS) thread
Hello World
Thread.ofVirtual()
.name("virtual-", 1)
Hello World
Thread.ofVirtual()
.name("virtual-", 1)
.start {
}.join()
Runnable
Hello World
Thread.ofVirtual()
.name("virtual-", 1)
.start {
Thread.sleep(2000)
println("Hello World:"+ Thread.currentThread())
}.join()
Output :
Hello World: VirtualThread[#23,virtual-1]/runnable@ForkJoinPool-1-worker-1
Example: Executor
val executor = Executors.
newVirtualThreadPerTaskExecutor()
Example: Executor
val executor = Executors.
newVirtualThreadPerTaskExecutor()
executor.use {
}
Example: Executor
val executor = Executors.
newVirtualThreadPerTaskExecutor()
executor.use {
val future = executor.submit {
}
}
Callable
Example: Executor
val executor = Executors.
newVirtualThreadPerTaskExecutor()
executor.use {
val future = executor.submit {
Thread.sleep(2000)
println("Hello World: " + Thread.currentThread())
}
}
Virtual thread
Scheduler
Scheduler
Virtual thread
Common Pool
Scheduler
Virtual thread
Platform Threads
Mounting
Scheduler
Virtual thread
Platform Threads
Continuation.run
Yield
Scheduler
Virtual thread
Platform Threads
Continuation.yield
Yield -> Unmounting
Scheduler
Virtual thread
Platform Threads
Virtual Threads stack frames
● Mounted -> On the carrier thread stack
● UnMounted -> in the Heap
○ pay as you go stack can be very small
Loom Is
JVM
Copying Stack frames
Changes in GC root scanning
JRE
Continuation
Changes in all IO APIs
Thread Locals
Context (e.g.MDC)
TransactionID
Shared Heavy Data Structures
❌
✅
Non thread safe Objects (XML Parser)
❌
Inheritable
You can prevent this from happening by setting
inheritInheritableThreadLocals(false)
STRUCTURED CONCURRENCY
JEP-428 (incubating)
Structured Concurrency
● Makes writing correct concurrent code easier
● Cancellation, error propagation, timeouts
● Observe hierarchy of virtual threads at runtime
Example: Structured Concurrency
val country = userRClient.findUserByEmail(userEmail).country
Example: Structured Concurrency
val country = userRClient.findUserByEmail(userEmail).country
val scope = StructuredTaskScope.
ShutdownOnSuccess<BiddingResponse>()
scope.use {
}
Example: Structured Concurrency
val country = userRClient.findUserByEmail(userEmail).country
val scope = StructuredTaskScope.
ShutdownOnSuccess<BiddingResponse>()
scope.use {
scope.fork { serverA.getBid(country) }
scope.fork { serverB.getBid(country) }
}
Example: Structured Concurrency
val country = userRClient.findUserByEmail(userEmail).country
val scope = StructuredTaskScope.
ShutdownOnSuccess<BiddingResponse>()
scope.use {
scope.fork { serverA.getBid(country) }
scope.fork { serverB.getBid(country) }
val firstSuccessfulFuture = scope.join()
return firstSuccessfulFuture.result().price
}
Example: Structured Concurrency
val country = userRClient.findUserByEmail(userEmail).country
val scope = StructuredTaskScope.
ShutdownOnSuccess<BiddingResponse>()
scope.use {
scope.fork { serverA.getBid(country) }
scope.fork { serverB.getBid(country) }
val firstSuccessfulFuture = scope.joinUntil(
Instant.now().plusMillis(3000))
return firstSuccessfulFuture.result().price
}
Scoped Values
JEP-429 (candidate)
Tooling
Debugger Breakpoint
Debugger Stack Trace
Debugger Virtual Threads
Thread dumps
jstack -l <pid>
Shows only platform threads
Thread dumps
jcmd <pid> Thread.dump_to_file -format=json <File name>
Thread.ofVirtual
executor.submit
scope.fork
Platform Threads
{
"tid": "5604",
"name": "",
"stack": [
"java.base/jdk.internal.vm.Continuation.yield(Continuation.java:357)",
"java.base/java.lang.VirtualThread.yieldContinuation(VirtualThread.java:370)",
"java.base/java.lang.VirtualThread.parkNanos(VirtualThread.java:532)",
"java.base/java.lang.VirtualThread.doSleepNanos(VirtualThread.java:713)",
"java.base/java.lang.VirtualThread.sleepNanos(VirtualThread.java:686)",
"java.base/java.lang.Thread.sleep(Thread.java:451)",
"playground.ExecutorTest$vthreadExecutorTest$1$1$1.invoke(ExecutorTest.kt:30)",
"playground.ExecutorTest$vthreadExecutorTest$1$1$1.invoke(ExecutorTest.kt:27)",
"playground.ExecutorTest.vthreadExecutorTest$lambda-1$lambda-0(ExecutorTest.kt:27)",
"java.base/java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:577)",
"java.base/java.util.concurrent.ThreadPerTaskExecutor$ThreadBoundFuture.run(ThreadPerTaskExecutor.ja
va:352)",
"java.base/java.lang.VirtualThread.run(VirtualThread.java:287)",
"java.base/java.lang.VirtualThread$VThreadContinuation.lambda$new$0(VirtualThread.java:174)",
"java.base/jdk.internal.vm.Continuation.enter0(Continuation.java:327)",
"java.base/jdk.internal.vm.Continuation.enter(Continuation.java:320)"
]
},
❌
✅
✅
✅
Java Flight Recorder (JFR)
● jdk.VirtualThreadStart
● jdk.VirtualThreadEnd
● jdk.VirtualThreadPinned
● jdk.VirtualThreadSubmitFailed
Summary
Should I use Project Loom in
Production?
Should I use Project Loom in
Production?
Of course not
Not Yet
But Maybe
● If you are starting to write a new service that is IO bound and
requires high level of concurrency (> 10K concurrent
connections)
● If you want to play around
○ https://github.com/lifey/loom-playground
○ https://github.com/cmpxchg16/kotlin-loom
● If you want to provide feedback
supports Virtual Threads
Since: v10.0.12
Enable by:
QueuedThreadPool.setUseVirtualThread(true)
https://github.com/oracle/graal/pull/4802
https://github.com/quarkusio/quarkus/pull/24942
Helidon Nima
With “dumb”
synchronous code on
Loom and some
simple tuning, quickly
got similar or better
performance to Netty
— Tomas Langer
(Helidon)
--enable-preview
JDK 19
--enable-preview
--add-modules jdk.incubator.concurrent
JDK 19
Pinned Threads
● When a virtual thread is in a synchronized block
(or in JNI call)
● It cannot be unmounted
● Even when blocked on IO
-Djdk.tracePinnedThreads=full
Don’t Po
Vir Th e s
Loom me up Scotty!  Project Loom - What's in it for Me?

More Related Content

PDF
Current State of Coroutines
PDF
Decoding Kotlin - Your Guide to Solving the Mysterious in Kotlin - Devoxx PL ...
PDF
Androidの本当にあった怖い話
PDF
Kotlin coroutine - the next step for RxJava developer?
PDF
Presto anatomy
PPTX
Navigating the xDD Alphabet Soup
PPTX
Exploring Kotlin
PPTX
Building High Performance Web Applications and Sites
Current State of Coroutines
Decoding Kotlin - Your Guide to Solving the Mysterious in Kotlin - Devoxx PL ...
Androidの本当にあった怖い話
Kotlin coroutine - the next step for RxJava developer?
Presto anatomy
Navigating the xDD Alphabet Soup
Exploring Kotlin
Building High Performance Web Applications and Sites

Similar to Loom me up Scotty! Project Loom - What's in it for Me? (20)

PPTX
Clojure And Swing
PDF
Mastering Kotlin Standard Library
PPTX
Introduction to kotlin + spring boot demo
PDF
Actor based approach in practice for Swift developers
PPT
Deuce STM - CMP'09
PPTX
Decoding Kotlin - Your guide to solving the mysterious in Kotlin - JNation2025
PPTX
Could Virtual Threads cast away the usage of Kotlin Coroutines - DevoxxUK2025
PDF
Juju - Google Go in a scalable Environment
PDF
Kotlin for Android devs
PDF
外部環境への依存をテストする
PDF
Coroutines for Kotlin Multiplatform in Practise
PPTX
A TypeScript Fans KotlinJS Adventures
PDF
Kotlin - The Swiss army knife of programming languages - Visma Mobile Meet-up...
PDF
Building a DRYer Android App with Kotlin
PDF
Implicit parameters, when to use them (or not)!
PDF
Hadoop + Clojure
PPT
jimmy hacking (at) Microsoft
PDF
[245] presto 내부구조 파헤치기
PDF
Griffon @ Svwjug
PPT
Effecient javascript
Clojure And Swing
Mastering Kotlin Standard Library
Introduction to kotlin + spring boot demo
Actor based approach in practice for Swift developers
Deuce STM - CMP'09
Decoding Kotlin - Your guide to solving the mysterious in Kotlin - JNation2025
Could Virtual Threads cast away the usage of Kotlin Coroutines - DevoxxUK2025
Juju - Google Go in a scalable Environment
Kotlin for Android devs
外部環境への依存をテストする
Coroutines for Kotlin Multiplatform in Practise
A TypeScript Fans KotlinJS Adventures
Kotlin - The Swiss army knife of programming languages - Visma Mobile Meet-up...
Building a DRYer Android App with Kotlin
Implicit parameters, when to use them (or not)!
Hadoop + Clojure
jimmy hacking (at) Microsoft
[245] presto 내부구조 파헤치기
Griffon @ Svwjug
Effecient javascript
Ad

More from Haim Yadid (20)

PDF
On-Call AI Assistant: Streamlining Production Error Investigation with LLM
PDF
“Show Me the Garbage!”, Garbage Collection a Friend or a Foe
PDF
Kotlin Backend Development 6 Yrs Recap. The Good, the Bad and the Ugly
PPTX
“Show Me the Garbage!”, Understanding Garbage Collection
PDF
Java Memory Structure
PDF
Basic JVM Troubleshooting With Jmx
PDF
The Freelancer Journey
PDF
Building microservices with Kotlin
PDF
Taking Kotlin to production, Seriously
PDF
Let's talk about Garbage Collection
PDF
JVM Garbage Collection logs, you do not want to ignore them! - Reversim Summi...
PDF
mjprof: Monadic approach for JVM profiling
PDF
Java 8 Launch - MetaSpaces
PDF
Java 8 - Stamped Lock
PDF
The Future of Futures - A Talk About Java 8 CompletableFutures
PDF
Concurrency and Multithreading Demistified - Reversim Summit 2014
PDF
A short Intro. to Java Mission Control
PDF
Java Enterprise Edition Concurrency Misconceptions
PDF
Tales About Scala Performance
PDF
Israeli JUG - IL JUG presentation
On-Call AI Assistant: Streamlining Production Error Investigation with LLM
“Show Me the Garbage!”, Garbage Collection a Friend or a Foe
Kotlin Backend Development 6 Yrs Recap. The Good, the Bad and the Ugly
“Show Me the Garbage!”, Understanding Garbage Collection
Java Memory Structure
Basic JVM Troubleshooting With Jmx
The Freelancer Journey
Building microservices with Kotlin
Taking Kotlin to production, Seriously
Let's talk about Garbage Collection
JVM Garbage Collection logs, you do not want to ignore them! - Reversim Summi...
mjprof: Monadic approach for JVM profiling
Java 8 Launch - MetaSpaces
Java 8 - Stamped Lock
The Future of Futures - A Talk About Java 8 CompletableFutures
Concurrency and Multithreading Demistified - Reversim Summit 2014
A short Intro. to Java Mission Control
Java Enterprise Edition Concurrency Misconceptions
Tales About Scala Performance
Israeli JUG - IL JUG presentation
Ad

Recently uploaded (20)

PPTX
Introduction to Windows Operating System
PDF
AI/ML Infra Meetup | Beyond S3's Basics: Architecting for AI-Native Data Access
PPTX
AMADEUS TRAVEL AGENT SOFTWARE | AMADEUS TICKETING SYSTEM
PPTX
Oracle Fusion HCM Cloud Demo for Beginners
PDF
CCleaner 6.39.11548 Crack 2025 License Key
PDF
Website Design Services for Small Businesses.pdf
PDF
Salesforce Agentforce AI Implementation.pdf
PDF
How Tridens DevSecOps Ensures Compliance, Security, and Agility
PDF
Visual explanation of Dijkstra's Algorithm using Python
PPTX
Computer Software and OS of computer science of grade 11.pptx
PDF
Cost to Outsource Software Development in 2025
PDF
Types of Token_ From Utility to Security.pdf
PDF
iTop VPN Crack Latest Version Full Key 2025
PDF
AI Guide for Business Growth - Arna Softech
PDF
Product Update: Alluxio AI 3.7 Now with Sub-Millisecond Latency
PDF
MCP Security Tutorial - Beginner to Advanced
PPTX
Patient Appointment Booking in Odoo with online payment
PPTX
"Secure File Sharing Solutions on AWS".pptx
PPTX
CNN LeNet5 Architecture: Neural Networks
PPTX
GSA Content Generator Crack (2025 Latest)
Introduction to Windows Operating System
AI/ML Infra Meetup | Beyond S3's Basics: Architecting for AI-Native Data Access
AMADEUS TRAVEL AGENT SOFTWARE | AMADEUS TICKETING SYSTEM
Oracle Fusion HCM Cloud Demo for Beginners
CCleaner 6.39.11548 Crack 2025 License Key
Website Design Services for Small Businesses.pdf
Salesforce Agentforce AI Implementation.pdf
How Tridens DevSecOps Ensures Compliance, Security, and Agility
Visual explanation of Dijkstra's Algorithm using Python
Computer Software and OS of computer science of grade 11.pptx
Cost to Outsource Software Development in 2025
Types of Token_ From Utility to Security.pdf
iTop VPN Crack Latest Version Full Key 2025
AI Guide for Business Growth - Arna Softech
Product Update: Alluxio AI 3.7 Now with Sub-Millisecond Latency
MCP Security Tutorial - Beginner to Advanced
Patient Appointment Booking in Odoo with online payment
"Secure File Sharing Solutions on AWS".pptx
CNN LeNet5 Architecture: Neural Networks
GSA Content Generator Crack (2025 Latest)

Loom me up Scotty! Project Loom - What's in it for Me?