Thread.interrupted() is always false in debugger

Chris Plummer chris.plummer at oracle.com
Tue Aug 20 16:27:07 UTC 2024


The presence of the breakpoint likely results in the debug agent 
executing code that does a JVMTI RawMonitorWait. However, there is code 
in place in the debug agent to repost the interrupt if it happens before 
or during the wait. See the code and comment in debugMonitorWait() and 
its call to handleInterrupt(), which calls 
threadControl_setPendingInterrupt(). It seems this code is failing somehow.


There were changes during JDK 23 in this area for virtual thread 
support, and the changes possibly could impact platform threads also. 
See JDK-8324868 <https://bugs.openjdk.org/browse/JDK-8324868> and 
JDK-8325187 <https://bugs.openjdk.org/browse/JDK-8325187>. It would be 
worth trying with the latest sources to see if the issue is still 
reproducible.


Regarding calling Thread.currentThread() from the watch panel, the use 
of the JDI method invocation support can change the state of the program 
being debugged. So if you do an invoke on the interrupted thread, it 
would not surprise me if the interrupt got cleared as a result, and I 
think this is to be expected.


Chris


On 8/20/24 6:47 AM, Gillespie, Oli wrote:
>
> There are lots of paths that clear the interrupted flag. In your 
> example, I hit at least this one when calling Thread.currentThread 
> from the watch panel:
>
> ```
>
>     at java.base/java.lang.Thread.interrupted(Thread.java:1030)
>     at java.base/jdk.internal.loader.Resource.getBytes(Resource.java:96)
>     at 
> java.base/jdk.internal.loader.URLClassPath$JarLoader$2.getBytes(URLClassPath.java:895)
>     at 
> java.base/jdk.internal.loader.BuiltinClassLoader.defineClass(BuiltinClassLoader.java:859)
>     at 
> java.base/jdk.internal.loader.BuiltinClassLoader.findClassOnClassPathOrNull(BuiltinClassLoader.java:760)
>     at 
> java.base/jdk.internal.loader.BuiltinClassLoader.loadClassOrNull(BuiltinClassLoader.java:681)
>     at 
> java.base/jdk.internal.loader.BuiltinClassLoader.loadClass(BuiltinClassLoader.java:639)
>     at 
> java.base/jdk.internal.loader.ClassLoaders$AppClassLoader.loadClass(ClassLoaders.java:188)
>     at java.base/java.lang.ClassLoader.loadClass(ClassLoader.java:525)
>     at java.base/java.lang.Class.forName0(Native Method)
>     at java.base/java.lang.Class.forName(Class.java:467)
>
> ```
>
> but the key for your example seems to be 
> https://github.com/openjdk/jdk17u/blob/master/src/hotspot/share/prims/jvmtiRawMonitor.cpp 
> <https://github.com/openjdk/jdk17u/blob/master/src/hotspot/share/prims/jvmtiRawMonitor.cpp>. 
> If you replace is_interrupted(true) with is_interrupted(false) in the 
> 3 calls from that file, your example works as you expect. That might 
> help your investigations.
>
> Oli
> ------------------------------------------------------------------------
> *From:* serviceability-dev <serviceability-dev-retn at openjdk.org> on 
> behalf of Egor Ushakov <egor.ushakov at jetbrains.com>
> *Sent:* 20 August 2024 13:32:36
> *To:* serviceability-dev
> *Subject:* [EXTERNAL] Thread.interrupted() is always false in debugger
>
> *CAUTION*: This email originated from outside of the organization. Do 
> not click links or open attachments unless you can confirm the sender 
> and know the content is safe.
>
>
> Hi everyone!
>
> we have a long standing issue 
> https://youtrack.jetbrains.com/issue/IDEA-169706
> Maybe someone could clarify why it happens and if there's a possible 
> workaround.
> Here's the simplified test case:
> public class Interruption {
>      public static void main(String[]args) {
>          Thread thread =Thread.currentThread();
>          thread.interrupt();
>
>          if (Thread.interrupted()) { // <----- stop on a breakpoint here
>              System.out.println("Interrupted");
>          }else {
>              System.out.println("Not interrupted");
>          }
>      }
> }
>
> Obviously the program prints:
> Interrupted But if stopped on a breakpoint in the debugger, evaluation of
> Thread.interrupted() always returns false.
> More of that/interrupted /field value in the thread object is also reported as false:
>
>
> If interrupted method is debugged step by step it is obvious that interrupted value is true,
> but the debugger continue to show it as false.
>
> Any ideas why it could happen and how to fix it?
>
> Thanks!
> Egor
>
>
>
> Amazon Development Centre (London) Ltd.Registered in England and Wales 
> with registration number 04543232 with its registered office at 1 
> Principal Place, Worship Street, London EC2A 2FA, United Kingdom.
>
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <https://mail.openjdk.org/pipermail/serviceability-dev/attachments/20240820/d0208e3c/attachment-0001.htm>
-------------- next part --------------
A non-text attachment was scrubbed...
Name: U29ugEUZ0HjcKutG.png
Type: image/png
Size: 122053 bytes
Desc: not available
URL: <https://mail.openjdk.org/pipermail/serviceability-dev/attachments/20240820/d0208e3c/U29ugEUZ0HjcKutG-0001.png>


More information about the serviceability-dev mailing list