Velocity Reviews

Velocity Reviews (http://www.velocityreviews.com/forums/index.php)
-   Java (http://www.velocityreviews.com/forums/f30-java.html)
-   -   Runtime.exec(cmd) hangs up (http://www.velocityreviews.com/forums/t509355-runtime-exec-cmd-hangs-up.html)

Vic 05-24-2007 10:43 PM

Runtime.exec(cmd) hangs up
 
I am having a problem with Runtime.exec(cmd) where cmd is a string and
is as follows -

cmd = "home/qaplay/loader/604/soaploaderclient.ps nemo 50624 55604
genevaman qa /home/vpatanka/604Current/lib/loader/data/
DuplicateTransactionTest.0.lrd -bcp > & $GVHOME/tempOut.txt"


The actual code is like this ->
public CommandExecuter (String cmd) throws java.io.IOException{
System.out.println("CommandExecuter: EXECUTING COMMAND: "+cmd);
Process proc = Runtime.getRuntime().exec(cmd);

BufferedReader in = new BufferedReader(new
InputStreamReader(proc.getInputStream()));
BufferedReader err = new BufferedReader(new
InputStreamReader(proc.getErrorStream()));

stdout = "";
while ((line = in.readLine()) != null)
stdout += line +"\n";
if (stdout == "")
stdout = null;

stderr = "";
while ((line = err.readLine()) != null)
stderr += line +"\n";
if (stderr == "")
stderr = null;

//System.out.println ("CommandExecuter stdout="+stdout);
//System.out.println ("CommandExecuter stderr="+stderr);
}
}

I can run the same cmd on the shell and I get a an output which is
pretty big so I am not copying it over here but if you guyz need it
then I can do that. Please let me know what am I missing here in
Runtime.exec() or its something else


Vic 05-24-2007 10:55 PM

Re: Runtime.exec(cmd) hangs up
 
one correction -
cmd = "home/qaplay/loader/604/soaploaderclient.ps nemo 50624 55604
genevaman qa /home/vpatanka/604Current/lib/loader/data/
DuplicateTransactionTest.0.lrd -bcp"

On May 24, 3:43 pm, Vic <vikra...@gmail.com> wrote:
> I am having a problem with Runtime.exec(cmd) where cmd is a string and
> is as follows -
>
> cmd = "home/qaplay/loader/604/soaploaderclient.ps nemo 50624 55604
> genevaman qa /home/vpatanka/604Current/lib/loader/data/
> DuplicateTransactionTest.0.lrd -bcp > & $GVHOME/tempOut.txt"
>
> The actual code is like this ->
> public CommandExecuter (String cmd) throws java.io.IOException{
> System.out.println("CommandExecuter: EXECUTING COMMAND: "+cmd);
> Process proc = Runtime.getRuntime().exec(cmd);
>
> BufferedReader in = new BufferedReader(new
> InputStreamReader(proc.getInputStream()));
> BufferedReader err = new BufferedReader(new
> InputStreamReader(proc.getErrorStream()));
>
> stdout = "";
> while ((line = in.readLine()) != null)
> stdout += line +"\n";
> if (stdout == "")
> stdout = null;
>
> stderr = "";
> while ((line = err.readLine()) != null)
> stderr += line +"\n";
> if (stderr == "")
> stderr = null;
>
> //System.out.println ("CommandExecuter stdout="+stdout);
> //System.out.println ("CommandExecuter stderr="+stderr);
> }
>
> }
>
> I can run the same cmd on the shell and I get a an output which is
> pretty big so I am not copying it over here but if you guyz need it
> then I can do that. Please let me know what am I missing here in
> Runtime.exec() or its something else




Vic 05-24-2007 11:05 PM

Re: Runtime.exec(cmd) hangs up
 
type
cmd = "home/qaplay/loader/604/soaploaderclient.ps nemo 50624 55604
genevaman qa /home/vpatanka/604Current/lib/loader/data/
DuplicateTransactionTest.0.lrd -bcp"
On May 24, 3:43 pm, Vic <vikra...@gmail.com> wrote:
> I am having a problem with Runtime.exec(cmd) where cmd is a string and
> is as follows -
>
> cmd = "home/qaplay/loader/604/soaploaderclient.ps nemo 50624 55604
> genevaman qa /home/vpatanka/604Current/lib/loader/data/
> DuplicateTransactionTest.0.lrd -bcp > & $GVHOME/tempOut.txt"
>
> The actual code is like this ->
> public CommandExecuter (String cmd) throws java.io.IOException{
> System.out.println("CommandExecuter: EXECUTING COMMAND: "+cmd);
> Process proc = Runtime.getRuntime().exec(cmd);
>
> BufferedReader in = new BufferedReader(new
> InputStreamReader(proc.getInputStream()));
> BufferedReader err = new BufferedReader(new
> InputStreamReader(proc.getErrorStream()));
>
> stdout = "";
> while ((line = in.readLine()) != null)
> stdout += line +"\n";
> if (stdout == "")
> stdout = null;
>
> stderr = "";
> while ((line = err.readLine()) != null)
> stderr += line +"\n";
> if (stderr == "")
> stderr = null;
>
> //System.out.println ("CommandExecuter stdout="+stdout);
> //System.out.println ("CommandExecuter stderr="+stderr);
> }
>
> }
>
> I can run the same cmd on the shell and I get a an output which is
> pretty big so I am not copying it over here but if you guyz need it
> then I can do that. Please let me know what am I missing here in
> Runtime.exec() or its something else




Matt Humphrey 05-25-2007 12:33 AM

Re: Runtime.exec(cmd) hangs up
 

"Vic" <vikrantp@gmail.com> wrote in message
news:1180046607.237152.145810@r19g2000prf.googlegr oups.com...
|I am having a problem with Runtime.exec(cmd) where cmd is a string and
| is as follows -
|
| cmd = "home/qaplay/loader/604/soaploaderclient.ps nemo 50624 55604
| genevaman qa /home/vpatanka/604Current/lib/loader/data/
| DuplicateTransactionTest.0.lrd -bcp > & $GVHOME/tempOut.txt"
|
|
| The actual code is like this ->
| public CommandExecuter (String cmd) throws java.io.IOException{
| System.out.println("CommandExecuter: EXECUTING COMMAND: "+cmd);
| Process proc = Runtime.getRuntime().exec(cmd);
|
| BufferedReader in = new BufferedReader(new
| InputStreamReader(proc.getInputStream()));
| BufferedReader err = new BufferedReader(new
| InputStreamReader(proc.getErrorStream()));
|
| stdout = "";
| while ((line = in.readLine()) != null)
| stdout += line +"\n";
| if (stdout == "")
| stdout = null;
|
| stderr = "";
| while ((line = err.readLine()) != null)
| stderr += line +"\n";
| if (stderr == "")
| stderr = null;

The first thing that I see is that your command contains io redirection.
You have to invoke a shell in order to use those operators--you don't get
one automatically. Also, you can find the details elsewhere on the web or
the cljp past messages, but reading stdout and then reading stderr will not
solve the blocking problem. Both must be read simultaneously because if
either fills up its OS pipe buffer, your exec cmd will be automatically
suspended to give your Java reader a chance to empty the buffer. However,
your Java program will be waiting for output which will never arrive. In
this case, the stderr buffer could fill up and suspend the process while
your Java program waits for more output. There are a variety of tools and
techniques to help with this nowadays.

Matt Humphrey matth@ivizNOSPAM.com http://www.iviz.com/



Vic 05-25-2007 12:44 AM

Re: Runtime.exec(cmd) hangs up
 
Matt,
Thanks for a reply. I actually typed cmd incorrectly which I fixed in
the same post later on. sorry about that

cmd = ""home/qaplay/loader/604/soaploaderclient.ps nemo 50624 55604
genevaman qa /home/vpatanka/604Current/lib/loader/data/
DuplicateTransactionTest.0.lrd -bcp"

I think I know what you are talking about. Are you talking about
StreamGobbler or something of that sort? I did google it for my
problem and saw a few posts talking about it so just wondering.
I'll try it out n will get back to you soon. Thanks

On May 24, 5:33 pm, "Matt Humphrey" <m...@ivizNOSPAM.com> wrote:
> "Vic" <vikra...@gmail.com> wrote in message
>
> news:1180046607.237152.145810@r19g2000prf.googlegr oups.com...
> |I am having a problem with Runtime.exec(cmd) where cmd is a string and
> | is as follows -
> |
> | cmd = "home/qaplay/loader/604/soaploaderclient.ps nemo 50624 55604
> | genevaman qa /home/vpatanka/604Current/lib/loader/data/
> | DuplicateTransactionTest.0.lrd -bcp > & $GVHOME/tempOut.txt"
> |
> |
> | The actual code is like this ->
> | public CommandExecuter (String cmd) throws java.io.IOException{
> | System.out.println("CommandExecuter: EXECUTING COMMAND: "+cmd);
> | Process proc = Runtime.getRuntime().exec(cmd);
> |
> | BufferedReader in = new BufferedReader(new
> | InputStreamReader(proc.getInputStream()));
> | BufferedReader err = new BufferedReader(new
> | InputStreamReader(proc.getErrorStream()));
> |
> | stdout = "";
> | while ((line = in.readLine()) != null)
> | stdout += line +"\n";
> | if (stdout == "")
> | stdout = null;
> |
> | stderr = "";
> | while ((line = err.readLine()) != null)
> | stderr += line +"\n";
> | if (stderr == "")
> | stderr = null;
>
> The first thing that I see is that your command contains io redirection.
> You have to invoke a shell in order to use those operators--you don't get
> one automatically. Also, you can find the details elsewhere on the web or
> the cljp past messages, but reading stdout and then reading stderr will not
> solve the blocking problem. Both must be read simultaneously because if
> either fills up its OS pipe buffer, your exec cmd will be automatically
> suspended to give your Java reader a chance to empty the buffer. However,
> your Java program will be waiting for output which will never arrive. In
> this case, the stderr buffer could fill up and suspend the process while
> your Java program waits for more output. There are a variety of tools and
> techniques to help with this nowadays.
>
> Matt Humphrey m...@ivizNOSPAM.comhttp://www.iviz.com/




Mike Schilling 05-25-2007 12:53 AM

Re: Runtime.exec(cmd) hangs up
 

"Vic" <vikrantp@gmail.com> wrote in message
news:1180046607.237152.145810@r19g2000prf.googlegr oups.com...
>I am having a problem with Runtime.exec(cmd) where cmd is a string and
> is as follows -
>
> cmd = "home/qaplay/loader/604/soaploaderclient.ps nemo 50624 55604
> genevaman qa /home/vpatanka/604Current/lib/loader/data/
> DuplicateTransactionTest.0.lrd -bcp > & $GVHOME/tempOut.txt"
>
>
> The actual code is like this ->
> public CommandExecuter (String cmd) throws java.io.IOException{
> System.out.println("CommandExecuter: EXECUTING COMMAND: "+cmd);
> Process proc = Runtime.getRuntime().exec(cmd);
>
> BufferedReader in = new BufferedReader(new
> InputStreamReader(proc.getInputStream()));
> BufferedReader err = new BufferedReader(new
> InputStreamReader(proc.getErrorStream()));
>
> stdout = "";
> while ((line = in.readLine()) != null)
> stdout += line +"\n";
> if (stdout == "")
> stdout = null;
>
> stderr = "";
> while ((line = err.readLine()) != null)
> stderr += line +"\n";
> if (stderr == "")
> stderr = null;
>
> //System.out.println ("CommandExecuter stdout="+stdout);
> //System.out.println ("CommandExecuter stderr="+stderr);
> }
> }
>
> I can run the same cmd on the shell and I get a an output which is
> pretty big so I am not copying it over here but if you guyz need it
> then I can do that. Please let me know what am I missing here in
> Runtime.exec() or its something else



The obvious issue is that this code won't start to read stderr until the
exec'd process closes stdout, so the process may be hung trying to wite to
stderr. Try reading from stdout and stderr at the same time (in different
threads.) A nice, symmetrical way to do this is

1. Runtime.exec()
2. Start a thread that reads from stdout as long as there's anything to
read and then exits.
3. Start another thread that reads from stderr as long as there's
anything to read and then exits.
4. Process.waitFor();



Vic 05-25-2007 05:54 PM

Re: Runtime.exec(cmd) hangs up
 
I was wondering if its possible to read only stdout as a temporary fix
if its gonna work, would this hang up problem be still there if I just
do

Process proc = Runtime.getRuntime().exec(cmd);
BufferedReader in = new BufferedReader(new
InputStreamReader(proc.getInputStream()));
proc.waitfor (in the try catch block)
.........
.........

I actually tried the above version but didn't work


On May 24, 5:53 pm, "Mike Schilling" <mscottschill...@hotmail.com>
wrote:
> "Vic" <vikra...@gmail.com> wrote in message
>
> news:1180046607.237152.145810@r19g2000prf.googlegr oups.com...
>
>
>
> >I am having a problem with Runtime.exec(cmd) where cmd is a string and
> > is as follows -

>
> > cmd = "home/qaplay/loader/604/soaploaderclient.ps nemo 50624 55604
> > genevaman qa /home/vpatanka/604Current/lib/loader/data/
> > DuplicateTransactionTest.0.lrd -bcp > & $GVHOME/tempOut.txt"

>
> > The actual code is like this ->
> > public CommandExecuter (String cmd) throws java.io.IOException{
> > System.out.println("CommandExecuter: EXECUTING COMMAND: "+cmd);
> > Process proc = Runtime.getRuntime().exec(cmd);

>
> > BufferedReader in = new BufferedReader(new
> > InputStreamReader(proc.getInputStream()));
> > BufferedReader err = new BufferedReader(new
> > InputStreamReader(proc.getErrorStream()));

>
> > stdout = "";
> > while ((line = in.readLine()) != null)
> > stdout += line +"\n";
> > if (stdout == "")
> > stdout = null;

>
> > stderr = "";
> > while ((line = err.readLine()) != null)
> > stderr += line +"\n";
> > if (stderr == "")
> > stderr = null;

>
> > //System.out.println ("CommandExecuter stdout="+stdout);
> > //System.out.println ("CommandExecuter stderr="+stderr);
> > }
> > }

>
> > I can run the same cmd on the shell and I get a an output which is
> > pretty big so I am not copying it over here but if you guyz need it
> > then I can do that. Please let me know what am I missing here in
> > Runtime.exec() or its something else

>
> The obvious issue is that this code won't start to read stderr until the
> exec'd process closes stdout, so the process may be hung trying to wite to
> stderr. Try reading from stdout and stderr at the same time (in different
> threads.) A nice, symmetrical way to do this is
>
> 1. Runtime.exec()
> 2. Start a thread that reads from stdout as long as there's anything to
> read and then exits.
> 3. Start another thread that reads from stderr as long as there's
> anything to read and then exits.
> 4. Process.waitFor();




Daniel Pitts 05-25-2007 06:19 PM

Re: Runtime.exec(cmd) hangs up
 
On May 25, 10:54 am, Vic <vikra...@gmail.com> wrote:
> I was wondering if its possible to read only stdout as a temporary fix
> if its gonna work, would this hang up problem be still there if I just
> do
>
> Process proc = Runtime.getRuntime().exec(cmd);
> BufferedReader in = new BufferedReader(new
> InputStreamReader(proc.getInputStream()));
> proc.waitfor (in the try catch block)
> ........
> ........
>
> I actually tried the above version but didn't work

[snip];

You cant just waitFor, you actually have to actively read both stdout
and stderr. Although, if you don't care about distinguishing one from
the other, there IS an option (using ProcessBuilder I think) to
combine both into a single stream. You can then just read from that
stream and be happy with your results.


Vic 05-25-2007 07:43 PM

Re: Runtime.exec(cmd) hangs up
 
Alright so here is my new code now, I implemented it the way you said
(with some online help)
class StreamGobbler extends Thread {
InputStream is;
String type;

StreamGobbler(InputStream is, String type){
this.is = is;
this.type = type;
}

public void run(){
try{
InputStreamReader isr = new InputStreamReader(is);
BufferedReader br = new BufferedReader(isr);
String line = null;
while((line = br.readLine()) != null){
System.out.println(type+">"+line);
}
}
catch(IOException ioe){
ioe.printStackTrace();
}
}
}

class CommandExecuter {
public static String stdout = null;
public static String stderr = null;
private String line;

public CommandExecuter (String cmd) throws java.io.IOException{
System.out.println("CommandExecuter: EXECUTING COMMAND: "+cmd);
Process proc = Runtime.getRuntime().exec(cmd);

StreamGobbler errorGobbler = new
StreamGobbler(proc.getErrorStream(),"ERROR");
StreamGobbler outputGobbler = new
StreamGobbler(proc.getInputStream(),"OUTPUT");

errorGobbler.start();
outputGobbler.start();

try{
//VicP - temporary code to check the process status
int val = proc.waitFor();
//proc.wait(120000);
}
catch (Throwable t){
t.printStackTrace();
}
}
}
But now the question is how do I set the value of stdout and stderr in
CommandExecuter(As we are doing the stuff in thwo different threads
now)? I need these values as they are checked in the calling function
(which calls the Command executer constructor). Could you please
suggest me some changes to get this?
On May 24, 5:53 pm, "Mike Schilling" <mscottschill...@hotmail.com>
wrote:
> "Vic" <vikra...@gmail.com> wrote in message
>
> news:1180046607.237152.145810@r19g2000prf.googlegr oups.com...
>
>
>
> >I am having a problem with Runtime.exec(cmd) where cmd is a string and
> > is as follows -

>
> > cmd = "home/qaplay/loader/604/soaploaderclient.ps nemo 50624 55604
> > genevaman qa /home/vpatanka/604Current/lib/loader/data/
> > DuplicateTransactionTest.0.lrd -bcp > & $GVHOME/tempOut.txt"

>
> > The actual code is like this ->
> > public CommandExecuter (String cmd) throws java.io.IOException{
> > System.out.println("CommandExecuter: EXECUTING COMMAND: "+cmd);
> > Process proc = Runtime.getRuntime().exec(cmd);

>
> > BufferedReader in = new BufferedReader(new
> > InputStreamReader(proc.getInputStream()));
> > BufferedReader err = new BufferedReader(new
> > InputStreamReader(proc.getErrorStream()));

>
> > stdout = "";
> > while ((line = in.readLine()) != null)
> > stdout += line +"\n";
> > if (stdout == "")
> > stdout = null;

>
> > stderr = "";
> > while ((line = err.readLine()) != null)
> > stderr += line +"\n";
> > if (stderr == "")
> > stderr = null;

>
> > //System.out.println ("CommandExecuter stdout="+stdout);
> > //System.out.println ("CommandExecuter stderr="+stderr);
> > }
> > }

>
> > I can run the same cmd on the shell and I get a an output which is
> > pretty big so I am not copying it over here but if you guyz need it
> > then I can do that. Please let me know what am I missing here in
> > Runtime.exec() or its something else

>
> The obvious issue is that this code won't start to read stderr until the
> exec'd process closes stdout, so the process may be hung trying to wite to
> stderr. Try reading from stdout and stderr at the same time (in different
> threads.) A nice, symmetrical way to do this is
>
> 1. Runtime.exec()
> 2. Start a thread that reads from stdout as long as there's anything to
> read and then exits.
> 3. Start another thread that reads from stderr as long as there's
> anything to read and then exits.
> 4. Process.waitFor();




Mike Schilling 05-25-2007 08:10 PM

Re: Runtime.exec(cmd) hangs up
 

"Vic" <vikrantp@gmail.com> wrote in message
news:1180122190.487170.204980@a35g2000prd.googlegr oups.com...
> Alright so here is my new code now, I implemented it the way you said
> (with some online help)
> class StreamGobbler extends Thread {
> InputStream is;
> String type;
>
> StreamGobbler(InputStream is, String type){
> this.is = is;
> this.type = type;
> }
>
> public void run(){
> try{
> InputStreamReader isr = new InputStreamReader(is);
> BufferedReader br = new BufferedReader(isr);
> String line = null;
> while((line = br.readLine()) != null){
> System.out.println(type+">"+line);
> }
> }
> catch(IOException ioe){
> ioe.printStackTrace();
> }
> }
> }
>
> class CommandExecuter {
> public static String stdout = null;
> public static String stderr = null;
> private String line;
>
> public CommandExecuter (String cmd) throws java.io.IOException{
> System.out.println("CommandExecuter: EXECUTING COMMAND: "+cmd);
> Process proc = Runtime.getRuntime().exec(cmd);
>
> StreamGobbler errorGobbler = new
> StreamGobbler(proc.getErrorStream(),"ERROR");
> StreamGobbler outputGobbler = new
> StreamGobbler(proc.getInputStream(),"OUTPUT");
>
> errorGobbler.start();
> outputGobbler.start();
>
> try{
> //VicP - temporary code to check the process status
> int val = proc.waitFor();
> //proc.wait(120000);
> }
> catch (Throwable t){
> t.printStackTrace();
> }
> }
> }
> But now the question is how do I set the value of stdout and stderr in
> CommandExecuter(As we are doing the stuff in thwo different threads
> now)? I need these values as they are checked in the calling function
> (which calls the Command executer constructor). Could you please
> suggest me some changes to get this?


Have your StreamGobbler class keep track of the characters it's read, much
as your original code did, and add a method to return the result, something
like (not tested or even compiled)

class StreamGobbler extends Thread {
InputStream is;
String type;
String read;

StreamGobbler(InputStream is, String type){
this.is = is;
this.type = type;
}

public String getResult() {
return result;
}

public void run(){
StringBuffer buffer = new StringBuffer();
try{
InputStreamReader isr = new InputStreamReader(is);
BufferedReader br = new BufferedReader(isr);
String line = null;
while((line = br.readLine()) != null){
buffer.append(line);
buffer.append("\n");
}
}
catch(IOException ioe){
ioe.printStackTrace();
}
finally {
result = buffer.toString();
}
}
}

In the main program, do the following:

// wait for process to stop
int val = proc.waitFor();
// wait for threads to finish reading output
outputGobbler.join();
errorGobbler.join();
// get output
stdout = outputGobbler.getResult();
stderr = errorGobbler.getResult();




All times are GMT. The time now is 03:58 AM.

Powered by vBulletin®. Copyright ©2000 - 2014, vBulletin Solutions, Inc.
SEO by vBSEO ©2010, Crawlability, Inc.