Serial.available does not return correct value

The Serial.available() function (on computer side) sometimes returns 0 even if there is something in the buffer. For testing Arduino runs a simple “echo” sketch:

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

void loop() {
  if (Serial.available()) {
    char result=Serial.read();
    Serial.print(result);
  }
}

And Processing running is nearly minimal program:

import processing.serial.*;

Serial Arduino;

void setup() {
  Arduino  = new Serial(this,Serial.list()[0],115200);
  delay(3000);
  Arduino.write("   ");  //Flush garbage caused by reset
  delay(200);
  Arduino.clear();
  for (char i='0'; i<='9'; i++) {
    print("Sending " + i + " received ");
    Arduino.write(i);
    println(safeSerialRead());
  }
  exit();
}
  
int SerialTimeout=500;

char safeSerialRead() {
  int waitingStart=millis();
  while (Arduino.available()==0) {
    if ((millis()-waitingStart)>SerialTimeout) {
      print("***Serial timeout*** ");
      break;
    }
  }
  return (char(Arduino.read()));
}

The result in processing monitor is:

Sending 0 received 0
Sending 1 received 1
Sending 2 received 2
Sending 3 received 3
Sending 4 received 4
Sending 5 received ***Serial timeout*** 5
Sending 6 received ***Serial timeout*** 6
Sending 7 received 7
Sending 8 received 8
Sending 9 received ***Serial timeout*** 9

Note that immediately after the timeout the buffer is read anyway and ALWAYS gives the right result - so in reality the correct data were received but number of available bytes was not updated for some reason.
The exchanges that timeouts are repeatable and change with any change in the program. It also changes when extending the timeout.
For 1000 ms 7, 8 and 9 timeouts.
For 2000 and 3000 ms only 8 and 9 timeouts.
But for 10000 ms 3, 4, 6, 7, 8 and 9 timeouts.

Anyone encountered this error? Is there something to do against this?

Hi @Smajdalf, Can’t see any definite error there, but your Processing sketch doesn’t have any delays, so is a ‘busy loop’ and may not be allowing something else to happen. I suggest delay(20) in the while loop. (Which Arduino are you using?)

I have found calling draw() (which I don’t use at all) before the Serial.available() fixes the issue.
The Processing reference says

Called directly after ‘setup()’ , the ‘draw()’ function continuously executes the lines of code contained inside its block (…) ‘draw()’ is called automatically and should never be called explicitly.

It also says

There can only be one ‘draw()’ function for each sketch, and ‘draw()’ must exist if you want the code to run continuously, or to process events such as ‘mousePressed()’ . Sometimes, you might have an empty call to ‘draw()’ in your program, as shown in the second example above.

I did try to add an empty ‘draw()’ as the Reference says but it didn’t help. Only directly calling ‘draw()’ (which I shouldn’t do). It works despite it is not defined. Is there a correct way to trigger Serial update?

Serial update should just happen. My idea was that other things need to be given time to happen, so add delay, or use draw to repeat your action. Your code doesn’t allow setup to complete. Does that matter? don’t know, so assume it does.