+#!/usr/bin/perl
+#
+# This code is distributed under the terms of the GPL
+#
+# (c) 2006-2008 marco.s - http://update-accelerator.advproxy.net
+#
+# Portions (c) 2008 by dotzball - http://www.blockouttraffic.de
+#
+# $Id: checkdeaddl,v 1.1 2008/11/29 00:00:00 marco.s Exp $
+#
+
+use strict;
+
+use Fcntl ':flock'; # import LOCK_* constants
+use HTTP::Date;
+
+require '/var/ipfire/updatexlrator/updxlrator-lib.pl';
+
+my $repository='/var/updatecache';
+my $logfile="/var/log/updatexlrator/download.log";
+my $logging=0;
+my $debug=0;
+my %proxysettings=();
+my %xlratorsettings=();
+my $updatefile='';
+my @downloads=();
+my $passive_mode=0;
+my $maxusage=0;
+my $nice='';
+my $lockfile = "/var/log/updatexlrator/checkdeaddl.lck";
+
+&debuglog("Check if there is a lock ");
+open SEM, ">$lockfile" or die "Can't write-open $lockfile: $!";
+flock SEM, LOCK_EX;
+&debuglog("No lock, proceed ");
+
+&writelog("Check for dead downloads ");
+
+if (-e "${UPDXLT::apphome}/settings")
+{
+ &UPDXLT::readhash("${UPDXLT::apphome}/settings", \%xlratorsettings);
+ if ($xlratorsettings{'ENABLE_LOG'} eq 'on') { $logging=1; };
+ if ($xlratorsettings{'PASSIVE_MODE'} eq 'on') { $passive_mode=1; };
+ if ($xlratorsettings{'LOW_DOWNLOAD_PRIORITY'} eq 'on') { $nice='/bin/nice --adjustment=15 '; };
+ $maxusage = $xlratorsettings{'MAX_DISK_USAGE'};
+}
+else
+{
+ &writelog("Updatexlrator not enabled, exit");
+ exit 0;
+}
+if (!$maxusage) { $maxusage=75; };
+
+if($passive_mode || (&UPDXLT::diskusage($repository) > $maxusage))
+{
+ # nothing to do
+ &writelog("Running in passive mode or maximum diskusage exceeded, exit");
+ exit 0;
+}
+
+
+if (-e "${UPDXLT::swroot}/proxy/settings") { &UPDXLT::readhash("${UPDXLT::swroot}/proxy/settings", \%proxysettings); }
+
+if (-e "${UPDXLT::swroot}/proxy/advanced/settings")
+{
+ %proxysettings=();
+ &UPDXLT::readhash("${UPDXLT::swroot}/proxy/advanced/settings", \%proxysettings);
+}
+
+
+foreach my $dir (<$repository/download/*>)
+{
+ if (-d $dir)
+ {
+ foreach my $updatefile (<$dir/*>)
+ {
+ unless ($updatefile =~ /.info$/)
+ {
+ push(@downloads, $updatefile);
+ }
+ }
+ }
+}
+
+foreach my $updatefile (@downloads)
+{
+ if(-e "$updatefile.info")
+ {
+ &checkdeaddl($updatefile);
+ }
+}
+
+
+# clean lock file
+close(SEM);
+unlink "$lockfile";
+
+# -------------------------------------------------------------------
+
+sub checkdeaddl
+{
+ my $updatefile = shift;
+
+ my %dlinfo = ();
+ &UPDXLT::readhash("$updatefile.info", \%dlinfo);
+
+ my @http_header = ();
+ my $http_result = '000 n/a';
+ my $returncode = 0;
+ my $remote_size = 0;
+ my $remote_mtime = 0;
+ my $login = '';
+
+ my $cmd_ps = "/bin/ps aux | /bin/grep -E \"(download|wget).*$dlinfo{'SRCURL'}\" | /bin/grep -v \"/bin/grep\"";
+ my @runningdl = `$cmd_ps`;
+
+ if(@runningdl > 0)
+ {
+ # download is still running, no need to restart download
+ return;
+ }
+
+ if (($proxysettings{'UPSTREAM_PROXY'}) && ($proxysettings{'UPSTREAM_USER'}))
+ {
+ $login = "--proxy-user=\"$proxysettings{'UPSTREAM_USER'}\"";
+ if ($proxysettings{'UPSTREAM_PASSWORD'})
+ {
+ $login .= " --proxy-password=\"$proxysettings{'UPSTREAM_PASSWORD'}\"";
+ }
+ }
+
+ $ENV{'http_proxy'} = $proxysettings{'UPSTREAM_PROXY'};
+ @http_header = `${UPDXLT::wget} $login --user-agent="${UPDXLT::useragent}" --spider -S $dlinfo{'SRCURL'} 2>&1`;
+ $ENV{'http_proxy'} = '';
+
+ foreach (@http_header)
+ {
+ chomp;
+ if (/^\s*HTTP\/\d+\.\d+\s\d+\s+\w+/) { $http_result = $_; $http_result =~ s/^\s*HTTP\/\d+\.\d+\s+//; }
+ if (/^\s*Content-Length:\s/) { $remote_size = $_; $remote_size =~ s/[^0-9]//g; }
+ if (/^\s*Last-Modified:\s/) { $remote_mtime = $_; $remote_mtime =~ s/^\s*Last-Modified:\s//; $remote_mtime = HTTP::Date::str2time($remote_mtime) }
+ }
+
+ &writelog($updatefile);
+ &writelog("HTTP result: $http_result");
+ &writelog("Source time: $remote_mtime");
+ &writelog("Cached time: " . $dlinfo{'REMOTETIME'});
+
+ if ($http_result =~ /\d+\s+OK$/)
+ {
+ my $cmd = "$nice$UPDXLT::apphome/bin/download $dlinfo{'VENDORID'} $dlinfo{'SRCURL'} $dlinfo{'CFMIRROR'}";
+
+ if ($remote_size > &UPDXLT::diskfree($repository))
+ {
+ &writelog("Can't download file, because remote filesize exceeds maximum diskusage");
+ }
+ elsif ($remote_mtime == $dlinfo{'REMOTETIME'})
+ {
+ # still the same file, continue download
+ &writelog("Status: Ok, continue download");
+ $cmd .= " 1 &";
+ &debuglog("Running command $cmd");
+ system("$cmd");
+ }
+ else
+ {
+ # File is changed on remote site, download from scratch
+ &writelog("Status: Outdated, restart download from scratch");
+ unlink($updatefile);
+ $cmd .= " 0 &";
+ &debuglog("Running command $cmd");
+ system("$cmd");
+ }
+ } else {
+ $_ = $http_result;
+ s/\D+//;
+ if ($_ eq '404')
+ {
+ &writelog("Status: No source");
+ $dlinfo{'STATUS'} = ${UPDXLT::sfNoSource};
+ } else {
+ &writelog("Status: Error");
+ $dlinfo{'STATUS'} = ${UPDXLT::sfUnknown};
+ }
+ &UPDXLT::writehash("$updatefile.info", \%dlinfo);
+ }
+}
+
+# -------------------------------------------------------------------
+
+sub writelog
+{
+ if ($logging)
+ {
+ open (LOGFILE,">>$logfile");
+ my @now = localtime(time);
+ printf LOGFILE "%04d-%02d-%02d %02d:%02d:%02d [%d] %s\n",$now[5]+1900,$now[4]+1,$now[3],$now[2],$now[1],$now[0],$$,$_[0];
+ close LOGFILE;
+ }
+}
+
+# -------------------------------------------------------------------
+
+sub debuglog
+{
+ if ($debug)
+ {
+ open(LOGFILE,">>/var/log/updatexlrator/debug.log");
+ my @now = localtime(time);
+ printf LOGFILE "%04d-%02d-%02d %02d:%02d:%02d [%d] [%s] %s\n",$now[5]+1900,$now[4]+1,$now[3],$now[2],$now[1],$now[0],$$,"updxlrator",$_[0];
+ close(LOGFILE);
+ }
+}
+
+# -------------------------------------------------------------------