Serial problem

Status
Not open for further replies.

amittel

Member
Hi!
I have a strange problem with Serial and Serial2 on a Teensy3.1.
Serial is used to output some debug messages via PC. Serial2 is connected to a bluetooth 2.0 device.
Sending data over bluetooth is working fine. But sending data to the mobile results in a strange problem.
I only want to transmit S:2#, where the number should go up. This is also not working.

I show you the excerpts from the file, so you can get an idea. I attach the complete file.

This is my setup
Code:
void setup() {
  pinMode(ledPIN, OUTPUT);
  pinMode(buzzer1PIN, OUTPUT);

  Serial.begin(9600);  //USB
  Serial2.begin(9600); //Bluetooth

  startLed();
}

void loop() {
  digitalWrite(ledPIN, HIGH);

  if (Serial2.available()) {
    Serial.println("Serial data available");
    char mode = Serial2.read();
    Serial.print("Mode Identifier: ");Serial.println(mode);

    if(mode == 'W') {
      Serial.println("Parsing WORKOUT data...");
      wStation    = Serial2.parseInt();
      wRound      = Serial2.parseInt();
      wWorkMin    = wWorkMin_tmp    = Serial2.parseInt();
      wWorkSec    = wWorkSec_tmp    = Serial2.parseInt();
      wPauseMin   = wPauseMin_tmp   = Serial2.parseInt();
      wPauseSec   = wPauseSec_tmp   = Serial2.parseInt();
      wPrepMin    = wPrepMin_tmp    = Serial2.parseInt();

...
wCurrentStation++;
//Sending current station to mobile
char buffer[5];
sprintf (buffer, "S:%d#",wCurrentStation);
Serial2.write(buffer);

Here is the log from the mobile captured over Chrome.
The counting is ok. Eight times "S:2#" is correct. So Serial2.write() is fired correct, but the incremented wCurrentStation isn't set.
Code:
Connected!
Sending Workout: W02,08,00,03,00,02,00,01
S:2#

S:2#
Serial data available
S:2#
erial data available
S:2#
rial data available
S:2#
ial data available
S:2#
al data available
S:2#
l data available
S:2#
I don't get it, why he is sending stuff from Serial?!
Also I'm creating a new variable for sending, but somehow there is stuff from the Serial inside somewho.
Also it's not counting up.
 

Attachments

  • Crosstimer.cpp
    10.6 KB · Views: 80
Last edited:
Holy Moly! You are right!
I'm sorry I mixed the following lines:
Code:
wRound      = Serial2.parseInt();
wStation    = Serial2.parseInt();
So my fault.

Now my output is looking better, but still a little strange
Code:
 Sending Workout: W02,10,00,02,00,01,00,01
 Serial data available    [COLOR="#FF0000"]<-- Still from my Serial?[/COLOR]
S:2#
 S:3#
 S:4#
 S:5#
 S:6#
 S:7#
 S:8#
Also there is a leading space.

I think the problem is still here somewhere
Code:
  if (Serial2.available()) {
    Serial.println("Serial data available"); [COLOR="#FF0000"]<-- I think here. But it shouldn't go over Serial2[/COLOR]
    char mode = Serial2.read();
    Serial.print("Mode Identifier: ");Serial.println(mode);

    if(mode == 'W') {
      Serial.println("Parsing WORKOUT data...");
      wRound      = Serial2.parseInt();
      wStation    = Serial2.parseInt();
 
Last edited:
Probably this:

Code:
        Serial2.println("R:"+wCurrentRound);

Adding a number after a string literal causes it to print whatever happens to be in memory *after* the "R:" data.

Try this for string concatenation:

Code:
        Serial2.println(String("R:")+wCurrentRound);

(I'm pretty sure Serial and Serial2 actually work....)
 
You are right.
I edited the part for the rounds and now everything is working fine.

The thing I don't understand is, that since I have a state machine it shouldn't be doing anything with the wCurrentRound until it's in that state.
That's why I thought it is not relevant.

But hey, you never stop learning :)
 
Adding a number after a string literal causes it to print whatever happens to be in memory *after* the "R:" data.
I'd be interested to know why this is. That's very odd behaviour I don't think I would have been able to find easily.
 
Last edited:
The power of C is that you can tell it what to do - the problem is the compiler works with what you give it. The function definition doesn't provide for this to work without help (Paul provided one such helper) - but the compiler found a way to take what was provided and map it to what was specified by the function. In this case that resolved to something not what you intended. At runtime the function just doesn't work with that in a usable way.

https://www.arduino.cc/en/Serial/Println

https://www.arduino.cc/en/Serial/Print
 
Last edited:
Right I think I'm kind of understanding

"R:" is parsed as a char str[]. As this is a pointer when wCurrentRound is added to it the memory location changes. From that location it will continually print until a '/0' is met.

Is that what's going on here?
 
Right I think I'm kind of understanding

"R:" is parsed as a char str[]. As this is a pointer when wCurrentRound is added to it the memory location changes. From that location it will continually print until a '/0' is met.

Is that what's going on here?

Exactly, the above println statement is equivalent to
Code:
printf("%s\n\r",&array + num)

and then the behaviour is obvious
 
Last edited:
Excellent! Thanks for clearing that up WMXZ

I forgot how strange things got when you start putting pointers out of bounds. C++ generally does a good job of doing most of that under the hood but of course string() is a class not a datatype to it's forced to use a char array
 
Status
Not open for further replies.
Back
Top