system.io.ports使用rtsenabled接收错误的数据包

时间:2010-08-27 12:08:22

标签: c# serial-port .net

我正在编写一种方法,该方法发送特定数据包并从电子设备获得回复。我正在使用带有rtsEnabled = true的system.io.ports。

问题是当进入应用程序时,接收的数据包会被更改。我正在监视使用eltima收到的内容以及eltima收到的数据包,并且应用程序有两个不同的字节。

应用程序正在将每个十六进制的字节(例如FF或BB)更改为3F。 以下是Eltima给出的内容:

  

5b 00 00 09 32 13 31 33 35 36 31 39 31 30 30 38 32 35 00 01 ff 64 01 00 bb 0f 5d --Eltima

     

5B 00 00 09 32 13 31 33 35 30 32 37 31 30 30 38 32 35 00 01 3F 64 01 00 3F 04 5D - 我的应用

以下是我的代码:

public string MakeSerialConnection(string COM, int baud, string dest)
    {
        SerialPort port = new SerialPort(COM, baud, Parity.None, 8, StopBits.One);
        try
        {
            if (!(port.IsOpen))
            {
                string destination = dest;
                //BUILD PACKET FOR SENDING
                byte[] fullPacket = BuildPacket(destination);
                port.Open();
                port.RtsEnable = false;

                port.Handshake = Handshake.None;

                //SEND PACKET TO DEVICE
                port.Write(fullPacket,0,9);

                #region RECEIVE DATA FROM SERIAL
                //MAKE PROCESS STOP FOR 5sec
                Thread.Sleep(240);

                port.RtsEnable = true;

                Thread.Sleep(1000);
                string reading = port.ReadExisting();
               // int readingint = port.ReadByte();

                    port.Close();
                    port.Dispose();
                    return reading;
                #endregion
            }
            else
            {
                return "";
            }
        }
        catch (Exception ex)
        {
            throw ex;
        }
        finally
        {
            if (port != null)
            {
                //port.Close();
                if (port.IsOpen)
                {
                    port.Close();
                }
                port.Dispose();
            }

        }

请帮我弄清楚为什么会发生这种情况

3 个答案:

答案 0 :(得分:1)

你看一下ASCII代码图表,你会看到0x3f是?的字符代码。这是Encoding.GetString()无法将字节值转换为字符时将获得的替换字符。有道理,默认的SerialPort.Encoding是ASCII,0xff不是该编码中的有效字符代码。

根本问题是您正在阅读字符串。但是设备不发送字符串,而是发送字节。您必须使用SerialPort.Read()而不是ReadExisting()。

答案 1 :(得分:1)

不要将读取的字节放入字符串中。如SwDevMan所述,您不是通过端口发送字符串而是字节数组。作为良好实践,请避免将数据转换为不属于的类型。有时,框架背后的代码会在您不知情的情况下更改数据。

使用Read()或ReadByte()并将字节放入要构建的数组或字节或列表中。 Read()是逻辑方式,但ReadByte有它的用途。使用ReadByte()将一次读取一个字节。如果您希望第一个字节是特殊标志,例如命令开始标志,您可以立即验证它并选择丢弃或继续阅读。

        while (serialport.BytesToRead > 0)
        {
            startingByte= Convert.ToByte(serialport.ReadByte());
            CheckIfStartOfCommand(startingByte)
            ...
        }

否则,使用Read()将一定数量的字节输入预设数组。

答案 2 :(得分:0)

设备规范对Handshaking的评价是什么?您可能必须将握手设置为RequestToSend。此外,如果可能,请使用DataReceived接收数据而不是睡觉。

我还会检查串口的Encoding以确保它与设备使用的匹配。默认值为ASCIIEncoding,因此如果设备正在使用其他内容(例如:Unicode),则需要进行更改。