Minimaslistic Telnet库 - 将输出读取到最后

时间:2014-03-24 14:08:27

标签: c# telnet

我正在开发一个项目,我应该在Unix服务器上运行命令并获得这些命令的完整输出。为此,我使用代码项目(http://www.codeproject.com/Articles/19071/Quick-tool-A-minimalistic-Telnet-library)中的Minimaslistic Telnet库。现在,除了输出之外,一切都很好,因为我想要全部阅读,而不仅仅是它的一部分。我可以拥有可能需要很长时间的命令。这是Minimaslistic Telnet库中的读取输出方法:

public string Read()
{
    if (!tcpSocket.Connected) return null;
    StringBuilder sb=new StringBuilder();
    do
    {
        ParseTelnet(sb);
        System.Threading.Thread.Sleep(TimeOutMs);
    } while (tcpSocket.Available > 0);
    return sb.ToString();
}


void ParseTelnet(StringBuilder sb)
{
    while (tcpSocket.Available > 0)
    {
        int input = tcpSocket.GetStream().ReadByte();
        switch (input)
        {
            case -1 :
                break;
            case (int)Verbs.IAC:
                // interpret as command
                int inputverb = tcpSocket.GetStream().ReadByte();
                if (inputverb == -1) break;
                switch (inputverb)
                {
                    case (int)Verbs.IAC: 
                        //literal IAC = 255 escaped, so append char 255 to string
                        sb.Append(inputverb);
                        break;
                    case (int)Verbs.DO: 
                    case (int)Verbs.DONT:
                    case (int)Verbs.WILL:
                    case (int)Verbs.WONT:
                        // reply to all commands with "WONT", unless it is SGA (suppres go ahead)
                        int inputoption = tcpSocket.GetStream().ReadByte();
                        if (inputoption == -1) break;
                        tcpSocket.GetStream().WriteByte((byte)Verbs.IAC);
                        if (inputoption == (int)Options.SGA )
                            tcpSocket.GetStream().WriteByte(inputverb == (int)Verbs.DO ? (byte)Verbs.WILL:(byte)Verbs.DO); 
                        else
                            tcpSocket.GetStream().WriteByte(inputverb == (int)Verbs.DO ? (byte)Verbs.WONT : (byte)Verbs.DONT); 
                        tcpSocket.GetStream().WriteByte((byte)inputoption);
                        break;
                    default:
                        break;
                }
                break;
            default:
                sb.Append( (char)input );
                break;
        }
    }
}

此代码示例读取输出,但异步,我需要在退出之前等待输出。是否有任何关于更改代码以满足我的要求的想法?谢谢!

1 个答案:

答案 0 :(得分:1)

我同意Joachim,在循环中调用read并解析输出结束是最好的方法。对我来说不幸的是,我输出的每个命令都没有标准化结束。相反,我使用流的读取超时来近似输出的结束(我意识到这并不完美)。我设置了更高的初始超时以允许数据开始流动,然后降低超时以找到输出的结束。它看起来像这样:

static string ReadFromStream(int initialTimeout, int subsequentTimeout)
    {
        // Initialize output
        string output = null;

        try
        {
            // Set initial read timeout -- This is needed because occasionally
            // it takes a while before data starts flowing
            stream.ReadTimeout = initialTimeout;

            while (stream.CanRead)
            {
                // Read bytes in from stream
                readBuffer = new byte[tcpClient.ReceiveBufferSize];
                stream.Read(readBuffer, 0, tcpClient.ReceiveBufferSize);

                // Convert the bytes to string and save to output
                output = string.Format("{0}{1}", output, Encoding.ASCII.GetString(readBuffer).Trim());

                // Set subsequent read timeout
                stream.ReadTimeout = subsequentTimeout;
            }
        }
        // Since we don't know when the output will end, we wait for, and catch the timeout
        catch (IOException) { }

        // Return output
        return output;
    }