0
votes

I'm working on a C++ program to communicate with an Arduino that's running an automated system. I'm using the serial library from this:

https://playground.arduino.cc/Interfacing/CPPWindows

I'm trying to send the Arduino a string which it will then parse into a command that will tell it how the system should move. The code for reading the command from the serial is this:

`void serialEvent() {

  while (Serial.available()) {
    char in = (char)Serial.read();
    input.concat(in);
  }
  int endChar = input.indexOf('\r');
  if (endChar != -1) {
    //inputLog.concat(input);
    //inputLog.concat('\n');
    String command = input.substring(0,endChar);
    command.toLowerCase();
    input.remove(0, endChar+1);
    String keyword = command.substring(0,4);
    if(keyword == "move"){
          int i = command.indexOf('x');
          if (i != -1) {
            endChar = command.indexOf(i, ',');
            xMove = command.substring(i + 1, endChar).toFloat();
          }
          i = command.indexOf('y');
          if (i != -1) {
            endChar = command.indexOf(i, ',');
            yMove = command.substring(i + 1, endChar).toFloat();
          }
    } else if (keyword == "stop") {
      xMove = 0;
      yMove = 0;
    } else if (keyword == "xpos") {
      Serial.print("X: ");
      Serial.println(xPos);
    } else if (keyword == "ypos") {
      Serial.print("Y: ");
      Serial.println(yPos);
    } else if (keyword == "getp") {
      Serial.print("X: ");
      Serial.print(xPos);
      Serial.print(", Y: ");
      Serial.println(yPos);
    } else if (keyword == "setx") {
      xPos = command.substring(4).toFloat();
    } else if (keyword == "sety") {
      yPos = command.substring(4).toFloat();
    } else if (keyword == "setp") {
      int i = command.indexOf('x');
          if (i != -1) {
            endChar = command.indexOf(i, ',');
            xPos = command.substring(i + 1, endChar).toFloat();
          }
          i = command.indexOf('y');
          if (i != -1) {
            endChar = command.indexOf(i, ',');
            yPos = command.substring(i + 1, endChar).toFloat();
          }
    } else if (keyword == "getl") {
      Serial.println(inputLog);
      inputLog = "";
    } else {
      Serial.println("error: 1");
      return;
    }
    Serial.println("ok\r");
    //Serial.print(nc);
  }

}`

This part seems to be running correctly, because I can run it with the Arduino Serial Monitor and it works. Here is a short test of the code I wrote in C++:

while (SP->IsConnected())
{
    string outputData = "";
    cin >> outputData;
    outputData.append(pcr);
    //outputData.append(pnc);
    writeResult = SP->WriteData((char*)outputData.c_str(), outputData.length());
    //writeResult = writeResult && SP->WriteData(pnc, 1);
    //writeResult = writeResult & SP->WriteData(pcr, 1);
    
    while (true) {
        Sleep(500);
        char incomingData[256] = "";
        readResult = SP->ReadData(incomingData, dataLength);
        //printf("Bytes read: (0 means no data available) %i\n", readResult);
        //incomingData[readResult] = 0;
        input.append(incomingData, 0, readResult);

        check_ok = input.find(pcr);
        check_error = input.find(error);

        if (check_ok != string::npos || check_error != string::npos || readResult == 0) {
            cout << "Receiving: " << input << '\n';
            input.clear();
            break;
        }
    }
}

The variable, pcr is defined earlier in the code as a pointer to the carriage return character, which the Arduino uses to identify the end of a command. My results of running this code is that the Arduino seems to read off the first command and execute it; however, it also reads off several gibberish characters, most of which equate to -52 as a numerical value. Any following commands don't seem to do anything and the arduino continues getting the gibberish characters. Additionally it seems that the ReadData function in C++ works fine. Does anyone know why this occurs? Is the Arduino's serial buffer getting corrupted by the WriteData function somehow?


Solved

I appear to have found the issue. The statement outputData(pcr) needed to be outputData(pcr, 0, 1) because the pointer was not null terminating. Thus the string was appending extra characters until it reached a null character.

1
Did you set up the serial port properly? Correct baud rate, ending char, stuff like that? Normally a gibberish output to a serial monitor means a bad baud rateChad K
No, its not a bad baud rate. It still reads out everything it should coherently. Its only that it adds gibberish on to the end of the data that I send the arduino.Zachary Goddard
Okay, that's good. Did you check and make sure the stop bit, parity, and newline chars are correctly configured?Chad K
That I'm unsure of. I assumed the serial class I'm using would handle those. How should they be configured to be correct?Zachary Goddard
I'm not sure how you would do that. I only experimented with serial a few times. I think you would aim towards doing something like SP->parity = something. Look at the examples on this page msdn.microsoft.com/en-us/library/…Chad K

1 Answers

0
votes

How long your data line is? Are you using TTL levels to send the data or not? If your line is longer than several meters and you are using TTL level communication (routing wires directly between devices) then you definitely will receive garbage from other device. Long line communication lines should use RS232 or RS485 instead, which are specially designed for it.