C# RS232串口通信如何隐藏回显数据 实现PuTTY同款显示效果
问题原因
你的SAS Expander固件开启了串口远端回显:你向串口发送的命令会被固件先原样回传,再返回实际执行结果。PuTTY默认对回显内容做了匹配过滤,因此不会重复显示你输入的命令;你原来的代码直接将所有串口收到的数据打印到控制台,所以回显的命令内容也会显示。
解决方案
方案1:关闭设备端回显(优先)
绝大多数支持串口交互的嵌入式固件都支持关闭回显的指令,比如标准AT指令集的ATE0就是关闭回显的命令,你可以查询SAS Expander的固件手册,在串口初始化完成后发送一次关闭回显的命令,后续就不会再收到回显内容,无需额外逻辑处理。
方案2:软件层统一过滤回显
如果无法关闭设备回显,可以通过全局匹配逻辑过滤回显内容,无需为每条命令单独加处理代码,完整改动如下:
- 首先在
SerialPortProgram类中添加两个全局成员,用来缓存待过滤的命令和串口接收数据:
class SerialPortProgram { // 存储最近发送的命令(包含结尾的\r),用来匹配回显 private static string _lastSentCommand = string.Empty; // 串口接收缓冲区,解决数据分片到达的问题 private static StringBuilder _receiveBuffer = new StringBuilder(); // 剩下的原有代码不变 // ...
- 简化发送命令的逻辑,所有用户输入统一处理,不需要每个命令单独加分支:
while (true) { string userResponse = Console.ReadLine(); string sendContent = userResponse + "\r"; mySerialPort.Write(sendContent); // 记录刚发送的命令,用于后续过滤回显 _lastSentCommand = sendContent; }
- 修改接收回调的逻辑,自动过滤回显内容:
private static void DataReceivedHandler(object sender, SerialDataReceivedEventArgs e) { SerialPort sp = (SerialPort)sender; // 把本次收到的内容追加到缓冲区 _receiveBuffer.Append(sp.ReadExisting()); string bufferContent = _receiveBuffer.ToString(); // 存在待过滤的回显,且缓冲区内容长度足够匹配时,执行过滤 if (!string.IsNullOrEmpty(_lastSentCommand) && bufferContent.Length >= _lastSentCommand.Length) { if (bufferContent.StartsWith(_lastSentCommand)) { // 移除开头的回显内容 bufferContent = bufferContent.Substring(_lastSentCommand.Length); // 回显过滤完成,清空标记 _lastSentCommand = string.Empty; } } // 输出处理后的内容 Console.Write(bufferContent); // 清空缓冲区避免重复打印 _receiveBuffer.Clear(); }
如果测试发现固件回显的换行符和你发送的不一致(比如你发的是\r,回显的是\r\n),只需要调整_lastSentCommand的后缀为对应换行符即可。
内容的提问来源于stack exchange,提问作者Jacky
相关产品推荐
相关产品推荐

