sbsv1_os/e32toolp/test/cw_ide_test.pl
changeset 0 83f4b4db085c
child 1 d4b442d23379
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/sbsv1_os/e32toolp/test/cw_ide_test.pl	Tue Feb 02 01:39:43 2010 +0200
@@ -0,0 +1,418 @@
+#!perl
+# Copyright (c) 2004-2009 Nokia Corporation and/or its subsidiary(-ies).
+# All rights reserved.
+# This component and the accompanying materials are made available
+# under the terms of "Eclipse Public License v1.0"
+# which accompanies this distribution, and is available
+# at the URL "http://www.eclipse.org/legal/epl-v10.html".
+#
+# Initial Contributors:
+# Nokia Corporation - initial contribution.
+#
+# Contributors:
+#
+# Description:
+# Script to build specified MMP files with both command line and IDE, then
+# use EVALID to compare the results.
+# Inspired by "buildall.pl", written by Cuong Phan
+# 
+#
+
+use strict;
+use File::Basename;		# for fileparse()
+use File::Path;			# for mkpath
+use Cwd;				# for cwd
+use OLE;
+use Getopt::Long;
+
+sub Usage ($) 
+	{
+	my ($message) = @_;
+	print <<ENDHERESTRING;
+$message
+
+Usage : perl cw_ide_test.pl [-v] -f mmplist platform1 [platform2 ...]
+
+Builds specified MMP files with both the command line and the CodeWarrior IDE,
+storing the build products in zip files and comparing them with EVALID.
+The output can be summarised using scanlog.pl.
+
+All of the specified MMP files are build for all of the specified platforms.
+If -v is specified, the detailed build commands are included in the output.
+
+ENDHERESTRING
+
+	exit 1;
+	}
+
+my %Options=();
+GetOptions(\%Options, "v", "f=s");
+
+&Usage("No platforms specified") if (@ARGV < 1);
+&Usage("Must specify list of mmp files using -f") if (!defined($Options{"f"}));
+
+my @mmplist=();
+my $specifiedCWD;
+open FILELIST, "<$Options{f}" or &Usage("Cannot open $Options{f}");
+while (<FILELIST>)
+	{
+	$specifiedCWD = "";
+		
+	if (/#.*cwd:/i)
+		{
+		$specifiedCWD = $_;
+		$specifiedCWD =~ s/^.*cwd:/cwd:/i;
+		$specifiedCWD =~ s/\).*$//;
+		$specifiedCWD =~ s/\s*//g;
+		$specifiedCWD =~ s/\//\\/g;
+		$specifiedCWD .="?";
+		}
+		
+	s/#.*$//;		# remove comments
+	s/\s*$//;		# remove trailing ws
+	s/^\s*//;		# remove leading ws
+	s/\//\\/g;		# convert / to \
+	next if ($_ eq "");
+	push @mmplist, $specifiedCWD.$_;
+	}
+close FILELIST;
+
+&Usage("No MMP files?") if (@mmplist == 0);
+
+# create an instance of CodeWarrior
+my $CW = CreateObject OLE  "CodeWarrior.CodeWarriorApp";
+if (!defined($CW))
+	{
+	print "Failed to start CodeWarrior\n";
+	exit(1);
+	}
+
+# turn on autoflush, to get stdout in the right place...
+# These runes come from perlfaq5
+
+my $old_fh = select(STDOUT);
+$| = 1;
+select($old_fh);
+
+foreach my $mmpfile (@mmplist)
+	{
+	$specifiedCWD = "";
+
+	if ($mmpfile =~ /^cwd:/)
+		{
+		$specifiedCWD = $mmpfile;
+		$specifiedCWD =~ s/^cwd://;
+		$specifiedCWD =~ s/\?.*$//;
+		$mmpfile =~ s/^cwd:.*\?//;
+		}
+
+	if (!-f $mmpfile)
+		{
+		print "MISSING: $mmpfile\n";
+		next;
+		}
+	
+	foreach my $platform (@ARGV)
+		{
+		$platform = uc $platform;
+		my ($mmpname, $mmpdir, $mmpext) = fileparse($mmpfile,'\..*');
+		my $phasename = $mmpname."_".$platform;
+		
+		my $origdir = cwd;
+
+		if ($specifiedCWD)
+			{
+			print ("chdir $specifiedCWD\n");			
+			chdir ($specifiedCWD);
+
+			# Workaround for Base components, where GENEXEC.MKE needs to be executed to export the required headers for a build
+			do_system ("bldmake bldfiles");
+			do_system ("abld makefile $platform");
+			}
+		else
+			{
+			print ("chdir $mmpdir\n");
+			chdir ($mmpdir);
+			}
+
+		my $time = localtime;
+		print "===-------------------------------------------------\n";
+		print "=== $phasename\n";
+		print "===-------------------------------------------------\n";
+		print "=== $phasename started $time\n";
+
+		if ($specifiedCWD)
+			{
+			$mmpdir = "\\".$mmpdir;
+			}
+		else
+			{
+			$mmpdir = "";
+			}
+
+		&do_one_mmp_file($phasename, $mmpname, $platform, $mmpdir);
+
+		$time = localtime;
+		print "=== $phasename finished $time\n";
+
+		chdir($origdir);
+		print ("chdir $origdir\n");
+		}
+	}
+
+$CW->Quit(0);
+exit(0);
+
+sub do_system($)
+	{
+	my ($cmd) = @_;
+	print "    $cmd\n";
+	return system($cmd);
+	}
+
+sub zip_and_check($$$)
+	{
+	my ($zipname, $releaseref, $complain) = @_;
+	
+	unlink($zipname) if (-f $zipname);
+	
+	my @ziplist;
+	foreach (sort keys %$releaseref)
+		{
+		if (-f $_)
+			{
+			push @ziplist,$_;	# add to zip archive
+			}
+		else
+			{
+			print "MISSING: $_\n" if ($complain);
+			}
+		}
+	
+	if (scalar @ziplist ==0 && $complain)
+		{
+		print "Can't create empty archive $zipname\n";
+		return;
+		}
+	
+	# Make the non-empty archive
+	
+	open ZIP, "| zip -q $zipname -@";
+	print ZIP
+	 join("\n",@ziplist,"");
+	close ZIP;
+	print "Created $zipname\n";
+	}
+	
+sub do_one_mmp_file($$$)
+	{
+	my ($phasename, $mmpname, $platform, $mmpdir) = @_;
+
+	print "=== $phasename == $mmpname.mmp\n";
+
+	# use MAKMAKE to generate the makefile
+	# make CLEAN to remove any existing build results
+	# make ALL to build everything
+	# make WHAT to get the releaseables, as per abld.pl
+	# check the releaseables and zip up the ones which do exist
+	# make CLEAN again to get ready for the IDE build...
+		
+	my $makefile = "$mmpname.$platform";
+	my %allreleaseables=();		# complete list, for putting back afterwards
+	my %releaseables=();		# just things we expect the IDE to build
+	my %uncheckedreleaseables=();
+	my $makecmd = "make -s";
+	$makecmd = "make" if ($Options{"v"});
+	
+	unlink $makefile if (-f $makefile);
+	&do_system("perl -S makmake.pl $mmpdir$mmpname $platform");
+	return if (!-f $makefile);
+	
+	open PIPE,"make -s -r -f $makefile WHAT |";
+	while (<PIPE>) 
+		{
+		next if (/Nothing to be done for \S+\.$/o);
+#		releasables split on whitespace - quotes possible -stripped out
+		while (/("([^"\t\n\r\f]+)"|([^ "\t\n\r\f]+))/go) 
+			{
+			my $file = ($2 ? $2 : $3);
+			$allreleaseables{$file}=1;
+			next if ($file =~ /epoc32\\localisation\\/i);
+			next if ($file =~ /epoc32\\data/i && $platform =~ /winscw/i);
+			$releaseables{$file}=1;
+			}
+		}
+	close PIPE;
+	&zip_and_check("$mmpname.orig.$platform.zip", \%allreleaseables, 0);
+	
+	&do_system("$makecmd -r -f $makefile CLEAN");
+	&do_system("$makecmd -r -f $makefile ALL");
+	&zip_and_check("$mmpname.cmd.$platform.zip", \%releaseables, 1);
+
+	&do_system("$makecmd -r -f $makefile CLEAN");
+	
+	print "=== $phasename == $mmpname.mcp\n";
+
+	# Remove the remnants of previous projects
+	# use MAKMAKE to generate the importable .xml
+	# import the xml to create the .mcp
+	# build the relevant targets
+	# extract the contents of the "Errors & Warnings" window
+	# check against the commandline list of releasables, zip up the ones which exist
+	
+	my $currentdir = cwd;
+	$currentdir =~ s/\//\\/g;
+	my $xmlfile = "$currentdir\\$mmpname.xml";
+	my $mcpfile = "$currentdir\\$mmpname.mcp";
+	my $mcpdata = "$currentdir\\${mmpname}_Data";
+	
+	&do_system("rmdir /s/q $mcpdata") if (-d $mcpdata);
+	unlink $mcpfile if (-f $mcpfile);
+	unlink $xmlfile if (-f $xmlfile);
+
+	&do_system("perl -S makmake.pl $mmpdir$mmpname CW_IDE:$platform");
+	if (-f $xmlfile)
+		{
+		&fixup_XML($xmlfile) if ($Options{"v"});
+		my $project = $CW->ImportProject($xmlfile, $mcpfile, 'true');
+		if (defined($project))
+			{
+			my $success = &BuildTargets($project->Targets,$platform);
+			$project->Close();
+			return if (!$success);
+			&zip_and_check("$mmpname.ide.$platform.zip", \%releaseables, 1);
+			}
+		else
+			{
+			print "ERROR: failed to import $xmlfile\n";
+			return;
+			}
+		}
+	else
+		{
+		print "ERROR: failed to create $xmlfile\n";
+		return;
+		}
+
+	print "=== $phasename == $mmpname.evalid\n";
+
+	# remove & recreate a clean temporary directory for unzipping
+	# unzip the saved results of the cmd and ide builds
+	# use EVALID to compare the releaseables
+		
+	my $evaliddir = "c:\\temp\\evalid";
+	&do_system("rmdir /s/q $evaliddir") if (-d $evaliddir);
+	mkpath([$evaliddir]);
+	
+	if (   &do_system("unzip -q $mmpname.cmd.$platform.zip -d $evaliddir\\cmd")==0
+		&& &do_system("unzip -q $mmpname.ide.$platform.zip -d $evaliddir\\ide")==0)
+		{
+		open EVALID,"perl -S evalid.pl $evaliddir\\ide $evaliddir\\cmd -c |";
+		while (<EVALID>)
+			{
+			print $_ if (/^(PROBLEM|Failed)/);
+			print $_ if (/^OK/ && $Options{"v"});
+			if (/^FAILED/)
+				{
+				if (/\.map\t/i)
+					{
+					print "WARNING(S): $_";
+					}
+				else
+					{
+					print "FATAL ERROR(S): $_";
+					}
+				}
+			}
+		close EVALID;
+		}
+	else
+		{
+		print "FATAL ERROR(S): problems unpacking zip files\n";
+		}
+	&do_system("rmdir /s/q $evaliddir") if (-d $evaliddir);
+	
+	# Restore original files, if any
+	if (-e "$mmpname.orig.$platform.zip")
+		{
+		&do_system("unzip -q -o $mmpname.orig.$platform.zip -d \\");
+		}
+	}
+
+sub fixup_XML($)
+	{
+	my ($xmlfile) = @_;
+	open XML,"<$xmlfile" or return;
+	my @lines = <XML>;
+	close XML;
+	
+	foreach (@lines)
+		{
+		# Insist that build commands are logged to the output window, irrespective of CW version
+		s-<SETTING><NAME>LogMessages</NAME><VALUE>false</VALUE></SETTING>-<SETTING><NAME>LogMessages</NAME><VALUE>true</VALUE></SETTING>-;
+		s-<SETTING><NAME>ShowCommandLine</NAME><VALUE>false</VALUE></SETTING>-<SETTING><NAME>ShowCommandLine</NAME><VALUE>true</VALUE></SETTING>-;
+
+		# Remove generation of Browse info by Language Parser (temporary workaround for crashes in automated IDE builds)
+		s-<SETTING><NAME>BrowserGenerator</NAME><VALUE>2</VALUE></SETTING>-<SETTING><NAME>BrowserGenerator</NAME><VALUE>0</VALUE></SETTING>-;		
+		}
+		
+	open XML,">$xmlfile" or return;
+	print XML @lines;
+	close XML;
+	}
+	
+sub BuildTargets($$)
+	{
+	my ($targets,$platform) = @_;
+
+	for (my $item=0; $item<$targets->Count; $item++ ) 
+		{
+		my $target = $targets->Item($item);
+	    my $targetName = $target->name;
+	    # Skip platforms we aren't interested in...
+	    next if ($targetName !~ /$platform /i);
+
+		print "Building $targetName...\n";
+		     
+	    $target->RemoveObjectCode( 'true' );
+
+		my $buildMessages = $target->BuildAndWaitToComplete();
+		if (!defined($buildMessages))
+			{
+			printf "FATAL ERROR(S): build aborted? (%s)\n", $target->LastError();
+			return 0;
+			}
+			
+		my $messageList = $buildMessages->Informations;
+		&printMessages("",$messageList) if defined($messageList);
+		
+		my $warningCount = $buildMessages->WarningCount;
+		my $errorCount = $buildMessages->ErrorCount;    
+		print "Completed $targetName with $errorCount errors and $warningCount warnings\n";
+
+		if ($errorCount > 0)
+			{
+			$messageList = $buildMessages->Errors;
+			&printMessages("FATAL ERROR(S): ", $messageList);
+			}
+		if ($warningCount > 0)
+			{
+			$messageList = $buildMessages->Warnings;
+			&printMessages("WARNING: ", $messageList);
+			}
+		} 
+	return 1;
+	}
+
+sub	printMessages ($$)
+	{
+    my ($prefix,$messageList) = @_;
+
+	# traverse through the list of messages
+	for (my $item = 0; $item < ($messageList->Count); $item++)
+		{
+        my $message = $messageList->Item($item);
+		print $prefix,$message->MessageText,"\n";
+		}
+	}
+