2
votes

I am working on a strange bug in our implementation of ArcGIS maps. Recently, I've noticed that our software works properly when I put a breakpoint in certain place and run application in debug mode (probably we are facing concurrency/thread issue). After the breakpoint is hit, I immediately (1-2 seconds) resume application and everything on map draws perfectly. However, when I replace breakpoint with Thread.sleep(2000); and run application, the bug is still there.

To me its really weird, I thought both things would do exactly the same. The breakpoint is set to "Suspend Thread" and I use Eclipse IDE.

What is the difference between put thread to sleep and suspend thread in Java?

EDIT: I don't ask for this specific bug solution. I just want to know what's the difference in execution of program in these two cases:

Case 1

  1. open Eclipse IDE
  2. put breakpoint at the line X
  3. debug as... My Program
  4. ButtonEvent, program hits breakpoint at line X
  5. I click on resume button in Eclipse

Case 2

  1. open Eclipse IDE
  2. put Thread.sleep(2000) at the very beginning of line X
  3. debug as... My Program
  4. ButtonEvent

Pasting code here will make no difference since I am not asking about any particular code execution scenario, I am just only interested whether JVM treats breakpoints in the same way as it treats Thread.sleep(). What is happening in JVM when thread is put to sleep for a particular time? What is happening in JVM when thread is put to suspend (by hitting breakpoint)? Is there any difference?

2
we dont see any code. this question is too broad without any info. please add your code so we can understand your error - Dima
There is no code to attach. Example would be to complicated and it can take about month to produce SSCCE . I am asking strictly about diff's in Thread.sleep() and breakpoint - kukis
if there is no code, there is no answer... Thread.sleep puts the thread to sleep. breakpoint puts all the threads that gets to it on hold. - Dima
It's not just about sleep() vs. a breakpoint. You should be asking, what's the difference between running the program in a debugger and running it normally (whatever "normal" means). Have you tried it in the debugger using the sleep() call instead of a breakpoint? I don't know how you normally run the program, and I don't know how your Eclipse is set up, and I don't know a whole lot about Java debuggers; so for all I know, when you run in the debugger, it could be an entirely different JVM. - Solomon Slow
A different JVM should not make a difference if your program is correct, but it could make a world of difference if your program has concurrency bugs. - Solomon Slow

2 Answers

4
votes

There are some fairly big differences, yes.

Thread.sleep requests the OS to remove the thread from CPU scheduling for n millis. Note that the impact of this is OS specific, and is mostly limited to the one thread.

Entering a break point requires activating the JVM's Debug Mode, which affects the behavior of the JVM as a whole and thus affects timings/races. AMD has documented the performance effects of putting the JVM into debug mode. The effects do vary, and a lot of them come down communication between JVM and debugger and limiting the optimizations that the JVM is allowed to make when in debug mode. The most extreme example is to not let the JVM use native byte codes for some methods, thus forcing it to use the much slower interpreter. However the most important difference from the point of view of this question is that debuggers offer the ability to halt a single thread or multiple threads.

There is a big difference between a thread requesting to go to sleep, and a thread causing another thread to become blocked. In Java, it requires co-operation between threads to halt a thread, even for a break point. In the case of a break point, the co-operation is done for us by the JVM and it only occurs when a thread reaches a safe point. Safe points do not occur at every line of code, and thus will affect race conditions quite strongly as the JVM has to wait for a thread to reach a safe point before it can be halted and the debugger can take over. Safe points typically happen where method calls and the back edges of loops (but not always).

0
votes

I think that suspend will force you to use Thread.resume() to reactivate the Thread, while you don't have to do that if using Thread.sleep().

From the API, about resume(): "This method puts a thread in suspended state and can be resumed using resume() method."

Sleep will only stop it, but then you won't have to activate it again.

Hope it helps.