C#串口检查方法
·
1. 基础版本 - 检查串口状态
using System;
using System.IO.Ports;
using System.Threading;
public class SerialPortChecker
{
/// <summary>
/// 检查串口是否可以正常打开和关闭
/// </summary>
/// <param name="portName">串口名称,如 "COM4"</param>
/// <param name="baudRate">波特率,默认9600</param>
/// <returns>检查结果对象</returns>
public static SerialPortCheckResult CheckSerialPort(string portName, int baudRate = 9600)
{
var result = new SerialPortCheckResult
{
PortName = portName,
BaudRate = baudRate
};
try
{
// 检查串口是否存在
if (!IsSerialPortExists(portName))
{
result.IsSuccess = false;
result.ErrorMessage = $"串口 {portName} 不存在";
return result;
}
result.PortExists = true;
// 尝试打开和关闭串口
using (SerialPort serialPort = new SerialPort(portName, baudRate))
{
try
{
// 尝试打开串口
serialPort.Open();
result.CanOpen = true;
result.OpenTime = DateTime.Now;
// 短暂延迟,确保端口稳定
Thread.Sleep(100);
// 尝试关闭串口
serialPort.Close();
result.CanClose = true;
result.CloseTime = DateTime.Now;
result.IsSuccess = true;
result.Message = "串口可以正常打开和关闭";
}
catch (UnauthorizedAccessException ex)
{
result.IsSuccess = false;
result.ErrorMessage = $"串口被其他应用程序占用: {ex.Message}";
}
catch (Exception ex)
{
result.IsSuccess = false;
result.ErrorMessage = $"串口操作失败: {ex.Message}";
}
}
}
catch (Exception ex)
{
result.IsSuccess = false;
result.ErrorMessage = $"检查串口时发生异常: {ex.Message}";
}
return result;
}
/// <summary>
/// 检查串口是否存在
/// </summary>
public static bool IsSerialPortExists(string portName)
{
string[] ports = SerialPort.GetPortNames();
foreach (string port in ports)
{
if (port.Equals(portName, StringComparison.OrdinalIgnoreCase))
return true;
}
return false;
}
/// <summary>
/// 获取所有可用的串口列表
/// </summary>
public static string[] GetAvailablePorts()
{
return SerialPort.GetPortNames();
}
}
public class SerialPortCheckResult
{
public string PortName { get; set; }
public int BaudRate { get; set; }
public bool IsSuccess { get; set; }
public bool PortExists { get; set; }
public bool CanOpen { get; set; }
public bool CanClose { get; set; }
public DateTime? OpenTime { get; set; }
public DateTime? CloseTime { get; set; }
public string Message { get; set; }
public string ErrorMessage { get; set; }
public override string ToString()
{
if (IsSuccess)
return $"✓ 串口 {PortName} 检查正常: {Message}";
else
return $"✗ 串口 {PortName} 检查失败: {ErrorMessage}";
}
}
2. 增强版本 - 支持更多参数和异步操作
using System;
using System.IO.Ports;
using System.Threading;
using System.Threading.Tasks;
public class AdvancedSerialPortChecker
{
/// <summary>
/// 异步检查串口状态
/// </summary>
public static async Task<SerialPortCheckResult> CheckSerialPortAsync(
string portName,
int baudRate = 9600,
Parity parity = Parity.None,
int dataBits = 8,
StopBits stopBits = StopBits.One,
int timeout = 2000)
{
return await Task.Run(() => CheckSerialPortWithDetails(portName, baudRate, parity, dataBits, stopBits, timeout));
}
/// <summary>
/// 详细检查串口状态
/// </summary>
public static SerialPortCheckResult CheckSerialPortWithDetails(
string portName,
int baudRate = 9600,
Parity parity = Parity.None,
int dataBits = 8,
StopBits stopBits = StopBits.One,
int timeout = 2000)
{
var result = new SerialPortCheckResult
{
PortName = portName,
BaudRate = baudRate,
Parity = parity,
DataBits = dataBits,
StopBits = stopBits
};
try
{
// 检查串口是否存在
if (!SerialPortChecker.IsSerialPortExists(portName))
{
result.IsSuccess = false;
result.ErrorMessage = $"串口 {portName} 不存在";
return result;
}
result.PortExists = true;
using (SerialPort serialPort = new SerialPort(portName, baudRate, parity, dataBits, stopBits))
{
serialPort.ReadTimeout = timeout;
serialPort.WriteTimeout = timeout;
try
{
// 记录开始时间
DateTime startTime = DateTime.Now;
// 尝试打开串口
serialPort.Open();
result.CanOpen = true;
result.OpenTime = DateTime.Now;
// 保持打开状态一小段时间,模拟实际使用
Thread.Sleep(500);
// 尝试关闭串口
serialPort.Close();
result.CanClose = true;
result.CloseTime = DateTime.Now;
result.Duration = (result.CloseTime - result.OpenTime).Value.TotalMilliseconds;
result.IsSuccess = true;
result.Message = $"串口配置正常 (波特率:{baudRate}, 数据位:{dataBits}, 停止位:{stopBits}, 校验位:{parity})";
}
catch (TimeoutException)
{
result.IsSuccess = false;
result.ErrorMessage = "串口操作超时,可能被占用或配置错误";
}
catch (UnauthorizedAccessException)
{
result.IsSuccess = false;
result.ErrorMessage = "串口被其他应用程序占用或无访问权限";
}
catch (Exception ex)
{
result.IsSuccess = false;
result.ErrorMessage = $"串口操作异常: {ex.Message}";
}
}
}
catch (Exception ex)
{
result.IsSuccess = false;
result.ErrorMessage = $"检查串口时发生系统异常: {ex.Message}";
}
return result;
}
}
// 扩展的检查结果类
public class DetailedSerialPortCheckResult : SerialPortCheckResult
{
public Parity Parity { get; set; }
public int DataBits { get; set; }
public StopBits StopBits { get; set; }
public double Duration { get; set; } // 操作持续时间(毫秒)
public override string ToString()
{
if (IsSuccess)
{
return $"✓ 串口 {PortName} 检查正常 | 波特率:{BaudRate} | 数据位:{DataBits} | 停止位:{StopBits} | 校验位:{Parity} | 耗时:{Duration}ms";
}
else
{
return $"✗ 串口 {PortName} 检查失败: {ErrorMessage}";
}
}
}
3. 批量检查多个串口
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
public class BatchSerialPortChecker
{
/// <summary>
/// 批量检查多个串口
/// </summary>
public static async Task<List<SerialPortCheckResult>> CheckMultiplePortsAsync(
List<string> portNames,
int baudRate = 9600)
{
var tasks = portNames.Select(portName =>
AdvancedSerialPortChecker.CheckSerialPortAsync(portName, baudRate));
var results = await Task.WhenAll(tasks);
return results.ToList();
}
/// <summary>
/// 检查所有可用的串口
/// </summary>
public static async Task<List<SerialPortCheckResult>> CheckAllAvailablePortsAsync(int baudRate = 9600)
{
string[] availablePorts = SerialPortChecker.GetAvailablePorts();
return await CheckMultiplePortsAsync(availablePorts.ToList(), baudRate);
}
}
4. 使用示例
class Program
{
static async Task Main(string[] args)
{
string portName = "COM4";
Console.WriteLine("串口状态检查工具");
Console.WriteLine("=================");
// 方法1: 基础检查
Console.WriteLine($"\n1. 基础检查 {portName}:");
var basicResult = SerialPortChecker.CheckSerialPort(portName);
Console.WriteLine(basicResult.ToString());
// 方法2: 详细检查
Console.WriteLine($"\n2. 详细检查 {portName}:");
var detailedResult = AdvancedSerialPortChecker.CheckSerialPortWithDetails(
portName,
baudRate: 115200,
parity: Parity.None,
dataBits: 8,
stopBits: StopBits.One);
Console.WriteLine(detailedResult.ToString());
// 方法3: 异步检查
Console.WriteLine($"\n3. 异步检查 {portName}:");
var asyncResult = await AdvancedSerialPortChecker.CheckSerialPortAsync(portName);
Console.WriteLine(asyncResult.ToString());
// 方法4: 检查所有可用串口
Console.WriteLine($"\n4. 检查所有可用串口:");
var allPortsResult = await BatchSerialPortChecker.CheckAllAvailablePortsAsync();
foreach (var result in allPortsResult)
{
Console.WriteLine($" {result}");
}
// 方法5: 检查串口是否存在
Console.WriteLine($"\n5. 串口存在性检查:");
string[] availablePorts = SerialPortChecker.GetAvailablePorts();
Console.WriteLine($" 可用串口: {string.Join(", ", availablePorts)}");
Console.WriteLine($" {portName} 是否存在: {SerialPortChecker.IsSerialPortExists(portName)}");
}
}
5. 控制台应用程序完整示例
using System;
using System.Threading.Tasks;
class SerialPortTester
{
static async Task Main(string[] args)
{
while (true)
{
Console.Clear();
Console.WriteLine("=== 串口连通性测试工具 ===");
Console.WriteLine("1. 检查特定串口");
Console.WriteLine("2. 检查所有串口");
Console.WriteLine("3. 退出");
Console.Write("请选择操作: ");
string choice = Console.ReadLine();
switch (choice)
{
case "1":
await CheckSpecificPort();
break;
case "2":
await CheckAllPorts();
break;
case "3":
return;
default:
Console.WriteLine("无效选择,按任意键继续...");
Console.ReadKey();
break;
}
}
}
static async Task CheckSpecificPort()
{
Console.Write("请输入串口名称 (如 COM4): ");
string portName = Console.ReadLine().ToUpper();
if (string.IsNullOrWhiteSpace(portName))
{
Console.WriteLine("串口名称不能为空!");
return;
}
Console.WriteLine($"正在检查串口 {portName}...");
var result = await AdvancedSerialPortChecker.CheckSerialPortAsync(portName);
// 显示彩色结果
Console.ForegroundColor = result.IsSuccess ? ConsoleColor.Green : ConsoleColor.Red;
Console.WriteLine($"\n检查结果: {result}");
Console.ResetColor();
if (result.IsSuccess)
{
Console.WriteLine($" 打开时间: {result.OpenTime}");
Console.WriteLine($" 关闭时间: {result.CloseTime}");
}
Console.WriteLine("\n按任意键继续...");
Console.ReadKey();
}
static async Task CheckAllPorts()
{
Console.WriteLine("正在扫描所有可用串口...");
var results = await BatchSerialPortChecker.CheckAllAvailablePortsAsync();
Console.WriteLine($"\n找到 {results.Count} 个串口:");
Console.WriteLine("======================");
foreach (var result in results)
{
Console.ForegroundColor = result.IsSuccess ? ConsoleColor.Green : ConsoleColor.Red;
Console.WriteLine($" {result.PortName
更多推荐


所有评论(0)