A useful serial port class (send and receive freely)

class for serial communication
/**/
#ifndef _CommUtils_H__
#define _CommUtils_H__

class CommUtils  
;

#endif


/**/
#include "stdafx.h"
#include "CommUtils.h"
#include "stdio.h"
const int READ_TIMEOUT = 500;

CommUtils::CommUtils()


CommUtils::~CommUtils()
{
    this->CloseCom();
}

bool CommUtils::OpenCom(int Port)
{
    if (bOpenCom)
    {
        this->CloseCom();
        bOpenCom = false;
    }
    char szport[10];
    sprintf(szport,"COM%d",Port);
    hComm = CreateFile(    szport,
                        GENERIC_READ|GENERIC_WRITE,
                        0,
                        NULL,
                        OPEN_EXISTING,
                        FILE_FLAG_OVERLAPPED, //FILE_ATTRIBUTE_NORMAL|
                        NULL);
    
    
    if (hComm == INVALID_HANDLE_VALUE)        return false;
    if (!SetupComm(hComm, 1024, 512))        return false;
    
    COMMTIMEOUTS commtimeouts;
    commtimeouts.ReadIntervalTimeout = MAXDWORD;
    commtimeouts.ReadTotalTimeoutConstant =0;
    commtimeouts.ReadTotalTimeoutMultiplier =0;
    commtimeouts.WriteTotalTimeoutConstant =0;
    commtimeouts.WriteTotalTimeoutMultiplier=0;
    
    if (!SetCommTimeouts(hComm, &commtimeouts))        return false;

    memset(&ReadovReady,0,sizeof(OVERLAPPED));
    memset(&WriteovReady,0,sizeof(OVERLAPPED));
    ReadovReady.hEvent = CreateEvent(NULL,TRUE,FALSE,NULL);
    WriteovReady.hEvent =CreateEvent(NULL,TRUE,FALSE,NULL);
    
    SECURITY_ATTRIBUTES sa;
    sa.nLength=sizeof(SECURITY_ATTRIBUTES);
    sa.lpSecurityDescriptor=NULL;
    sa.bInheritHandle = TRUE;
    
    DCB dcb;
    GetCommState(hComm, &dcb);
    dcb.fBinary = TRUE;
    dcb.fParity = TRUE;
    dcb.BaudRate = CBR_9600; // Baud rate 9600
    dcb.ByteSize = 8; // 8 data bits
    dcb.Parity = NOPARITY; // no parity
    dcb.StopBits = ONESTOPBIT; // 1 stop bit
    
    if (!SetCommState(hComm, &dcb ))        return false;

    bOpenCom = true;
    return bOpenCom;
}

bool CommUtils::WriteCom(unsigned char *sendchar, int sendsize)
{
    if (!bOpenCom)    return false;
    
    DWORD    BytesSent;
    DWORD    resD;        
    
    PurgeComm(hComm, PURGE_RXCLEAR | PURGE_TXCLEAR | PURGE_RXABORT | PURGE_TXABORT);
    
    BytesSent=0;
    BOOL hr = WriteFile(hComm,                            // Handle to COMM Port
                        sendchar,                        // Pointer to message buffer in calling finction
                        sendsize,                        // Length of message to send
                        &BytesSent,                        // Where to store the number of bytes sent
                        &WriteovReady);                    // Overlapped structure
    if(!hr)
    {
        if(GetLastError() != ERROR_IO_PENDING)
        {
            return false;
        }
        else
        {
            resD=WaitForSingleObject(WriteovReady.hEvent,INFINITE);
        }
        switch(resD)
        {
            case WAIT_OBJECT_0:
            {
                if(!GetOverlappedResult(hComm,&WriteovReady,&BytesSent,false))
                    return false;
                else
                    return true;
                
            }
            default:
                return false;
                break;
        }
    }
    return true;
}

void CommUtils::CloseCom()
{
    if (!bOpenCom)    return;

    CloseHandle(hComm);
    hComm=NULL;
    
    CloseHandle(ReadovReady.hEvent);
    CloseHandle(WriteovReady.hEvent );
    ReadovReady.hEvent =NULL;
    WriteovReady.hEvent =NULL;
}

bool CommUtils::ReadCom(unsigned char * ReceiveData, DWORD& ReceiveLength)
{
    if (!bOpenCom)    return false;
    if (ReadovReady.hEvent == NULL)    return false;
    
    ReceiveLength = 0;
    if (ReadFile(hComm, ReceiveData, 128, &ReceiveLength, &ReadovReady) == FALSE)
    {
        if (GetLastError() != ERROR_IO_PENDING)    return false;
    }

    if(ReceiveLength == 0)    return false;
    ReceiveData[ReceiveLength] = 0;

    DWORD dwRead;
    DWORD dwRes = WaitForSingleObject(ReadovReady.hEvent, READ_TIMEOUT);
    switch(dwRes)
    {
        case WAIT_OBJECT_0:
            if (!GetOverlappedResult(hComm, &ReadovReady, &dwRead, FALSE))    return false;
            break;

        case WAIT_TIMEOUT:
            break;                
            
        default:
            break;
    }
    return true;
}




Here's how to use it:
// 1. Include header files, define variables
#include "CommUtils.h"
CommUtils theComm;
unsigned char data[1024];
unsigned long len = 0;

// 2. Open the serial port and set the receive timer
theComm.OpenCom(1); // Open COM1 port
SetTimer(1, 50, 0);

// 3. Send data
theComm.WriteCom(data, len);

// 4. Receive data processing
void CUARTDlg::OnTimer(UINT nIDEvent)
{
    if (nIDEvent == 1)
    {
        if (theComm.ReadCom(data, len))
        {
            if (len > 0)    
            {
                // Receive data processing. . .
            }
        }
    }
    CDialog::OnTimer(nIDEvent);
}

Guess you like

Origin http://43.154.161.224:23101/article/api/json?id=325889453&siteId=291194637