#!/usr/bin/perl

use strict;

use Net::FTP;

my $version="1190";

my $installfile="distrib.tbz2";
my $installpath="/opt/pips";
my $libpath="/opt/pips";
my $workdir="/storage";
my $startfile="/etc/conf.d/local.start";
my $libfile="/etc/ld.so.conf";
my $webmindir="/usr/libexec/webmin/spikeapp";
my $pausefile="/opt/config/current/paused";

my $server="10.20.100.6";
my $rootdir="382";
my $username="ftp_boot";
my $password="ftp_boot";

my $appdir="app";
my $cardetdir="cardet";
my $cardetfile;

my $localfiles=0;
my $ftp;

print "This is instapp version $version on $^O\n";

if (scalar(@ARGV) >= 1)
{
    $server=$ARGV[0];
}

mkdir $installpath || die "Cannot make install directory $installpath\n";

if ( -e $installfile )
{
    $localfiles=1;
}
print "\n";

if ($localfiles == 0)
{
    chdir $workdir;

    # Choose and download an app

    $ftp=Net::FTP->new($server) || die "Cannot connect to $server\n";

    $ftp->login($username, $password) || die "Cannot log in to server\n";
    $ftp->binary();

    my $apppath="$rootdir/$appdir";
    my $appname=selectfromlist($apppath,"Application");
    $ftp->get("$apppath/$appname/$installfile") || die "Cannot retrieve $apppath/$appname/$installfile";

    my $cardetpath="$rootdir/$cardetdir";
    my $cardetver=selectfromlist($cardetpath,"ANPR engine version");
    $cardetpath="$cardetpath/$cardetver";
    $cardetfile=selectfromlist($cardetpath,"ANPR engine");
    $ftp->get("$cardetpath/$cardetfile") || die "Cannot retrieve $cardetpath/$cardetfile";
    $ftp->quit;
}

die "Install file is zero length, problem with transferring it?" if ((-s $installfile) == 0);

die "Corrupted install file, did you transfer the file in binary mode?"  if (system "tar -jtf $installfile  2>&1 >/dev/null");

open FILE, ">$pausefile";
print FILE "";
close FILE;

system ("mv $installpath/threeeighttwo $installpath/threeeighttwo.old");
system ("mv $installpath/ipconfigd $installpath/ipconfigd.old");
system ("rm -rf $installpath/webmin");
system ("tar -jxf $installfile -C $installpath");
system ("mv $installpath/distrib/* $installpath");

my $foundstart=0;
my $foundipcd=0;

open START, $startfile  || die "Cannot open start file";

while (my $line=<START>)
{
  if ($line=~/start382/)
  {
    $foundstart=1;
  }
  if ($line=~/ipconfigd/)
  {
    $foundipcd=1;
  }
}

close START;
my $foundlib=0;

open LDCONF, $libfile  || die "Cannot open $libfile file";

while (my $line=<LDCONF>)
{
  if ($line=~/$libpath/)
  {
    $foundlib=1;
  }
}

close LDCONF;

system ("mount -orw,remount /");
if ($foundipcd==0)
{
    open START, ">>$startfile";
    print START "$installpath/ipconfigd 2\>\&1 >/dev/null &\n";
    close START;
}

if ($foundstart==0)
{
    open START, ">>$startfile";
    print START "$installpath/start382 2\>\&1 >/dev/null &\n";
    close START;
}

if ($foundlib==0)
{
    open LDCONF, ">>$libfile";
    print LDCONF "$libpath\n";
    close LDCONF;
}

system("mv $installpath/libftp.so.3.1 /usr/local/lib");
symlink("/usr/local/lib/libftp.so.3.1", "/usr/local/lib/libftp.so.3");
symlink("/usr/local/lib/libftp.so.3.1", "/usr/local/lib/libftp.so");
symlink("$installpath/pipsshell", "/usr/bin/pipsshell");
if (defined $cardetfile)
{
    print "Installing cardet\n";
    print "$cardetfile to $libpath/$cardetfile" || die "Cannot copy anpr engine into place";
    system "mv $cardetfile $libpath/$cardetfile";
    foreach("libcardet.so","libcardet.so.1","libcardet.p382.so.1")
    {
	unlink "$libpath/$_";
	symlink "$libpath/$cardetfile","$libpath/$_";
    }
}
else
{
    print "No cardet to install\n";
}
system "ldconfig";

if ( -e "$installpath/webmin" )
{
    print "Installing webmin\n";
    mkdir $webmindir;
    system "rm -rf $webmindir";
    system "mkdir $webmindir";
    system "cp -a $installpath/webmin/* $webmindir";
    system "rm -rf $installpath/webmin";
}

system ("mount -oro,remount /");

print "Programming Xilinx PROM\n";
system ("cd $installpath && ./instfpga.pl");

print "Finalising\n";
if ($localfiles == 0)
{
    unlink $installfile;
}
unlink $pausefile;
system("sync");
print "Complete\n";

sub selectfromlist
{
    my $path=$_[0];
    my $desc=$_[1];
    my $name;
    my @list=();

    if ($localfiles==0)
    {
	@list=$ftp->ls($path);
    }
    else
    {
	opendir (DIRHANDLE, ".") || die ("Couldn't read from current directory");

	while (my $cdFile=readdir DIRHANDLE)
	{
	    if ($cdFile=~/libcardet/)
	    {
		push @list, $cdFile;
	    }
	}
	closedir (DIRHANDLE);

	if (scalar(@list)==0)
	{
	    print "No $desc to install from this directory\n";
	    return undef;
	}
    }

    while ($name eq "")
    {
	print "List of $desc"."s available from $path\n";

	foreach (@list)
	{
	    my $file=$_;
	    $file=~s/$path\///;
	    print "$file\n";
	}
	print "\nPlease enter the name of the one you want : ";
	my $choice=<STDIN>;
	chop $choice;

	my $matches=0;
	my $matched="";
	# Now check that choice matches one and only one entry from list
	if ((scalar @list == 1)&&($choice eq ""))
	{
		$matched=$list[0];
		$matched=~s/$path\///;
		$matches++;
		print "Only choice\n";
	}
	else
	{
	    foreach (@list)
	    {
		my $file=$_;
		$file=~s/$path\///;
		if ($file eq $choice)
		{
		    $matched=$file;
		    $matches++;
		    print "Exact match $matched\n";
		    next;
		}
		my @tokens=split /\.+/, $file;
		foreach (@tokens)
		{
		    if ($_ eq $choice)
		    {
			$matched=$file;
			$matches++;
			print "Token match $matched\n";
			last;
		    }
		}
	    }
	    if ($matches==0)
	    {
		print "Not single matched\n";
		foreach (@list)
		{
		    my $file=$_;
		    $file=~s/$path\///;
		    if ($file=~/$choice/)
		    {
			$matched=$file;
			$matches++;
		    }
		}
	    }
	}

	if ($matches==1)
	{
	    $name=$matched;
	    print "$desc selected\n";
	}
	else
	{
	    $name="";
	    print "$desc not available\n";
	}
    }
    $name;
}
