Virtual thread traps to avoid

Java 21 Course · lesson 3 of 15 · 4 min read

Three habits from the platform-thread era that quietly destroy virtual-thread performance.

Open this lesson in the learning hub

Key points

  • Do not pool them. They are cheap to create; a pool caps the very thing that made them useful.
  • Pinning: blocking inside synchronized pins the virtual thread to its carrier. Use ReentrantLock.
  • ThreadLocal: fine for a few hundred threads, wasteful across a million. Scoped values are the answer.
  • CPU-bound work gains nothing - virtual threads help when you are waiting, not when you are computing.
  • Run with -Djdk.tracePinnedThreads=full to see exactly where you are pinned.

Example

import java.util.concurrent.locks.ReentrantLock;

public class Main {
    static final Object MONITOR = new Object();
    static final ReentrantLock LOCK = new ReentrantLock();
    static int viaSync = 0, viaLock = 0;

    public static void main(String[] args) throws Exception {
        // synchronized: correct, but a blocking call inside it PINS the carrier
        Thread a = Thread.ofVirtual().start(() -> {
            for (int i = 0; i < 1000; i++) {
                synchronized (MONITOR) { viaSync++; }
            }
        });

        // ReentrantLock: the virtual thread can unmount while waiting
        Thread b = Thread.ofVirtual().start(() -> {
            for (int i = 0; i < 1000; i++) {
                LOCK.lock();
                try { viaLock++; } finally { LOCK.unlock(); }
            }
        });

        a.join();
        b.join();
        System.out.println("synchronized count : " + viaSync);
        System.out.println("ReentrantLock count: " + viaLock);
        System.out.println("isVirtual          : " + Thread.ofVirtual().unstarted(() -> {}).isVirtual());
    }
}

Virtual threads punish pooling and synchronized - the two habits platform threads taught you.

This is a reading copy. The full lesson — with the visual explainer, the interactive lab and a Run button for the code — lives in the Java 21 Course course, and every lesson in it is listed on the Java 21 Course contents page.