#!/usr/bin/perl

# ============================================================================
# Cray Lim (cray@shark.me.nus.edu.sg)
# Script for checking and posting IP updates to DyNS dynamic DNS service
# Copyright (C) 2004 Cray Lim
#
# IMPORTANT : Please note that lynx must be installed on your system for the
#             script to work.
# NOTE      : This program accepts 0 argument (IP update mode) and 1 argument,
#             "checkip" (displaying the current external IP) or "force" 
#			  (forced IP update)  I recommend running this script from 
#			  your $HOME/bin directory.
# EXAMPLE   : ./getip [checkip|force]
#
#
# This program is free software; you can redistribute it and/or
# modify it under the terms of the GNU General Public License
# as published by the Free Software Foundation; either version 2
# of the License, or (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
# GNU General Public License for more details.
# This program is free software; you can redistribute it and/or
# modify it under the terms of the GNU General Public License
# as published by the Free Software Foundation; either version 2
# of the License, or (at your option) any later version.
# ============================================================================

# key in your account info in the below 3 lines 
my $username="myusername"; # key in  your Dyns username here
my $password="mypassword"; # key in your Dyns account password
my $host="myhost.dyns.cx"; # key in your Dyns host.domain
my $script_dir="$ENV{'HOME'}/bin/"; # directory where the script resides (with an ending "/")
									# or use absolute path eg. /home/cray/bin/ 

									
# you do not need to editing anything below this line
my $num_para= $#ARGV;
my $usr_para=pop @ARGV; # obtaining the command line parameter
my $new_ip; # new external IP
my $current_ip_file=$script_dir."currentip.gip"; # store current IP
my $current_ip; # current IP
my $update_status; # update status from Dyns
my $ip_address_checker_url="http://www.bnl.gov/itd/webapps/checkip.asp"; # a service that returns your ext IP
my $dyns_update_url="http://www.dyns.net/postscript011.php"; # Dyns IP posting/updating URL

# IP address mining
$new_ip=`lynx -dump "$ip_address_checker_url"`;
$new_ip=~/\s+Your IP Address is:\s+(\d+\.\d+\.\d+\.\d+)/; # mine out the external IP address
$new_ip=$1;

sub store_current_ip # sub-routine to write the IP address to the compare file
{
   open OUTFILE, "> $current_ip_file";
   print OUTFILE "$new_ip";
   close OUTFILE;
   print "Dyns host $host is updated to the new IP: $new_ip\n";
}

sub dyns_update # sub-routine to update DyNS with the latest IP
{
   $update_status=`lynx -dump "$dyns_update_url?username=$username&password=$password&host=$host&ip=$new_ip"`;
   if ($update_status=~/200/)
   {
   		&store_current_ip;
   }
   elsif ($update_status=~/wait +(\d+) +s/)
   {
		print "Updating too frequently.  Please try again $1s later.\n";
   }
   else
   {
		print "Update is unsuccessful.  Please try again later.\n";
   }
}

if ($num_para >= 1)
{
   	print "Incorrect number of argument.  Program accepts 0 or 1 argument.\neg. getip [checkip|force]\n";
   	exit(0);
}

if (($usr_para eq "checkip"))
{
   	print "The current external IP is : $new_ip\n";
   	exit(0);
}
elsif (($usr_para eq "force"))
{	
	&dyns_update;
   	exit(0);
}
elsif (defined($usr_para))
{
   	print "Invalid argument \"$usr_para\".  Program only accepts \"checkip\" or \"force\" as argument.\neg. getip checkip or getip force\n";
   	exit(0);
}

if (!(-e $current_ip_file)) # running getip for the 1st time.  compare file not found
{
	&dyns_update;
}  
else
{
   	open INFILE, "$current_ip_file";
   	$current_ip=<INFILE>;
   	close INFILE;
   	if ($current_ip eq $new_ip)
   	{
		print "There is no change in IP. No update to Dyns required\n";
   	}  
   	else
   	{
   		&dyns_update;	
   	}
}
