Serial problem

Hii... I have a problem ,.. :~
When the micro-controller performed delay, I sent data through the serial port. But at the sub-program called store run, the data could not be processed.
Does anyone know why??

Here is the listing

store.txt (9.45 KB)

store.txt (9.45 KB)

I have tried another program that apply the principles but with a shorter void read. It works.

Does anybody know why?

void setup() {
Serial.begin(9600);
pinMode(13, OUTPUT);
}

void loop() {
digitalWrite(13, HIGH); // set the LED on
delay(5000); // wait for a second
read();
digitalWrite(13, LOW); // set the LED off
delay(1000);
}

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

I'm sorry, I don't know what you're asking, but your first example screams "use arrays". (And whispers "don't use Strings"))

alva:

  delay(5000);              // wait for a second

Comments should match the code, or just omit them.

when i send the data while microcontroller running the delay,
micro still processing data after the delay finished

That's how interrupts work.

String c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t,u,v;

Please note that, at present, the String library has bugs as discussed here and here.

In particular, the dynamic memory allocation used by the String class may fail and cause random crashes.

I recommend reworking your code to manage without String. Use C-style strings instead (strcpy, strcat, strcmp, etc.).

In both the first and the second program, I sent the data while the micro-processor was delay,
My question is:
Why the data could not be processed in the first program, yet it could be processed in the second program?

What i asked about why at the first program the interrupt (Nick said) doesnt work, and at the second program it works.

There are no interrupts in either program, so your question doesn't make sense.

Serial data is received using interrupts, but the interrupt service routine is not code you need to provide. All that the serial interrupt routine does is get a byte and put it in a buffer. It is your responsibility to get that data from the buffer before the buffer gets full, without abusing the poor Arduino with Strings.

To make it better, this is the case:

In the first program, when I sent the data, the arduino was in 'delay' condition. But when the 'delay' condition was over, the data couldn't be processed.

In the second program, when I sent the data, the arduino was in 'delay' condition. But when the 'delay' condition was over, the data could be processed.
Why?

In the second program, In the first program,

Could you maybe take another look at that last paragraph, and see how it reads?

Sorry for grammatical error... try to fix it

alva:
In the first program, when I sent the data, the arduino was in 'delay' condition. But when the 'delay' condition was over, the data couldn't be processed.

What do you mean "the data couldn't be processed"? Can you please post what you are sending and what output you see? That is a pretty meaningless description.

At the first program, I sent the following data:

SK,2000,SETLAIN,1,SETGT,1,SETTEMP,1,SETPH,1,SETAT,1,SETLEMBAB,1,SET,1,SETK,1,SETLL,0,

This data was sent when the arduino processed the delay in 5 second in the void kontroler ().
When the ardino has finished running the void kontroler (), it supposed to run void store ().
Normally, the data supposed to be processed in the void store()
and it should be appeared on the serial screen when currentCommand == 20.
The problem: it did not show up in the screen.

My expectation: to see

SK,2000,SETLAIN,1,SETGT,1,SETTEMP,1,SETPH,1,SETAT,1,SETLEMBAB,1,SET,1,SETK,1,SETLL,0,
2000,1,1,1,1,1,1,1,1,0

in the serial screen

A different result happened when I used the second program (after ledpin 13 was active and was doing delay), I sent the data :d.
After the arduino finished with the delay, the data was processed in the void store () and it was successfully appeared in the serial screen.

How did it happen?
Why it gave a different respond?

this is my first program and my second program

second_program.txt (378 Bytes)

first_program.txt (9.35 KB)

Someone have any idea?? :cold_sweat:

You're sending 85 characters and possibly more if you're got a CR or LF on the end. In the more recent versions of the IDE, that's enough to overflow the 64 byte read buffer. If you're early in your delay when the data is sent, some of it will get thrown away so your code will never see the 20th comma that triggers your serial prints of your results.

I'd suggest moving the printing code so that it runs every time you've received a character so you can see what you're getting. Or change the check to print when the currentCommand exceeds 10.

Once you satisfy yourself what's wrong though, you're going to want to ditch both the delays and the use of String; which sadly, looks like practically a complete rewrite. When you do, take a look at strtok - it's one way to parse out your data from a char array.

alva:
Someone have any idea?? :cold_sweat:

Don't use delay.

@ Wildbill:
Thanks for your explanation as it helps me out with my problem.
I still some other issues:

  1. How would you get a newer version of IDE?
  2. What is the maximum character I could send in 64 bytes read buffer?
  3. If I throw out String, what is the substitute?
  4. Considering question no.3, is there other way to solve my problem without re-writing the program? Can I limit the character of the data without rewriting the program?

@Nick Gammon:

Thank you for advice. However, if I don't use delay, based on your experience, what function should I use to hold the led to light for 5 second? if I use interupts timer,can i use 2 different timers in one arduino?

@others:

Is there any other comment? I do appreciate your participation :slight_smile:

However, if I don't use delay, based on your experience, what function should I use to hold the led to light for 5 second?

Have a look at the "blink without delay" example that came with the IDE for a clue.

alva:
2. What is the maximum character I could send in 64 bytes read buffer?

You don't send in a read buffer, however I think the answer would be 64.

  1. You can download the latest version from the main site if you don't already have it, but the issue isn't the IDE, your code needs to change.
    1. Tweak your input data to be less than 64 and reduce the number of commas that trigger printing and you should see something coming from the Arduino.
  2. Null terminated arrays of char and the standard c functions that handle them with names that start with str, such as strcpy, strcat.
  3. You can still use String, though it is ill advised because of the memory allocation bug that comes with it. But you need to get rid of delay as AWOL advised.

Let me give you a really good reason not to use "delay()".
At 9600 bits per second, if you were executing a "delay (1000);", and the transmitter were sending continuously, you could overflow the receive buffer (and know nothing about it!) 15 times.
Sadly, you're not executing "delay (1000)", you're executing "delay (5000)".
That's 4800 characters lost.