The Resurrection of Virtual Threads: Unraveling Their Journey From JDK 1.1 to JDK 21
As we move forward, virtual threads provide an efficient concurrency model, propelling Java into a new era of multi-threading.
Join the DZone community and get the full member experience.
Join For FreeA few months ago, I penned an article discussing the debut of virtual threads in JDK 21 and their role in enabling the thread-per-request pattern. You can access the full article here.
During my interactions with the readers, I uncovered an intriguing historical tidbit: virtual threads had been introduced previously, way back in the days of JDK 1, only to be subsequently phased out.
To be candid, this was news to me, given my Java journey began in the early 2000s. My curiosity piqued, and I embarked on a quest for insights into the initial introduction and subsequent discontinuation of virtual threads, leading to their remarkable resurgence in JDK 21.
In this article, I will reveal the insights I unearthed during my quest.
Green threads, also known as virtual threads or user-level threads, were originally used in early versions of Java, including JDK 1.0, for concurrency. These threads are managed by a user-level library or runtime system rather than the underlying operating system. They were designed to provide a lightweight way of achieving concurrency without relying on the operating system's native threads.
However, there were several reasons why green threads were dropped after JDK 1.0 in favor of native threads:
- Platform independence: Java's "write once, run anywhere" promise was challenging to uphold with green threads. Green threads were highly dependent on the underlying runtime system, making it difficult to maintain platform independence.
- Limited concurrency: Green threads were not well-suited for applications that required true parallelism, especially on multi-core processors. They couldn't take full advantage of the available hardware resources.
- Scalability: Green threads could not fully leverage modern hardware, as they relied on a single process to handle all threads. Native threads or platform threads, on the other hand, can be distributed across multiple processes.
- Blocking I/O: Green threads couldn't efficiently handle blocking I/O operations. When a green thread blocked on I/O, it would often block all other threads in the process, causing poor performance.
- Portability: Applications using green threads could behave differently on different platforms, making it challenging to ensure consistent behavior across various systems.
- Operating system support: As Java evolved, the use of native threads became more practical due to improvements in operating system support for multithreading. Native threads offered better performance and compatibility with modern systems.
Due to these limitations, Java shifted towards using native threads to improve performance, scalability, and portability. This change resulted in better support for concurrent and parallel programming, making Java more suitable for a wider range of applications and systems.
In JDK 21, Java introduced a new concurrency model based on virtual threads, which can be seen as a reimagined version of green threads. These virtual threads aim to address some of the challenges that green threads faced in earlier versions of Java. While they share similarities with green threads, they are designed with modern solutions in mind. Here's how they address the challenges mentioned:
- Platform independence: Virtual threads maintain platform independence. They are integrated into the Java platform itself and do not rely on external user-level libraries. This ensures that the "write once, run anywhere" principle is upheld.
- Limited concurrency: Virtual threads can provide more concurrency than green threads. They are designed to take advantage of modern multi-core processors, allowing for better parallelism and performance.
- Scalability: Virtual threads can be efficiently scheduled across multiple processors and cores, making them suitable for modern hardware with high scalability.
- Blocking I/O: Virtual threads can efficiently handle blocking I/O operations. When a virtual thread blocks on I/O, it is automatically suspended without affecting the execution of other virtual threads. This improves performance in applications with I/O-bound tasks.
- Portability: The behavior of virtual threads is consistent across different platforms, ensuring that applications using virtual threads will have predictable and reliable performance.
- Operating system support: JDK 21 is designed to work with native threads when necessary, ensuring good compatibility with modern operating systems. It strikes a balance between virtual threads and native threads to optimize performance and resource utilization.
While virtual threads draw inspiration from green threads, they are not a complete reversion to the old green thread model. Instead, they combine the best aspects of both green threads and native threads to provide a more versatile and efficient concurrency model. This approach allows Java to better adapt to contemporary hardware and address the challenges that green threads faced in earlier versions of the language.
Opinions expressed by DZone contributors are their own.
Comments