加入收藏 | 设为首页 | 会员中心 | 我要投稿 李大同 (https://www.lidatong.com.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 编程开发 > Java > 正文

WriteFile在使用WaitCommEvent时挂起应用程序

发布时间:2020-12-15 02:10:24 所属栏目:Java 来源:网络整理
导读:我正在讨论使用事件驱动方法进行串口通信的win32编程问题.我的通信句柄创建为: hComm = CreateFile(lpszCommName,GENERIC_READ | GENERIC_WRITE,NULL,OPEN_EXISTING,NULL); 我将我的CommTimeouts设置为: commTimeout.ReadIntervalTimeout = MAXWORD; commT
我正在讨论使用事件驱动方法进行串口通信的win32编程问题.我的通信句柄创建为:

hComm = CreateFile(lpszCommName,GENERIC_READ | GENERIC_WRITE,NULL,OPEN_EXISTING,NULL);

我将我的CommTimeouts设置为:

commTimeout.ReadIntervalTimeout = MAXWORD;
    commTimeout.ReadTotalTimeoutConstant = 0;
    commTimeout.ReadTotalTimeoutMultiplier = 0;
    commTimeout.WriteTotalTimeoutConstant = 0;
    commTimeout.WriteTotalTimeoutMultiplier = 0;

我为ReadFile创建了一个如下所示的线程:

SetCommMask(hComm,EV_RXCHAR);
while (isConnected)
{
    if (WaitCommEvent(hComm,&dwEvent,NULL)) //If i comment out this block my write file will work fine
    {
        ClearCommError(hComm,&dwError,&cs);
        if ((dwEvent & EV_RXCHAR) && cs.cbInQue)
        {
            if (!ReadFile(hComm,str,cs.cbInQue,&read_byte,NULL))
              /* Process error*/
            else if (read_byte)
                /* Print to screen */
        }
        else {
            /* Process error*/
        }
    }
}
PurgeComm(hComm,PURGE_RXCLEAR);

我的Wrifile进入WndProc,当WM_CHAR被触发时,它会向通信设备发送字符:

VOID Write_To_Serial(WPARAM wParam,HWND hwnd){
        DWORD write_byte;
        char    str[10];
        sprintf_s(str,"%c",(char)wParam);         //Convert wParam to a string
        WriteFile(hComm,strlen(str),&write_byte,NULL)//Program hangs here
    }

我的问题是每次WriteFile()被调用我的应用程序挂起,我必须强制关闭它.如果我在我的读取线程中注释掉WaitCommEvent()它工作正常,但我无法阅读.任何指针都将不胜感激.谢谢

解决方法

这是同步IO操作的预期行为.

根据MSDN(https://msdn.microsoft.com/en-us/library/ff802693.aspx)中的串行通信文章中的以下描述,

It is the responsibility of the application to serialize access to the
port correctly. If one thread is blocked waiting for its I/O operation
to complete,all other threads that subsequently call a communications
API will be blocked until the original operation completes. For
instance,if one thread were waiting for a ReadFile function to
return,any other thread that issued a WriteFile function would be
blocked.

WriteFile必须等到WaitCommEvent函数完成其操作.

一个小的解决方法是在需要调用WriteFile时取消挂起的WaitCommEvent操作(例如通过使用CancelIoEx API).

VOID Write_To_Serial(WPARAM wParam,(char)wParam);         //Convert wParam to a string
        CancelIoEx(hComm,NULL);
        WriteFile(hComm,NULL);//Program hangs here
    }

WaitCommEvent在取消时返回FALSE.因此,WaitCommEvent之后的代码将不会被执行.

但是,在极端情况下,调用ReadFile函数的线程有可能在WndProc到WriteFile之前重新调用WaitCommEvent函数.如果发生这种情况,则需要单独处理. WaitCommEvent返回FALSE时可能会有一点延迟.

(编辑:李大同)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读