MFC自动检测串口
基于MSComm串口通讯的波特率自动检测方法
以字符 串形 式设 置或 返 回传 输速 率 、 校 验方 式 、 位 数
据位、 停止 位等 。如 本例 设为 “ 9 0 n 8 1 , 12 0, , ,” 表示 波 特率
怎 样 既不 牺 牲 VB语 言 和 MS o m 的简 单 方 便 性 . Cm 而又能 自动测 出终 端 的通信 速率 . 以调整使 主机波特 率与
之 一致 ?本文 通过 一个 实验 , 出易 行 的方法 。 给 1 硬软 件装 置
11 硬 件 .
通讯 事 件或错 误 的返 回值
关 键词 : 串口通讯 ; Co ; 特 率 ; MS mm 波 自动检 测 中图分 类号 : P 9 T 3 文 献标 识码 : A 文章 编号 :6 2 0 7 2 0 )5 0 4 — 3 17 —06 (0 7 0 — 13 0 从 输入 缓 冲区 中返 回并删 除字符 。
Ou p t tu
编 程 的 Aci x控 件 , te v 它使应 用 程序 编程 容易 和可 靠 。 MS o C mm控 件 的属性 与本 文有关 的如下 :
C mmP r o ot
同时运 行两 个程 序 . 两个 程 序 间传送 数据 . 在 模拟 主
机 与终 端 间的通讯 主机波 特率 设为 1 2 0 终端 以不 同波特 率发 送 字符 90 .
…
设置 通讯 端 口号码
S ti g et s n
a ’
,
接 收 到 的字 节转 为 十 六 进制 符 , 到 表一 ( : 得 注 因收
发 波特 率不 同 的原 因 . 主机 端 可能 得 到 的不 止 一个 字节 .
用MFC写串口
API串口编程资料(1)在用ReadFile 和WriteFile读写串行口时,需要考虑超时问题。
如果在指定时间内没有读出或写入指定数量的字节,那么ReadFile或WriteFIle的操作就会结束。
要查询当前的超时设置应调用GetCommTimeouts函数,该函数会填充一个COMMTIMEOUTS结构。
调用SetCommTimeouts函数可以用某一个COMMTIMEOUTS结构的内容来设置超时。
typedef struct _COMMTIMEOUTS (DWORD ReadIntervalTimeout; //读时间间隔超时DWORD ReadTotalTimeoutMultiplier; //读时间系数DWORD ReadTotalTimeoutConstant; //读时间常数DWORD WriteTotalTimeoutMultiplier; //写时间系数DWORD WriteTotalTimeoutConstant; //写时间常量) COMMTIMEOUTS,*LPCOMMTIMEOUTS;(1)CreateFile打开串口:HANDLE hCom;DWORD dwError;hCom=CreateFile("COM1",GENERIC_READ|GENERIC_WRITE, //允许读和写0, //独占方式NULLOPEN_EXITSTING, //FILE_ATTRIBUTE_NORMAL|FILE_FLAG_OVERLAPPED, //重叠方式 NULL)if(hCom==INVALID_HANDLE_VALUE){dwError=GetLastError(); //得到错误信息//。
//处理错误}//重叠I/O操作就是异步操作或非阻塞操作,即在执行一项操作时,若系统有别的操作请求,可以立即返回执行其他任务,这样程序就不会类似死机一样停在那里。
而NomOverLapped方式则正好相反,程序应该在于同步方式下如果有一个API函数在操作中,另一个会阻塞直到上一个操作完成,所以当读数据的线程停留在WaitCommEvent的时候,写操作WriteFile 就停在原地等待。
MFC下的MSCOMM控件用于串口通信的几个例子
MFC下的MSCOMM控件用于串口通信的几个例子MFC下的MSCOMM控件用于串口通信的几个例子VC基于MSCOMM控件串口通讯(转)/hanhaitianyu/blog/item/0c4cc0ef5d344 ef7b3fb9526.html在mfc中进行串口通讯最简单的方法莫过于在对话框中使用MSCOMM控件了,MSComm通信控件提供了一系列标准通信命令的接口,它允许建立串口连接,可以连接到其他通信设备(如Modem).还可以发送命令、进行数据交换以及监视和响应在通信过程中可能发生的各种错误和事件,从而可以用它创建全双工、事件驱动的、高效实用的通信程序。
一、用MSComm控件通信1.串口通信基础知识一般悦来,计算机都有一个或多个串行端口,它们依次为com1、Com2、…,这些串口还提供了外部设备与pC进行数据传输和通信的通道。
这些串口在CPU和外设之间充当解释器的角色。
当字符数据从CPU发送给外设时,这些字符数据将被转换成串行比特流数据;当接收数据时,比特流数据被转换为字符数据传递给CPU,再进一步说,在操作系统方面,Windows用通信驱动程序(COMM.DRV)调用API函数发送和接收数据,当用通信控件或声明调用API函数时,它门由COMM. DRV解释并传递给设备驱动程序,作为一个程序员,要编写通信程序.只需知道通信控件提供给Windows通信AP1函数的接口即可.换句话说,只需设定和监视通信控件的属性和事件即可。
2.使用Mscomm控件在开始使用MSComm控件之前。
需要先了解其属性、事件或错误属性描述CommPort 设置或返回通信端口号Settings 以字符串的形式设置或返回波特率、奇偶校验、数据位和停止位PortOpen 设置或返回通信端口的状态。
也可以打开和关闭端口Input 返回和删除接收缓冲区中的字符Output 将字符串写入发送缓冲区CommEvent属性为通信事件或错误返回下列值之一。
串口波特率自动检测
ELSIF Byte >= 0xF1 THEN
19200 Baud
ELSE
CASE Byte IN
0x0D: 9600 Baud
0xE6: 4800 Baud
0x78: 2400 Baud
0xE0,0xF0: 1800 Baud
0x80: 1200 Baud
ELSE: Line noise; reset
关键词:自动检测;波特率
串行通信是终端和主机之间的主要通信方式,通信波特率一般选择1800、4800、9600和 19200等。终端的类型有很多种,其通信速率也有很多种选择。主机怎样确定终端的通信速率呢?本文给出了一种简单、易行的方法:设定主机的接收波特率(以9600波特为例),终端发送一个特定的字符(以回车符为例),主机根据接收到的字符信息就可以确定终端的通信波特率。本文对这种方法予以详述。
3 实现方式
通过以上分析,各种波特率都可以通过回车符的发送和接收信息来测定,算法实现的伪代码在本文
的最后给出。应用实践证明了这种方法的有效性。
; Pseudo code to determine what baud rate a transmitter is at,
on the b asis of a single
2 低波特率的检测
当发送速率低于1200波特时,接收端收到的字节都是0x00,因此只能确定其速率低于12 00波特,而不可能再得到更多的信息。为了解决这个问题,可以在9600波特的速率下继续接收下一个字节信息。发送速率为600波特或更低时,一个位的发送时间要大于9600波特时整个字节的接收时间。因此,发送端每一个从‘1’(终止位)到‘0’(起始位)的跳变都会让接收端认为一个新的字节开始了。表2所示为600波特或更低的传输速率时接收端回车符的二进制序列(只给出开始的一些位)。
mfc串口类使用方法
mfc串口类使用方法MFC串口类使用方法一、引言MFC(Microsoft Foundation Classes)是微软公司为Windows操作系统开发的一套C++类库,提供了一系列的类和函数,简化了Windows程序的开发。
MFC串口类是其中的一个重要组成部分,用于实现在Windows平台下对串口进行读写操作。
本文将介绍MFC串口类的使用方法,帮助读者快速上手并实现串口通信功能。
二、MFC串口类的基本介绍MFC提供了一个名为CSerialPort的串口类,通过该类可以方便地进行串口的打开、关闭、读写等操作。
在使用MFC串口类之前,需要在代码中包含相应的头文件:#include "afxwin.h"三、打开串口在使用串口之前,首先需要打开串口。
打开串口的函数原型如下:BOOL CSerialPort::Open(int nPort, int nBaud, char nParity, int nDatabits, int nStopbits, DWORD dwCommEvents, UINT nBufferSize = 512);参数说明:nPort:串口号,例如1代表COM1;nBaud:波特率,例如9600;nParity:奇偶校验位,可以选择'N'(无校验)、'E'(偶校验)或'O'(奇校验);nDatabits:数据位,可以选择5、6、7或8;nStopbits:停止位,可以选择1或2;dwCommEvents:串口事件,可以选择EV_RXCHAR(接收到字符时触发)或EV_RXFLAG(接收到指定标志位时触发);nBufferSize:缓冲区大小,默认为512。
示例代码如下:CSerialPort serial;if (serial.Open(1, 9600, 'N', 8, 1, EV_RXCHAR)){// 串口打开成功}else{// 串口打开失败}四、关闭串口在使用完串口后,需要关闭串口。
mfc获取插入串口的详细描述
一、介绍MFC及其作用MFC(Microsoft Foundation Class)是微软公司提供的用于Windows应用程序开发的类库,它为C++程序员提供了一套面向对象的编程接口,使得开发Windows应用程序变得更加简单和高效。
MFC可以用来创建图形用户界面(GUI)、处理消息和事件、管理窗口和控件等,是Windows下开发桌面应用程序的重要工具之一。
其中,串口通信在许多实际应用中具有重要的作用,而MFC提供了方便的类库来实现串口通信。
二、串口通信的基本概念1. 串口通信是指通过串行端口进行数据交换的一种通信方式,主要包括RS-232、RS-485、USB串口等。
2. 串口通信中,数据是按照一定的位序列依次传输的,通常包括起始位、数据位、校验位和停止位。
3. 串口通信分为同步串口和异步串口两种,其中异步串口通信最为常见,其数据传输不需要时钟信号。
4. 串口通信常用于嵌入式系统、传感器、工业自动化等领域,以及一些老旧设备上。
三、在MFC中获取插入串口的详细描述1. MFC提供了CSerialPort类来实现串口通信,其中获取插入串口的详细描述是一个重要的功能。
2. 获取插入串口的详细描述可以包括串口的端口号、设备名称、设备描述等信息。
3. 在MFC中,可以通过遍历系统中的串口端口来获取插入串口的详细描述信息。
四、具体步骤1. 需要包含头文件,引入CSerialPort类的定义和相关函数。
2. 通过查询注册表或WMI(Windows Management Instrumentation)来获取系统中已插入的串口端口信息。
3. 每个串口端口在注册表中都有对应的注册表项,可以通过遍历注册表的方式来获取插入串口的详细描述信息。
4. 对于WMI,可以调用相关接口来获取串口设备的详细信息。
五、代码示例下面是一个简单的代码示例,展示了如何在MFC中获取插入串口的详细描述信息:```C++void CMyDlg::EnumSerialPorts(){CString str;HKEY hKey;LONG lResult = RegOpenKeyEx(HKEY_LOCAL_MACHINE,_T("HARDWARE\\DEVICEMAP\\SERIALCOMM"), 0, KEY_READ,hKey);if(lResult != ERROR_SUCCESS){AfxMessageBox(_T("Error opening SerialComm Key!"));return;}TCHAR lpValueName[256];DWORD dwValueNameSize = 256;BYTE lpData[256];DWORD dwDataSize = 256;DWORD dwIndex = 0;lResult = RegEnumValue(hKey, dwIndex, lpValueName, dwValueNameSize, NULL, NULL, lpData, dwDataSize);while(lResult == ERROR_SUCCESS){CString strPortName(reinterpret_cast<LPCTSTR>(lpData)); str.Format(_T("s - s"), lpValueName, strPortName);m_lbPorts.AddString(str);dwValueNameSize = 256;dwDataSize = 256;dwIndex++;lResult = RegEnumValue(hKey, dwIndex, lpValueName, dwValueNameSize, NULL, NULL, lpData, dwDataSize);}RegCloseKey(hKey);}```六、总结通过上述步骤和代码示例,我们可以在MFC中轻松获取插入串口的详细描述信息,这对于进行串口通信或者设备监控等应用非常有用。
VCMFC编写串口调试助手
V C M F C编写串口调试助手集团标准化工作小组 [Q8QX9QT-X8QQB8Q8-NQ8QJ8-M8QMN]VC(MFC)编写串口调试助手1.序确定基本功能:1.自动寻找串口,并自动添加到下拉框中共选择;2.有波特率、数据位、停止位、校验位的选择设置;3.串口打开控制按钮;4.发送、清除按钮;5.接收是自动实现的;6.有定时自动发送功能;7.有传送文件功能;8.有状态栏显示,指示串口状态,设置参数和发送接收显示。
下面就一步步实现,本人纯业余,只是记录下来这个学习过程,请勿拍砖。
开发平台Visual C++英文版,电脑是i7-2670Q四核8G内存1G独显的笔记本,装的win7 64位旗舰版,因此VC6兼容不是太好,有些小毛病,不过不影响编写。
2.创建MFC项目File -> New -> Projects选择MFC AppWizard(exe),项目名称commassist选择OK选中Dialog based,点击Next> 。
默认选项,点击Next> ,继续默认选项,点击Next> ,如果选中As a statically linked library,生产的EXE可直接在没装VC的机器上运行。
可以在项目中进行更改。
选择第二个CCommassistDlg,点击Finish点击OK。
项目创建完毕,进入项目。
删除界面上确定和取消按钮以及静态文字。
3.创建界面保存后便可以开始创建界面了。
参考界面仿照设计的界面,具体添加按钮或编辑框等的布局步骤就不用细说了。
4.图标修改在资源视图中选择Icon右键InsertIcon加入打开和关闭的Icon图标或自行绘制,如下图IDR_MAINFRAME原为MFC提供的图标,这里我直接改成自己的,生成EXE后将会显示这个图标。
下面将帮助页面图标也改为自绘图标。
在打开按钮旁边加入自绘的打开和关闭图标:先加入工具条中的Picture,然后选中右键看属性,并如图将Image选为默认的IDI_ICON_CLOSE。
串口测试方法和步骤
串口测试方法和步骤串口测试是指通过串口与外部设备通信进行数据的收发和交互的过程。
串口测试可以用于验证串口的功能、测试串口设备的可靠性以及确定串口通信协议的正确性等方面。
以下是串口测试的一般方法和步骤。
1.确定串口连接:首先需要确认计算机与外部设备的串口连接是否正确。
通常情况下,计算机有多个串口,需要确定与外部设备连接的是哪一个串口。
2.设置串口参数:打开串口测试软件,选择与外部设备连接的串口。
然后,需要设置串口的一些参数,包括波特率、数据位、停止位、校验位等。
这些参数需要与外部设备的设置一致。
3.发送数据:串口测试软件一般都具备发送数据的功能。
在发送数据时,可以输入要发送的数据内容,并选择发送的方式,可以是单次发送,也可以是连续发送。
4.接收数据:测试软件提供接收数据的功能,在接收数据时,可以选择接收的数据转换格式,一般包括ASCII码、十六进制等。
接收到的数据会显示在测试软件的接收区域。
5.校验接收数据:校验接收到的数据是否与预期一致。
可以通过查看接收区域中显示的数据,与预期的数据进行对比。
6.错误处理:当发生错误时,需要进行错误处理。
可以查看错误日志或者通过测试软件提供的报错功能,来定位错误的原因。
7.测试功能:测试软件一般还提供了一些功能,如自动测试、循环测试等。
可以使用这些功能对串口进行更全面的测试。
8.测试性能:除了功能测试外,还可以测试串口的性能。
可以测试串口的最大传输速率,保证其能够满足实际需求。
9.测试协议:如果需要验证串口通信协议的正确性,可以编写测试脚本或使用测试工具对协议进行测试。
通过模拟多种情况,测试协议的鲁棒性和稳定性。
10.编写测试报告:对测试过程进行总结,并编写测试报告,描述测试的步骤、结果和问题。
测试报告可以帮助开发人员和工程师更好地改进和优化系统,提高串口的稳定性和可靠性。
总结:串口测试是一项重要的任务,可以帮助验证串口的功能和可靠性,在产品开发和测试中具有重要意义。
MFC自动检测串口
怎样检测电脑的串口是否存在?程序在初始化的时候,自动检测系统的串口是否存在或者被占用,可以使用如下的方法:在基于对话框的设计中,我们采用MSComm控件作为串口接口使用,但该控件没有提供检测所使用串口是否存在的函数,所以我们在程序初始化的时候如果使用了系统中不存在的串口(如,在有些笔记本中,COM1是不存在的),系统会异常,造成系统初始化不正常。
为了解决这个问题,同时使我们的程序有更好的交互特性,我们可以采用如下的方法来实现这个判断。
该代码仅供参考。
该段代码一般放在OnInitDialog中。
HANDLE m_hCom;CString com[2] = {"COM1", "COM2"};CString str="";int cnt = 0;for(int i = 0; i< 2; i++){m_hCom = CreateFile(com[i], GENERIC_READ | GENERIC_WRITE, 0, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL|FILE_FLAG_OVERLAPPED, NULL); //这里的CreateFile函数起了很大的作用,可以用来创建系统设备文件,如果该设备不存在或者被占用,则会返回一个错误,即下面的INVALID_HANDLE_VALUE ,据此可以判断可使用性。
详细参见MSDN中的介绍。
if(m_hCom == INVALID_HANDLE_VALUE) // 如果没有该设备,或者被其他应用程序在用*******************{str+=com[i]; // 记录下该串口名称,以备后面提示用str+=" ";}else{cnt = i + 1; // 如果存在,则记录下来。
这里只记录了一个,也可以采用一个数组来记录所有存在串口;}CloseHandle(m_hCom); // 关闭文件句柄,后面我们采用控件,不用API }if(cnt) // 如果串口存在,则执行相应的初始化(采用控件){if(m_ctrlMscom.GetPortOpen()) // m_ctrlMscom是控件的一个实例{m_ctrlMscom.SetPortOpen(FALSE);}m_ctrlMscom.SetCommPort(cnt);if(!m_ctrlMscom.GetPortOpen()){m_ctrlMscom.SetPortOpen(TRUE);}m_ctrlMscom.SetSettings("4800,n,8,1");m_ctrlMscom.SetInputMode(1);m_ctrlMscom.SetRThreshold(RX_PKG_SIZE);m_ctrlMscom.SetInputLen(0);m_ctrlMscom.GetInput();m_strComStatus.Format("COM%d, 4800, n, 8, 1", cnt);m_ComSettting[0] = cnt-1;}else // 如果不存在,则显示错误信息,而不进行串口操作,防止系统异常造成界面的初始化不完全{AfxMessageBox(str+"doesn't exist or is being used by otherprogram",MB_OK);m_ComSettting[0] = 0;m_strComStatus.Format("No COM can be used! Plesase check your hardware!");}程序中标记***************的部分是该实现的关键,也就是CreateFile()这个API的调用的作用和返回值得判断,对于一般串口设置程序来说,很好用了。
MFC通过mscomm控件实现自动选择串口
最近在看MFC串口通信,网上有好多资料能实现通信,但是实现自动选择串口的比较少。
刚刚编出来一个,学MFC不久方法比较笨,不过还是可以自动选择1~8串口的,大家凑合着看看。
我只写一下自动选择串口的部分,也就是初始化函数,其他的通信部分网上有好多资料,都差不多。
就是初始化mscomm函数,我的初始化函数是int dakaiduankou()(名字起得挺傻的)这个函数要设置一个返回值,因为要用return NULL;具体函数是:if(m_ctrlComm.GetPortOpen())//如果发现串口本来是打开的,则关闭串口m_ctrlComm.SetPortOpen(FALSE);m_ctrlComm.SetInputMode(1);//输入方式为二进制方式m_ctrlComm.SetInBufferSize(1024);//设置输入缓冲区大小m_ctrlComm.SetOutBufferSize(512);//设置输出缓冲区大小m_ctrlComm.SetSettings("9600,n,8,1");//波特率9600,无校验,8个数据位,1个停止位m_ctrlComm.SetRThreshold(1);//参数1表示每当串口接收缓冲区中有多于或等于1个字符时将引发一个接收数据的OnComm 事件m_ctrlComm.SetInputLen(0);//设置当前接收区数据长度为0 try{if(!m_ctrlComm.GetPortOpen()){m_ctrlComm.SetCommPort(1);m_ctrlComm.SetPortOpen(TRUE);MessageBox("使用端口1");Sleep(20);return NULL;}}catch (...){}try{if(!m_ctrlComm.GetPortOpen()){m_ctrlComm.SetCommPort(2);m_ctrlComm.SetPortOpen(TRUE); MessageBox("使用端口2"); Sleep(20);return NULL;}}catch (...){}try{if(!m_ctrlComm.GetPortOpen()) {m_ctrlComm.SetCommPort(3);m_ctrlComm.SetPortOpen(TRUE); MessageBox("使用端口3"); Sleep(20);return NULL;}catch (...){}try{if(!m_ctrlComm.GetPortOpen()) {m_ctrlComm.SetCommPort(4);m_ctrlComm.SetPortOpen(TRUE); MessageBox("使用端口4"); Sleep(20);return NULL;}}catch (...){}tryif(!m_ctrlComm.GetPortOpen()) {m_ctrlComm.SetCommPort(5);m_ctrlComm.SetPortOpen(TRUE); MessageBox("使用端口5"); Sleep(20);return NULL;}}catch (...){}try{if(!m_ctrlComm.GetPortOpen()) {m_ctrlComm.SetCommPort(6);m_ctrlComm.SetPortOpen(TRUE);MessageBox("使用端口6"); Sleep(20);return NULL;}}catch (...){}try{if(!m_ctrlComm.GetPortOpen()) {m_ctrlComm.SetCommPort(7);m_ctrlComm.SetPortOpen(TRUE); MessageBox("使用端口7"); Sleep(20);return NULL;}}catch (...){}try{if(!m_ctrlComm.GetPortOpen()){m_ctrlComm.SetCommPort(8);m_ctrlComm.SetPortOpen(TRUE);MessageBox("使用端口8");Sleep(20);return NULL;}}catch (...){MessageBox("通信端口错误,请查看通信端口是否存在","测试平台",MB_OK|MB_ICONINFORMATION);}。
VC(MFC)编写串口调试助手
VC(MFC)编写串口调试助手1.序确定基本功能:1.自动寻找串口,并自动添加到下拉框中共选择;2.有波特率、数据位、停止位、校验位的选择设置;3.串口打开控制按钮;4.发送、清除按钮;5.接收是自动实现的;6.有定时自动发送功能;7.有传送文件功能;8.有状态栏显示,指示串口状态,设置参数和发送接收显示。
下面就一步步实现,本人纯业余,只是记录下来这个学习过程,请勿拍砖。
开发平台Visual C++6.0英文版,电脑是i7-2670Q四核8G内存1G独显的笔记本,装的win7 64位旗舰版,因此VC6兼容不是太好,有些小毛病,不过不影响编写。
2.创建MFC项目File -> New -> Projects选择MFC AppWizard(exe),项目名称commassist选择OK选中Dialog based,点击Next> 。
默认选项,点击Next> ,继续默认选项,点击Next> ,如果选中As a statically linked library,生产的EXE可直接在没装VC的机器上运行。
可以在项目中进行更改。
选择第二个CCommassistDlg,点击Finish点击OK。
项目创建完毕,进入项目。
删除界面上确定和取消按钮以及静态文字。
3.创建界面保存后便可以开始创建界面了。
参考界面仿照设计的界面,具体添加按钮或编辑框等的布局步骤就不用细说了。
4.图标修改在资源视图中选择Icon右键InsertIcon加入打开和关闭的Icon图标或自行绘制,如下图IDR_MAINFRAME原为MFC提供的图标,这里我直接改成自己的,生成EXE后将会显示这个图标。
下面将帮助页面图标也改为自绘图标。
在打开按钮旁边加入自绘的打开和关闭图标:先加入工具条中的Picture,然后选中右键看属性,并如图将Image选为默认的IDI_ICON_CLOSE。
如下图5.基本设置下面对各个按钮及编辑框设置进行描述右键串口对应的Combo Box,ID设置为IDC_COMLIST,Type设置为Drop List,Sort不选择(我系统是WIN7 64位,不选中反而自动排序,至于XP得试试看了,以下的选择相同)。
基于CSerialMFC的串口调试助手程序实现
基于CSerialMFC的串口调试助手程序实现文章以MFC的CDialog类为中心,加上CSerial类的支持,采用RS-232接口标准,使用MFC进行串口调试助手程序开发,并在程序中提供通信口、波特率、数据位、校验位和停止位等通信参数的设置。
希望能够对相关工作提供参考。
标签:串口通信;C++;MFC;RS-2321 串行通讯协议如今计算机网络技术和多微机系统的应用广泛,计算机通信的重要性越发显现[1]。
计算机通信可以分为并行通信和串行通信。
并行通信将数据字节的各位用多条数据线同时传送,控制简单,传输速度快,但是成本较高。
串行通信则将数据字节分成一位一位的形式在一条传输线上逐个传送,成本低,但是控制复杂。
串行通信更方便易行,所以应用十分广泛,文章中的串口通讯采用串行通讯。
在实现计算机通信中,首先需要确定使用什么协议。
所谓协议,实际上就是通信双方彼此都知道、并且遵守的东西。
协议包含的信息必须在通信之前送达,协议对于所控制的通信而言是先驗的[3]。
作为一种点对点的通信方式,串行通信在数据流向中可分为单工、半双工和双工。
单工指物理上一方只能向另一方传送数据;半双工指物理上双方可以互传数据,但是任一时刻只能有一个方向的流。
全双工指在同一时刻,任何一方都可以向另一方发送数据。
较为流行的串行通信协议可分为同步串行协议和异步串行协议[1]。
同步协议中,双方约定好采样率后即开始数据的传输,数据的协调过程不需要专门的起始信息,但是要建立发送方时钟对接收方时钟的直接控制,双方达到完全同步,线上的每个数据都是有效的。
异步协议中,不再要求收发双方时钟的完全一致,发送方在任何时刻都可以发送若干比特组成的帧,接收方对数据的到达是无法预测的。
帧与帧之间的间隔由发送方控制,可以取任意值[1]。
发送端和接收端都以“接收时钟”和“波特率因子”决定一位的时间长度。
以起止式异步传输协议为例,每次异步传输的信息都以一个起始位开头,以一个停止位结束。
用MFC编写简单串口
1.建立项目:打开VC++6.0,建立一个基于对话框的MFC应用程序SCommTest(与我源代码一致,等会你会方便一点);2.在项目中插入MSComm控件选择Project菜单下Add To Project子菜单中的Components and Controls…选项,在弹出的对话框中双击Registered ActiveX Controls项(稍等一会,这个过程较慢),则所有注册过的ActiveX控件出现在列表框中。
选择Microsoft Communications Control, version 6.0,,单击Insert按钮将它插入到我们的Project中来,接受缺省的选项。
(如果你在控件列表中看不到Microsoft Communications Control, version 6.0,那可能是你在安装VC6时没有把ActiveX一项选上,重新安装VC6,选上ActiveX 就可以了),这时在ClassView视窗中就可以看到CMSComm类了,(注意:此类在ClassWizard中看不到,重构clw文件也一样),并且在控件工具栏Controls中出现了电话图标(如图1所示),现在要做的是用鼠标将此图标拖到对话框中,程序运行后,这个图标是看不到的。
3.利用ClassWizard定义CMSComm类控制对象打开ClassWizard->Member Viariables选项卡,选择CSCommTestDlg类,为IDC_MSCOMM1添加控制变量:m_ctrlComm,这时你可以看一看,在对话框头文件中自动加入了//{{AFX_INCLUDES() #i nclude "mscomm.h" //}}AFX_INCLUDES (这时运行程序,如果有错,那就再从头开始)。
4.在对话框中添加控件向主对话框中添加两个编辑框,一个用于接收显示数据ID为IDC_EDIT_RXDATA,另一个用于输入发送数据,ID为IDC_EDIT_TXDATA,再添加一个按钮,功能是按一次就把发送编辑框中的内容发送一次,将其ID 设为IDC_BUTTON_MANUALSEND。
串口MSComm控件五种不同校验方式对数据收发的影响
串口MSComm控件五种不同校验方式对数据收发的影响串口MSComm控件有五种校验方式,分别是无校验(None),奇校验(Odd),偶校验(Even),1校验(Mark),0校验(Space)。
在RS232/RS485/RS422通讯中,通过串口发送一字节(8BIT)数据时,首先发送起始位(固定为0),然后发送8位数据(先低位后高位),如果校验方式不是无校验(None),则紧接着会发送一位校验位,最后发送停止位。
停止位固定为1。
停止位依据串口属性的设置可为1位,1.5位或2位。
为了说明简洁起见,下面均假设停止位位数为1而数据位位数为8。
在数据发送时,如果校验方式设置为无校验(None),则不发送校验位;否则会发送一位校验位。
具体地,如果校验方式设置为1校验(Mark),校验位固定为1;如果校验方式设置为0校验(Space),校验位固定为0;如果校验位为奇校验(Odd),或者偶校验(Even),那么校验位可能为0也可能为1,依据所发送的数据计算得出。
计算方法:如果是奇校验,那么8位数据和1位校验位的累加和必是奇数;对应的,如果是偶校验,8位数据和1位校验位的累加和必为偶数。
比如,数据37,其二进制编码为00100101,编码中含有5个0和3个1,5*0+3*1=3,如果采用奇校验,那么校验位为0;如果使用偶校验,校验位则为1。
使用MSComm控件发送数据时,校验位无需用户干预,数据发送时自动地由操作系统计算、添加、发出。
串口MSComm控件在接收数据时,如果无校验,则只要检测到串口出现了数据,数据总能收到(试验发现,即使停止位为0也不会被认为是错误帧而遭遇抛弃);而采用了某种校验后,只有校验通码正确的数据才能被正确地收到。
试验中发现,发生校验错的那些数据在后面能校验通过的数据被收到时才被输出,输出值一律为5BH。
为什么是5BH(‘[’)呢?不明白,纳闷中…下面是试验过程中的截图:第一组试验:发送方发送的1个数据桢有10位组成:1位起始位,8位数据位,1位停止位试验(1.1)发方:9600,N,8,1(发出的数据位数为8)收方:9600,N,8,1解读:协议完全匹配,所有数据均能被正确收到。
用MFC实现的z-stack串口调试程序
Z-stack串口调试程序文档(1)需要分析1.实现基本的串口收发A.手动设置串口基本参数:a.串口选择b.波特率选择c.数据位选择d.停止位选择e.奇偶校验选择B.显示格式控制和发送格式控制可以手动选择十六进制或字符串格式发送或显示C.实现发送区与接收区的手动清空2.在基本串口收发的基础上,实现按z-stack协议的消息格式来收发按z-stack消息帧格式填写发送数据,然后程序内部进行相应的拼接。
3. 对接收数据的相应处理(2)概要设计功能划分:1.串口基本参数设置功能2.数据发送功能3.数据接收并显示功能4.z-stack协议的消息格式填写发送数据功能5.对接收数据处理功能(暂留)(3)详细设计详细设计界面如下:(4)编码与实现1.对话框程序导入时对一些控件的初始化BOOL CtestDlg::OnInitDialog(){// TODO: 在此添加额外的初始化代码CString combobox_item=NULL;//combobox_item用来暂存各个组合框项的值//初始化组合框1--串口选择CComboBox* comboobject_one=NULL;//获取combobox窗口指针comboobject_one=(CComboBox*)GetDlgItem(IDC_COMBO1);combobox_item="COM1";comboobject_one->InsertString(0,(LPCTSTR)combobox_item);//添加选项COM1 combobox_item="COM2";comboobject_one->InsertString(1,(LPCTSTR)combobox_item);//添加选项COM2 combobox_item="COM3";comboobject_one->InsertString(2,(LPCTSTR)combobox_item);//添加选项COM3 combobox_item="COM4";comboobject_one->InsertString(3,(LPCTSTR)combobox_item);//添加选项COM4 combobox_item="COM5";comboobject_one->InsertString(4,(LPCTSTR)combobox_item);//添加选项COM5 combobox_item="COM6";comboobject_one->InsertString(5,(LPCTSTR)combobox_item);//添加选项COM6 combobox_item="COM7";comboobject_one->InsertString(6,(LPCTSTR)combobox_item);//添加选项COM7 combobox_item="COM8";comboobject_one->InsertString(7,(LPCTSTR)combobox_item);//添加选项COM8 combobox_item="COM9";comboobject_one->InsertString(8,(LPCTSTR)combobox_item);//添加选项COM9 combobox_item="COM10";comboobject_one->InsertString(9,(LPCTSTR)combobox_item);//添加选项CO10 comboobject_one->SetCurSel(2);//设置默认显示的是COM3,自己设置//初始化组合框2--波特率选择CComboBox* comboobject_two=NULL;//获取combobox窗口指针comboobject_two=(CComboBox*)GetDlgItem(IDC_COMBO2);combobox_item="9600";comboobject_two->InsertString(0,(LPCTSTR)combobox_item);//添加选项9600 combobox_item="110";comboobject_two->InsertString(1,(LPCTSTR)combobox_item);//添加选项"110" combobox_item="300";comboobject_two->InsertString(2,(LPCTSTR)combobox_item);//添加选项"300" combobox_item="600";comboobject_two->InsertString(3,(LPCTSTR)combobox_item);//添加选项"600"; combobox_item="1200";comboobject_two->InsertString(4,(LPCTSTR)combobox_item);//添加选项combobox_item="2400";comboobject_two->InsertString(5,(LPCTSTR)combobox_item);//添加选项combobox_item="4800";comboobject_two->InsertString(6,(LPCTSTR)combobox_item);//添加选项combobox_item="14400";comboobject_two->InsertString(7,(LPCTSTR)combobox_item);//添加选项combobox_item="19200";comboobject_two->InsertString(8,(LPCTSTR)combobox_item);//添加选项combobox_item="28800";comboobject_two->InsertString(9,(LPCTSTR)combobox_item);//添加选项combobox_item="38400";comboobject_two->InsertString(10,(LPCTSTR)combobox_item);//添加选项combobox_item="115200";comboobject_two->InsertString(11,(LPCTSTR)combobox_item);//添加选项combobox_item="57600";comboobject_two->SetCurSel(0);//设置默认显示的是9600,自己设置//初始化组合框3--数据位选择CComboBox* comboobject_three=NULL;//获取combobox窗口指针comboobject_three=(CComboBox*)GetDlgItem(IDC_COMBO3); combobox_item="5";comboobject_three->InsertString(0,(LPCTSTR)combobox_item);//添加选项combobox_item="6";comboobject_three->InsertString(1,(LPCTSTR)combobox_item);//添加选项combobox_item="7";comboobject_three->InsertString(2,(LPCTSTR)combobox_item);//添加选项combobox_item="8";comboobject_three->InsertString(3,(LPCTSTR)combobox_item);//添加选项comboobject_three->SetCurSel(3);//设置默认显示的是第3个"8",自己设置//初始化组合框4--停止位选择CComboBox* comboobject_four=NULL;//获取combobox窗口指针comboobject_four=(CComboBox*)GetDlgItem(IDC_COMBO4); combobox_item="1";comboobject_four->InsertString(0,(LPCTSTR)combobox_item);//添加选项combobox_item="2";comboobject_four->InsertString(1,(LPCTSTR)combobox_item);//添加选项comboobject_four->SetCurSel(0);//设置默认显示的是第一个"1",自己设置//初始化组合框5--校验位选择CComboBox* comboobject_fine=NULL;//获取combobox窗口指针comboobject_fine=(CComboBox*)GetDlgItem(IDC_COMBO5); combobox_item="无";comboobject_fine->InsertString(0,(LPCTSTR)combobox_item);//添加选项combobox_item="奇校验";comboobject_fine->InsertString(1,(LPCTSTR)combobox_item);//添加选项combobox_item="偶校验";comboobject_fine->InsertString(2,(LPCTSTR)combobox_item);//添加选项comboobject_fine->SetCurSel(0);//设置默认显示的是第一个"1",自己设置//初始化单选框//让第1个Radio初始时为选中状态((CButton*)GetDlgItem(IDC_RADIO1))->SetCheck( 1 );//用来标记是否选择了第1个Radio按钮,值为1则为选择,值为0则为未选择radio_one_choice=1;//让第2个Radio初始时为未选中状态((CButton*)GetDlgItem(IDC_RADIO2))->SetCheck( 0 );radio_two_choice=0;//让第3个Radio初始时为未选中状态((CButton*)GetDlgItem(IDC_RADIO3))->SetCheck( 0 );radio_three_choice=0;//让第4个Radio初始时为选中状态((CButton*)GetDlgItem(IDC_RADIO4))->SetCheck( 1 );radio_four_choice=1;//让第5个Radio初始时为未选中状态((CButton*)GetDlgItem(IDC_RADIO5))->SetCheck( 0 );radio_fine_choice=0;//让第6个Radio初始时为选中状态((CButton*)GetDlgItem(IDC_RADIO6))->SetCheck( 1 );radio_six_choice=1;/*按Z-Stack协议消息帧的格式来限定每个字段的最大输入长度:说明:因为是以十六进制填写的,所以当某个字段实际占n个字节时,则对应编辑框限定的长度为2*n,因为十六进制的每个4bit对应编辑框的一个字节CEdit::SetLimitText( UINT nMax );==nMax:text limit, in bytes.*/m_edit3.SetLimitText(2);//SOP (Start of Packet):帧头,占一个字节,固定为0x02 m_edit4.SetLimitText(4);//CMD (Command ID):命令号,占两字节m_edit5.SetLimitText(2);//LEN (Length):占一个字节,表示Data的长度m_edit6.SetLimitText(2);//FCS (Frame check sequence) :帧检验序列,占一个字节。
mfc串口
mfc串口.txt如果你看到面前的阴影,别怕,那是因为你的背后有阳光!我允许你走进我的世界,但绝不允许你在我的世界里走来走去。
用户登录 | 用户注册首页┆网络学院┆软件下载┆源码下载┆新云专区┆推荐软件┆源码排行┆软件排行┆最新源码┆最新软件┆新云论坛首页ASP编程.NET专区PHP编程Java编程数据库类网页设计服务器类编程开发图形设计软件教学安全相关热门标签:QQ(467) Windows(317) 浏览器(272) 加速器(169) Vista(92) 杀毒软件(91)当前位置:新云网络→网络学院→编程开发→ Visual C++ →串行通信的基本原理及用MFC实现串口通信编程日期:2006-03-27 15:45:42 来源:本站整理串行通信的基本原理及用MFC实现串口通信编程减小字体增大字体在Windows应用程序的开发中,我们常常需要面临与外围数据源设备通信的问题。
计算机和单片机(如MCS-51)都具有串行通信口,可以设计相应的串口通信程序,完成二者之间的数据通信任务。
实际工作中利用串口完成通信任务的时候非常之多。
已有一些文章介绍串口编程的文章在计算机杂志上发表。
但总的感觉说来不太全面,特别是介绍32位下编程的更少,且很不详细。
笔者在实际工作中积累了较多经验,结合硬件、软件,重点提及比较新的技术,及需要注意的要点作一番探讨。
希望对各位需要编写串口通信程序的朋友有一些帮助。
一.串行通信的基本原理串行端口的本质功能是作为CPU和串行设备间的编码转换器。
当数据从 CPU经过串行端口发送出去时,字节数据转换为串行的位。
在接收数据时,串行的位被转换为字节数据。
在Windows环境(Windows NT、Win98、Windows2000)下,串口是系统资源的一部分。
应用程序要使用串口进行通信,必须在使用之前向操作系统提出资源申请要求(打开串口),通信完成后必须释放资源(关闭串口)。
串口通信程序的流程如下图:二.串口信号线的接法一个完整的RS-232C接口有22根线,采用标准的25芯插头座(或者9芯插头座)。
基于MFC串口事件驱动检测遥测数据包的设计与实现
基于MFC串口事件驱动检测遥测数据包的设计与实现王宏斌;段玲;孙文君;贺俊旺【期刊名称】《工业控制计算机》【年(卷),期】2015(000)008【摘要】在星上单机测试过程中,需要将星上数据通过CCSDS协议及其封装下传到地面PC机上,供其解析和分析。
由于地面解析软件部分设计不合理,导致数据丢失或者实时性不强,造成测试人员误判,从而引起单机性能指标的误判。
针对此类问题,基于MFC设计软件,提出基于串口驱动事件的方式,对星上遥测数据包进行丢包检测,同时对星上遥测数据包遥测量进行解析和判读。
通过此软件,有效地检测到星上单机软件丢包现象的情况并简易地实现了星上遥测量状态的监测。
%ln testing process of satel ite machine,the data of satel ite needs to be transferred to PC on the ground under the CCSDS protocol and its encapsulation for parsing and analysis.Due to design of ground analytic software is unreason-able,it leads to loss of data or real time capability not strong,which causes testers misjudgment and leads to miscalculation of a performance index.Aiming at this problem,based on the MFC design software and the way in which a serial port driv-er,the satel ite telemetry packet loss can be detected,while the satel ite telemetry data packet parsing and interpretation.【总页数】2页(P15-16)【作者】王宏斌;段玲;孙文君;贺俊旺【作者单位】上海微小卫星工程中心,上海 201203;东华大学纺织学院,上海201620;上海微小卫星工程中心,上海 201203;上海微小卫星工程中心,上海201203【正文语种】中文【相关文献】1.基于PC104的电缆检测仪串口通信软件设计与实现 [J], 冯海星;先明乐2.基于事件驱动方式的高速串口通信方案的设计 [J], 吴智龙;李伟彤3.基于事件驱动的入侵检测系统设计与实现 [J], 郝平;李杰4.基于串口通信的测压管水位检测系统设计与实现 [J], 曹乐南;李伟恒5.基于MFC的航空电子系统综合自动检测设备客户端软件设计与实现 [J], 王凯; 陈德军; 范光华; 宋帆因版权原因,仅展示原文概要,查看原文内容请购买。
检测串口程序
bSuccess = TRUE;
portse.Add(i);
////可用的串口
//Don't forget to close the port, since we are going to do nothing with it anyway
CloseHandle(hPort);
}
//Add the port number to the array which will be returned
str.Format(_T("%d "),uiset);
m_bolPort.AddString(str);
}
}
}
EnumerateSerialPorts 函数如下:
void Ctbo*_debug_viewDlg::EnumerateSerialPorts(CUIntArray& ports, CUIntArray& portse,
BOOL bSuccess = FALSE;
HANDLE hPort = ::CreateFile(sPort, GENERIC_READ | GENERIC_WRITE, 0, 0, OPEN_E*ISTING,
0, 0);
if (hPort == INVALID_HANDLE_VALUE)
//...
.
z.
-
}
Add 函数如下定义:
void Ctbo*_debug_viewDlg::Add(void)
{
EnumerateSerialPorts(ports,portse,portsu);
unsigned short uicounter;
unsigned short uiset;
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
怎样检测电脑的串口是否存在?
程序在初始化的时候,自动检测系统的串口是否存在或者被占用,可以使用如下的方法:
在基于对话框的设计中,我们采用MSComm控件作为串口接口使用,但该控件没有提供检测所使用串口是否存在的函数,所以我们在程序初始化的时候如果使用了系统中不存在的串口(如,在有些笔记本中,COM1是不存在的),系统会异常,造成系统初始化不正常。
为了解决这个问题,同时使我们的程序有更好的交互特性,我们可以采用如下的方法来实现这个判断。
该代码仅供参考。
该段代码一般放在OnInitDialog中。
HANDLE m_hCom;
CString com[2] = {"COM1", "COM2"};
CString str="";
int cnt = 0;
for(int i = 0; i< 2; i++)
{
m_hCom = CreateFile(com[i], GENERIC_READ | GENERIC_WRITE, 0, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL|
FILE_FLAG_OVERLAPPED, NULL); //这里的CreateFile函数起了很大的作用,可以用来创建系统设备文件,如果该设备不存在或者被占用,则会返回一个错误,即下面的INVALID_HANDLE_VALUE ,据此可以判断可使用性。
详细参见MSDN中的介绍。
if(m_hCom == INVALID_HANDLE_VALUE) // 如果没有该设备,或者被其他应用程序在用*******************
{
str+=com[i]; // 记录下该串口名称,以备后面提示用
str+=" ";
}
else
{
cnt = i + 1; // 如果存在,则记录下来。
这里只记录了一个,也可以采用一个数组来记录所有存在串口;
}
CloseHandle(m_hCom); // 关闭文件句柄,后面我们采用控件,不用API }
if(cnt) // 如果串口存在,则执行相应的初始化(采用控件)
{
if(m_ctrlMscom.GetPortOpen()) // m_ctrlMscom是控件的一个实例
{
m_ctrlMscom.SetPortOpen(FALSE);
}
m_ctrlMscom.SetCommPort(cnt);
if(!m_ctrlMscom.GetPortOpen())
{
m_ctrlMscom.SetPortOpen(TRUE);
}
m_ctrlMscom.SetSettings("4800,n,8,1");
m_ctrlMscom.SetInputMode(1);
m_ctrlMscom.SetRThreshold(RX_PKG_SIZE);
m_ctrlMscom.SetInputLen(0);
m_ctrlMscom.GetInput();
m_strComStatus.Format("COM%d, 4800, n, 8, 1", cnt);
m_ComSettting[0] = cnt-1;
}
else // 如果不存在,则显示错误信息,而不进行串口操作,防止系统异常造成界面的初始化不完全
{
AfxMessageBox(str+"doesn't exist or is being used by other
program",MB_OK);
m_ComSettting[0] = 0;
m_strComStatus.Format("No COM can be used! Plesase check your hardware!");
}
程序中标记***************的部分是该实现的关键,也就是CreateFile()这个API的调用的作用和返回值得判断,对于一般串口设置程序来说,很好用了。
这样我们就可以设计一个比较完整的串口设置代码了。