String issue

Hello,

I’m trying read a SMS from a Ericsson t68i with Arduino and them, do somethings.

So, the t68i just uses PDU format, and when I try to read the message, it comes incomplete.

this is the code i’m using:

#include <NewSoftSerial.h>
#include <avr/pgmspace.h>

NewSoftSerial Uart(10, 11);


int buttonState = 0; 
int botao = 12;
int rele = 13; 



String send_command(String at_cmd, int dly){

  String msg;
  char incomingByte;
  
  Uart.println(at_cmd);
  delay(dly);
  while (Uart.available() > 0) 
  {
    incomingByte = (Uart.read());
    msg = msg + char(incomingByte);
  }  
  delay(1000);

  return msg;
}

void setup() {

  Uart.begin(9600);
  Serial.begin(9600);
  
//Coloca o pino 13 em Output onde será ligado o relé
  pinMode(rele, OUTPUT);
  pinMode(botao, INPUT);

  String at_response;
  String at_response2;
  String at_response3;
  String at_response4;
  

  at_response = send_command("AT+CPMS=\"ME\"",1000);
  if (at_response.substring(at_response.length()-4) == ("OK\r\n")) {
    Serial.println(at_response);
  }
  
  

  
  at_response2 = send_command("AT+CMGR=1",1000);
 Serial.print(at_response2);

The answer I get:

+CPMS=“ME”

+CPMS: 1,70,0,30,1,70

OK

+CMGR=1

+CMGR: 1,24
0791551118312800240B811079186914F500001

So, the last line is the message in PDU format (at_response2). It should be like this:

0791551118312800240B811079186914F500001101313204812905CCF4392C07

How can I solve it?

Thank you so much!

Returning automatic variables is rarely a good idea.

AWOL: Returning automatic variables is rarely a good idea.

why?

  delay(1000);

  return msg;

Why delay before returning?

why?

The variable you are returning goes out of scope (ceases to exist) when the function ends. You returned a pointer to the memory space that the variable was using, that may get overwritten at any time.

You should pass the function a reference to the place where you want it to write data to.

void send_command(String at_cmd, int dly, String &reply)
{
}

Then, get rid of msg, replace all references to msg with reply, and remove the return statement.

PaulS,

I got this code here: http://arduino.cc/playground/Main/SonyEricsson

So, with some work i did it work with my cell phone. So somethings i didn't undertand yet.

Thats why I don't know about this delay before returning and I didn't undertand so much, how may I do in this part of code that you did.

it's to be like this?

void send_command(String at_cmd, int dly, String &reply){

 // String msg;
  char incomingByte;
  
  Uart.println(at_cmd);
  delay(dly);
  while (Uart.available() > 0) 
  {
    incomingByte = (Uart.read());
    reply = reply + char(incomingByte);
  }  

  return reply;
}
    reply = reply + char(incomingByte);

Works, I suppose, but

    reply += incomingByte;

is all that is required, and certainly looks cleaner.

  return reply;

What part of "and remove the return statement" didn't you understand?

Sorry about the return, i read again what you said and I corrected it before your answer.
It’s returning an error to compile:
projeto_lab.cpp: In function ‘void setup()’:
projeto_lab:13: error: too few arguments to function ‘void send_command(String, int, String)’
projeto_lab:49: error: at this point in file
projeto_lab:13: error: too few arguments to function ‘void send_command(String, int, String)’
projeto_lab:59: error: at this point in file
projeto_lab:13: error: too few arguments to function ‘void send_command(String, int, String)’
projeto_lab:67: error: at this point in file

The full code now is:

#include <NewSoftSerial.h>

NewSoftSerial Uart(10, 11);

void send_command(String at_cmd, int dly, String &reply){

// String msg;
char incomingByte;

Uart.println(at_cmd);
delay(dly);
while (Uart.available() > 0)
{
incomingByte = (Uart.read());
// reply = reply + char(incomingByte);
reply += incomingByte;
}
// delay(1000);

//return reply;
}

void setup() {

Uart.begin(9600);
Serial.begin(9600);

String at_response;
String at_response2;

at_response = send_command(“AT+CPMS=“ME””,1000);
if (at_response.substring(at_response.length()-4) == (“OK\r\n”)) {
Serial.println(at_response);
}

at_response2 = send_command(“AT+CMGR=1”,1000);
Serial.print(at_response2);

at_response = send_command("AT+CPMS=\"ME\"",1000);

The send_command function now requires three arguments, and does not return a value.

send_command("AT+CPMS=\"ME\"",1000, at_response);

huum, OK...now i undertood. But, this comparison is not working anymore (the answer is always NOT OK):

  send_command("AT+CPMS=\"ME\"",1000, at_response);
  if (at_response.substring(at_response.length()-4) == ("OK\r\n")) {
    Serial.println("OK");
  }
  else {
    Serial.println("NOT OK");
       }

There is a debug to do with this code now?

thank you man!!

There is a debug to do with this code now?

Add

Serial.print("at_response: '");
Serial.print(at_response);
Serial.println("]");

after:

  send_command("AT+CPMS=\"ME\"",1000, at_response);

Show us the output.

the outpu is just:

at_response: ']

I tried the old code to make sure that the cell phone is ok, and it’s ok!

Serial.print("at_response: '");

The ' should have been [.

If you copy those three lines into the send_command function, and change at_response to reply, what do you see?

PaulS: Serial.print("at_response: '");

The ' should have been [.

If you copy those three lines into the send_command function, and change at_response to reply, what do you see?

i didn't undertand this.

PaulS, we can talk in another place (email or MSN) if you can, and after we write here the solution.

You can PM me.

I meant that

Serial.print("at_response: '");

should have been

Serial.print("at_response: [");

Now it's working the debug.

But it's with the same result of the old code:

[ +CPMS="ME"

+CPMS: 1,70,0,30,1,70

OK ] [ +CMGR=1

+CMGR: 1,,24 0791551118312800240B811079186914F500001]

But it’s with the same result of the old code:

Changing the way that the collected data is made known to the caller will not change the data.

The problem is here:

  while (Uart.available() > 0) 
  {
    incomingByte = (Uart.read());
    reply = reply + char(incomingByte);
  }

This expects all the data to have arrived by the time that the function is called. There is no guarantee that this will happen.

There is some end-of-message marker that signifies that the complete message has been received. You need to wait, in the send_command function, until that end character is received.

This is not working yet. I still have this from the phone:

+CPMS="ME"

+CPMS: 1,70,0,30,1,70

OK

+CMGR=1

+CMGR: 1,,24
0791551118312800240B811079186914F500001

instead of:

+CPMS="ME"

+CPMS: 1,70,0,30,1,70

OK

+CMGR=1

+CMGR: 1,,24
0791551118312800240B811079186914F500001101313204812905CCF4392C07

OK, we can see the output, but what does the code look like?

The code now is:

#include <NewSoftSerial.h>

NewSoftSerial Uart(10, 11);

void send_command(String at_cmd, int dly, String &reply){

 // String msg;
  char incomingByte;
  
  Uart.println(at_cmd);
  delay(dly);
  while (Uart.available() > 0)
  {

    incomingByte = (Uart.read());
   // reply = reply + char(incomingByte);
reply += incomingByte;  
}  
}



void setup() {

  Uart.begin(4800);
  Serial.begin(9600);
  
//Coloca o pino 13 em Output onde será ligado o relé
  pinMode(rele, OUTPUT);
  pinMode(botao, INPUT);

  String at_response;
  String at_response2;

  

  send_command("AT+CPMS=\"ME\"",1000, at_response);
Serial.print(at_response);

  
  send_command("AT+CMGR=1", 1000, at_response2);
Serial.println(at_response2);
 
 
 
}
void loop() {}

The output is:
+CPMS=“ME”

+CPMS: 1,70,0,30,1,70

OK
+CMGR=1

+CMGR: 1,24
0791551118312800240B811079186914F500001

The last line is the SMS message I need to read and compare. So this is incomplete.
It had to be:
0791551118312800240B811079186914F500001101313204812905CCF4392C07

thanks!

+CPMS: 1,70,0,30,1,70

What do these numbers mean?

+CMGR: 1,,24

And these?