Dear Forumites
I'm trying to read a SIM phone book with a GPRS Sim900 shield on a Uno R3. As is evident from my coding, I'm new at this.
I want to use the Simcard to store messages and settings. When I query the phonebook, this is all I get:
AT+CPBF
+CPBF: 1,"0812036824",161,"Arthur-Master,E"
+CPBF: 2,"0815713157",161,"Arthur-Spare,H*"
+CPBF: 6,"0812036824",161,"Troubleshoot,6*"
+CPBF: 7,"0819999999",161,"Buitekant-Str-16*"
+CPBF: 8,"0819999999",161,"PANIC-Send-HELP*"
+CPBF: 9,"0819999999",161,"Alarm-Solar-Pump1*"
+CPBF: 10,"0819999999",161,"99h99*"
OK
*PSNWID: "649","01", "MTC Namibia", 0, "MTC Namibia", 0
*PSUTTZ: 2024, 8, 25, 21, 19, 15, "+8", 1
DST: 1
When I use my short code below, I get what I expect:
*PANIC-Send-HELP
Arthur-Master
Buitekant-Str-16
0812036824
Alarm-Solar-Pump1
Arthur-Master
Buitekant-Str-16
0812036824
All ready to go.*
But when I put the same code snippet into a larger program, it all goes to pieces. The problem seems to be that it's not reading every character on serial read, especially is looks like the first few characters are dropped, instead of
1,"0812036824",161,"Arthur-Master,E*"
I get
6824",161,"Arthur-Master,E*
The rest of the reads are good, but without the first part I'm lost. Sometimes it works as expected. Mostly it doesn't.
Can someone please point me in the right direction? The function that's applicable is "_getSimCard()"
#include <SoftwareSerial.h>
#include <avr/wdt.h>
// Define I/O pins
#define SIM800_Rx 7 //SIM800 Serial port Rx
#define SIM800_Tx 8 //SIM800 serial port Tx
#define SIM800_Reset 2 //SIM800 Reset pin
// Create an instance of software serial port
SoftwareSerial SSerial(SIM800_Tx, SIM800_Rx); // RX, TX
boolean Connected = false;
int i = 0;
int k = 0;
char PhBkAll[49];
char PhBkName[10][18];
char PhBkNum[6][11];
char PhBkAct[6][2];
char PhBkLine[3];
char PhBkLineNum;
char Serialread[] = "1";
const int TIMEOUT_AT = 8000;
long int Start = millis();
char SmsMsg[2][160];
//###############################################################################################
// SETUP
void setup() {
// Start serial ports
//-------------------
SSerial.begin(4800);
Serial.begin(4800);
delay(2000);
//Initialise SIM800
InitGSM();
// Get contacts on simcard
_getSimCard();
Serial.println("All ready to go.");
}
//###############################################################################################
// MAIN LOOP
void loop() {
}
//###############################################################################################
// Init GSM Module
void InitGSM() {
Connected = false;
// Setup I/Os
pinMode(SIM800_Reset, OUTPUT);
// Reboot SIM800
digitalWrite(SIM800_Reset, LOW);
delay(1000);
digitalWrite(SIM800_Reset, HIGH);
delay(5000);
//Scan for GSM Module
SSerial.print(F("AT\r\n"));
WaitOK();
// Set device to read SMS if available and print to serial
SSerial.print(F("AT+CNMI=1,2,0,0,0\r\n"));
WaitOK();
//Delete old SMS
SSerial.print(F("AT+CMGD=1,4\r\n"));
WaitOK();
// Set SMS mode to ASCII
SSerial.print(F("AT+CMGF=1\r\n"));
WaitOK();
while (!SSerial.available()) {
}
delay(1000); //wait for time to be set
while (SSerial.available()) {
char c1 = char(SSerial.read());
c1 = c1;
}
}
//###############################################################################################
// Wait for the OK response from software serial port
void WaitOK() {
char c1 = ' ';
char c2 = ' ';
boolean OK = false;
while (!SSerial.available()) {
}
while (!OK) {
while (SSerial.available()) {
c1 = c2;
c2 = char(SSerial.read());
if ( (c1 == 'O') and (c2 == 'K') ) {
OK = true;
}
}
}
}
//###############################################################################################
// Read contacts from simcard
void _getSimCard() {
int NewLn = 0;
int SwitchTest = 0;
char LineNum[2];
int Type = 0;
_clearArray(PhBkNum[0], 10);
_clearArray(PhBkNum[1], 10);
_clearArray(PhBkNum[2], 10);
_clearArray(PhBkNum[3], 10);
_clearArray(PhBkNum[4], 10);
_clearArray(PhBkNum[5], 10);
_clearArray(PhBkName[0], 18);
_clearArray(PhBkName[1], 18);
_clearArray(PhBkName[2], 18);
_clearArray(PhBkName[3], 18);
_clearArray(PhBkName[4], 18);
_clearArray(PhBkName[5], 18);
_clearArray(PhBkName[6], 18);
_clearArray(PhBkName[7], 18);
_clearArray(PhBkName[8], 18);
_clearArray(PhBkName[9], 18);
_clearArray(PhBkAct[0], 2);
_clearArray(PhBkAct[1], 2);
_clearArray(PhBkAct[2], 2);
_clearArray(PhBkAct[3], 2);
_clearArray(PhBkAct[4], 2);
_clearArray(PhBkAct[5], 2);
_clearArray(SmsMsg[0], 160);
_clearArray(SmsMsg[1], 160);
SSerial.println("AT+CPBF");
Start = millis();
k = 0;
while ((millis() - Start) < TIMEOUT_AT) {
while (SSerial.available()) {
Serialread[0] = char(SSerial.read());
Serialread[1] = '\0';
if (k <= 49) {
strcat (PhBkAll, Serialread);
}
if ( k > 4 ) {
if (PhBkAll [k - 5] == 'C' && PhBkAll [k - 4] == 'P' && PhBkAll [k - 3] == 'B' && PhBkAll [k - 2] == 'F' && PhBkAll [k - 1] == ':' && PhBkAll [k] == ' ') {
NewLn = 1;
_clearArray(PhBkAll, 49);
k = -1;
}
}
if (Serialread[0] == '*' && NewLn == 1 ) {
//Serial.print ("NewString: ");
//Serial.println (PhBkAll);
if ( PhBkAll[1] != ',' ) {
strncpy ( PhBkLine, &PhBkAll[0], 1);
strncat ( PhBkLine, &PhBkAll[1], 1);
}
else {
strncpy ( PhBkLine, &PhBkAll[0], 1);
}
SwitchTest = atoi(PhBkLine);
SwitchTest--;
switch (SwitchTest) {
case 0 ... 5: {
strncpy ( PhBkNum[SwitchTest], &PhBkAll[3], 10);
strncpy ( PhBkName[SwitchTest], &PhBkAll[20], k - 22);
strncpy ( PhBkAct[SwitchTest], &PhBkAll[k - 1], 1);
break;
}
case 6 ... 8: {
strncpy ( PhBkName[SwitchTest], &PhBkAll[20], k - 20);
break;
}
case 9: {
strncpy ( PhBkName[SwitchTest], &PhBkAll[21], k - 21);
break;
}
default: {
break;
}
}
_clearArray(PhBkLine, 3);
_clearArray(PhBkAll, 49);
NewLn = 0;
k = -1;
}
k++;
}
}
switch (Type) {
case 1: {
for (int m = 0; m != 5 ; m++) {
itoa(m+1, LineNum, 10);
if (strlen(PhBkName[m]) != 0) {
if (m==0) {
strcpy(SmsMsg[0], LineNum);
}
else {
strcat(SmsMsg[0], LineNum);
}
strcat(SmsMsg[0], ":");
strcat(SmsMsg[0], PhBkAct[m]);
strcat(SmsMsg[0], ",");
strcat(SmsMsg[0], PhBkName[m]);
strcat(SmsMsg[0], ",");
strcat(SmsMsg[0], PhBkNum[m]);
if ( m != 5 ) {
SmsMsg[0][strlen(SmsMsg[0])] = '\n';
SmsMsg[0][strlen(SmsMsg[0])+1] = '\0';
}
}
}
break;
}
case 2: { //This is a sms to master for all the text settings
for (int m = 5; m != 10 ; m++) {
itoa(m+1, LineNum, 10);
if (strlen(PhBkName[m]) != 0) {
if (m==5) {
strcpy(SmsMsg[1], LineNum);
strcat(SmsMsg[1], ":");
strcat(SmsMsg[1], PhBkAct[5]);
strcat(SmsMsg[1], ",");
strcat(SmsMsg[1], PhBkName[5]);
strcat(SmsMsg[1], ",");
strcat(SmsMsg[1], PhBkNum[5]);
}
else {
strcat(SmsMsg[1], LineNum);
strcat(SmsMsg[1], ":");
strcat(SmsMsg[1], PhBkName[m]);
}
if ( m != 9 ) {
SmsMsg[1][strlen(SmsMsg[1])] = '\n';
SmsMsg[1][strlen(SmsMsg[1])+1] = '\0';
}
}
}
//Serial.println(SmsMsg[1]);
break;
}
default:{
strcpy(SmsMsg[0], PhBkName[7]); //Panic Message
SmsMsg[0][strlen(SmsMsg[0])] = '\n';
SmsMsg[0][strlen(SmsMsg[0])] = '\n';
SmsMsg[0][strlen(SmsMsg[0])+1] = '\0';
strcat(SmsMsg[0], PhBkName[0]);
SmsMsg[0][strlen(SmsMsg[0])] = '\n';
SmsMsg[0][strlen(SmsMsg[0])+1] = '\0';
strcat(SmsMsg[0], PhBkName[6]);
SmsMsg[0][strlen(SmsMsg[0])] = '\n';
SmsMsg[0][strlen(SmsMsg[0])+1] = '\0';
strcat(SmsMsg[0], PhBkNum[0]);
Serial.println(SmsMsg[0]);
strcpy(SmsMsg[1], PhBkName[8]); //Alarm Message
SmsMsg[1][strlen(SmsMsg[1])] = '\n';
SmsMsg[1][strlen(SmsMsg[1])] = '\n';
SmsMsg[1][strlen(SmsMsg[1])+1] = '\0';
strcat(SmsMsg[1], PhBkName[0]);
SmsMsg[1][strlen(SmsMsg[1])] = '\n';
SmsMsg[1][strlen(SmsMsg[1])+1] = '\0';
strcat(SmsMsg[1], PhBkName[6]);
SmsMsg[1][strlen(SmsMsg[1])] = '\n';
SmsMsg[1][strlen(SmsMsg[1])+1] = '\0';
strcat(SmsMsg[1], PhBkNum[0]);
Serial.println(SmsMsg[1]);
break;
}
}
}
//###############################################################################################
//Clear entire character array
void _clearArray(char* array, int size) {
for (int p = 0; p < size; p++) {
array[p] = '\0'; // Set each element to the null character
}
}
Best regards