JDK-8221892 : ThreadPoolExecutor: Thread.isAlive() is not equivalent to not being startable
  • Type: Bug
  • Component: core-libs
  • Sub-Component: java.util.concurrent
  • Affected Version: 8,11,13
  • Priority: P3
  • Status: Resolved
  • Resolution: Fixed
  • Submitted: 2019-04-03
  • Updated: 2020-04-08
  • Resolved: 2019-05-02
The Version table provides details related to the release that this issue/RFE will be addressed.

Unresolved : Release in which this issue/RFE will be addressed.
Resolved: Release in which this issue/RFE has been resolved.
Fixed : Release in which this issue/RFE has been fixed. The release containing this fix may be available for download as an Early Access Release or a General Availability Release.

To download the current JDK release, click here.
JDK 11 JDK 13
11.0.5Fixed 13 b20Fixed
Related Reports
Relates :  
Relates :  
Description
As referenced by Thomas Stuefe in:

http://mail.openjdk.java.net/pipermail/hotspot-runtime-dev/2019-April/033512.html

ThreadPoolExecutor.addWorker has:

 if (t.isAlive()) // precheck that t is startable
         throw new IllegalThreadStateException();

but that is not a sufficient check for being "startable" as a thread that has already terminated is "not alive". If such a thread is then "started" the code will throw IllegalThreadStateException without doing proper cleanup of the worker list.
Comments
Fix Request (11u) Fixes implementation corner case in TPE code. Applies cleanly to 11u, passes tier1, tier2.
02-07-2019

Yes, an antagonistic thread factory could return a thread that has already terminated, so the check thread.getState() == Thread.State.NEW is better.
03-04-2019