12daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch#!/usr/bin/perl -w
22daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch
32daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch# Copyright (C) 2005, 2006, 2007 Apple Computer, Inc.  All rights reserved.
42daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch# Copyright (C) 2011 Carl Lobo.  All rights reserved.
52daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch#
62daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch# Redistribution and use in source and binary forms, with or without
72daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch# modification, are permitted provided that the following conditions
82daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch# are met:
92daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch#
102daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch# 1.  Redistributions of source code must retain the above copyright
112daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch#     notice, this list of conditions and the following disclaimer. 
122daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch# 2.  Redistributions in binary form must reproduce the above copyright
132daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch#     notice, this list of conditions and the following disclaimer in the
142daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch#     documentation and/or other materials provided with the distribution. 
152daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch# 3.  Neither the name of Apple Computer, Inc. ("Apple") nor the names of
162daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch#     its contributors may be used to endorse or promote products derived
172daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch#     from this software without specific prior written permission. 
182daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch#
192daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch# THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
202daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch# EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
212daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
222daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch# DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
232daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch# DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
242daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch# (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
252daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch# LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
262daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch# ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
272daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
282daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch# THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
292daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch
302daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch# Updates a development environment to the new WebKitAuxiliaryLibrary
312daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch
322daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochuse strict;
332daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochuse warnings;
342daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch
352daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochuse File::Find;
362daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochuse File::Spec;
372daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochuse File::Temp ();
382daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochuse FindBin;
392daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochuse HTTP::Date qw(str2time);
402daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochuse POSIX;
412daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochuse lib $FindBin::Bin;
422daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochuse webkitdirs;
432daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch
442daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochif ($#ARGV != 1) {
452daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch    die <<EOF;
462daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben MurdochUsage:
472daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch        update-webkit-dependancy <URL with the dependancy zip file> <*prefix dir inside zip without filename>
482daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch
492daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch        * If filename is requirements.zip and the contents of the zipfile are "requirements/x" then prefix = "."
502daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch        * If filename is xyz.zip and the contents of the zipfile are xyz/abc/x" then prefix = "abc"
512daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch        * x is lib or include or bin.
522daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben MurdochEOF
532daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch}
542daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch
552daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochsub lastModifiedToUnixTime($);
562daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochsub getLibraryName($);
572daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch
582daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch# Time in seconds that the new zip file must be newer than the old for us to
592daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch# consider them to be different. If the difference in modification time is less
602daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch# than this threshold, we assume that the files are the same. We need this
612daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch# because the zip file is served from a set of mirrors with slightly different
622daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch# Last-Modified times.
632daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochmy $newnessThreshold = 30;
642daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch
652daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochmy $libsURL = shift;
662daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochmy $prefixInZip = shift;
672daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochmy $sourceDir = sourceDir();
682daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochmy $file = getLibraryName($libsURL);
692daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochmy $zipFile = "$file.zip"; 
702daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochmy $webkitLibrariesDir = toUnixPath($ENV{'WEBKITLIBRARIESDIR'}) || "$sourceDir/WebKitLibraries/win";
712daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochmy $tmpRelativeDir = File::Temp::tempdir("webkitlibsXXXXXXX", TMPDIR => 1, CLEANUP => 1);
722daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochmy $tmpAbsDir = File::Spec->rel2abs($tmpRelativeDir);
732daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch
742daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochprint "Checking Last-Modified date of $zipFile...\n";
752daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch
762daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochmy $result = system "curl -s -I $libsURL | grep Last-Modified > \"$tmpAbsDir/$file.headers\"";
772daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch
782daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochif (WEXITSTATUS($result)) {
792daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch    print STDERR "Couldn't check Last-Modified date of new $zipFile.\n";
802daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch    print STDERR "Please ensure that $libsURL is reachable.\n";
812daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch
822daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch    if (! -f "$webkitLibrariesDir/$file.headers") {
832daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch        print STDERR "Unable to check Last-Modified date and no version of $file to fall back to.\n";
842daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch        exit 1;
852daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch    }
862daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch
872daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch    print STDERR "Falling back to existing version of $file.\n";
882daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch    exit 0;
892daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch}
902daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch
912daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochif (open NEW, "$tmpAbsDir/$file.headers") {
922daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch    my $new = lastModifiedToUnixTime(<NEW>);
932daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch    close NEW;
942daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch
952daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch    if (defined $new && open OLD, "$webkitLibrariesDir/$file.headers") {
962daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch        my $old = lastModifiedToUnixTime(<OLD>);
972daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch        close OLD;
982daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch        if (defined $old && abs($new - $old) < $newnessThreshold) {
992daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch            print "Current $file is up to date\n";
1002daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch            exit 0;
1012daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch        }
1022daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch    }
1032daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch}
1042daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch
1052daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochprint "Downloading $zipFile...\n\n";
1062daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch$result = system "curl -o \"$tmpAbsDir/$zipFile\" $libsURL";
1072daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochdie "Couldn't download $zipFile!" if $result;
1082daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch
1092daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch$result = system "unzip", "-q", "-d", $tmpAbsDir, "$tmpAbsDir/$zipFile";
1102daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochdie "Couldn't unzip $zipFile." if $result;
1112daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch
1122daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochprint "\nInstalling $file...\n";
1132daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch
1142daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochsub wanted
1152daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch{
1162daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch    my $relativeName = File::Spec->abs2rel($File::Find::name, "$tmpAbsDir/$file/$prefixInZip");
1172daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch    my $destination = "$webkitLibrariesDir/$relativeName";
1182daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch
1192daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch    if (-d $_) {
1202daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch        mkdir $destination;
1212daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch        return;
1222daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch    }
1232daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch
1242daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch    system "cp", $_, $destination;
1252daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch}
1262daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch
1272daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben MurdochFile::Find::find(\&wanted, "$tmpAbsDir/$file");
1282daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch
1292daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch$result = system "mv", "$tmpAbsDir/$file.headers", $webkitLibrariesDir;
1302daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochprint STDERR "Couldn't move $file.headers to $webkitLibrariesDir" . ".\n" if $result;
1312daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch
1322daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochprint "The $file has been sucessfully installed in\n $webkitLibrariesDir\n";
1332daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochexit;
1342daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch
1352daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochsub toUnixPath
1362daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch{
1372daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch    my $path = shift;
1382daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch    return unless $path;
1392daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch    chomp($path = `cygpath -u '$path'`);
1402daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch    return $path;
1412daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch}
1422daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch
1432daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochsub lastModifiedToUnixTime($)
1442daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch{
1452daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch    my ($str) = @_;
1462daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch
1472daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch    $str =~ /^Last-Modified: (.*)$/ or return;
1482daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch    return str2time($1);
1492daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch}
1502daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch
1512daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdochsub getLibraryName($)
1522daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch{
1532daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch    my $url = shift;
1542daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch    $url =~ m#/([^/]+)\.zip$#;
1552daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch    return $1;
1562daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch}
1572daae5fd11344eaa88a0d92b0f6d65f8d2255c00Ben Murdoch
158