您现在的位置:中国下载站学院中心网络编程Visual C++教程Visual C++开发技巧 → 文章列表

Windows平台下基于串口的数据采集系统

作者:佚名  来源:不详  发布时间:2006-12-29 13:42:49   

减小字体 增大字体

 
 
摘 要 介绍了一种简易的Windows平台下基于串口的数据采集系统。系统上层软件采用简单的非重叠I/O模式,通过合理的设置,有效地解决了I/O读写阻塞问题

  关键词 串行通讯,非重叠I/O,数据采集

  串行通讯因其线路简单,开发相对比较容易,所以经常应用于各种监控、测试和自动化设备中。在DOS环境下,上层软件可以直接对端口进行读写,但是在 Windows环境下,不能直接对硬件进行读写,而只能调用一系列的系统函数。这对上层程序的开发带来了一定的复杂性。本文给出了Windows环境下,对串口进行读写的一种简化步骤,降低了程序的复杂性。

  1、Windows环境下串口读写的一般过程

  在现行32位的Windows系统中,串行通信是作为文件读写来处理的。其串口读写的一般过程为:

  

  1.1 打开串口

  在Windows环境下,打开串口使用CreateFile函数,其原型为:

HANDLE CreateFile(
LPCTSTR lpFileName,
DWORD dwDesiredAccess,
DWORD dwShareMode,
LPSECURITY_ATTRIBUTES lpSA,
DWORD dwCreate,
DWORD dwFlagsAndAttributes,
HANDLE hTemplate
);

  其中比较重要的几个参数是:

  ﹥ lpFileName —— 为端口名称,如”COM1”,”COM2”等等;
  ﹥dwDesiredAccess —— 希望对串口进行何种操作,可为GENERIC_READ(读)、GENERIC_WRITE(写)或两者的位或;
  ﹥ dwCreate —— 必须设置为OPEN_EXISTING;
  ﹥ dwFlagsAndAttributes —— 可为FILE_FLAG_ OVERLAPPED (重叠模方式)或NULL(非重叠模式);

  ﹥ dwShareMode和hTemplate参数在打开串口时必须为NULL;

  1.2 配置串口

  包括初始化端口、设置DCB结构和设置超时值。

  使用SetupComm函数初始化端口,设置端口的读写缓冲区大小。

  设置DCB结构包括波特率、字节长度、校验位、停止位等等。使用SetCommState函数。

  设置超时值使用SetCommTimeouts函数。下一节以下将对该函数做进一步说明。

  1.3 串口读写

  Win32环境下对串口的读写采用ReadFile和WriteFile函数。读写方式有两种:重叠模式和非重叠模式(或者称为异步模式和同步模式)。

  1.4 关闭串口

  串口使用完毕,使用CloseHandle函数关闭即可。

  2、重叠模式和非重叠模方式

  一般认为非重叠I/O模式比较简单,但是会占用大量I/O时间,而重叠I/O模式比较灵活,但是编程复杂。

  非重叠模式下,读写函数知道执行完毕才返回,因而会阻塞同步执行的其它线程。而在重叠模式下,读写函数会立即返回,I/O操作在后台进行,这样线程就可以处理其它事务。

  重叠模式需要监测和处理通信事件的状态,给编程带来了很大复杂性。其实,通过对端口进行合理的设置,编程简单的非重叠模式,也可以发挥出重叠模式的优点。

  3、优化的非重叠模式

  在前面提到,在串口读写之前,需要设置读写超时值。使用的函数是SetCommTimeouts,其原型为:

BOOL SetCommTimeouts(
HANDLE hFile,
LPCOMMTIMEOUTS lpTimeouts
);


  其中第二个参数是一个指向串口超时结构(COMMTIMEOUTS)的指针。该结构指明了串口读写的各种超时间隔值。当设置结构成员 ReadIntervalTimeout为MAXDWORD,并且同时设置成员ReadTotalTimeoutConstant以及成员 ReadTotalTimeoutMultiplier为0时,ReadFile函数会立即返回,即使没有读入任何字节。这样就不会引起任何阻塞了。

 4、程序关键代码

  基于以上介绍的方法,作者开发了一套Windows环境下基于串口的数据采集系统,经过长时间的测试,运行良好。
程序接收到用户的开始测试命令后,打开并设置串口。采用非重叠I/O模式,并设置超时值使得ReadFile函数在没有串口数据情况下立即返回。程序使用定时器来定时读取串口数据。实践证明,这种方式编程容易,结构清晰,并且占用系统资源较少。下面给出程序关键代码。

  4.1 打开并设置串口

//READBUFFER和WRITEBUFFER是
//用户自己定义的两个宏
BOOL InitCOM(LPCTSTR strPort,
DWORD BaudRate, //波特率
BYTE ByteSize, //字节长度
BYTE Parity, //校验位
BYTE StopBits, //停止位
DWORD dwInQueue = READBUFFER, //读缓冲区大小
DWORD dwOutQueue = WRITEBUFFER //写缓冲区大小
)
{
 DCB dCB;
 COMMTIMEOUTS ct;

 //打开串口,并得到串口句柄
 m_hCOM = CreateFile( strPort,
 GENERIC_READ | GENERIC_WRITE,0, NULL, OPEN_EXISTING,0, NULL);
 if(m_hCOM==INVALID_HANDLE_VALUE)
  return FALSE;

 //初始化串口,设置读写缓冲区大小
 if( !SetupComm(m_hCOM, dwInQueue, dwOutQueue) ||
!PurgeComm(m_hCOM, PURGE_TXCLEAR|PURGE_RXCLEAR) )
 {
  CloseHandle(m_hCOM);
  m_hCOM=INVALID_HANDLE_VALUE;
  return FALSE;
 }
 
 //设置DCB结构
 if(!GetCommState(m_hCOM, &dCB))
 {
  CloseHandle(m_hCOM);
  m_hCOM=INVALID_HANDLE_VALUE;
  return FALSE;
 }
 dCB.BaudRate = BaudRate;
 dCB.ByteSize = ByteSize;
 dCB.Parity = Parity;
 dCB.StopBits = StopBits;
 if(!SetCommState(m_hCOM, &dCB))
 {
  CloseHandle(m_hCOM);
  m_hCOM= INVALID_HANDLE_VALUE;
  return FALSE;
 }

 //设置超时值,使得当串口没有数据时,
 //ReadFile函数立即返回
 ct.ReadIntervalTimeout= MAXDWORD;
 ct.ReadTotalTimeoutConstant= 0;
 ct.ReadTotalTimeoutMultiplier= 0;
 ct.WriteTotalTimeoutConstant= 0;
 ct.WriteTotalTimeoutMultiplier=0;
 if(!SetCommTimeouts(m_hCOM, &ct))
 {
  CloseHandle(m_hCOM);
  m_hCOM= INVALID_HANDLE_VALUE;
  return FALSE;
 }
 return TRUE;
}

  代开串口并设置成功后,返回TRUE,否则返回FALSE。

  4.2 设置定时器,并定时读串口

//设置定时读串口
SetTimer(hwnd,NULL, uElapse,Reading)
//uElapse是定时器间隔时间(以毫秒为单位),
//视底层串口数据发送电路而定,
//一般使用50毫秒~5000秒
//Reading是读串口函数
VOID CALLBACK Reading( HWND hwnd,UINT uMsg,UINT_PTR idEvent,DWORD dwTime)
{
 unsigned char buffer[READBUFFER];
 if ( ReadFile(m_hCOM, buffer, pchBuffer, READBUFFER, &dwReadNum, NULL) && dwReadNum)
 {
  //有dwReadNum个字节读入
  //处理读入的数据
  //...
 }
}


在百度中搜索更多Windows平台下基于串口的数据采集系统相关网页 转贴于:中国下载站

  • 上一篇文章:VC中利用MFC设计绘图程序初步
  • 下一篇文章:C++中巧用#define访问类的私有成员
  • 阅读统计:[]
  • 中国下载站】【设为主页】【收藏本页】【打印本文】【回到顶部】【关闭此页

    相关文章
    文章评论(评论内容只代表网友观点,与本站立场无关!)

    用户名: 查看更多评论

    分 值:100分 85分 70分 55分 40分 25分 10分 0分

    内 容:

             (注“”为必填内容。) 验证码: 验证码,看不清楚?请点击刷新验证码


    设为首页 - 关于我们 - 广告服务 - 网站地图 - 加入收藏 - 网站声明 - 网站帮助 - 友情链接

    • Copyright (C) 2006-2008 www.cndownz.com All Rights Reserved.
      中国下载站 版权所有. 粤ICP备05141802号. 对本站有任何建议、意见或投诉,请来信:cndownzcom@yahoo.com.cn.
      喜欢中国下载站(cndownz.com),请把中国下载站(cndownz.com)告诉你QQ上的5位好友,多谢支持!