I got a question about interrupting threads in Java. Say I have a Runnable:
public MyRunnable implements Runnable {
public void run() {
operationOne();
operationTwo();
operationThree();
}
}
I want to implement something like this:
Thread t = new Thread(new MyRunnable());
t.run();
... // something happens
// we now want to stop Thread t
t.interrupt(); // MyRunnable receives an InterruptedException, right?
... // t is has now been terminated.
How can I implement this in Java? Specifically, how do I catch the InterruptedException in MyRunnable?
I recommend testing for Thread.isInterrupted(). Javadoc here. The idea here is that you are doing some work, most likely in a loop. On every iteration you should check if the interrupted flag is true and stop the work.
while(doingWork && !Thread.isInterrupted() {
// do the work
}
Edit: To be clear, your thread won't receive an InterruptedException if the sub tasks are not blocking or worst, eat that exception. Checking for the flag is the right method but not everybody follows it.
First, the 2nd line of your 2nd block of code should be t.start(), not t.run(). t.run() simply calls your run method in-line.
And yes, MyRunnable.run() must check periodically, while it is running, for Thread.currentThread().isInterrupted(). Since many things you might want to do in a Runnable involve InterruptedExceptions, my advice is to bite the bullet and live with them. Periodically call a utility function
public static void checkForInterrupt() throws InterruptedException {
if (Thread.currentThread().isInterrupted())
throw new InterruptedException();
}
EDIT added
Since I see a comment that the poster has no control over the individual operations, his MyRunnable.run() code should look like
public void run() {
operation1();
checkForInterrupt();
operation2();
checkForInterrupt();
operation3();
}
an InterruptedThreadException is only thrown when the thread is being blocked (wait, sleep, etc.) . Otherwise, you'll have to check Thread.currentThread().isInterrupted().
I think the answers above will pretty much fit your problem. I just want to add something on InterruptedException
Javadoc says:
InterruptedException :Thrown when a thread is waiting, sleeping, or
otherwise paused for a long time and another thread interrupts it
using the interrupt method in class Thread.
This means InterruptedException won't be thrown while running
operationOne();
operationTwo();
operationThree();
unless you are either sleeping, waiting for a lock or paused somewhere in these three methods.
EDIT If the provided code can not be changed as suggested by the nice and useful answers around here then I am afraid you have no way of interrupting your thread. As apposed to other languages such as C# where a thread can be aborted by calling Thread.Abort() Java does not have that possibility. See this link to know more about the exact reasons.
First of all, should be class in there
public class MyRunnable extends Thread {
public void run() {
if(!isInterrupted()){
operationOne();
operationTwo();
operationThree();
}
}
}
Would this work better?
Related
How can I lock a method until an other method is invoked?
public class TestLock{
public void methodIsLockedAfterFirstCall(){
doSomething();
//now lockThisMethod (when invoked, the thread shall sleep)
}
public void methodToDoSomethingAfterTheFirstMethod(){
doSomeOtherThing()
//unlock the first Method?
}
}
Is there something already in Java for this or should I do it some way around ( e.g. Boolean or AtomicLong)?
If you want to build this up from base principles you'd do something like:
private final AtomicBoolean lock = new AtomicBoolean();
public void methodIsLockedAfterFirstCall() {
doSomething();
synchronized (lock) {
while (lock.getAndSet(true)) try {
lock.wait();
} catch (InterruptedException e) {
return; // SEE NOTE 1
}
}
}
public void methodToDoSomethingAfterTheFirstMethod() {
doSomeOtherThing();
synchronized (lock) {
lock.set(false):
lock.notifyAll();
}
}
This code:
Uses a private lock. Locking om something public is only acceptable if you document this behaviour and maintain this behaviour for future versions (or mark your new version as utterly incompatible with the old). As a rule, public locks are an error. synchronizing on this, therefore, is usually wrong. This code locks on a private variable.
This code does not run afoul of JMM issues by using AtomicBoolean.
NOTE 1: InterruptedException only ever occurs if you (or other code running on the JVM) explicitly calls .interrupt() on the thread (it does not occur if e.g. the user hits CTRL+C, or killall YourProcess, or 'end task' in the task manager, or any other way that doesn't involve code running in that VM that calls .interrupt(). What to do? Well, do not just e.printStackTrace(), the usual mainstay of java programmers who no idea what they are doing. What did you want to happen when you write thread.interrupt(), somewhere else in the codebase? Do that. If the notion of 'stop waiting for that second call now' is a sensible idea, then document the behaviour in this method. Here I've chosen to just return (stop waiting), but keep the lock in locked state.
Does not use notify/wait as a mechanism to communicate data; only as a mechanism to communicate when to wait and when to stop waiting. This is generally a good idea, it can be very hard to debug relevant state when that state is captured by 'were you notified or not', and makes it impossible to use the wait(timeout) variant. That's why there is a while loop. Being woken up just results in trying to getAndSet again, which can reuslt in waiting some more. That's a good thing.
Or, use something from j.u.concurrent. Some ideas:
A Lock which the first method locks and the second method unlocks.
A Semaphore doesn't sound right, as .release() will add 1 to the count, always, so if you call the second method whilst the 'lock status' is UNLOCKED, you'd erroneously be adding a permit. You can't do if (semaphore.availablePermits() < 1) semaphore.release(); as that'd have a race condition unless you do this in a synchronized block which kinda defeats the purpose.
There is a lot under the java.util.concurrent.locks and java.util.concurrent packages.
Maybe CountDownLatch is the easier one to use:
private final CountDownLatch latch = new CountDownLatch(1);
public class TestLock{
public void methodIsLockedAfterFirstCall() throws InterruptedException {
doSomething();
//now lockThisMethod (when invoked, the thread shall sleep)
latch.await()
}
public void methodToDoSomethingAfterTheFirstMethod(){
doSomeOtherThing()
//unlock the first Method?
latch.countDown();
}
}
let's say I use a jar that IBM has created.
Let's say that this Jar has a function that I need but is ultimately build as such:
while (true) {
System.out.println(1)
}
(of course it doesn't really just printing 1, but for the example let's say it is)
So, I made the call to the function that does it in another thread using future. How can I completely kill the thread that this code is running in? Or alternatively, how can I kill the asynchronous task in Kotlin that runs the code.
Solutions in Kotlin or Java will be great,
thanks in advance!
EDIT:
I've found out, that if this is a thread, I can Thread#stop() it to really make it stop. But unfortunately making the constructor throwing exceptions multiple times, causes the JVM to erase the class from memory causing a NoClassDefFoundError when instantiating the class the next time..
If you can capture it's thread you should be able to kill it so long as it is doing some kind of blocking function internally.
class OtherFunction implements Runnable {
#Override
public void run() {
while(true) {
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
// We assume the thread will exit when interrupted.
System.out.println("Bye!!");
return;
}
System.out.println("Hello");
}
}
}
class Killable implements Runnable {
final Runnable target;
private Thread itsThread;
Killable(Runnable target) {
this.target = target;
}
#Override
public void run() {
// Catch the thread id of the target.
itsThread = Thread.currentThread();
// Launch it.
target.run();
}
public void kill() {
// Give it a good kick.
itsThread.interrupt();
}
}
public void test() throws InterruptedException {
OtherFunction theFunction = new OtherFunction();
Killable killableVersion = new Killable(theFunction);
new Thread(killableVersion).start();
// Wait for a few seconds.
Thread.sleep(10000);
// Kill it.
killableVersion.kill();
}
It seems like Thread#stop() solved my problem. I know it's deprecated and can be prevented with catch(Throwable t) but at least it did the trick for me.
By the way, to get the thread from the executor, I've used AtomicReference<Thread> and set it in the callback.
Thread#stop() is deprecated as 'inherently unsafe' and should be avoided if at all possible.
It's a source of instability and corruption and may fail anyway!
It actually causes a ThreadDeath exception to be throw in the target thread.
The authors of whatever code it pops into are unlikely to have expected that outcome.
Objects may be in an inconsistent state, external resources may be held and get leaked, files may be incompletely written.
There are ways of handling unexpected errors but in practice most code is written assuming it knows which exceptions might be thrown and not in anticipation for such a 'surprise'.
Given ThreadDeath is a Throwable any catch(Throwable t) will catch it and again, unless great care was taken in every piece of code the thread might execute (unrealistic) ThreadDeath might just get absorbed and not end the thread.
The correct way to handle this is declare an atomic variable (usually as part of the Runnable that represents the task.
AtomicBoolean stopThread=new AtomicBoolean(false);
Then write the loop as:
while (!stopThread.get()) {
System.out.println(1);
}
And provide a method:
public void stopThread(){
stopThread.set(true);
}
Alternatively you can use interrupt() and check interrupted(). These are cleaner methods provided in the Thread class. interrupted() has the behaviour of clearing the flag when called. That's not always helpful and while the flag can be examined by Thread.currentThread().isInterrupted() the 'checking the flag clears it' behaviour can be unhelpful and also suffers some of the issues of stop() because it can cause "surprising" exceptions to be throw at points other code has never anticipated. The right approach is to use your own flag and be in full control of where the process decides to quit.
Take your pick.
See also: Java Thread Primitive Deprecation
Ever wondered why when you click 'Cancel' on some concurrent process you are often made to wait ages for it to respond?
This is why. The task needs to come to a well defined point and do any necessary clean up to terminate in a well defined way.
Think of Thread#stop() as like stopping a cyclist by kicking them off their bike. The method here waves a red flag at them and they then come to a halt as swiftly as they safely can.
Thread#stop() should never have been in Java and you should never use it.
You get away with it in development and small systems. It causes havoc in large production environments.
It's not just deprecated as 'not recommended' it is 'inherently unsafe' do not use it.
It's been deprecated for years and its disappointing that some 'removal date' has never been advertised.
Here's an example that uses either Thread#stop() or interrupt() depending on whether you opt for being dangerous.
import java.lang.System;
import java.lang.Thread;
class Ideone
{
private static boolean beDangerous=true;//Indicates if we're going to use the Thread#stop()....
//This main method uses either stop() or interrupt() depending on the option.
public static void main (String[] args) throws java.lang.Exception
{
PrimeFactor factor=new PrimeFactor();
try{
for(int i=1;i<30;++i){
Thread thrd=new Thread(new Primer(factor));
thrd.start();
Thread.sleep(10);//Represents some concurrent processing...
if(beDangerous){
thrd.stop();
}else{
thrd.interrupt();
}
thrd.join();
if(!factor.check()){
System.out.println("Oops at "+i);
}
}
}catch(Throwable t){
System.out.println(t);
}
}
//This class just hammers the PrimeFactor object until interrupt()ed (or stop()ed).
private static class Primer implements Runnable {
private PrimeFactor factor;
public Primer(PrimeFactor ifactor){
factor=ifactor;
}
public void run(){
int i=1;
while(!Thread.interrupted()){
factor.set(i++);
}
}
}
//Don't worry about this bit too much.
//It's a class that does a non-trivial calculation and that's all we need to know.
//"You're not expected to understand this". If you don't get the joke, Google it.
//This class calculates the largest prime factor of some given number.
//Here it represents a class that ensures internal consistency using synchronized.
//But if we use Thread#stop() this apprently thread-safe class will be broken.
private static class PrimeFactor {
private long num;
private long prime;
public static long getFactor(long num){
if(num<=1){
return num;
}
long temp=num;
long factor=2;
for(int i=2;temp!=1;++i){
if(temp%i==0){
factor=i;
do{
temp=temp/i;
}while(temp%i==0);
}
}
return factor;
}
public synchronized void set(long value){
num=value;
prime=getFactor(value);
}
public synchronized boolean check(){
return prime==getFactor(num);
}
}
}
Typical partial output:
Oops at 1
Oops at 2
Oops at 3
Oops at 6
Oops at 8
Notice that the PrimeFactor class can be described as thread-safe. All it's methods are synchronized. Imagine it's in some library. It's unrealistic to expect "thread-safe" to mean Thread#stop()-safe and the only way to do that would be intrusive. Putting calls to it in a try-catch(ThreadDeath tde) block won't fix anything. The damage will have been down before it's caught.
Don't convince yourself that changing set() to the following solves it:
public synchronized void set(long value){
long temp=getFactor(value);
num=value;
prime=temp;
}
First and foremost the the ThreadDeath exception could throw during the assignments so all that does is potentially shorten the odds on the Race Condition. It hasn't been negated. Never make "how likely is that to happen" arguments about race conditions. Programs call methods billions of times so billion to one-shots come up regularly.
To use Thread#stop() you can essentially never use any library objects including java.* and jump through hoops to handle ThreadDeath everywhere in your code and almost certainly eventually fail anyway.
In java there is no official way of killing thread. This is bug. (no need to argue with it here) Thread#stop() should not be deprecated. It may be improved that it cannot be consumed. Even now it will work most of the time just fine.
Right now, if I write function which will be executed with kill need, I would start new thread and joint to it with timeout or other disconnect mechanism. This will make your code to continue like main thread was killed. Problem is that main thread is still running. All resources are still in use. This is still better than application being frozen. Calling thread.interrupt() is first step but it this does not work using thread.stop() is adequate here. It won't make things worse.
If you really must kill the thread, only way would be to start another jvm via jni, run unsafe code there and use linux kill -9 to stop the whole process if needed.
I believe killing thread is perfectly possible, only jvm developers didn't care enough. I get into this situation all the time and answers like don't use any libraries, fix all foreign code, write your own language or live with it are just frustrating.
This question already has answers here:
Do I need to synchronize a call to the interrupt method?
(3 answers)
Closed 5 years ago.
I have this kind of code:
class Foo {
private final Thread mainThread = ...;
public void start() { this.mainThread.start(); }
public void stop() { this.mainThread.interrupt(); }
}
Note that Foo.mainThread is kind enough to check every now and then if it was interrupted by someone, and in the case it cleanly exits.
Now in my application there are many threads that share a Foo and are possibly interested in stopping it. Is everything OK or should I be paranoid and declare Foo.stop() to be a synchronized method?
Thread.interrupt basically just sets a flag. Certain operations, such as Thread.sleep will cause this flag to be checked, and an exception is thrown if the flag is set to true.
Provided you're handling InterruptedExceptions
properly*, there's no reason why two threads both setting the flag would be a problem.
So no. Don't bother synchronizing stop.
You probably do want to synchronize start, though. Starting a thread twice will result in a IllegalThreadStateException. I'd re-write that function like so**:
private boolean started = false;
public void start()
{
if (started) return;
synchronized(this)
{
if (!started)
{
this.mainThread.start();
started = true;
}
}
}
Here's a good article which explains how Thread.interrupt works.
*By 'properly' I mean don't do anything strange, like perform an operation which can throw an InterruptedException while you're handling an InterruptedException. That would be silly.
**A simpler solution would synchronize the whole method, but may result in synchronizing too often. This way, we only synchronize if two threads both compete to start an un-started thread at exactly the same time, and never synchronize after that.
I wrote a test app that should never stop. It issues t.wait() (t is a Thread object), but I never call notify. Why does this code end?
Despite the main thread synchronizing on t, the spawned thread runs, so it doesn't lock this object.
public class ThreadWait {
public static void main(String sArgs[]) throws InterruptedException {
System.out.println("hello");
Thread t = new MyThread();
synchronized (t) {
t.start();
Thread.sleep(5000);
t.wait();
java.lang.System.out.println("main done");
}
}
}
class MyThread extends Thread {
public void run() {
for (int i = 1; i <= 5; i++) {
java.lang.System.out.println("" + i);
try {
Thread.sleep(500);
} catch (Exception e) {
throw new RuntimeException(e);
}
}
}
}
The result is that the main thread waits 5 seconds and during this time worker gives its output. Then after 5 seconds are finished, the program exits. t.wait() does not wait. If the main thread wouldn't sleep for 5 seconds (commenting this line), then t.wait() would actually wait until the worker finishes. Of course, join() is a method to use here, but, unexpectedly, wait() does the same thing as join(). Why?
Maybe the JVM sees that, since only one thread is running, there is no chance to notify the main thread and solves the deadlock. If this is true, is it a documented feature?
I'm testing on Windows XP, Java 6.
You're waiting on a Thread - and while most objects aren't implicitly notified, a Thread object is notified when the thread terminates. It's documented somewhere (I'm looking for it...) that you should not use wait/notify on Thread objects, as that's done internally.
This is a good example of why it's best practice to use a "private" object for synchronization (and wait/notify) - something which only your code knows about. I usually use something like:
private final Object lock = new Object();
(In general, however, it's cleaner to use some of the higher-level abstractions provided by java.util.concurrent if you can. As noted in comments, it's also a good idea to implement Runnable rather than extending Thread yourself.)
The JavaDoc for wait gives the answer: spurious wakeups are possible. This means the JVM is free to end a call to wait whenever it wants.
The documentation even gives you a solution if you don't want this (which is probably always the case): put the call to wait in a loop and check whether the condition you wait for has become true after every wakeup.
I want to write a command line daemon that runs forever. I understand that if I want the JVM to be able to shutdown gracefully in linux, one needs to wrap the bootstrap via some C code. I think I'll be ok with a shutdown hook for now.
On to my questions:
My main(String[]) block will fire off a separate Superdaemon.
The Superdaemon will poll and loop forever.
So normally I would do:
class Superdaemon extends Thread { ... }
class Bootstrap
{
public static void main( String[] args )
{
Thread t = new Superdaemon();
t.start();
t.join();
}
}
Now I figured that if I started Superdaemon via an Executor, I can do
Future<?> f = exec.submit( new Superdaemon() );
f.get();
Is Future.get() implemented with Thread.join() ?
If not, does it behave equivalently ?
Regards,
ashitaka
Yes, the way you've written these is equivalent.
However, you don't really need to wait for the Superdaemon thread to complete. When the main thread finishes executing main(), that thread exits, but the JVM will not. The JVM will keep running until the last non-daemon thread exits its run method.
For example,
public class KeepRunning {
public static void main(String[] args) {
Superdaemon d = new Superdaemon();
d.start();
System.out.println(Thread.currentThread().getName() + ": leaving main()");
}
}
class Superdaemon extends Thread {
public void run() {
System.out.println(Thread.currentThread().getName() + ": starting");
try { Thread.sleep(2000); } catch(InterruptedException e) {}
System.out.println(Thread.currentThread().getName() + ": completing");
}
}
You'll see the output:
main: leaving main()
Thread-0: starting
Thread-0: completing
In other words, the main thread finishes first, then the secondary thread completes and the JVM exits.
The issue is that books like JCIP is advocating that we use Executors to starts Threads. So I'm trying my best not to use Thread.start(). I'm not sure if I would necessarily choose a particular way of doing things just based on simplicity. There must be a more convincing reason, no ?
The convincing reason to use java.util.concurrent is that multi-threaded programming is very tricky. Java offers the tools to that (Threads, the synchronized and volatile keywords), but that does not mean that you can safely use them directly without shooting yourself in the foot: Either too much synchronization, resulting in unnecessary bottlenecks and deadlocks, or too less, resulting in erratic behaviour due to race conditions).
With java.util.concurrent you get a set of utilities (written by experts) for the most common usage patterns, that you can just use without worrying that you got the low-level stuff right.
In your particular case, though, I do not quite see why you need a separate Thread at all, you might as well use the main one:
public static void main( String[] args )
{
Runnable t = new Superdaemon();
t.run();
}
Executors are meant for tasks that you want to run in the background (when you have multiple parallel tasks or when your current thread can continue to do something else).
Future.get() will get the future response from an asynchronous call. This will also block if the call has not been completed yet. It is much like a thread join.
http://java.sun.com/j2se/1.5.0/docs/api/java/util/concurrent/Future.html
Sort'a. Future.get() is for having a thread go off and calculate something and then return it to the calling thread in a safe fashion. It'd work if the get never returned. But, I'd stick with the join call as it's simpler and no Executer overhead (not that there would be all that much).
Edit
It looks like ExecutorService.submit(Runnable) is intended to do exectly what you're attempting. It just returns null when the Runnable completes. Interesting.