Listing of deploy/store_gps_datagrams.pl


#!/usr/bin/perl -w
#
# This program receives UDP datagrams from Aspicore GSM Tracker,
# parses and stores them to a MySQL database
#
# Tested with WinXP and perl, v5.8.0 built for MSWin32-x86-multi-thread
# Binary build 806 provided by ActiveState Corp. http://www.ActiveState.com
# Built 00:45:44 Mar 31 2003
#
# Tested also with Windows 2003 Server and perl, v5.8.4 built for MSWin32-x86-multi-thread
# Binary build 810 
# Built Jun  1 2004 11:52:21
# ------------------------------
# Installing MySQL API into perl:
# (The interface requires Perl Version 5.6.0 or later)
# ppm> install DBI
# ppm> install DBD-MySQL
# ------------------------------
# Change History:
# 2004-11-22 jje - SQL script created for MySQL 4.0
# 2005-03-31 jje - Adapted for MySQL 4.1.1 and above (renamed columns UTC_TIME and UTC_DATE into UTCTIME and UTCDATE)
# 2005-04-04 jje - REMOTE_IP added into database

require 5.008;
use strict;
BEGIN { $ENV{PATH} = '/usr/ucb:/bin' }
use Socket;
use DBI;

# =======
# GLOBALS (that are used from the subroutines)
# =======
my $sth;
                                   
# ============
# SUBROUTINES
# ============
sub logmsg { print "$0 $$: @_ at ", scalar localtime, "\n" } 

sub parsedgram {
  my $datagram = shift;
  my $remoteip = shift;

  $datagram  =~ s/\r//g;  # remove  characters 

  # extract IMEI
  my $phone_id;
  if ($datagram =~ /IMEI (\d+)\n/) {
    $phone_id = $1;
  }
  if (defined $phone_id) {
    print "phone_id: <$phone_id>\n";
  }

  # extract Label
  my $label;
  if ($datagram =~ /\nLabel ([\S ]*)\n/) {
    $label = $1;
  }
  if (defined $label) {
    print "label: <$label>\n";
  }

  # extract the entire NMEA sentence
  my $nmea;
  my ( $utc_time, $status, $lat_deg_part, $lat_min_part, $lat_n_or_s, 
       $long_deg_part, $long_min_part, $long_e_or_w, $speed_knots,
       $course_deg, $utc_date );
  my ( $latitude, $longitude );

  if ($datagram =~ /(\$GPRMC,[\S ]*)\n/) {
    $nmea = $1;
  }
  if (defined $nmea) {
    print "NMEA: <$nmea>\n";

    # extract individual NMEA fields
    if ($datagram =~ /\$GPRMC,([\d\.]*),([AV]),(\d\d)([\d\.]*),([NS]),(\d\d\d)([\d\.]*),([EW]),([\d\.]*),([\d\.]*),(\d\d\d\d\d\d),[\S ]*\n/) {
        $utc_time = $1;
        $status = $2;
        $lat_deg_part = $3;
        $lat_min_part = $4;
        $lat_n_or_s = $5;
        $long_deg_part = $6;
        $long_min_part = $7;
        $long_e_or_w = $8;
        $speed_knots = $9;
        $course_deg = $10;
        $utc_date = $11;

        # convert latitude into decimal degrees
        if ($lat_n_or_s =~ /S/) {
            $latitude = "-";
        }
        else {
            $latitude = "";
        }
        $latitude = $latitude . ($lat_deg_part + ($lat_min_part / 60));
        print "latitude: <$latitude>\n";

        # convert longitude into decimal degrees
        if ($long_e_or_w =~ /W/) {
            $longitude = "-";
        }
        else {
            $longitude = "";
        }
        $longitude = $longitude . ($long_deg_part + ($long_min_part / 60));
        print "longitude: <$longitude>\n";

        # Insert into the SQL database
        my $rc = $sth->execute( $phone_id, $status, $latitude, $longitude, $speed_knots, $course_deg, 
              $utc_time, $utc_date, $label, $remoteip  )
            or die "Can't execute statement: $DBI::errstr";
        
    }

  } # if (defined $nmea)

} 

# ============
# MAIN PROGRAM
# ============

# Show version
# print "Perl version $]\n";

# Open database connection

# For MySQL
my $data_source = "dbi:mysql:gsmtrack";
my $user = "root";
my $password = shift || ""; # you may give password at the command line

# For MSSQL
# my $data_source = "dbi:ODBC:DSNGSMTRACK";
# my $user = "";
# my $password = "";

my $dbh = DBI->connect($data_source, $user, $password)
    or die "Can't connect to $data_source: $DBI::errstr";

# If you get the following error with MySQL 4.1.1 or newer
# 
#   DBI connect('gsmtrack','root',...) failed: Client does not support authenticatio
#   n protocol requested by server; consider upgrading MySQL client ...
#
# Reset the root password to pre-4.1 style as follows: 
#   mysql>  SET PASSWORD = OLD_PASSWORD('newpwd');
#
# (See http://dev.mysql.com/doc/mysql/en/old-client.html)

# Prepare the SQL statement for fast execution
my $sql_stmt;
$sql_stmt = q{
            INSERT INTO GPS (PHONE,STATUS,LATITUDE,LONGITUDE,SPEED_KNOTS,COURSE_DEG,UTCTIME,UTCDATE,LABEL,REMOTE_IP)
            VALUES (?,?,?,?,?,?,?,?,?,?)
};
$sth = $dbh->prepare( $sql_stmt ) or die "Can't prepare statement: $DBI::errstr";

# Open the UDP socket
my $port = shift || 1002;
my $proto = getprotobyname('udp');
socket(SOCKET, PF_INET, SOCK_DGRAM, $proto) || die "socket: $!";
bind(SOCKET, sockaddr_in($port, INADDR_ANY)) or die "bind: $!";

logmsg "server started on port $port";

my ( $hisiaddr, $hispaddr, $host, $rdatagram);

# loop forever
while (1) {
    $rdatagram = '';
    ($hispaddr = recv(SOCKET, $rdatagram, 260, 0))        || die "recv: $!";
    ($port, $hisiaddr) = sockaddr_in($hispaddr);
    $host = gethostbyaddr($hisiaddr, AF_INET);
    print "\n";
    logmsg "connection from $host [", 
            inet_ntoa($hisiaddr), "] at port $port";
    # print $rdatagram;
    parsedgram $rdatagram, inet_ntoa($hisiaddr);
}

# This is never actually reached due to the infinite loop above
$dbh->disconnect;
exit;

This file was generated by Gabriel Knoy's perl2html script.