为什么在Process.Start之前需要手动Thread.Sleeping?

时间:2014-07-28 15:47:36

标签: c# android stream

我有一个场景,我正在从C#应用程序读取Android手机上的文件,使用adb.exe进入手机的shell并使用C#应用程序中的Process读取文件。但是,如果我希望它实际工作,我需要在Process.Start之前使用Thread.Sleep。有什么想法吗?

以下是代码:

ProcessStartInfo cmdInfo;

string resulterr = "";
string result = "";

cmdInfo = new ProcessStartInfo(" adb.exe ", "shell cat /etc/bluetooth/bt_stack.conf");
cmdInfo.CreateNoWindow = true;
cmdInfo.RedirectStandardOutput = true;
cmdInfo.RedirectStandardError = true;
cmdInfo.UseShellExecute = false;

Process cmd = new Process();
cmd.StartInfo = cmdInfo;

var output = new StringBuilder();
var error = new StringBuilder();

cmd.OutputDataReceived += (o, ef) => output.Append(ef.Data);
cmd.ErrorDataReceived += (o, ef) => error.Append(ef.Data);

//if I don`t have this Thread.Sleep, the error string is "device not found"!!
Thread.Sleep(5000);

cmd.Start();
cmd.BeginOutputReadLine();
cmd.BeginErrorReadLine();
cmd.WaitForExit();
cmd.Close();
resulterr = error.ToString();
result = output.ToString();
cmd.Dispose();

任何想法为什么这适用于线程睡眠但没有它工作?我可以跑

shell cat /etc/bluetooth/bt_stack.conf
从命令行ad naseaum

没有延迟也没有问题 - 为什么我在这里需要它们?

1 个答案:

答案 0 :(得分:0)

好的,在我的情况下,设备实际上还没有准备好接收命令。我等待这样一个好的设备状态。

    ProcessStartInfo lcmdInfo1;

    lcmdInfo1 = new ProcessStartInfo(" adb.exe ", "get-state");
    lcmdInfo1.CreateNoWindow = true;
    lcmdInfo1.RedirectStandardOutput = true;
    lcmdInfo1.RedirectStandardError = true;
    lcmdInfo1.UseShellExecute = false;

    Process cmd2 = new Process();
    cmd2.StartInfo = lcmdInfo1;

    var output = new StringBuilder();
    var error = new StringBuilder();

    cmd2.OutputDataReceived += (o, ef) => output.Append(ef.Data);
    cmd2.ErrorDataReceived += (o, ef) => error.Append(ef.Data);
    cmd2.Start();
    cmd2.BeginOutputReadLine();
    cmd2.BeginErrorReadLine();
    cmd2.WaitForExit();
    cmd2.Close();
    lresulterr1 = error.ToString();
    lresult1 = output.ToString();
    cmd2.Dispose();

    //sometimes there is an issue with a previously issued command that causes the device status to be 'Unknown'. Wait until the device status is 'device'
    while (!lresult1.Contains("device"))
    { 
        lcmdInfo1 = new ProcessStartInfo(" adb.exe ", "get-state");
        lcmdInfo1.CreateNoWindow = true;
        lcmdInfo1.RedirectStandardOutput = true;
        lcmdInfo1.RedirectStandardError = true;
        lcmdInfo1.UseShellExecute = false;

        cmd2 = new Process();
        cmd2.StartInfo = lcmdInfo1;

        output = new StringBuilder();
        error = new StringBuilder();

        cmd2.OutputDataReceived += (o, ef) => output.Append(ef.Data);
        cmd2.ErrorDataReceived += (o, ef) => error.Append(ef.Data);
        cmd2.Start();
        cmd2.BeginOutputReadLine();
        cmd2.BeginErrorReadLine();
        cmd2.WaitForExit();
        cmd2.Close();
        lresulterr1 = error.ToString();
        lresult1 = output.ToString();
        cmd2.Dispose();
    }
 //now your device is ready. Go ahead and fire off the shell commands