简体   繁体   中英

Serial communication c++

I'm trying do some serial communication between my pc and an arduino ATmega2560

First the microntroller's program :

void setup() {
    Serial.begin(9600);
}

void loop() {
    Serial.write('A');
}

The arduino program is very basic, his aim is to check the next program which is on the pc.

The main.cpp :

#include <iostream>
#include "SerialPort.h"

using namespace std;

int main()
{
    SerialPort port("com3", 9600);

    while (1)
    {
        //Receive
        unsigned char dataR;
        port.receive(dataR, 1);
        cout << dataR << endl;
    }
    return 0;
}

The SerialPort.h:

#include <windows.h>
#include <iostream>

class SerialPort
{
public:
    //Constructors
    SerialPort();
    SerialPort(const char* port, unsigned long BaudRate);

    //Initialization
    void Initialize(const char* port, unsigned long BaudRate);

    //Serial I/O
    void receive(unsigned char &data, unsigned int byteSize);
    void transmit(unsigned char *data, unsigned int byteSize);

    //State
    void connect();
    void disconnect();
    bool isConnected();

    //Destructor
    ~SerialPort();

private:
    HANDLE handler;
    bool isConnect;
};

And the SerialPort.cpp :

#include "SerialPort.h"

/*Constructors*/
SerialPort::SerialPort()
    : isConnect(false) {}

SerialPort::SerialPort(const char* port, unsigned long BaudRate)
    : isConnect(false)
{
    Initialize(port, BaudRate);
}

/*Initialization*/
void SerialPort::Initialize(const char* port, unsigned long BaudRate)
{
    handler = CreateFile(port, GENERIC_READ | GENERIC_WRITE, NULL, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL);
    if (handler == INVALID_HANDLE_VALUE)
    {
        std::cout << "ERROR!::Error during opening port" << port << std::endl;
        return;
    }

    DCB serialParameters;
    if (!GetCommState(handler, &serialParameters)) /*Get com parameters*/
    {
        std::cout << "ERROR!::failed to get current serial parameters" << std::endl;
        return;
    }

    serialParameters.DCBlength = sizeof(DCB);
    serialParameters.BaudRate = BaudRate;
    serialParameters.ByteSize = 1; /*8 bit data format*/
    serialParameters.StopBits = TWOSTOPBITS;
    serialParameters.Parity = PARITY_NONE;

    if (!SetCommState(handler, &serialParameters)) /*Send modified com parameters*/
    {
        std::cout << "ALERT!:Failed to set THE Serial port parameters" << std::endl;
        return;
    }

    isConnect = true;
    PurgeComm(handler, PURGE_RXCLEAR | PURGE_TXCLEAR);
}

/*Serial I/O*/
void SerialPort::receive(unsigned char &data, unsigned int byteSize)
{
    ReadFile(handler, &data, byteSize, NULL, NULL);
}

void SerialPort::transmit(unsigned char *data, unsigned int byteSize)
{
    WriteFile(handler, data, byteSize, NULL, NULL);
}

/*State*/
void SerialPort::connect()
{
    isConnect = true;
}

void SerialPort::disconnect()
{
    isConnect = false;
}
bool SerialPort::isConnected()
{
    return isConnect;
}

/*Destructors*/
SerialPort::~SerialPort()
{
    if (isConnect)
    {
        isConnect = false;
        CloseHandle(handler);
    }
}

I've an issue with this program : I don't receive the right data. Where I should get on the terminal

A
A
A
...

I get weird characters made of ? in a square

I hope you understood my problem Thanks

The DCB ByteSize parameter is in bits . You have specified a UART frame with one data bit - which is not supported by the hardware at either end.

For a conventional N,8,1 data frame, use

        serialParameters.ByteSize = 8 ;
        serialParameters.StopBits = ONESTOPBIT ;
        serialParameters.Parity = NOPARITY ;

ByteSize is perhaps a misleading name. It defines the number of bits between the start and stop bit in an UART frame. Most commonly this is 8, but for pure ASCII data transfer 7 might be used - historically at least.

The Atmel AVR UART supports frames with 5 to 9 data bits. The PC's UART may be virtual, but will typically be compatible with the 16550 UART, which supported 5 to 8 bit data frames, however these days you are more likely to be using USB-Serial adapter, and the UART on the USB/Serial bridge may not support all 16550 modes - the common FTDI232R for example only supports 7 or 8 bit frames, while Prolific PL2303 supportts 5 to 8. It probably pays to avoid unconventional frames and stick to N,8,1 if you want to be sure it will work on a range of hardware.

From the Arduino documentation on Serial.begin() (emphasis added):

An optional second argument configures the data, parity, and stop bits. The default is 8 data bits, no parity, one stop bit .

I see this in your code (with no second parameter):

Serial.begin(9600);

and this

serialParameters.StopBits = TWOSTOPBITS;

I think that may be your problem.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM