2008-12-16 8 views
6

he un archivo ejecutable que se ejecuta al instante desde un símbolo del sistema, pero no parece volver nunca cuando generado usando System.Diagnostics.Process:Procesamiento .NET cuestiones de desove

Básicamente, estoy escribiendo una biblioteca .NET envoltura alrededor de la interfaz Accurev CLI, por lo que cada llamada al método engendra el proceso CLI para ejecutar un comando.

Esto funciona muy bien para todos, pero un solo comando:

accurev.exe show depots 

Sin embargo, cuando se ejecuta este desde una consola, que funciona muy bien, cuando yo lo llamo el uso de un proceso de .NET, se cuelga ... El proceso de código de desove que uso es:

public static string ExecuteCommand(string command) 
    { 

     Process p = createProcess(command); 

     p.Start();    
     p.WaitForExit(); 

     // Accurev writes to the error stream if ExitCode is non zero. 
     if (p.ExitCode != 0) 
     { 
      string error = p.StandardError.ReadToEnd(); 
      Log.Write(command + " failed..." + error); 
      throw new AccurevException(error);     
     } 
     else 
     { 
      return p.StandardOutput.ReadToEnd(); 
     } 

    } 

    /// Creates Accurev Process 
    /// </summary> 
    /// <param name="command"></param> 
    /// <returns></returns> 
    private static Process createProcess(string command) 
    { 
     Log.Write("Executing Command: " + command); 

     ProcessStartInfo startInfo = new ProcessStartInfo(); 
     Process p = new Process(); 

     startInfo.CreateNoWindow = false; 
     startInfo.RedirectStandardOutput = true; 
     startInfo.RedirectStandardInput = true; 
     startInfo.RedirectStandardError = true; 

     startInfo.UseShellExecute = false; 
     startInfo.Arguments = command; 
     startInfo.FileName = _accurev; 

     p.StartInfo = startInfo; 

     return p; 
    } 

se cuelga en p.WaitForExit().

¿Algún consejo?

EDIT: ¡Solucionado!

.NET cuelgue del proceso si los desbordamientos de búfer de salida, que me pasa a utilizar un método de lectura asíncrona y todo funciona:

public static string ExecuteCommand(string command) 
    { 
     StringBuilder outputData = new StringBuilder(); 

     Process p = createProcess(command); 

     p.OutputDataReceived += delegate(object sender, DataReceivedEventArgs e) 
     { 
      outputData.AppendLine(e.Data); 
     }; 

     p.Start(); 
     p.BeginOutputReadLine(); 

     p.WaitForExit(); 

     // Accurev writes to the error stream if ExitCode is non zero. 
     if (p.ExitCode != 0) 
     { 
      string error = p.StandardError.ReadToEnd(); 
      Log.Write(command + " failed..." + error); 
      throw new AccurevException(error);     
     } 
     else 
     { 
      return outputData.ToString(); 
     } 

    } 
+0

Puede que le interese [esta publicación] (http://www.codeducky.org/process-handling-net/) que analiza algunas de las complejidades del trabajo con .NET procesa de esta manera. – ChaseMedallion

Respuesta

1

es el proceso generado aún con vida mientras WaitForExit() está ejecutando? ¿Puedes adjuntar un depurador?

2

¿Está buscando una entrada? En particular, me doy cuenta de que está redirigiendo el código fuente, pero no lo está cerrando, por lo que si está leyendo desde el código fuente, se bloqueará.

+1

Bueno, cerrar - stdout vs stdin ;-p –

-2

sustituya el WaitForExit() con algo como esto:

while (!p.WaitForExit(100)) 
    Console.Write("."); 

La otra cosa a intentar es establecer UseShellExecute a verdadero, y observando que dio lugar a la ventana de la consola. Consulte esta página para conocer las complejidades de ese parámetro: http://blogs.msdn.com/jmstall/archive/2006/09/28/CreateNoWindow.aspx

+0

Como el poster está redireccionando la entrada, dudo que funcione. –

Cuestiones relacionadas