⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 serial.cpp

📁 wince下面一个串口程序,用于读取并分GPS数据,主要可以提取经纬度和时间
💻 CPP
字号:
// Serial.cpp: implementation of the CSerial class.
//
//////////////////////////////////////////////////////////////////////
/*
**	FILENAME			CSerial.cpp
**
**	PURPOSE				This class can read, write and watch one serial port.
**					It sends messages to its owner when something happends on the port
**					The class creates a thread for reading and writing so the main
**					program is not blocked.
**
**	CREATION DATE		15-09-2003
**	LAST MODIFICATION	08-11-2003
**
**	AUTHOR			rootgr wu
**
**
*/
#include "stdafx.h"
#include "comm.h"
#include "Serial.h"

#ifdef _DEBUG
#undef THIS_FILE
static char THIS_FILE[]=__FILE__;
#define new DEBUG_NEW
#endif

//////////////////////////////////////////////////////////////////////
// Construction/Destruction
//////////////////////////////////////////////////////////////////////

CSerial::CSerial()
{
	// Init handle to NULL
	m_hPort = NULL;
	m_hThread = NULL;
	m_nPortNr=0;

	m_hWnd=NULL;
}

CSerial::~CSerial()
{
	// release resources	
	//DWORD dwExitCode;

	if(m_hPort !=NULL) 
		CloseHandle(m_hPort);
	m_hPort = NULL;

	if(m_hWnd!=NULL)
		CloseHandle(m_hWnd);
	m_hWnd = NULL;
	/*  Force Exit Thread.
	if(m_hThread!=NULL)
	{
		GetExitCodeThread(m_hThread,&dwExitCode);
		ExitThread(dwExitCode);
	}
	*/
	StopReadThread();
	m_hThread=NULL;

}

BOOL CSerial::InitializePort(HWND hWnd,CString PortNum,UINT Baud, CString Parity, UINT DataBits, UINT StopBits)
{
	CString Nnn;

	// initialize critical section
	InitializeCriticalSection(&m_cs);
	// now it critical!
 	EnterCriticalSection(&m_cs);
	// Empty Port Handle.
	if(m_hPort!=NULL) 
	{
		CloseHandle(m_hPort);		
		m_hPort = NULL;
	}
	
	if(m_hThread!=NULL)
	{
		CloseHandle(m_hThread);
		m_hThread = NULL;
	}

	if(m_hWnd!=NULL)
	{
		CloseHandle(m_hWnd);
		m_hWnd = NULL;
	}
	// format port num.
	if(PortNum==L"COM1") m_nPortNr=1;
	if(PortNum==L"COM2") m_nPortNr=2;

	Nnn = PortNum + ":";
	// set message Handle.
	m_hWnd=hWnd;
	
	// Clear RX Buffer.
//	memset(m_RXBuff,0,512);
	
	m_hPort = CreateFile (Nnn,				// Pointer to the name of the port
							GENERIC_READ | GENERIC_WRITE,
											// Access (read-write) mode
							0,				// Share mode
							NULL,			// Pointer to the security attribute
							OPEN_EXISTING,	// How to open the serial port
							0,				// Port attributes
							NULL);			// Handle to port with attribute
											// to copy
	if (m_hPort == INVALID_HANDLE_VALUE)
	{  
		AfxMessageBox(_T("can't open port!"));
		return FALSE;
	}

	// Get Comm DCB
	if(!GetCommState(m_hPort,&m_dcb)) return FALSE;

	// Set Comm DCB
	m_dcb.BaudRate = Baud;

	if(Parity == "NONE") m_dcb.Parity = 0;
	if(Parity == "ODD") m_dcb.Parity = 1;
	if(Parity == "EVEN") m_dcb.Parity = 2;

	m_dcb.ByteSize = DataBits;

	if(StopBits == 1) m_dcb.StopBits = ONESTOPBIT;
	if(StopBits == 1.5) m_dcb.StopBits = ONE5STOPBITS;
	if(StopBits == 2) m_dcb.StopBits = TWOSTOPBITS;
	
	if(!SetCommState(m_hPort,&m_dcb)) return FALSE;

	// Get Comm Timeouts
	if(!GetCommTimeouts(m_hPort,&m_CommTimeouts)) return FALSE;

	// Set Comm Timeouts
	m_CommTimeouts.ReadIntervalTimeout = 500;
	m_CommTimeouts.ReadTotalTimeoutMultiplier = 500;
	m_CommTimeouts.ReadTotalTimeoutConstant = 1000;
	m_CommTimeouts.WriteTotalTimeoutMultiplier = 500;
	m_CommTimeouts.WriteTotalTimeoutConstant = 1000;

	if(!SetCommTimeouts(m_hPort,&m_CommTimeouts)) 
		return FALSE;

	// Set Comm Mask
	if(!SetCommMask(m_hPort,EV_RXCHAR | EV_CTS | EV_DSR | EV_RING))
		return FALSE;

	// flush the port
 	PurgeComm(m_hPort, PURGE_RXCLEAR | PURGE_TXCLEAR | PURGE_RXABORT | PURGE_TXABORT);

	// release critical section
	LeaveCriticalSection(&m_cs);
	return TRUE;
}

BOOL CSerial::WriteChar(BYTE Byte)
{
	DWORD dwNumBytesWritten;
	BOOL bResult;

	// Clear Comm Error
	PurgeComm(m_hPort, PURGE_RXCLEAR | PURGE_TXCLEAR | PURGE_RXABORT | PURGE_TXABORT);

	// write to port.
	bResult = WriteFile(m_hPort,				// Handle to COMM Port
						&Byte,					// Pointer to message buffer in calling finction
						1,			// Length of message to send
						&dwNumBytesWritten,		// Where to store the number of bytes sent
						NULL);

	if(!bResult || dwNumBytesWritten == 0) return FALSE;
	return TRUE;
}

DWORD WINAPI CSerial::ReadThread(LPVOID lpParam)
{
	CSerial *p=(CSerial *)lpParam;
	DWORD dwCommStatus = 0;			// comm event
	BOOL bResult = FALSE;			// waitcommevent result
	BOOL bClear = FALSE;			// clearcomm result
	BOOL bReadResult = FALSE;		// readfile result
	DWORD dwNumBytesRead = 0;		// number readed
	COMSTAT comstat;				// COMSTAT struct 
	DWORD dwError;					// error message
	unsigned char RXBuff;			// receive buffer

	// check if the port is opened,then clear buffer first.	
	if (p->m_hPort)  
		PurgeComm(p->m_hPort, PURGE_RXCLEAR | PURGE_TXCLEAR | PURGE_RXABORT | PURGE_TXABORT);
	else
		return 0;
	// clear buffer again,maybe it is no necessary.
	PurgeComm(p->m_hPort, PURGE_RXCLEAR | PURGE_TXCLEAR | PURGE_RXABORT | PURGE_TXABORT);
	
	while (1) 
	{
		// Wait for an event to occur for the port.
		bResult = WaitCommEvent (p->m_hPort, &dwCommStatus, NULL);

		if (bResult && (dwCommStatus & EV_RXCHAR)) 
		{
			do
			{
				// now it critical!
 				EnterCriticalSection(&p->m_cs);

				// Clear port Error message.	
				bClear = ClearCommError(p->m_hPort, &dwError, &comstat);
				if(comstat.cbInQue ==0) break;

				// clear RX Buffer and count
				dwNumBytesRead = 0;
				RXBuff = 0;
				bReadResult = ReadFile(p->m_hPort ,			// Handle to COMM port
										&RXBuff,			// RX Buffer Pointer
										1,					// Read one byte
										&dwNumBytesRead,	// Stores number of bytes read
										NULL);

				// release critical section
				LeaveCriticalSection(&p->m_cs);
				
				// display data.
				if(bReadResult && dwNumBytesRead == 1)
				{
					SendMessage(p->m_hWnd,WM_COMM_RXCHAR,(WPARAM)RXBuff,(LPARAM)p->m_nPortNr);
				}

			}while(bReadResult && dwNumBytesRead == 1);
		}		
	}
	return 1;
}

BOOL CSerial::ClosePort()
{
	// Close Port Handle.
	if(m_hPort!=NULL)
		CloseHandle(m_hPort);
	
	if(m_hWnd!=NULL)
		CloseHandle(m_hWnd);

		// Set port handle to NULL.
	m_hPort=NULL;
	m_hWnd=NULL;

	// delete CRITICAL_SECTION
	DeleteCriticalSection(&m_cs);

	return TRUE;
}

BOOL CSerial::StartReadThread()
{
	DWORD dwThreadID;
	// Start Comm Thread.
	if(!(m_hThread=(HANDLE)CreateThread(NULL,0,ReadThread,this,0,&dwThreadID))) 
		return FALSE;
	return TRUE;
}

BOOL CSerial::WriteChar(LPCTSTR lpString)
{
	DWORD dwNumBytesWritten;
	BOOL bResult;
	//UINT len = wcslen(lpString);
	// Clear Comm Error
	PurgeComm(m_hPort, PURGE_RXCLEAR | PURGE_TXCLEAR | PURGE_RXABORT | PURGE_TXABORT);
	
	// write to port.
	bResult = WriteFile(m_hPort,					// Handle to COMM Port
						lpString,					// Pointer to message buffer in calling finction
						wcslen(lpString)*2,			// Length of message to send
						&dwNumBytesWritten,			// Where to store the number of bytes sent
						NULL);

	if(!bResult || dwNumBytesWritten == 0) return FALSE;
	return TRUE;
}

BOOL CSerial::WriteChar(char *buf)
{
	DWORD dwNumBytesWritten;
	BOOL bResult;

	// Clear Comm Error
	PurgeComm(m_hPort, PURGE_RXCLEAR | PURGE_TXCLEAR | PURGE_RXABORT | PURGE_TXABORT);

	// write to port.
	bResult = WriteFile(m_hPort,					// Handle to COMM Port
						buf,					// Pointer to message buffer in calling finction
						strlen(buf),			// Length of message to send
						&dwNumBytesWritten,			// Where to store the number of bytes sent
						NULL);

	if(!bResult || dwNumBytesWritten == 0) return FALSE;
	return TRUE;

}


void CSerial::StopReadThread()
{
	DWORD dwExitCode;		// thread exit code
	UINT nError;			// return error code
	GetExitCodeThread(m_hThread,&dwExitCode);  // get Exit code
	nError = TerminateThread(m_hThread,dwExitCode); // stop and delete readthread
	if(nError = 0)
	{
		TRACE(L"TerminateThread Fail");
	//	AfxMessageBox(L"TerminateThread Fail");
	}
}

BOOL CSerial::WriteChar(char *buf, int nsize)
{
	DWORD dwNumBytesWritten;
	BOOL bResult;

	// Clear Comm Error
	PurgeComm(m_hPort, PURGE_RXCLEAR | PURGE_TXCLEAR | PURGE_RXABORT | PURGE_TXABORT);

	// write to port.
	bResult = WriteFile(m_hPort,					// Handle to COMM Port
						buf,						// Pointer to message buffer in calling finction
						nsize,						// Length of message to send
						&dwNumBytesWritten,			// Where to store the number of bytes sent
						NULL);

	if(!bResult || dwNumBytesWritten == 0) return FALSE;
	return TRUE;

}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -