How to take data from gps then send to my phone in arduino uno?

I want do project which is use GPS & GSM module use arduino take data from GPS(GY-GPS/NEO6MV2) and send by GSM(SIM900 GSM/GPRS Module ) to my phone I 'am use separate GPS module I try this code but still have problem.

#include <SoftwareSerial.h>
#include "SIM900.h"
#include <TinyGPS.h>
#include "sms.h"
SMSGSM sms;

TinyGPS gps;
SoftwareSerial ss(4, 3);
SoftwareSerial SIM900(7, 8);

static void smartdelay(unsigned long ms);
static void print_float(float val, float invalid, int len, int prec);
static void print_int(unsigned long val, unsigned long invalid, int len);
static void print_date(TinyGPS &gps);
static void print_str(const char *str, int len);
String strL, strN, message, textForSMS;
char charL[10], charN[10], text[200];
int m = 1;
boolean started = false;

void setup()
{
  Serial.begin(9600);
  ss.begin(9600);
  gsm.begin(9600);
}

void loop()
{
  float flat, flon;
  unsigned long age, date, time, chars = 0;
  unsigned short sentences = 0, failed = 0;

  gps.f_get_position(&flat, &flon, &age);
  textForSMS = "Moosa Home"; //testing gps from here
  Serial.println(textForSMS);
  Serial.println(flat, 6);
  Serial.println(flon, 6);
  Serial.print("longitude: ");
  print_float(flat, TinyGPS::GPS_INVALID_F_ANGLE, 10, 6);
  Serial.println("");
  Serial.print("latitude : ");
  print_float(flon, TinyGPS::GPS_INVALID_F_ANGLE, 10, 6);
  smartdelay(1000);
  Serial.println(""); //till here
  delay(1000);
  if (m == 20) //send sms on third reading
  {
    Serial.println("XXXXXXXXX"); //to check whether 'if' works
    dtostrf(flat, 4, 6, charL);
    for (int i = 0; i < 10; i++)
    {
      strL += charL[i];
    }
    dtostrf(flon, 4, 6, charN);
    for (int i = 0; i < 10; i++)
    {
      strN += charN[i];
    }
    message = "Abuwesam Home";
    message = message + "/nLat: ";
    message = message + strL;
    message = message + "/nLon: ";
    message = message + strN;
    message.toCharArray(text, 250);
    Serial.println(text);

    if (sms.SendSMS("+999999999999999", text))
    {
      Serial.println("\nSMS sent OK.");
    }
    else
    {
      Serial.println("\nError sending SMS.");
    }
    do {} while (1);

  }
  m++;
}
static void smartdelay(unsigned long ms)
{
  unsigned long start = millis();
  do
  {
    while (ss.available())
      gps.encode(ss.read());
  } while (millis() - start < ms);
}

static void print_float(float val, float invalid, int len, int prec)
{
  if (val == invalid)
  {
    while (len-- > 1)
      Serial.print('*');
    Serial.print(' ');
  }
  else
  {
    Serial.print(val, prec);
    int vi = abs( val);
    int flen = prec + (val < 0.0 ? 2 : 1); // . and -
    flen += vi >= 1000 ? 4 : vi >= 100 ? 3 : vi >= 10 ? 2 : 1;
    for (int i = flen; i < len; ++i)
      Serial.print(' ');
  }
  smartdelay(0);
}




static void print_str(const char *str, int len)
{
  int slen = strlen(str);
  for (int i = 0; i < len; ++i)
    Serial.print(i < slen ? str[i] : ' ');
  smartdelay(0);
}

I receive SMS Home/nLat:1000.00000/nLon:1000.00000`

where my mistake in this code I am sure Gps & gsm work properly

Please modify your Post and use the code button </> so your code looks like this and is easy to copy to a text editor. And it won't have italics either.

...R

Does the line Serial.println(text); show the correct data?

If so it seems that the problem is with the line if (sms.SendSMS("+999999999999999", text)) and I am not familiar with the SMS library.

Have you written a short program just to test your ability to send SMS messages such as "Hello World"?

Your code is very difficult to read. Use the AutoFormat tool to lay it out properly.

I see this line message.toCharArray(text, 250); and this line
char charL[10], charN[10], text[200]; so it looks like you may be writing outside the bounds of the array

...R

Yes I am try gps alone work properly and also try gsm alone work properly but when make it together this happen

abuwesam:
Yes I am try gps alone work properly and also try gsm alone work properly but when make it together this happen

It would be very helpful if you would answer the specific question I asked. I have a suspicion that what I have quoted does not mean "Yes, the line Serial.println(text); shows the correct data"

This is an important point and it would not be sensible to make other suggestions until I am certain that your program is or is not working at that line.

Also, post a short program that works with the GSM alone so I can see how that is done.

...R

abuwesam:
for gsm only

Thank you.

But you did not answer my other much more important question and I can't make any progress without your answer.

...R

Serial.println(text) doesn't show the correct data

abuwesam:
Serial.println(text) doesn't show the correct data

It's a pity it has taken from Reply #3 to Reply #8 to find that out. There is no point worrying about anything else until you get that working.

It actually looks as if this line is not working

print_float(flat, TinyGPS::GPS_INVALID_F_ANGLE, 10, 6);

What is that line trying to do?
Instead of combining a bunch of things on one line rewrite the code to do each piece on its own line. Then you can print the intermediate values and find where the problem is.

...R

You have both gps and gsm modules on software serial ports. But software serial ports can only have one actively listening at a time. You first made an ss software serial, and then a gsm software serial. This makes arduino only listen to gsm software serial, because it was made later. Read software serial documents and find how to use listen(). You can listen until you have a complete sentence to spit out gps coordinate, then switch to gsm's software serial and send SMS. If you're not happy with this, use an Arduino MEGA 2560 with 4 hardware serials. They work simultaneously.

Thank you all
I solve problem but still have small point
I get longitude: but not get latitude :
this code use

#include <SoftwareSerial.h>
#include "SIM900.h"
#include <TinyGPS.h>
#include "sms.h"
SMSGSM sms;
 

TinyGPS gps;
SoftwareSerial ss(4, 3);
SoftwareSerial SIM900(7, 8);
 

static void smartdelay(unsigned long ms);
static void print_float(float val, float invalid, int len, int prec);
static void print_int(unsigned long val, unsigned long invalid, int len);
static void print_str(const char *str, int len);
String strL, strN, poss, moosa, textForSMS;
char charL[10], charN[10], text[400];
int o = 1;
boolean started = false;
 

void setup()
 

{
  Serial.begin(9600);
  ss.begin(9600);
}
 

void loop()
{
  float flat, flon;
  unsigned long age, date, time, chars = 0;
  unsigned short sentences = 0, failed = 0;
 

  while (o < 4) {
    gps.f_get_position(&flat, &flon, &age);
    textForSMS = "Abuwesam Home"; //testing gps from here
    Serial.println(textForSMS);
    Serial.print("longitude: ");
    print_float(flat, TinyGPS::GPS_INVALID_F_ANGLE, 10, 6);
    Serial.println("");
    Serial.print("latitude : ");
    print_float(flon, TinyGPS::GPS_INVALID_F_ANGLE, 10, 6);
    smartdelay(1000);
    Serial.println(""); //till here
    delay(1000);
    o++;
  }
  
  Serial.println("XXXXXXXXX"); //to check whether 'if' works
  dtostrf(flat, 8, 6, charL);
  for (int i = 0; i < 10; i++)
  {
    strL += charL[i];
  }
  dtostrf(flon, 8, 6, charN);
  for (int i = 0; i < 10; i++)
  {
    strN += charN[i];
  }
  moosa = "Abuwesam Home Location";
  moosa = moosa + "\nlongitude: " + strN + "\nlatitude :  " + strL;
  poss = moosa ;
  poss.toCharArray(text, 400);
  gsm.begin(9600);
  
  
  
  Serial.println(text);
  if (sms.SendSMS("+9999999999", text))
    {
    Serial.println("\nSMS sent OK.");
    }
    else
    {
    Serial.println("\nError sending SMS.");
    }
    do {} while (1);
 

  //}
  //o++;
}
static void smartdelay(unsigned long ms)
{
  unsigned long start = millis();
  do
  {
    while (ss.available())
      gps.encode(ss.read());
  } while (millis() - start < ms);
}
 

static void print_float(float val, float invalid, int len, int prec)
{
  if (val == invalid)
  {
    while (len-- > 1)
      Serial.print('*');
    Serial.print(' ');
  }
  else
  {
    Serial.print(val, prec);
    int vi = abs( val);
    int flen = prec + (val < 0.0 ? 2 : 1); // . and -
    flen += vi >= 1000 ? 4 : vi >= 100 ? 3 : vi >= 10 ? 2 : 1;
    for (int i = flen; i < len; ++i)
      Serial.print(' ');
  }
  smartdelay(0);
}
 

static void print_str(const char *str, int len)
{
  int slen = strlen(str);
  for (int i = 0; i < len; ++i)
    Serial.print(i < slen ? str[i] : ' ');
  smartdelay(0);
}

The display

Using TinyGPS on SoftwareSerial + a loop() structure using delay(1000), has very low odds of working. The m counter is really useless here, because loop() will execute 1000's of times while the GPS characters are arriving. And doing a get_position is useless, because you may not have any GPS data yet.

Basically, loop() should be constantly running, without delays. When something important happens (like getting a complete GPS sentence, or enough time has passed), that's when you do your other work (like send an SMS message). The TinyGPS smartDelay is not smart.

You should restructure the loop to look more like this example from the NeoGPS library. All the non-GPS work should be performed where the digitalWrite is in that example (line 62). That's where you would take the time to send an SMS.

The TinyGPS examples are fine by themselves, but it is difficult to extend them to do other things, like send an SMS. As I said, the loop structure must change.

I suggest taking a look at the NeoGPS library I wrote, as the examples are more robust. The library also uses much less RAM and CPU time, but that isn't a big problem if all you need to do is send an SMS message. If you do want to try it, be sure to review the default SoftwareSerial choice.

If you get the simple NMEAblink.ino example to work, I would suggest trying NMEA.ino. Then insert your code into the doSomeWork function. Most of what you have in loop needs to go in the doSomeWork function, which is called only when a complete RMC sentence is received:

#include <SoftwareSerial.h>
#include "SIM900.h"
#include "NMEAGPS.h"
#include "sms.h"

SMSGSM sms;

static NMEAGPS gps;
SoftwareSerial ss(4, 3);
SoftwareSerial SIM900(7, 8);

static uint8_t number_valid_locations = 0; // consecutive good data

void doSomeWork()
{
  char text[60];
  char *ptr = &text[0];

  strcpy( ptr, "Abuwesam Home\nlatitude: " );
  ptr = &ptr[ strlen(ptr) ]; // step to the end
  dtostrf( gps.fix().latitude(), 8, 6, ptr );
  ptr = &ptr[ strlen(ptr) ];
  strcpy( ptr, "\nlongitude: " );
  ptr = &ptr[ strlen(ptr) ];
  dtostrf( gps.fix().longitude(), 8, 6, ptr );

  Serial.println( text );

  gsm.begin(9600); // not listening to GPS any more!
  if (sms.SendSMS("+9999999999", text)) {
    Serial.println("\nSMS sent OK.");
  } else {
    Serial.println("\nError sending SMS.");
  }

  do {} while (1);
}

void setup()
{
  Serial.begin(9600);
  ss.begin(9600);
}

void loop()
{
  while (ss.available()) {

    if (gps.decode( ss.read() ) == NMEAGPS::DECODE_COMPLETED) {

      if (gps.nmeaMessage == NMEAGPS::NMEA_RMC) {

        if (gps.fix().valid.location) {
          number_valid_locations++;

          if (number_valid_locations >= 4) {
            doSomeWork();
            number_valid_locations = 0; // reset counter
          }

        } else // no valid location, reset counter
          number_valid_locations = 0;

      }
    }
  }
}

Regardless of which library you use, you also need to check whether the data is valid. What if your GPS isn't receiving any satellites? It may still send an RMC sentence, but there won't be any lat/lon data. You probably shouldn't send an SMS if the location field is not valid.

Cheers,
/dev

From a brief read of the documentation for the TinyGPS library I would change this

static void smartdelay(unsigned long ms)
{
  unsigned long start = millis();
  do
  {
    while (ss.available())
      gps.encode(ss.read());
  } while (millis() - start < ms);
}

and I would use the 2nd example from Serial Input Basics to take the data from the GPS device. That would put the complete message in the array recvdChars[] and then when I got newData == true I would feed the gps.encode() function from the data in recvdChars.

The examples in Serial Input Basics are simple, reliable, non-blocking and don't depend on the speed at which serial data may or may not arrive.

...R

Thanks bro
I get error in code this massage
Arduino: 1.6.6 Hourly Build 2015/10/09 12:42 (Windows 10), Board: "Arduino/Genuino Uno"

E:\test\last\last.ino: In function 'void doSomeWork()':

last:22: error: 'class NMEAGPS' has no member named 'fix'

dtostrf( gps.fix().latitude(), 8, 6, ptr );

^

last:26: error: 'class NMEAGPS' has no member named 'fix'

dtostrf( gps.fix().longitude(), 8, 6, ptr );

^

E:\test\last\last.ino: In function 'void loop()':

last:50: error: 'class NMEAGPS' has no member named 'decode'

if (gps.decode( ss.read() ) == NMEAGPS::DECODE_COMPLETED) {

^

last:50: error: 'DECODE_COMPLETED' is not a member of 'NMEAGPS'

if (gps.decode( ss.read() ) == NMEAGPS::DECODE_COMPLETED) {

^

last:52: error: 'class NMEAGPS' has no member named 'nmeaMessage'

if (gps.nmeaMessage == NMEAGPS::NMEA_RMC) {

^

last:52: error: 'NMEA_RMC' is not a member of 'NMEAGPS'

if (gps.nmeaMessage == NMEAGPS::NMEA_RMC) {

^

last:54: error: 'class NMEAGPS' has no member named 'fix'

if (gps.fix().valid.location)

^

exit status 1
'class NMEAGPS' has no member named 'fix'

This report would have more information with
"Show verbose output during compilation"
enabled in File > Preferences.

what this mean

Check the documentation for the library. You seem to be calling fix() and decode() incorrectly.

And, as usual, if you want help you must post the code that causes the errors.

...R

I successfully the built the sketch I posted, but I commented out the SIM900 & SMS includes and code. Did you install NeoGPS? At a minimum, these files should be in the same directory as your .INO:

    CosaCompat.h
    GPSfix.h
    GPSfix_cfg.h
    NMEAGPS.cpp
    NMEAGPS.h
    NMEAGPS_cfg.h
    NeoGPS_cfg.h
    Time.cpp
    Time.h

And like Robin2 said, please post the code.

Also, this line looks like a mistake, maybe from merging?

  gsm.begin(9600);

I don't see gsm declared anywhere. Please put the build error messages into a [code]...[/code] section, just like your code.

Cheers,
/dev

Thanks All

abuwesam:
Thanks All

If that means you now have it working please post your code so that others can benefit from your learning.

...R

i get the data from GPS.but serial printing did not give the result of sending sms.i am beginner. i am not good at coding

Tareq007:
i get the data from GPS.but serial printing did not give the result of sending sms.i am beginner. i am not good at coding

Post your code so we can see where you have got to.
And please use the code button </> so your code looks like this and is easy to copy to a text editor

...R

i am using the code of abuwasem which he already posted.

#include <SoftwareSerial.h>
#include "SIM900.h"
#include <TinyGPS.h>
#include "sms.h"
SMSGSM sms;


TinyGPS gps;
SoftwareSerial ss(2, 3);
SoftwareSerial SIM900(8,7);


static void smartdelay(unsigned long ms);
static void print_float(float val, float invalid, int len, int prec);
static void print_int(unsigned long val, unsigned long invalid, int len);
static void print_str(const char *str, int len);
String strL, strN, poss, tareq, textForSMS;
char charL[10], charN[10], text[400];
int o = 1;
boolean started = false;


void setup()


{
 Serial.begin(9600);
 ss.begin(9600);
}


void loop()
{
 float flat, flon;
 unsigned long age, date, time, chars = 0;
 unsigned short sentences = 0, failed = 0;


 while (o<4) {
   gps.f_get_position(&flat, &flon, &age);
   textForSMS = "tareq Home"; //testing gps from here
   Serial.println(textForSMS);
   Serial.print("longitude: ");
   print_float(flat, TinyGPS::GPS_INVALID_F_ANGLE, 10, 6);
   Serial.println("");
   Serial.print("latitude : ");
   print_float(flon, TinyGPS::GPS_INVALID_F_ANGLE, 10, 6);
   smartdelay(1000);
   Serial.println(""); //till here
   delay(1000);
   o++;
 }
   Serial.println("nil"); //to check whether 'if' works
 dtostrf(flat, 8, 6, charL);
 for (int i = 0; i < 10; i++)
 {
   strL += charL[i];
 }
 dtostrf(flon, 8, 6, charN);
 for (int i = 0; i < 10; i++)
 {
   strN += charN[i];
 }

 tareq = "tareq Home Location";
 tareq = tareq + "\nlongitude: " + strN + "\nlatitude :  " + strL;
 poss = tareq;
 poss.toCharArray(text, 400);
 gsm.begin(9600);
 delay(1000);
 
 
 Serial.println(text);
 if (sms.SendSMS("+8801839443686", text))
   {
   Serial.println("\nSMS sent OK.");
   }
   else
   {
   Serial.println("\nError sending SMS.");
   }
   do {} while (1);


 //}
 //o++;
}
static void smartdelay(unsigned long ms)
{
 unsigned long start = millis();
 do
 {
   while (ss.available())
     gps.encode(ss.read());
 } while (millis() - start < ms);
}


static void print_float(float val, float invalid, int len, int prec)
{
 if (val == invalid)
 {
   while (len-- > 1)
     Serial.print('*');
   Serial.print(' ');
 }
 else
 {
   Serial.print(val, prec);
   int vi = abs( val);
   int flen = prec + (val < 0.0 ? 2 : 1); // . and -
   flen += vi >= 1000 ? 4 : vi >= 100 ? 3 : vi >= 10 ? 2 : 1;
   for (int i = flen; i < len; ++i)
     Serial.print(' ');
 }
 smartdelay(0);
}


static void print_str(const char *str, int len)
{
 int slen = strlen(str);
 for (int i = 0; i < len; ++i)
   Serial.print(i < slen ? str[i] : ' ');
 smartdelay(0);
}