Add wxWebKit sample and build script, and integrate it with build-webkit. Also make...
[WebKit-https.git] / WebKitTools / Scripts / webkitdirs.pm
1 # Copyright (C) 2005, 2006, 2007 Apple Inc. All rights reserved.
2 #
3 # Redistribution and use in source and binary forms, with or without
4 # modification, are permitted provided that the following conditions
5 # are met:
6 #
7 # 1.  Redistributions of source code must retain the above copyright
8 #     notice, this list of conditions and the following disclaimer. 
9 # 2.  Redistributions in binary form must reproduce the above copyright
10 #     notice, this list of conditions and the following disclaimer in the
11 #     documentation and/or other materials provided with the distribution. 
12 # 3.  Neither the name of Apple Computer, Inc. ("Apple") nor the names of
13 #     its contributors may be used to endorse or promote products derived
14 #     from this software without specific prior written permission. 
15 #
16 # THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
17 # EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 # WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 # DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
20 # DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 # (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 # LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 # ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 # (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
25 # THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26
27 # Module to share code to get to WebKit directories.
28
29 use strict;
30 use warnings;
31 use FindBin;
32 use File::Basename;
33 use POSIX;
34
35 BEGIN {
36    use Exporter   ();
37    our ($VERSION, @ISA, @EXPORT, @EXPORT_OK, %EXPORT_TAGS);
38    $VERSION     = 1.00;
39    @ISA         = qw(Exporter);
40    @EXPORT      = qw(&chdirWebKit &baseProductDir &productDir &XcodeOptions &XcodeOptionString &XcodeOptionStringNoConfig &passedConfiguration &setConfiguration &safariPath &checkFrameworks &currentSVNRevision);
41    %EXPORT_TAGS = ( );
42    @EXPORT_OK   = ();
43 }
44
45 our @EXPORT_OK;
46
47 my $baseProductDir;
48 my @baseProductDirOption;
49 my $configuration;
50 my $configurationForVisualStudio;
51 my $configurationProductDir;
52 my $sourceDir;
53 my $currentSVNRevision;
54 my $osXVersion;
55 my $isQt;
56 my $isGtk;
57 my $isWx;
58
59 # Variables for Win32 support
60 my $vcBuildPath;
61 my $windowsTmpPath;
62
63 sub determineSourceDir
64 {
65     return if $sourceDir;
66     $sourceDir = $FindBin::Bin;
67     
68     # walks up path checking each directory to see if it is the main WebKit project dir, 
69     # defined by containing JavaScriptCore, WebCore, and WebKit
70     until ((-d "$sourceDir/JavaScriptCore" && -d "$sourceDir/WebCore" && -d "$sourceDir/WebKit") || (-d "$sourceDir/Internal" && -d "$sourceDir/OpenSource"))
71     {
72         if ($sourceDir !~ s|/[^/]+$||) {
73             die "Could not find top level webkit directory above source directory using FindBin.\n";
74         }
75     }
76
77     $sourceDir = "$sourceDir/OpenSource" if -d "$sourceDir/OpenSource";
78 }
79
80 # used for scripts which are stored in a non-standard location
81 sub setSourceDir($)
82 {
83     ($sourceDir) = @_;
84 }
85
86 sub determineBaseProductDir
87 {
88     return if defined $baseProductDir;
89     determineSourceDir();
90     if (isOSX()) {
91         open PRODUCT, "defaults read com.apple.Xcode PBXApplicationwideBuildSettings 2> /dev/null |" or die;
92         $baseProductDir = join '', <PRODUCT>;
93         close PRODUCT;
94
95         $baseProductDir = $1 if $baseProductDir =~ /SYMROOT\s*=\s*\"(.*?)\";/s;
96         undef $baseProductDir unless $baseProductDir =~ /^\//;
97
98         if (!defined($baseProductDir)) {
99             open PRODUCT, "defaults read com.apple.Xcode PBXProductDirectory 2> /dev/null |" or die;
100             $baseProductDir = <PRODUCT>;
101             close PRODUCT;
102             if ($baseProductDir) {
103                 chomp $baseProductDir;
104                 undef $baseProductDir unless $baseProductDir =~ /^\//;
105             }
106         }
107     } else {
108         $baseProductDir = $ENV{"WEBKITOUTPUTDIR"};
109         if (isCygwin() && $baseProductDir) {
110             my $unixBuildPath = `cygpath --unix \"$baseProductDir\"`;
111             chomp $unixBuildPath;
112             $baseProductDir = $unixBuildPath;
113         }
114     }
115
116     if ($baseProductDir && isOSX()) {
117         $baseProductDir =~ s|^\Q$(SRCROOT)/..\E$|$sourceDir|;
118         $baseProductDir =~ s|^\Q$(SRCROOT)/../|$sourceDir/|;
119         $baseProductDir =~ s|^~/|$ENV{HOME}/|;
120         die "Can't handle Xcode product directory with a ~ in it.\n" if $baseProductDir =~ /~/;
121         die "Can't handle Xcode product directory with a variable in it.\n" if $baseProductDir =~ /\$/;
122         @baseProductDirOption = ();
123     }
124
125     if (!defined($baseProductDir)) {
126         $baseProductDir = "$sourceDir/WebKitBuild";
127         @baseProductDirOption = ("SYMROOT=$baseProductDir", "OBJROOT=$baseProductDir") if (isOSX());
128         if (isCygwin()) {
129             my $dosBuildPath = `cygpath --windows \"$baseProductDir\"`;
130             chomp $dosBuildPath;
131             $ENV{"WEBKITOUTPUTDIR"} = $dosBuildPath;
132         }
133     }
134 }
135
136 sub setBaseProductDir($)
137 {
138     ($baseProductDir) = @_;
139 }
140
141 sub determineConfiguration
142 {
143     return if defined $configuration;
144     determineBaseProductDir();
145     if (open CONFIGURATION, "$baseProductDir/Configuration") {
146         $configuration = <CONFIGURATION>;
147         close CONFIGURATION;
148     }
149     if ($configuration) {
150         chomp $configuration;
151         # compatibility for people who have old Configuration files
152         $configuration = "Release" if $configuration eq "Deployment";
153         $configuration = "Debug" if $configuration eq "Development";
154     } else {
155         $configuration = "Release";
156     }
157 }
158
159 sub determineConfigurationForVisualStudio
160 {
161     return if defined $configurationForVisualStudio;
162     determineConfiguration();
163     $configurationForVisualStudio = $configuration;
164     return unless $configuration eq "Debug";
165     setupCygwinEnv();
166     chomp(my $dir = `cygpath -ua '$ENV{WEBKITLIBRARIESDIR}'`);
167     $configurationForVisualStudio = "Debug_Internal" if -f "$dir/bin/CoreFoundation_debug.dll";
168 }
169
170 sub determineConfigurationProductDir
171 {
172     return if defined $configurationProductDir;
173     determineBaseProductDir();
174     if(isCygwin()) {
175         $configurationProductDir = "$baseProductDir/bin";
176     } else {
177         determineConfiguration();
178         $configurationProductDir = "$baseProductDir/$configuration";
179     }
180 }
181
182 sub setConfigurationProductDir($)
183 {
184     ($configurationProductDir) = @_;
185 }
186
187 sub determineCurrentSVNRevision
188 {
189     return if defined $currentSVNRevision;
190     determineSourceDir();
191     my $svnInfo = `LC_ALL=C svn info $sourceDir | grep Revision:`;
192     ($currentSVNRevision) = ($svnInfo =~ m/Revision: (\d+).*/g);
193     die "Unable to determine current SVN revision in $sourceDir" unless (defined $currentSVNRevision);
194     return $currentSVNRevision;
195 }
196
197
198 sub chdirWebKit
199 {
200     determineSourceDir();
201     chdir $sourceDir or die;
202 }
203
204 sub baseProductDir
205 {
206     determineBaseProductDir();
207     return $baseProductDir;
208 }
209
210 sub sourceDir
211 {
212     determineSourceDir();
213     return $sourceDir;
214 }
215
216 sub productDir
217 {
218     determineConfigurationProductDir();
219     return $configurationProductDir;
220 }
221
222 sub configuration()
223 {
224     determineConfiguration();
225     return $configuration;
226 }
227
228 sub configurationForVisualStudio()
229 {
230     determineConfigurationForVisualStudio();
231     return $configurationForVisualStudio;
232 }
233
234 sub currentSVNRevision
235 {
236     determineCurrentSVNRevision();
237     return $currentSVNRevision;
238 }
239
240 sub XcodeOptions
241 {
242     determineBaseProductDir();
243     determineConfiguration();
244     return (@baseProductDirOption, "-configuration", $configuration);
245 }
246
247 sub XcodeOptionString
248 {
249     return join " ", XcodeOptions();
250 }
251
252 sub XcodeOptionStringNoConfig
253 {
254     return join " ", @baseProductDirOption;
255 }
256
257 my $passedConfiguration;
258 my $searchedForPassedConfiguration;
259 sub determinePassedConfiguration
260 {
261     return if $searchedForPassedConfiguration;
262     $searchedForPassedConfiguration = 1;
263     for my $i (0 .. $#ARGV) {
264         my $opt = $ARGV[$i];
265         if ($opt =~ /^--debug$/i || $opt =~ /^--devel/i) {
266             splice(@ARGV, $i, 1);
267             $passedConfiguration = "Debug";
268             return;
269         }
270         if ($opt =~ /^--release$/i || $opt =~ /^--deploy/i) {
271             splice(@ARGV, $i, 1);
272             $passedConfiguration = "Release";
273             return;
274         }
275     }
276     $passedConfiguration = undef;
277 }
278
279 sub passedConfiguration
280 {
281     determinePassedConfiguration();
282     return $passedConfiguration;
283 }
284
285 sub setConfiguration
286 {
287     if (my $config = shift @_) {
288         $configuration = $config;
289         return;
290     }
291
292     determinePassedConfiguration();
293     $configuration = $passedConfiguration if $passedConfiguration;
294 }
295
296 sub safariPathFromSafariBundle
297 {
298     my ($safariBundle) = @_;
299
300     return "$safariBundle/Contents/MacOS/Safari" if isOSX();
301     return $safariBundle if isCygwin();
302 }
303
304 sub installedSafariPath
305 {
306     my $safariBundle;
307
308     if (isOSX()) {
309         $safariBundle = "/Applications/Safari.app";
310     } elsif (isCygwin()) {
311         $safariBundle = `"$configurationProductDir/FindSafari.exe"`;
312         $safariBundle =~ s/[\r\n]+$//;
313         $safariBundle = `cygpath -u '$safariBundle'`;
314         $safariBundle =~ s/[\r\n]+$//;
315         $safariBundle .= "Safari.exe";
316     }
317
318     return safariPathFromSafariBundle($safariBundle);
319 }
320
321 # Locate Safari.
322 sub safariPath
323 {
324     # Use WEBKIT_SAFARI environment variable if present.
325     my $safariBundle = $ENV{WEBKIT_SAFARI};
326     if (!$safariBundle) {
327         determineConfigurationProductDir();
328         # Use Safari.app in product directory if present (good for Safari development team).
329         if (isOSX() && -d "$configurationProductDir/Safari.app") {
330             $safariBundle = "$configurationProductDir/Safari.app";
331         } elsif (isCygwin() && -x "$configurationProductDir/bin/Safari.exe") {
332             $safariBundle = "$configurationProductDir/bin/Safari.exe";
333         } else {
334             return installedSafariPath();
335         }
336     }
337     my $safariPath = safariPathFromSafariBundle($safariBundle);
338     die "Can't find executable at $safariPath.\n" if isOSX() && !-x $safariPath;
339     return $safariPath;
340 }
341
342 sub builtDylibPathForName
343 {
344     my $framework = shift;
345     determineConfigurationProductDir();
346     if (isQt() or isGtk()) {
347         return "$configurationProductDir/$framework";
348     }
349     if (isOSX()) {
350         return "$configurationProductDir/$framework.framework/Versions/A/$framework";
351     }
352     if (isCygwin()) {
353         if ($framework eq "JavaScriptCore") {
354                 return "$baseProductDir/lib/$framework.lib";
355         } else {
356             return "$baseProductDir/$framework.intermediate/$configuration/$framework.intermediate/$framework.lib";
357         }
358     }
359
360     die "Unsupported platform, can't determine built library locations.";
361 }
362
363 # Check to see that all the frameworks are built.
364 sub checkFrameworks
365 {
366     return if isCygwin();
367     my @frameworks = ("JavaScriptCore", "WebCore");
368     push(@frameworks, "WebKit") if isOSX();
369     for my $framework (@frameworks) {
370         my $path = builtDylibPathForName($framework);
371         die "Can't find built framework at \"$path\".\n" unless -x $path;
372     }
373 }
374
375 sub hasSVGSupport
376 {
377     return 0 if isCygwin();
378
379     my $path = shift;
380
381     if (isQt()) {
382         return 1;
383     }
384
385     if (isGtk() and $path =~ /WebCore/) {
386         $path .= "/../lib/libWebKitGtk.so";
387     }
388
389     open NM, "-|", "nm", $path or die;
390     my $hasSVGSupport = 0;
391     while (<NM>) {
392         $hasSVGSupport = 1 if /SVGElement/;
393     }
394     close NM;
395     return $hasSVGSupport;
396 }
397
398 sub removeLibraryDependingOnSVG
399 {
400     my $frameworkName = shift;
401     my $shouldHaveSVG = shift;
402
403     my $path = builtDylibPathForName($frameworkName);
404     return unless -x $path;
405
406     my $hasSVG = hasSVGSupport($path);
407     system "rm -f $path" if ($shouldHaveSVG xor $hasSVG);
408 }
409
410 sub checkWebCoreSVGSupport
411 {
412     my $required = shift;
413     my $framework = "WebCore";
414     my $path = builtDylibPathForName($framework);
415     my $hasSVG = hasSVGSupport($path);
416     if ($required && !$hasSVG) {
417         die "$framework at \"$path\" does not include SVG Support, please run build-webkit --svg\n";
418     }
419     return $hasSVG;
420 }
421
422 sub isQt()
423 {
424     determineIsQt();
425     return $isQt;
426 }
427
428 sub checkArgv($)
429 {
430     my $argToCheck = shift;
431     foreach my $opt (@ARGV) {
432         if ($opt =~ /^$argToCheck/i ) {
433             @ARGV = grep(!/^$argToCheck/i, @ARGV);
434             return 1;
435         }
436     }
437     return 0;
438 }
439
440 sub determineIsQt()
441 {
442     return if defined($isQt);
443
444     # Allow override in case QTDIR is not set.
445     if (checkArgv("--qt")) {
446         $isQt = 1;
447         return;
448     }
449
450     # The presence of QTDIR only means Qt if --gtk is not on the command-line
451     if (isGtk()) {
452         $isQt = 0;
453         return;
454     }
455     
456     $isQt = defined($ENV{'QTDIR'});
457 }
458
459 sub isGtk()
460 {
461     determineIsGtk();
462     return $isGtk;
463 }
464
465 sub determineIsGtk()
466 {
467     return if defined($isGtk);
468
469     if (checkArgv("--gtk")) {
470         $isGtk = 1;
471     } else {
472         $isGtk = 0;
473     }
474 }
475
476 sub isWx()
477 {
478     determineIsWx();
479     return $isWx;
480 }
481
482 sub determineIsWx()
483 {
484     return if defined($isWx);
485
486     if (checkArgv("--wx")) {
487         $isWx = 1;
488     } else {
489         $isWx = 0;
490     }
491 }
492
493 sub isCygwin()
494 {
495     return ($^O eq "cygwin");
496 }
497
498 sub isDarwin()
499 {
500     return ($^O eq "darwin");
501 }
502
503 sub isOSX()
504 {
505     return isDarwin() unless (isQt() or isGtk() or isWx());
506     return 0;
507 }
508
509 sub determineOSXVersion()
510 {
511     return if $osXVersion;
512
513     if (!isOSX()) {
514         $osXVersion = -1;
515         return;
516     }
517
518     my $version = `sw_vers -productVersion`;
519     my @splitVersion = split(/\./, $version);
520     @splitVersion >= 2 or die "Invalid version $version";
521     $osXVersion = {
522             "major" => $splitVersion[0],
523             "minor" => $splitVersion[1],
524             "subminor" => (defined($splitVersion[2]) ? $splitVersion[2] : 0),
525     };
526 }
527
528 sub osXVersion()
529 {
530     determineOSXVersion();
531     return $osXVersion;
532 }
533
534 sub isTiger()
535 {
536     return isOSX() && osXVersion()->{"minor"} == 4;
537 }
538
539 sub isLeopard()
540 {
541     return isOSX() && osXVersion()->{"minor"} == 5;
542 }
543
544 sub relativeScriptsDir()
545 {
546     my $scriptDir = File::Spec->catpath("", File::Spec->abs2rel(dirname($0), getcwd()), "");
547     if ($scriptDir eq "") {
548         $scriptDir = ".";
549     }
550     return $scriptDir;
551 }
552
553 sub launcherPath()
554 {
555     my $relativeScriptsPath = relativeScriptsDir();
556     if (isGtk() || isQt()) {
557         return "$relativeScriptsPath/run-launcher";
558     } elsif (isOSX() || isCygwin()) {
559         return "$relativeScriptsPath/run-safari";
560     }
561 }
562
563 sub launcherName()
564 {
565     if (isGtk()) {
566         return "GtkLauncher";
567     } elsif (isQt()) {
568         return "QtLauncher";
569     } elsif (isOSX() || isCygwin()) {
570         return "Safari";
571     }
572 }
573
574 sub checkRequiredSystemConfig
575 {
576     if (isOSX()) {
577         chomp(my $productVersion = `sw_vers -productVersion`);
578         if ($productVersion lt "10.4") {
579             print "*************************************************************\n";
580             print "Mac OS X Version 10.4.0 or later is required to build WebKit.\n";
581             print "You have " . $productVersion . ", thus the build will most likely fail.\n";
582             print "*************************************************************\n";
583         }
584         my $xcodeVersion = `xcodebuild -version`;
585         if ($xcodeVersion !~ /DevToolsCore-(\d+)/ || $1 < 747) {
586             print "*************************************************************\n";
587             print "Xcode Version 2.3 or later is required to build WebKit.\n";
588             print "You have an earlier version of Xcode, thus the build will\n";
589             print "most likely fail.  The latest Xcode is available from the web:\n";
590             print "http://developer.apple.com/tools/xcode\n";
591             print "*************************************************************\n";
592         }
593     } elsif (isGtk() or isQt() or isWx()) {
594         my @cmds = qw(flex bison gperf);
595         my @missing = ();
596         foreach my $cmd (@cmds) {
597             if (not `$cmd --version`) {
598                 push @missing, $cmd;
599             }
600         }
601         if (@missing) {
602             my $list = join ", ", @missing;
603             die "ERROR: $list missing but required to build WebKit.\n";
604         }
605     }
606     # Win32 and other platforms may want to check for minimum config
607 }
608
609 sub setupCygwinEnv()
610 {
611     return if !isCygwin();
612     return if $vcBuildPath;
613
614     my $programFilesPath = `cygpath "$ENV{'PROGRAMFILES'}"`;
615     chomp $programFilesPath;
616     $vcBuildPath = "$programFilesPath/Microsoft Visual Studio 8/Common7/IDE/devenv.com";
617     if (! -e $vcBuildPath) {
618         # VC++ not found, try VC++ Express
619         my $vsInstallDir;
620         if ($ENV{'VSINSTALLDIR'}) {
621             $vsInstallDir = $ENV{'VSINSTALLDIR'};
622         } else {
623             $programFilesPath = $ENV{'PROGRAMFILES'} || "C:\\Program Files";
624             $vsInstallDir = "$programFilesPath/Microsoft Visual Studio 8";
625         }
626         $vsInstallDir = `cygpath "$vsInstallDir"`;
627         chomp $vsInstallDir;
628         $vcBuildPath = "$vsInstallDir/Common7/IDE/VCExpress.exe";
629         if (! -e $vcBuildPath) {
630             print "*************************************************************\n";
631             print "Cannot find '$vcBuildPath'\n";
632             print "Please execute the file 'vcvars32.bat' from\n";
633             print "'$programFilesPath\\Microsoft Visual Studio 8\\VC\\bin\\'\n";
634             print "to setup the necessary environment variables.\n";
635             print "*************************************************************\n";
636             die;
637         }
638     }
639
640     chomp($ENV{'WEBKITLIBRARIESDIR'} = `cygpath -wa "$sourceDir/WebKitLibraries/win"`) unless $ENV{'WEBKITLIBRARIESDIR'};
641
642     $windowsTmpPath = `cygpath -w /tmp`;
643     chomp $windowsTmpPath;
644     print "Building results into: ", baseProductDir(), "\n";
645     print "WEBKITOUTPUTDIR is set to: ", $ENV{"WEBKITOUTPUTDIR"}, "\n";
646     print "WEBKITLIBRARIESDIR is set to: ", $ENV{"WEBKITLIBRARIESDIR"}, "\n";
647 }
648
649 sub buildVisualStudioProject
650 {
651     my ($project, $clean) = @_;
652     setupCygwinEnv();
653
654     my $config = configurationForVisualStudio();
655
656     chomp(my $winProjectPath = `cygpath -w "$project"`);
657     
658     my $command = "/build";
659     if ($clean) {
660         $command = "/clean";
661     }
662
663     print "$vcBuildPath $winProjectPath /build $config\n";
664     return system $vcBuildPath, $winProjectPath, $command, $config;
665 }
666
667 sub qtMakeCommand($)
668 {
669     my ($qmakebin) = @_;
670     chomp(my $mkspec = `$qmakebin -query QMAKE_MKSPECS`);
671     $mkspec .= "/default";
672
673     my $compiler = "";
674     open SPEC, "<$mkspec/qmake.conf" or return "make";
675     while (<SPEC>) {
676         if ($_ =~ /QMAKE_CC\s*=\s*([^\s]+)/) {
677             $compiler = $1;
678         }
679     }
680     close SPEC;
681
682     #print "default spec: " . $mkspec . "\n";
683     #print "compiler found: " . $compiler . "\n";
684
685     if ($compiler eq "cl") {
686         return "nmake";
687     }
688
689     return "make";
690 }
691
692 sub buildQMakeProject(@)
693 {
694     my @buildArgs = @_;
695     my $clean = 0;
696
697     push @buildArgs, "-r";
698
699     my $qmakebin = "qmake"; # Allow override of the qmake binary from $PATH
700     for my $i (0 .. $#ARGV) {
701         my $opt = $ARGV[$i];
702         if ($opt =~ /^--qmake=(.*)/i ) {
703             $qmakebin = $1;
704         } elsif ($opt =~ /^--qmakearg=(.*)/i ) {
705             push @buildArgs, $1;
706         } elsif ($opt eq "--clean") {
707             $clean = 1; 
708         }
709     }
710
711     my $make = qtMakeCommand($qmakebin);
712     my $config = configuration();
713     my $prefix = $ENV{"WebKitInstallationPrefix"};
714
715     push @buildArgs, "OUTPUT_DIR=" . baseProductDir() . "/$config";
716     push @buildArgs, sourceDir() . "/WebKit.pro";
717     if ($config =~ m/debug/i) {
718         push @buildArgs, "CONFIG-=release";
719         push @buildArgs, "CONFIG+=debug";
720     } else {
721         push @buildArgs, "CONFIG+=release";
722         push @buildArgs, "CONFIG-=debug";
723     }
724
725     my $dir = baseProductDir();
726     if (! -d $dir) {
727         mkdir $dir or die "Failed to create product directory " . $dir;
728     }
729     $dir = $dir . "/$config";
730     if (! -d $dir) {
731         mkdir $dir or die "Failed to create build directory " . $dir;
732     }
733
734     chdir $dir or die "Failed to cd into " . $dir . "\n";
735
736     print "Calling '$qmakebin @buildArgs' in " . $dir . " ...\n\n";
737     print "Installation directory: $prefix\n" if(defined($prefix));
738
739     my $result = system $qmakebin, @buildArgs;
740     if ($result ne 0) {
741        die "Failed to setup build environment using $qmakebin!\n";
742     }
743
744     if ($clean) {
745       system "$make clean";
746     }
747
748     # There is now a --clean option for build-webkit, but it doesn't build
749     # after cleaning, as WEBKIT_FULLBUILD does. For now, have WEBKIT_FULLBUILD
750     # continue to behave after before.
751     if (!$clean || defined($ENV{"WEBKIT_FULLBUILD"})) {
752         $result = system "$make";
753     }
754     chdir ".." or die;
755     return $result;
756 }
757
758 sub buildQMakeQtProject($)
759 {
760     my ($project) = @_;
761
762     my @buildArgs = ("CONFIG+=qt-port");
763     return buildQMakeProject(@buildArgs);
764 }
765
766 sub buildQMakeGtkProject($)
767 {
768     my ($project) = @_;
769
770     if ($project ne "WebKit") {
771         die "The Gtk portbuilds JavaScriptCore/WebCore/WebKitQt in one shot! Only call it for 'WebKit'.\n";
772     }
773
774     my @buildArgs = ("CONFIG+=gtk-port");
775     push @buildArgs, "CONFIG-=qt";
776
777     return buildQMakeProject(@buildArgs);
778 }
779
780 sub setPathForRunningWebKitApp
781 {
782     my ($env) = @_;
783
784     return unless isCygwin();
785
786     $env->{PATH} = join(':', productDir(), dirname(installedSafariPath()), $env->{PATH} || "");
787 }
788
789 sub exitStatus($)
790 {
791     my ($returnvalue) = @_;
792     if ($^O eq "MSWin32") {
793         return $returnvalue >> 8;
794     }
795     return WEXITSTATUS($returnvalue);
796 }
797
798 sub runSafari
799 {
800     my ($debugger) = @_;
801
802     if (isOSX()) {
803         return system "$FindBin::Bin/gdb-safari", @ARGV if $debugger;
804
805         my $productDir = productDir();
806         print "Starting Safari with DYLD_FRAMEWORK_PATH set to point to built WebKit in $productDir.\n";
807         $ENV{DYLD_FRAMEWORK_PATH} = $productDir;
808         $ENV{WEBKIT_UNSET_DYLD_FRAMEWORK_PATH} = "YES";
809         return system safariPath(), @ARGV;
810     }
811
812     if (isCygwin()) {
813         my $script = "run-webkit-nightly.cmd";
814         my $result = system "cp", "$FindBin::Bin/$script", productDir();
815         return $result if $result;
816
817         my $cwd = getcwd();
818         chdir productDir();
819
820         my $debuggerFlag = $debugger ? "/debugger" : "";
821         $result = system "cmd", "/c", "call $script $debuggerFlag";
822         chdir $cwd;
823         return $result;
824     }
825
826     return 1;
827 }
828
829 1;