Getting data from serial monitor

Hello,

Can someone assist me to parse the following data which i am receiving on serial monitor. The data which i am getting on serial monitor is

+CRING: VOICE

+CLIP: "+919404789938",145,"",,"No1",0

+CRING: VOICE

+CLIP: "+919404789938",145,"",,"No1",0

i want to get the number +919404789938 and store it in a array

This is easy. Scan through the string and as soon as you see a ‘+’ start saving characters, stop at the ‘"’.

char source; // contains the string in the OP.
char res[32]; // where to store the phone number

int idx_scan= 0;
int idx_res = 0; index for result.

while (source[idx_scan] != ‘+’) idx_scan++; // so we get the ‘+’

while (source[idx_idxscan] != ‘"’) {
res[idx_res++] = source[idx_scan++];
}

res[idx_res] = ‘\0’; // terminate

Have a look at the examples in Serial Input Basics - simple reliable ways to receive data.

You could adapt the 3rd example to use the '+' as the start-marker and the '.' as the end-marker.

Or it might be better to receive the entire message and then parse it. The parse example in the link should get you started.

...R

Thanks for the suggestion's i tried KeithRB method as well as Robin2's method but it didn't work in my case. Robin2 3rd example is quite good and explains it very well.

As i am using two serial inputs one from Serial1 and another from Serial of mega so couldn't get the desired result. i have taken data from gsm modem on serial1 and given it to serial port. i have used the example given in arduino tutorial of MultiSerialMega .

// read from port 1, send to port 0:
  if (Serial1.available()) {
    int inByte = Serial1.read();
    Serial.write(inByte);
  }

  // read from port 0, send to port 1:
  if (Serial.available()) {
    int inByte = Serial.read();
    Serial1.write(inByte);
  }

whenever i make a call to modem i receive the string of data which i have placed in the above section and the data updates every second or so till the call is ended.

JairajDange:
As i am using two serial inputs one from Serial1 and another from Serial of mega so couldn’t get the desired result.

If you want help you need to post the complete program you have tried.

And “but it didn’t work in my case.” tells me nothing useful that I can use to help you.

…R

in the following code i tried to use your example 3 sketch

onst byte numChars = 32;
char receivedChars[numChars];

boolean newData = false;

void setup() {
    Serial.begin(9600);
    Serial.println("<Arduino is ready>");
Serial1.begin(9600);
delay(500);
pinMode(13,OUTPUT);
 Serial.println("Serial call");

Serial1.println("ATD>SM1"); 
// this works fine and calls number which is located in sim
delay(20000);
Serial.println("Call has been made");
}

instead of calling the functions i used the changes in sketch itself

void loop() {
    
// read from port 1, send to port 0:
  if (Serial1.available()) {
   int inByte = Serial1.read();
    Serial.write(inByte);

     
  }
  // read from port 0, send to port 1:
  if (Serial.available()) {
   int inByte = Serial.read();
    Serial1.write(inByte);


    static boolean recvInProgress = false;
    static byte ndx = 0;
    char startMarker = '+';
    char endMarker = ',';
    char rc;
 
    while (newData == false) {
        rc = inByte;

        if (recvInProgress == true) {
            if (rc != endMarker) {
                receivedChars[ndx] = rc;
                ndx++;
                if (ndx >= numChars) {
                    ndx = numChars - 1;
                }
            }
            else {
                receivedChars[ndx] = '\0'; // terminate the string
                recvInProgress = false;
                ndx = 0;
                newData = true;
            }
        }

        else if (rc == startMarker) {
            recvInProgress = true;
        }
    }
      if (newData == true) {
        Serial.print("This just in ... ");
        Serial.println(receivedChars);
        newData = false;
    
}
    
  }
    
}

now whenever i make a call i get following output on serial monitor

RING

RING

RING

RING

NO CARRIER

it doesn’t display a number

JairajDange: in the following code i tried to use your example 3 sketch

You don't seem to have read the first sentence of Reply #4 carefully.

...R

i have posted whole code in reply #5

JairajDange: i have posted whole code in reply #5

I am not going to try to join two parts together. I might make a mistake, or you may have done so.

...R

i posted code separately because i thought it would be easy to understand

here is the full code

const byte numChars = 32;
char receivedChars[numChars];

boolean newData = false;

void setup() {
    Serial.begin(9600);
    Serial.println("<Arduino is ready>");
Serial1.begin(9600);
delay(500);
pinMode(13,OUTPUT);

 Serial.println("Serial call");

Serial1.println("ATD>SM1"); 
// this works fine and calls number which is located in sim
delay(20000);
Serial.println("Call has been made");
}

void loop() {
    
// read from port 1, send to port 0:
  if (Serial1.available()) {
   int inByte = Serial1.read();
    Serial.write(inByte);

     
  }
  // read from port 0, send to port 1:
  if (Serial.available()) {
   int inByte = Serial.read();
    Serial1.write(inByte);


    static boolean recvInProgress = false;
    static byte ndx = 0;
    char startMarker = '+';
    char endMarker = ',';
    char rc;
 
    while (newData == false) {
        rc = inByte;

        if (recvInProgress == true) {
            if (rc != endMarker) {
                receivedChars[ndx] = rc;
                ndx++;
                if (ndx >= numChars) {
                    ndx = numChars - 1;
                }
            }
            else {
                receivedChars[ndx] = '\0'; // terminate the string
                recvInProgress = false;
                ndx = 0;
                newData = true;
            }
        }

        else if (rc == startMarker) {
            recvInProgress = true;
        }
    }
      if (newData == true) {
        Serial.print("This just in ... ");
        Serial.println(receivedChars);
        newData = false;
    
}
    
  }
    
}

You seem to be using my code to read from Serial whereas I thought the whole purpose was to apply it to Serial1 where the numbers come from.

Also it would be much easier (for you and for me) if you just keep my complete function and call it from loop() as in my example rather than trying to incorporate the code into loop(). Putting code into small single purpose functions makes it much easier to develop and to maintain.

And there would be nothing to prevent you having two copies of my function (with different function names) one to receive data from Serial and the other to receive data from Serial1

...R

Initially i used following code to make a call through the Gsm modem through Serial1 port of mega and getting data on Serial port .

void setup() {
  
Serial.begin(9600);
Serial1.begin(9600);
delay(500);


 Serial.println("Serial call");

Serial1.println("ATD>SM1"); 
// this works fine and calls number which is located in sim
delay(20000);
Serial.println("Call has been made");
}

void loop() {
// read from port 1, send to port 0:
  if (Serial1.available()) {
   int inByte = Serial1.read();
    Serial.write(inByte);

}
  // read from port 0, send to port 1:
  if (Serial.available()) {
   int inByte = Serial.read();
    Serial1.write(inByte);
  }

 

}

it worked very well

Then i tried to use your code to sort the data which i was getting on serial monitor but it was keeping the modem engaged continuous by sending data to port the code i used was

const byte numChars = 32;
char receivedChars[numChars];

boolean newData = false;
int inByte;
void setup() {
    Serial.begin(9600);
    Serial.println("<Arduino is ready>");
    Serial1.begin(9600);
delay(500);


 Serial.println("Serial call");

Serial1.println("ATD>SM1"); 
// this works fine and calls number which is located in sim
delay(20000);
Serial.println("Call has been made");
}

void loop() {

    if (Serial1.available()) {
    inByte = Serial1.read();
    Serial.write(inByte);
recvWithStartEndMarkers();
    showNewData();
}
  if (Serial.available()) {
    inByte = Serial.read();
    Serial1.write(inByte);
    recvWithStartEndMarkers();
    showNewData();
  }
  
}

void recvWithStartEndMarkers() {
    static boolean recvInProgress = false;
    static byte ndx = 0;
    char startMarker = '+';
    char endMarker = ',';
    char rc;
 
 // if (Serial.available() > 0) {
    while (Serial.available() > 0 && newData == false) {
        rc = inByte;

        if (recvInProgress == true) {
            if (rc != endMarker) {
                receivedChars[ndx] = rc;
                ndx++;
                if (ndx >= numChars) {
                    ndx = numChars - 1;
                }
            }
            else {
                receivedChars[ndx] = '\0'; // terminate the string
                recvInProgress = false;
                ndx = 0;
                newData = true;
            }
        }

        else if (rc == startMarker) {
            recvInProgress = true;
        }
    }
}

void showNewData() {
    if (newData == true) {
        Serial.print("This just in ... ");
        Serial.println(receivedChars);
        newData = false;
    }
}

so i tried to put the section of your code in loop itself so that it directly shall read the data from Serial1 port instead of calling and then sorting the string

JairajDange:
Then i tried to use your code to sort the data which …

You seem to have things all mixed up.

The call to recvWithStartEndMarkers() should not be inside any IF clause. It should be called directly from loop() - like in my demo.

And, as I said earlier, I thought you wanted to use that function to get data from Serial1 - but you are using it to get data from Serial. Which serial port is your GSM device (or whatever it is?) connected to?

…R

i thought of calling the recvWithStartEndMarkers() function when their is serial call takes place, so i used recvWithStartEndMarkers() in if condition so that it will engage only when their is a call from serial . The gsm is connected to Serial1 port of mega.

JairajDange: i thought of calling the recvWithStartEndMarkers() function when their is serial call takes place, so i used recvWithStartEndMarkers() in if condition so that it will engage only when their is a call from serial .

As I said (and showed in my demo) that is not right.

The gsm is connected to Serial1 port of mega.

So why is the recvWithStartEndMarkers() function reading from Serial?

I get the feeling a little more careful thinking is what you need to do.

...R

I guess i was wrong trying to read from both serial as well as serial1, i shall stick to serial1 which is connected to gsm modem

JairajDange: I guess i was wrong trying to read from both serial as well as serial1, i shall stick to serial1 which is connected to gsm modem

They are two completely different data streams. Maybe you need to read from both or maybe not. I mentioned how to read from both in Reply #10 - if you need to do that.

...R