0

I've an exe program placed on shared location. It doesn't take any arguments while starting. When it is launched in a command window, it displays a help menu with list of commands that can be executed with it and ends with > expecting an input command. I need to execute one particular command called TRIGGER from that list. So far this is what I've but it fails completely. It neither displays the output from the process nor takes the input command trigger from the stream.

public void execute(){

    String cmd = "\\\\sharedLocation\\server\\adm.exe";
    p = Runtime.getRuntime().exec(cmd);

    InputStream in = p.getInputStream();
    OutputStream out = p.getOutputStream();

    BufferedReader br= new BufferedReader(new InputStreamReader(in));
    BufferedWriter bw = new BufferedWriter(new OutputStreamWriter(out));

    bw.write("TRIGGER");            
    bw.flush();

    String output = "";
    while (!output.endsWith(">")) {     
        System.out.println("in loop");
        output = output + br.readLine(); 
    }

    System.out.println("Out"+output);


    out.close();            
    p.waitFor();
}

EDIT : adm.exe is launched by this program but it appears that adm.exe is a blocking process. It fails to println the "in loop" statement. However when I open up windows task manager and kill the adm.exe process tree, this shows up on the console

in loopnull
in loopnullnull
in loopnullnullnull
in loopnullnullnullnull
in loopnullnullnullnullnull
in loopnullnullnullnullnullnull
in loopnullnullnullnullnullnullnull
in loopnullnullnullnullnullnullnullnull
in loopnullnullnullnullnullnullnullnullnull
in loopnullnullnullnullnullnullnullnullnullnull
in loopnullnullnullnullnullnullnullnullnullnullnull
in loopnullnullnullnullnullnullnullnullnullnullnullnull
in loopnullnullnullnullnullnullnullnullnullnullnullnullnull
in loopnullnullnullnullnullnullnullnullnullnullnullnullnullnull
in loopnullnullnullnullnullnullnullnullnullnullnullnullnullnullnull
in loopnullnullnullnullnullnullnullnullnullnullnullnullnullnullnullnull
in loopnullnullnullnullnullnullnullnullnullnullnullnullnullnullnullnullnull
in loopnullnullnullnullnullnullnullnullnullnullnullnullnullnullnullnullnullnull
Outnullnullnullnullnullnullnullnullnullnullnullnullnullnullnullnullnullnullnullnull
Vamsi Emani
  • 10,072
  • 9
  • 44
  • 71

2 Answers2

1

Not sure but...

Timing

I understand that your execute method gets blocked at while waiting for some output and its finalization. It will not came until you send TRIGGER.

I would try to

  1. Send TRIGGER before (you will not lose any data, it gets buffered)
  2. At the end of method use p.waitFor() to avoid exiting until p finishes (well, anyway the while does that).

Edit

Does your adm.exe needs TRIGGER written in UTF-16? Because that's what you're sending if you use getBytes(). If you need another encoding (like UTF-8 or ASCII) try with getBytes("UTF-8") by example.

Sample

I should do something like:

public void execute() {

String cmd = "\\\\sharedLocation\\server\\adm.exe";
Process p = Runtime.getRuntime().exec(cmd);     

// send TRIGGER before everything (I can't consume the response if I don't ask for it first)
OutputStream out = p.getOutputStream();
out.write("TRIGGER".getBytes());
out.flush(); // flush to ensure it's sent, but don't close...

InputStream in = p.getInputStream();

String output = "";
int c = 0;
while (!output.endsWith(">")){
    c = in.read(); // you've eaten this when modified your code
    output+= (char)c; // I should change the way bytes convert to char, but that's another story
}

System.out.println(output);


// optional: if I want to wait for p to finish
p.waitFor();
}
helios
  • 13,574
  • 2
  • 45
  • 55
  • yeah you are right. I've changed the condition for while but strangely still it doesn't execute the loop as you said. Any guesses why? – Vamsi Emani Jul 23 '12 at 10:37
  • I wasn't complaining about the condition, but about placing the while *before* sending `TRIGGER`. I'll put an example... – helios Jul 23 '12 at 11:20
  • I've added a detail: use `flush` not `close` – helios Jul 23 '12 at 11:24
  • 2
    And... the adm.exe only needs `TRIGGER`? doesn't it need `TRIGGER\n`, `TRIGGER\r\n` or something? Maybe it's reading lines... – helios Jul 23 '12 at 11:25
  • why don't you use expectj for such tasks? it would be much easier? – tartar Jul 23 '12 at 11:31
1

Some general comments:

  1. Don't use Process, use ProcessBuilder instead. And if you want to do something more complex than starting an external process, use Commons Exec.

  2. What happens if you just type TRIGGER on the command line without pressing Return? If nothing happens, press return from Java, too: Wrap out in a PrintStream and use pw.println("TRIGGER")

  3. Since you don't get any output, maybe the command notices that it's not being started from a command prompt and behaves differently? If that's the case, run it with cmd /c \\\\sharedLocation\\server\\adm.exe

  4. Always use lists/arrays to supply command arguments to avoid problems with special characters

Aaron Digulla
  • 321,842
  • 108
  • 597
  • 820