1

I'm trying to make program which runs some executable program(call it p), given time limit t ms. It does following tasks:

  1. If program p has executed normally, print it's output to console.
  2. If program p couldn't execute completely within time limit, print "Sorry, needs more time!" and then terminate execution of p.
  3. If program p has terminated abnormally (e.g. RuntimeError), print "Can I've some debugger?"

I'm using ProcessResultReader class in the following program from here. My program is working as long as p finishes it's execution normally or terminate abnormally. But, it doesn't terminate if p itself doesn't terminate after timeout.(Try p with simple while(true) loop with no exit condition). It seems that thread stdout is alive even after execution of stdout.stop(). What am I doing wrong in this code?

Thanks.

import java.util.concurrent.TimeUnit;
import java.io.*;

class ProcessResultReader extends Thread
{

    final InputStream is;
    final StringBuilder sb;

    ProcessResultReader(final InputStream is)
    {
        this.is = is;
        this.sb = new StringBuilder();
    }
    public void run()
    {
        try
        {
            final InputStreamReader isr = new InputStreamReader(is);
            final BufferedReader br = new BufferedReader(isr);
            String line = null;
            while ((line = br.readLine()) != null)
            {
                this.sb.append(line).append("\n");
            }
        }
        catch (final IOException ioe)
        {
            System.err.println(ioe.getMessage());
            throw new RuntimeException(ioe);
        }
    }

    @Override
    public String toString()
    {
        return this.sb.toString();
    }
    public static void main(String[] args) throws Exception
    {
        int t = 1000; 
        Process p = Runtime.getRuntime().exec(cmd); //cmd is command to execute program p 
        ProcessResultReader stdout = new ProcessResultReader(p.getInputStream());
        stdout.start();
        if(!p.waitFor(t, TimeUnit.MILLISECONDS))
        {
            stdout.stop();
            p.destroy();
            System.out.println("Sorry, needs more time!");
        }
        else
        {
            if(p.exitValue()==0) System.out.println(stdout.toString());
            else System.out.println("Can I've some debugger?");
        }
    }
}
Community
  • 1
  • 1
user148865
  • 326
  • 1
  • 5
  • 19
  • 1
    I know [this](http://stackoverflow.com/a/2733370/1858327) isn't exactly what you're looking for but it seems like it could help or at least point you in the right direction. – Captain Man Apr 28 '15 at 15:39

1 Answers1

0

According to java docs, stdout.stop() was deprecated and even stdout.destroy() is never implemented.

For more information, see Why are Thread.stop, Thread.suspend and Thread.resume Deprecated?.

you could try this instead.

String cmd="cmd /c sleep 5";
    int timeout = 1; 
    Process p = Runtime.getRuntime().exec(cmd); //cmd is command to execute program p 
    ProcessResultReader stdout = new ProcessResultReader(p.getInputStream());
    stdout.start();
    if(!p.waitFor(timeout, TimeUnit.MILLISECONDS))
    {
        stdout.stop();
        p.destroy();
        System.out.println("Sorry, needs more time!");
        System.out.flush();
    }
    else
    {
        if(p.exitValue()==0) System.out.println(stdout.toString());
        else System.out.println("Can I've some debugger?");
    }
RayYen
  • 13
  • 4
  • I'm aware that `stop()` is deprecated. Note that I want to terminate execution of `p` when timeout occurs, not main. else, I would have used `System.exit`. – user148865 Apr 28 '15 at 16:49