【问题标题】:SerialDevice dispose method not working in certain cases, Windows 10 IOTSerialDevice dispose 方法在某些情况下不起作用,Windows 10 IOT
【发布时间】:2019-02-05 11:22:23
【问题描述】:

我开发了简单的 UWP 应用程序来通过串口进行通信。我正在使用 SerialDevice 类进行通信。在从串口读取任何数据之前,如果我处置 SerialDevice 对象,它的处置方法工作正常 一旦我开始通过串行端口读取数据,然后如果我想断开与该设备的连接并处理 SerialDevice 对象,它就会卡在 dispose 方法中。 以下是我用来读取、写入和断开连接的函数:

public class UARTCommunicationProvider
{
    SerialDevice _serialPort;
    private DataReader _serialPortReader;
    private DataWriter _serialPortWriter;
    private CancellationTokenSource _serialPortReadWriteCTS = null;
    public UARTCommunicationProvider()
    {
        _serialPortReadWriteCTS = new CancellationTokenSource();
    }
    public async Task<bool> ConnectAsync(string comportId)
    {
        _serialPort = await SerialDevice.FromIdAsync(comportId);

        if (_serialPort != null)
        {
            _serialPort.WriteTimeout = TimeSpan.FromMilliseconds(50);
            _serialPort.ReadTimeout = TimeSpan.FromMilliseconds(50);
            _serialPort.BaudRate = 9600;
            _serialPort.Parity = SerialParity.None;
            _serialPort.StopBits = SerialStopBitCount.One;
            _serialPort.DataBits = 8;
            _serialPort.Handshake = SerialHandshake.None;

            _serialPortReader = new DataReader(_serialPort.InputStream);
            // Set InputStreamOptions to complete the asynchronous read operation when one or more bytes is available
            _serialPortReader.InputStreamOptions = InputStreamOptions.Partial;
            _serialPortWriter = new DataWriter(_serialPort.OutputStream);
            return true;
        }
        else
        {
            return false;
        }
    }

    public async void CollectData()
    {
        var command = "FL 1\n";
        while (true)
        {
            var response = await ResponseForCommandAsync(command);
            Debug.WriteLine(response)

        }
    }

    public void Disconnect()
    {
        try
        {
            _serialPort?.Dispose(); //Stuck at this point when I try to dispose after reading few chunks of data from serial port
            _serialPortReadWriteCTS.Cancel();
            _serialPort = null;
        }
        catch (Exception ex)
        {

            throw;
        }
    }

    public async Task<string> ResponseForCommandAsync(string command)
    {
        string response = string.Empty;
        if (_serialPort != null)
        {
            // Load the text from the sendText input text box to the dataWriter object
            _serialPortWriter.WriteString(command);
            UInt32 bytesWritten = await _serialPortWriter.StoreAsync();
            if (bytesWritten > 0)
            {
                bytecount = bytecount + (int)bytesWritten;
                _logger.WriteLine("Data Sent Successfully", AEIoTCommon.Common.LoggingType.Verbose);
                response = await ReadAsync();
            }
        }

        return response;
    }

    private async Task<string> ReadAsync()
    {
        string valueRead = null;
        Task<UInt32> loadAsyncTask;

        uint ReadBufferLength = 1024;

        try
        {
            CancellationToken cancellationToken = _serialPortReadWriteCTS.Token;

            //If task cancellation was requested, comply
            cancellationToken.ThrowIfCancellationRequested();

            using (var childCancellationTokenSource = new CancellationTokenSource(3000))
            {
                // Create a task object to wait for data on the serialPort.InputStream
                loadAsyncTask = _serialPortReader.LoadAsync(ReadBufferLength).AsTask(childCancellationTokenSource.Token);

                // Launch the task and wait
                UInt32 bytesRead = await loadAsyncTask;
                if (bytesRead > 0)
                {
                    //byte[] buffer = new byte[bytesRead];
                    var value = _serialPortReader.ReadString(bytesRead);

                    valueRead = value;
                }
            }
        }
        catch (TaskCanceledException ex)
        {
            Disconnect();
        }


        return valueRead;
    }
}

【问题讨论】:

  • 您好 user224332,您可以使用 official serial sample 重现此问题吗?
  • colidyre,你发现了吗?我的应用程序在至少一个版本的 Windows 10(内部版本 16299)上执行相同的操作。它似乎在 Build 17763 上运行良好。

标签: uwp serial-port windows-10-iot-core


【解决方案1】:

我也遇到了 SerialDevice.Dispose() 在某些版本的 Windows 10 上挂起的问题(或者它可能与计算机硬件有关)。在研究了一般的 Windows/串行端口问题之后,挂起似乎是由于线程问题。我能够通过在我的断开功能中执行此操作来解决挂起问题:

    public void Disconnect()
    {
        :
        // Don't call dispose directly as it hangs on some computers
        // Calling this from a separate thread prevents it from hanging...
        Thread thr = new Thread(new ThreadStart(serialPortClose));
        thr.Start();
        :
    }


    void serialPortClose()
    {
        _serialDevice.Dispose();
        _serialDevice = null;
    }

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2021-11-01
    • 2018-11-28
    • 2011-09-04
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多