C# 检查 COM(串行)端口是否已打开

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/195483/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-03 17:35:23  来源:igfitidea点击:

C# check if a COM (Serial) port is already open

c#.netserial-port

提问by TK.

Is there an easy way of programmatically checking if a serial COM port is already open/being used?

是否有一种简单的方法可以以编程方式检查串行 COM 端口是否已打开/正在使用?

Normally I would use:

通常我会使用:

try
{
    // open port
}
catch (Exception ex)
{
    // handle the exception
}

However, I would like to programatically check so I can attempt to use another COM port or some such.

但是,我想以编程方式进行检查,以便我可以尝试使用另一个 COM 端口或类似端口。

采纳答案by Fionn

I needed something similar some time ago, to search for a device.

前段时间我需要类似的东西来搜索设备。

I obtained a list of available COM ports and then simply iterated over them, if it didn't throw an exception i tried to communicate with the device. A bit rough but working.

我获得了一个可用 COM 端口的列表,然后简单地遍历它们,如果它没有抛出异常,我尝试与设备进行通信。有点粗糙但工作。

var portNames = SerialPort.GetPortNames();

foreach(var port in portNames) {
    //Try for every portName and break on the first working
}

回答by gimel

The SerialPort classhas an Openmethod, which will throw a few exceptions. The reference above contains detailed examples.

SerialPort类有一个开放式的方法,这将引发一些例外。上面的参考资料包含详细的例子。

See also, the IsOpenproperty.

另请参阅IsOpen属性。

A simple test:

一个简单的测试:

using System;
using System.IO.Ports;
using System.Collections.Generic;
using System.Text;

namespace SerPort1
{
class Program
{
    static private SerialPort MyPort;
    static void Main(string[] args)
    {
        MyPort = new SerialPort("COM1");
        OpenMyPort();
        Console.WriteLine("BaudRate {0}", MyPort.BaudRate);
        OpenMyPort();
        MyPort.Close();
        Console.ReadLine();
    }

    private static void OpenMyPort()
    {
        try
        {
            MyPort.Open();
        }
        catch (Exception ex)
        {
            Console.WriteLine("Error opening my port: {0}", ex.Message);
        }
    }
  }
}

回答by Funky81

You can try folloing code to check whether a port already open or not. I'm assumming you dont know specificaly which port you want to check.

您可以尝试以下代码来检查端口是否已经打开。我假设您不知道要检查哪个端口。

foreach (var portName in Serial.GetPortNames()
{
  SerialPort port = new SerialPort(portName);
  if (port.IsOpen){
    /** do something **/
  }
  else {
    /** do something **/
  }
}

回答by Jeff

This is how I did it:

我是这样做的:

      [DllImport("kernel32.dll", CharSet = CharSet.Auto, SetLastError = true)]
    internal static extern SafeFileHandle CreateFile(string lpFileName, int dwDesiredAccess, int dwShareMode, IntPtr securityAttrs, int dwCreationDisposition, int dwFlagsAndAttributes, IntPtr hTemplateFile);

then later on

然后后来

        int dwFlagsAndAttributes = 0x40000000;

        var portName = "COM5";

        var isValid = SerialPort.GetPortNames().Any(x => string.Compare(x, portName, true) == 0);
        if (!isValid)
            throw new System.IO.IOException(string.Format("{0} port was not found", portName));

        //Borrowed from Microsoft's Serial Port Open Method :)
        SafeFileHandle hFile = CreateFile(@"\.\" + portName, -1073741824, 0, IntPtr.Zero, 3, dwFlagsAndAttributes, IntPtr.Zero);
        if (hFile.IsInvalid)
            throw new System.IO.IOException(string.Format("{0} port is already open", portName));

        hFile.Close();


        using (var serialPort = new SerialPort(portName, 115200, Parity.None, 8, StopBits.One))
        {
            serialPort.Open();
        }

回答by Switch

Sharing what worked for me (a simple helper method):

分享对我有用的东西(一个简单的辅助方法):

private string portName { get; set; } = string.Empty;

    /// <summary>
    /// Returns SerialPort Port State (Open / Closed)
    /// </summary>
    /// <returns></returns>
    internal bool HasOpenPort()
    {
        bool portState = false;

        if (portName != string.Empty)
        {
            using (SerialPort serialPort = new SerialPort(portName))
            {
                foreach (var itm in SerialPort.GetPortNames())
                {
                    if (itm.Contains(serialPort.PortName))
                    {
                        if (serialPort.IsOpen) { portState = true; }
                        else { portState = false; }
                    }
                }
            }
        }

        else { System.Windows.Forms.MessageBox.Show("Error: No Port Specified."); }

        return portState;
}


Notes:
- For more advanced technique(s) I recommend using ManagementObjectSearcher Class.
More info Here.
- For Arduino devices I would leave the Port Open.
- Recommend using a Try Catch block if you need to catch exceptions.
- Check also: "TimeoutException"
- More information on how to get SerialPort (Open) Exceptions Here.


注意:
- 对于更高级的技术,我建议使用ManagementObjectSearcher Class
更多信息在这里
- 对于 Arduino 设备,我会让端口保持打开状态。
- 如果您需要捕获异常,建议使用 Try Catch 块。
- 还要检查:“TimeoutException”
- 有关如何在此处获取 SerialPort (Open) Exceptions 的更多信息。

回答by Farrukh Azad

  public void MobileMessages(string ComNo, string MobileMessage, string MobileNo)
    {
        if (SerialPort.IsOpen )
            SerialPort.Close();
        try
        {
            SerialPort.PortName = ComNo;
            SerialPort.BaudRate = 9600;
            SerialPort.Parity = Parity.None;
            SerialPort.StopBits = StopBits.One;
            SerialPort.DataBits = 8;
            SerialPort.Handshake = Handshake.RequestToSend;
            SerialPort.DtrEnable = true;
            SerialPort.RtsEnable = true;
            SerialPort.NewLine = Constants.vbCrLf;
            string message;
            message = MobileMessage;

            SerialPort.Open();
            if (SerialPort.IsOpen  )
            {
                SerialPort.Write("AT" + Constants.vbCrLf);
                SerialPort.Write("AT+CMGF=1" + Constants.vbCrLf);
                SerialPort.Write("AT+CMGS=" + Strings.Chr(34) + MobileNo + Strings.Chr(34) + Constants.vbCrLf);
                SerialPort.Write(message + Strings.Chr(26));
            }
            else
                ("Port not available");
            SerialPort.Close();
            System.Threading.Thread.Sleep(5000);
        }
        catch (Exception ex)
        {

                message.show("The port " + ComNo + " does not exist, change port no ");
        }
    }