Serial Port UnauthorizedAccessException

kevin li 1 Reputation point
2021-04-04T11:16:11.08+00:00

I write software using c# in VS2017. My software runs on windows 10,64bits pc, and it will communicate with another device using rs422, which will convert to a USB to connect with my pc. The device will send messages to me every 0.5 seconds, and I can send messages to the device via rs422 in random order.
So I use SerialPort class to do the communication work.
In my process, I create several threads to send messages to the device in random order via the same SerialPort class instance.
Most times it works well. But in some cases, maybe because the hardware of the rs422 chip or wire isn’t stable, my app can’t receive any message from the device, and at the same time, only one thread can send messages using SerialPort.Write Method of SerialPort class instance. And when other threads try to access the instance using Write method of the class), it will raise an UnauthorizedAccessException, the Exception is as below:
*2021-01-03 17:59:46| Error| UartSender.DoMonitor=>Monitor=>RunInternal=>|Uart Send Exception
Access to the port is denied.

An exception of type System.UnauthorizedAccessException occurred and was caught.

01/03/2021 17:59:46
Type: System.UnauthorizedAccessException, mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
Message: Access to the port is denied.
Source: System
HelpLink:
TargetSite : Void WinIOError(Int32, System.String)
HResult : -2147024891
StackTrace : at System.IO.Ports.InternalResources.WinIOError(Int32 errorCode, String str)
at System.IO.Ports.SerialStream.BeginWriteCore(Byte[] array, Int32 offset, Int32 numBytes, AsyncCallback userCallback, Object stateObject)
at System.IO.Ports.SerialStream.Write(Byte[] array, Int32 offset, Int32 count, Int32 timeout)
at System.IO.Ports.SerialPort.Write(Byte[] buffer, Int32 offset, Int32 count)
at XXXXXX() in D:\XXXXX\UartSender.cs:line 120
AdditionalInfo
MachineName : DESKTOP-SHOR3RC
TimeStamp : 1/3/2021 9:59:46 AM
FullName : XXX, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null
AppDomainName : XXXXX.exe
ThreadIdentity :
WindowsIdentity : DESKTOP-SHOR3RC\ML_Server_HP*

If this happens, another thread will try to reconnect the serial port via close the serial port and open it again. Then when close or open the serial port, exceptions occur:

Close exception information is as below:
*2021-01-05 16:27:37| Error| XXXXX.CloseSerPort=>SerialPortInit=>DoMonitor=>|Exception
Access to the port is denied.

An exception of type System.UnauthorizedAccessException occurred and was caught.

01/05/2021 16:27:37
Type: System.UnauthorizedAccessException, mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
Message: Access to the port is denied.
Source: System
HelpLink:
TargetSite : Void WinIOError(Int32, System.String)
HResult : -2147024891
StackTrace : at System.IO.Ports.InternalResources.WinIOError(Int32 errorCode, String str)
at System.IO.Ports.SerialStream.Dispose(Boolean disposing)
at System.IO.Stream.Close()
at System.IO.Ports.SerialPort.Dispose(Boolean disposing)
at System.IO.Ports.SerialPort.Close()
at XXXXX.CloseSerPort() in D:\XXXXX.cs:line 199
AdditionalInfo
MachineName : DESKTOP-KBNRM8A
TimeStamp : 1/5/2021 8:27:37 AM
FullName : XXXX, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null
AppDomainName : XXXX.exe
ThreadIdentity :
WindowsIdentity : XXXX\XXXXX*

Open exception information is as below:

*2021-01-03 17:59:49| Error| XXXXXXX.SerialPortInit=>DoMonitor=>Monitor=>|Exception
Access to the port 'COM24' is denied.

An exception of type System.UnauthorizedAccessException occurred and was caught.

01/03/2021 17:59:49
Type: System.UnauthorizedAccessException, mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
Message: Access to the port 'COM24' is denied.
Source: System
HelpLink:
TargetSite : Void WinIOError(Int32, System.String)
HResult : -2147024891
StackTrace : at System.IO.Ports.InternalResources.WinIOError(Int32 errorCode, String str)
at System.IO.Ports.SerialStream..ctor(String portName, Int32 baudRate, Parity parity, Int32 dataBits, StopBits stopBits, Int32 readTimeout, Int32 writeTimeout, Handshake handshake, Boolean dtrEnable, Boolean rtsEnable, Boolean discardNull, Byte parityReplace)
at System.IO.Ports.SerialPort.Open()
at XXXX.SerialPortInit(String portName) in D:\XXXXX.cs:line 249
AdditionalInfo
MachineName : DESKTOP-SHOR3RC
TimeStamp : 1/3/2021 9:59:49 AM
FullName : XXXX, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null
AppDomainName : XXXX.exe
ThreadIdentity :
WindowsIdentity : XXXXXCX*

And from that on, my app can’t connect with the serial port.
Then I restart (close and open) my app again, when I open the serial port, the same exception as above occurs again.
Then the only way to solve it is to pull out the rs422 hardware and plugin it again.
So from the above process, I guess when the problem happens for the first time, the serial port instance and its relative resource seem to have been occupied exclusively by one thread, and other threads haven’t authorized to access it. And what is worse, even if the thread and its process has been destroyed, all the resource still hasn’t been released.
So my questions are:
(1) What methods or tools can give me clue to see what happens to it?
(2) What kinds of problems will result in the serial port and its resource will be occupied exclusively by one thread?
(3) How can I release the resource to reconnect the serial port?
(4) Can C# or windows provide me some APIs to monitor and solve the problem?

Windows for business | Windows Client for IT Pros | Devices and deployment | Set up, install, or upgrade
Windows for business | Windows Client for IT Pros | User experience | Other
Developer technologies | C#
0 comments No comments
{count} votes

2 answers

Sort by: Most helpful
  1. Daniel Zhang-MSFT 9,651 Reputation points
    2021-04-06T03:09:15.777+00:00

    Hi kevinli-1303,
    UnauthorizedAccessException usually indicates that the port has been opened somewhere.
    Please remember that the SerialPort.Close method takes some time to actually close the port.
    The exact amount of time is not predictable and could be many seconds when the machine is particularly busy.
    From offical document, only one open connection can exist for each SerialPort object.
    And the best practice for any application is to wait for some amount of time after calling the Close method before attempting to call the Open method, as the port may not be closed instantly.
    And I guess you try to open a port when is has not been close yet.
    So I suggest you try to add an if statement before open the port :

    if(!serialPort.IsOpen)  
    {  
     serialPort.Open()  
     }  
    

    Best Regards,
    Daniel Zhang


    If the response is helpful, please click "Accept Answer" and upvote it.

    Note: Please follow the steps in our documentation to enable e-mail notifications if you want to receive the related email notification for this thread.

    0 comments No comments

  2. Jordan Brauer 1 Reputation point
    2021-06-04T19:53:27.753+00:00

    Hi,

    I recently ran into the same issue on a COM port. What's confusing to me is why a call to SerialPort.Write() (in my case WriteLine()) results in an UnauthorizedAccessException? Its not listed under the exceptions that can occur from that function.

    I assume my continuing problem is that I can't open the port once I can't access it, so that also needs to be fixed on my end.

    Thanks,
    Jordan


Your answer

Answers can be marked as Accepted Answers by the question author, which helps users to know the answer solved the author's problem.