Best Approach(es) to Handling SMS Messages Over Atmega Serial

Hi,

First Quiestion - Sending SMS Messages

What would be the best way to convert this function into one that I can call up at will and pass a message to for sending but of differing data types each time?

E.G.

float myMessage = 37.5;
CALL SEND SMS FUNCTION

And later in my program I want to send a different data type using the same function…

char myMessage = “Some SMS TEXT”;
CALL SEND SMS FUNCTION

This is what I’ve got working so far for testing but now I want to pass different messages to the function rather than have them hard coded in to it.

// SEND SMS DATA / MESSAGES FUNCTION
  void txSMS(){  

      if(powerState == 0){
          digitalWrite(PWR_EN, HIGH);         // MAIN POWER CONTROL - TURN ON MAIN 3.7V POWER - LOW = OFF | HIGH = ON 
          delay(450);
          powerState = 1;
      }
      digitalWrite(GSM_PWR, HIGH);            // GSM POWER CONTROL - TURNS GSM ON - LOW = OFF | HIGH = ON
      delay(20000);                           // Wait for Network Connection to Establish (LED On GSM Blinks Once Every Second)
         
      Serial.println(F("AT+CMGF=1"));         // Set Modem to SMS TEXT MODE READY FOR SENDING SMS
      delay(100);

      // SEND MOBILE NUMBER TO GSM
      Serial.print(F("AT+CMGS=\""));
      Serial.print(mobNumber);
      Serial.print(F("\"\r"));
      delay(100);
      
      float temperature = averageTemperature(temperatures, opHours);
      //float battLevel = averageBattLevel(battLevels, opHors);

      // SEND MESSAGE CONTENT (READINGS)
      Serial.print(F("Average Temp: "));
      Serial.print(temperature);
      //Serial.println("Battery V: ");
      //Serial.print(battLevel);
      Serial.print((char)26);
      delay(100);
      Serial.println();
      delay(2000); 

      if(powerState == 1){
          digitalWrite(PWR_EN, LOW);          // MAIN POWER CONTROL - TURN OFF MAIN 3.7V POWER - DC REGULATOR - LOW = OFF | HIGH = ON
          powerState = 0;
      }
      digitalWrite(GSM_PWR, LOW);             // GSM POWER CONTROL - TURNS GSM OFF - LOW = OFF | HIGH = ON
      
  }

Second Question - Receiving and Parsing SMS Commands

I am trying to develop a function to read and process SMS Commands after my Atmega has woken up from Low Power Sleep and has powered up the GSM module to check for any SMS Messages.

I found this example code from these forums which I’ve adapted a little so I can test it out and it’s close to what I want but it’s just not quite what I would like.

#include <SoftwareSerial.h>
  
SoftwareSerial MYGSM(2,3);
 

// Example 5 - Receive with start- and end-markers combined with parsing

const byte numChars = 32;
char receivedChars[numChars];
char tempChars[numChars];        // temporary array for use when parsing

      // variables to hold the parsed data
char messageFromPC[numChars] = {0};
int integerFromPC = 0;
float floatFromPC = 0.0;

boolean newData = false;

//============

void setup() {
    Serial.begin(9600);
    MYGSM.begin(9600);

    Serial.println("This demo expects 3 pieces of data - text, an integer and a floating point value");
    Serial.println("Enter data in this style <HelloWorld, 12, 24.7>  ");
    Serial.println();

    //Set SMS mode to ASCII
    MYGSM.println(F("AT+CMGF=1\r\n"));
    delay(50);
   
    //Start listening to New SMS Message Indications
    MYGSM.println(F("AT+CNMI=2,1,0,0,0\r\n"));
    delay(50);
    MYGSM.println(F("AT+CMGR=1\r\n"));  
}

//============

void loop() {
    recvWithStartEndMarkers();
    if (newData == true) {
        strcpy(tempChars, receivedChars);
            // this temporary copy is necessary to protect the original data
            //   because strtok() used in parseData() replaces the commas with \0
        parseData();
        showParsedData();
        newData = false;
    }
}

//============

void recvWithStartEndMarkers() {
    static boolean recvInProgress = false;
    static byte ndx = 0;
    char startMarker = '<';
    char endMarker = '>';
    char rc;

    while (MYGSM.available() > 0 && newData == false) {
        rc = MYGSM.read();

        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 parseData() {      // split the data into its parts

    char * strtokIndx; // this is used by strtok() as an index

    strtokIndx = strtok(tempChars,",");      // get the first part - the string
    strcpy(messageFromPC, strtokIndx); // copy it to messageFromPC
 
    strtokIndx = strtok(NULL, ","); // this continues where the previous call left off
    integerFromPC = atoi(strtokIndx);     // convert this part to an integer

    strtokIndx = strtok(NULL, ",");
    floatFromPC = atof(strtokIndx);     // convert this part to a float

}

//============

void showParsedData() {
    Serial.print("Message ");
    Serial.println(messageFromPC);
    Serial.print("Integer ");
    Serial.println(integerFromPC);
    Serial.print("Float ");
    Serial.println(floatFromPC);
}


void delSMS(){
    if(messageEnd == true){
        MYGSM.println("AT+CMGD=1,4\r\n");
        messageEnd = false;
        Serial.println(F("Messages Deleted"));
    }
}

I have a dozen settings / options in my program which I hope to be changed / set / updated via received SMS Commands.

The problem with the code above is that it expects a certain number of commands in a certain order.

What I would like is to be able to do is either receive just a single command and process it or receive multiple commands in no set order and then process them - but I’m just not sure what changes to make or how to get there.

One thing I am trying to do is to keep the resource usage on the Atmega down as much as possible so I am trying to find the most efficient solution.

Any / All help would be really appreciated. Not necessarily in the form of code but some pointers in the direction of the right logical steps / approach would really help.

Many thanks.

I believe have found the answer to Question One.. and that is Function Overloading.

Multiple copies of the same function but each one set up to handle a different data type.

So I just need some guidance with Question Two:- Receiving and Parsing SMS Commands.

Thanks.