收藏 分销(赏)

基于WINDOWS-API的异步串口通信软件设计.doc

上传人:仙人****88 文档编号:11990230 上传时间:2025-08-26 格式:DOC 页数:6 大小:212.50KB 下载积分:10 金币
下载 相关 举报
基于WINDOWS-API的异步串口通信软件设计.doc_第1页
第1页 / 共6页
基于WINDOWS-API的异步串口通信软件设计.doc_第2页
第2页 / 共6页


点击查看更多>>
资源描述
基于WINDOWS API的异步串口通信软件设计 摘 要: 串口是常用的计算机与外部串行设备之间的数据传输通道,在VC++6.0中利用第三方控件实现串口通信时实时性较差,系统资源利用不足,为了提高串口通信的速度和资源利用率,软件采用WINDOWS API函数并基于多线程技术和自定义消息机制的异步串口通信的设计理念,结合串口通信的机理和多线程同步技术,分析了Win32系统下多线程异步串口通信软件的开发方法。软件主线程是数据采集程序的管理者,串口监测线程(辅助线程)在后台对串口进行实时监视,获得了良好稳定的通信效果。 关键词:串口通信;异步(重叠)I/O;多线程; 中图分类号:TP311 文献标识码: A 文章编号: 0 引 言 串口通信是计算机与其他设备进行数据通信时经常使用的方法之一,他具有实现简单,使用灵活方便,数据传输可靠等优点,因而在工业控制、数据采集和实时监控系统中得到广泛应用[1]。 在通常的串口通信软件开发的时候,大多数人采用的是使用如MSComm等第三方控件控件进行程序的开发。MSComm控件在串口编程时非常方便,程序员不必花时间去了解较为复杂的API函数,只需要在串口通信资源的属性(Properties)一项中配置串口,完成串口配置之后即可打开串口,进行数据读写。 但由于控件本身对于接收缓冲区大小设置的限定,如果接收缓冲区不能满足设计的要求,当缓冲区内数据达到消息响应值并响应存储命令,而新的数据传输速度大于已接收到数据的存储速度时,就会造成接收缓冲区的溢出,进而直接导致软件的崩溃[2]。 本文的串口通信软件的开发没有使用任何串口通信的第三方封装控件,全部使用windows API函数对串口进行操作和配置,而且使用了多线程技术和异步I/0操作,提高了串口通信的效率和程序的灵活性。 1 软件结构 本串口通信软件主要由三个主要模块构成,分别是:串口配置模块,数据采集模块和数据发送模块。三个模块分别对应CinData,CoutData和CGetComSet三个类。串口配置模块完成对串口关键参数的设置,采集和发送模块中分别创建了单独的线程控制数据的收发,同时在采集模块中还创建了对端口的监视事件,负责对串口进行实时监测。软件的组成结构如图1所示: 图1 串口通信软件结构 2 串口配置模块 串口的本质功能是作为CPU和串行设备间的编码转换器。当数据从 CPU经过串行端口发送出去时,字节数据转换为串行的位。在接收数据时,串行的位被转换为字节数据。对于两个通信的串口,最重要的参数是波特率、数据位、停止位和奇偶校验位[3]。由于每台电脑或者外设对自身串口的默认设置不尽相同,所以我们在进行通信之前一定要设置好这些参数,使通信双方的串口配置一致,才能确保通信的正常。本软件中串口配置模块完成发送端和接收端串口的配置,并可以自动识别本机上使有串口端口号,方便了用户的选择。串口配置模块界面如下图所示: 图2 串口配置模块界面 3 数据采集和发送模块 数据采集和发送模块是本软件的两个核心模块,两个模块中都分别创建了单独的采集线程和发送线程负责对串口进行读写操作,采集线程接收并保存收到的数据。配置模块完成对串口相关参数的配置后,也是通过全局变量把设定的参数值传到此两个模块中来进行对相关结构体成员附值的。界面如下: 图3 数据采集模块配置界面 3.1 异步I/0的使用 Windows文件操作分为同步I/O和异步I/O (Overlapped I/ O)两种方式,在同步I/O方式中,API会阻塞直到操作完成以后才能返回(在多线程方式中,虽然不会阻塞主线程,但是仍然会阻塞监听线程);而在异步I/O方式中,API会立即返回,操作在后台进行,避免线程的阻塞[5]。异步I/O非常灵活,它也可以实现阻塞(例如我们可以设置一定要读取到一个数据才能进行到下一步操作),这就使得线程可以从费时的I/O操作中解放出来,从而极大地提高了程序的运行效率。 为了使用异步I/O方式打开串口,在用CreateFile创建创建串口时,必须指定文件的属性为FILE_FLAG_OVERLAPPED: m_Comm= CreateFile(m_sPort, GENERIC_READ, 0, NULL,OPEN_EXISTING, ILE_ATTRIBUTE_NORMAL|FILE_FLAG_OVERLAPPED, NULL); 然后在 ReadFile()时lpOverlapped参数一定不能为NULL,接着检查函数调用的返回值,调用GetLastError(),看是否返回ERROR_IO_PENDING。如是,最后调用GetOverlappedResult()返回异步操作(overlapped operation)的结果;WriteFile()的使用类似。异步I/O的信息包含在结构体OVERLAPPED当中,其定义为: typedef struct _OVERLAPPED { DWORD Internal; DWORD InternalHigh; DWORD Offset; DWORD OffsetHigh; HANDLE hEvent; } OVERLAPPED; 其中hEvent是读写事件,当串口使用异步通讯时,函数返回时操作可能还没有完成,程序可以通过检查该事件得知是否读写完毕。当调用ReadFile, WriteFile 函数的时候,该成员会自动被置为无信号状态;当重叠操作完成后,该成员变量会自动被置为有信号状态。该事件的创建,可以对串口进行监测。 3.2 DCB和COMMTIMEOUTS结构体的配置 使用windows api进行串口通信的编程,对DCB和COMMTIMEOUTS两个结构体的配置是非常重要的工作,参数配置得是否科学将直接影响到通信的品质。我们使用的第三方控件实质就是封装了此些结构体在其中来对串口进行配置。DCB是设备控制块DCB(Device Control Block),在我们打开串口后,需要对串口进行初始化的工作,这些工作就是通过对DCB成员的赋值来实现的[5]。在查询或配置串口的属性时,都要用DCB结构来作为缓冲区。DCB的定义为: typedef struct _DCB { // dcb  DWORD DCBlength; // sizeof(DCB)  DWORD BaudRate; // current baud rate  DWORD fBinary: 1; // binary mode, no EOF check  DWORD fParity: 1; // enable parity checking  DWORD fOutxCtsFlow:1; // CTS output flow control  DWORD fOutxDsrFlow:1; // DSR output flow control  DWORD fDtrControl:2; // DTR flow control type  DWORD fDsrSensitivity:1; // DSR sensitivity  DWORD fTXContinueOnXoff:1; // XOFF continues Tx  DWORD fOutX: 1; // XON/XOFF out flow control  DWORD fInX: 1; // XON/XOFF in flow control  DWORD fErrorChar: 1; // enable error replacement  DWORD fNull: 1; // enable null stripping  DWORD fRtsControl:2; // RTS flow control  DWORD fAbortOnError:1; // abort reads/writes on error  WORD XonLim; // transmit XON threshold  WORD XoffLim; // transmit XOFF threshold  BYTE ByteSize; // number of bits/byte, 4-8  BYTE Parity; // 0-4=no,odd,even,mark,space  BYTE StopBits; // 0,1,2 = 1, 1.5, 2 } DCB; 其中包括常用的波特率,数据位,奇偶校验位和停止位的设置。另外,DCB还给程序员提供了对硬件流控制的设置。我们知道通,过串口传输数据时,由于计算机之间处理速度或其他因素的影响,会造成丢失数据的现象发生,数据流控制就是用于解决这个问题的。它通过控制发送数据的速度,确保数据在通信中不会出现丢失。数据流控制可以分为软件流控制(Xon/Xoff)和硬件流控制。软件流控制使用特殊的字符作为启动或停止的标志。而硬件流控制通过使用硬件信号(CTR/RTS)来实现。 串口通信中的硬件流控有两种,DTE(data terminal equipment即数据终端设备)/DSR(Data Set Ready)方式和RTS(请求发送,当数据终端准备好送出数据时,就发出有效的RTS信号)/CTS(Clear-To-Send protocol 的简写,是清除发送协议,通常和RTS连在一起)方式,这与DCB结构的初始化有关系,DCB结构中的OutxCtsFlow、 fOutxDsrFlow、fDsrSensitivity、fRtsControl、fDtrControl几个成员的初始值很关键,不同的值代表不同流控,也可以自己设置流控。硬件流控是靠软件实现的,之所以强调“硬件”二字,仅仅是因为硬件流控提供了用于流量情况指示的硬件连线方法。在通常的串口通信中,我们一般建议采用标准流行的软件流控方式,对硬件流控制的设置对于一般用户使用默认值即可,但对于特定需求来说,这些设置是非常必要的。当对DCB设置完成后,必须使用SetCommState使配置生效[3,5]。本程序中对DCB的部分配置代码为: dcb. DCBlength = sizeof(DCB); dcb.fBinary=TRUE; dcb.BaudRate = m_anBaud; // 数据传输速率 dcb.ByteSize = m_anDataBits; // 每字节位数 dcb.fParity = TRUE; dcb.Parity=EVENPARITY;// 校验设置 dcb.StopBits=ONESTOPBIT; SetCommState(m_Comm, &dcb);//把配置写入设备 COMMTIMEOUTS结构体是用进行超时设置的。在通信中,超时是个很重要的考虑因素,特别是在对实时性要求比较高的应用中,因为如果在数据接收过程中由于某种原因突然中断或停止,如果不采取超时控制机制,将会使得I/O线程被挂起或无限阻塞,严重影响正常的通信。用ReadFile和WriteFile读写串口时,需要考虑超时问题,如果在指定的时间内没有读出或写入指定数量的字符,那么ReadFile或WriteFile的操作就会结束,避免阻塞的发生。在用异步方式读写串口时,虽然ReadFile和WriteFile在完成操作以前就可能返回,但超时仍然是起作用的。在这种情况下,超时规定的是操作的完成时间,而不是ReadFile和WriteFile的返回时间。本程序中对COMMTIMEOUTS的配置代码如下: comTimeOut.ReadIntervalTimeout =MAXDWORD ; // 接收时,两字符间最大的时延 comTimeOut.ReadTotalTimeoutMultiplier =0; // 读取每字节的超时 comTimeOut.ReadTotalTimeoutConstant =0; // 读串口数据的固定超时 comTimeOut.WriteTotalTimeoutConstant =0; // 写串口数据的固定超时 SetCommTimeouts(m_Comm, &comTimeOut)); // 将超时参数写入设备控制 4 多线程的设计 4.1 多线程程序设计思想 在32位Windows系统中,术语多任务是指系统可以同时运行多个进程,而每个进程也可以同时执行多个线程。进程就是应用程序的运行实例。每个进程都有自己私有的虚拟地址空间,每个进程都有一个主线程,但可以建立另外的线程[4]。进程中的线程是并行执行的,每个线程占用CPU的时间由系统来划分.可以把线程看作是操作系统分配CPU时间的基本实体,系统不停的在各个线程之间切换,它对线程的中断是汇编语言级的.系统为每一个线程分配一个CPU时间段,某个线程只有在分配的时间段内才有对CPU的控制权。 进程中所有的线程共享进程的虚拟地址空间,这意味着所有线程都可以访问进程的全局变量和资源。这一方面为编程带来了方便,但另一方面也容易造成冲突.虽然在进程中进行费时的工作不会导致系统的挂起,但会导致进程本身的挂起[9]。所以,如果进程即要进行长期工作,又要响应用户的输入,那么它可以启动一个线程来专门负责费时的工作,而主线程仍然可以与用户进行交互.由此可见,利用Windows的异步(重叠)I/O操作和多线程特性,可以编出高效的通信程序。 4.2 多线程程序设计 根据多线程程序的开发思想,该串口通信软件由负责人机交互的主线程和对串口进行处理的后台监测线程组成[4].主线程是数据采集程序的管理者,用来初始化串口(通过调用相应的Windows API函数),自定义通信事件消息,创建、删除辅助线程,进行人机交互的操作及协调好各线程的运行。程序流程如图4所示: 图4 多线程流程图 串口监测线程在后台对串口进行实时监视,当监视到预定义的事件时,立即调用相应的线程进行处理,如果接收到数据就调用读线程自动接收数据并进行处理,然后执行后面的程序代码,继续对串口进行监视,直到串口上的预定义的事件再次发生。这样,真正做到了处理消息与监视串口两不误,即保证了数据采集的实时性,又避免了资源的浪费。 5 结束语 本文使用了多线程技术,在线程中收发数据和监控串口,并且使用了非阻塞通信技术,依靠异步(重叠overlapped)读写操作,让串口读写操作在后台运行。多线程技术能很好地解决各种逻辑并发和物理并发问题,使软件的各项性能指标均有所改善,如吞吐量、计算速度、响应时间等,提高了软件的执行效率和系统资源的利用率,同时也大大提高了程序的可读性和稳定性。 6
展开阅读全文

开通  VIP会员、SVIP会员  优惠大
下载10份以上建议开通VIP会员
下载20份以上建议开通SVIP会员


开通VIP      成为共赢上传

当前位置:首页 > 学术论文 > 其他

移动网页_全站_页脚广告1

关于我们      便捷服务       自信AI       AI导航        抽奖活动

©2010-2025 宁波自信网络信息技术有限公司  版权所有

客服电话:0574-28810668  投诉电话:18658249818

gongan.png浙公网安备33021202000488号   

icp.png浙ICP备2021020529号-1  |  浙B2-20240490  

关注我们 :微信公众号    抖音    微博    LOFTER 

客服