deprecated/buildtools/commonbldutils/sbsv2htmlscanlog/sbsv2htmlscanlog.pl
changeset 655 3f65fd25dfd4
equal deleted inserted replaced
649:02d78c9f018e 655:3f65fd25dfd4
       
     1 # Copyright (c) 2003-2009 Nokia Corporation and/or its subsidiary(-ies).
       
     2 # All rights reserved.
       
     3 # This component and the accompanying materials are made available
       
     4 # under the terms of "Eclipse Public License v1.0"
       
     5 # which accompanies this distribution, and is available
       
     6 # at the URL "http://www.eclipse.org/legal/epl-v10.html".
       
     7 #
       
     8 # Initial Contributors:
       
     9 # Nokia Corporation - initial contribution.
       
    10 #
       
    11 # Contributors:
       
    12 #
       
    13 # Description:
       
    14 #
       
    15 
       
    16 # summarise an automated build log
       
    17 use strict;
       
    18 use Getopt::Long;
       
    19 use HTML::Entities;
       
    20 use Carp;
       
    21 use File::stat;
       
    22 use FindBin;		# for FindBin::Bin
       
    23 
       
    24 # Add the directory contain this perl script into the path to find modules
       
    25 use lib $FindBin::Bin;
       
    26 use sbsv2scanlog;
       
    27 
       
    28 # For Date calculations
       
    29 use lib "$FindBin::Bin/../lib"; # For running in source
       
    30 use lib "$FindBin::Bin/build/lib"; # For running in epoc32\tools
       
    31 
       
    32 use XML::Parser;
       
    33 
       
    34 # Variables
       
    35 my $line;
       
    36 my $iSlurp;
       
    37 my %Components;
       
    38 my %Commands;
       
    39 my $component;
       
    40 my $command;
       
    41 my %errors;
       
    42 my %warnings;
       
    43 my %remarks;
       
    44 my %migrationNotes;
       
    45 my %AdvisoryNotes;
       
    46 my %CmdErrors;
       
    47 my %CmdWarnings;
       
    48 my %CmdRemarks;
       
    49 my %CmdMigrationNotes;
       
    50 my %CmdAdvisoryNotes;
       
    51 my %missing;
       
    52 my %not_built;
       
    53 my $starttime;
       
    54 my $duration;
       
    55 my $currentfiletime;
       
    56 my $warningcount;
       
    57 my $errorcount;
       
    58 my $remarkcount;
       
    59 my $migrationNoteCount;
       
    60 my $AdvisoryNoteCount;
       
    61 my ($iStatus, $iName);
       
    62 my $warningmigrated;
       
    63 my %htmlColours=(
       
    64 "errors" =>"#ff0000",
       
    65 "warnings" =>"#fff000",
       
    66 "remarks" =>"#ffccff",
       
    67 "migrationNotes" =>"#ffcc99",
       
    68 "AdvisoryNotes" => "#ffa500"
       
    69 );
       
    70 my $MigrateNextExitCode = 0;
       
    71 my $inRecipe = 0;
       
    72 my $RetryInProgress = 0;
       
    73 
       
    74 # Package variables - these can also be accessed the from package "SubHandlers"
       
    75 use vars qw($component $command %Components %Commands);
       
    76 our $iLog;
       
    77 
       
    78 my $Dsec;
       
    79 
       
    80 # Main section
       
    81 
       
    82 my ($iOutput, $iTitle, $iVerbose, @iLogs) =&ProcessCommandLine();
       
    83 
       
    84 # Open Output file
       
    85   open (HTML, ">$iOutput") or die "Couldn't open $iOutput for writing: $!\n";
       
    86 
       
    87 
       
    88 # Parse each log File
       
    89 foreach $iLog (@iLogs) # parses through all logs 
       
    90 {
       
    91     # Check the log file exists
       
    92     if (-e $iLog)
       
    93     {
       
    94         # Process the logs
       
    95         &ProcessLog();
       
    96     } else {
       
    97       print "WARNING: $iLog does not exist\n";
       
    98     }
       
    99 
       
   100 
       
   101 }
       
   102 
       
   103 &PrintResults($iTitle);
       
   104 
       
   105 # Print HTML Footer
       
   106 &PrintHTMLFooter();
       
   107 
       
   108 
       
   109 # ProcessLog
       
   110 #
       
   111 # Inputs
       
   112 # $iLog - Logfile name
       
   113 #
       
   114 # Outputs
       
   115 #
       
   116 # Description
       
   117 # This function processes the commandline
       
   118 sub ProcessLog()
       
   119 {
       
   120   #Clear current file time as starting processing a new log
       
   121   $currentfiletime = 0;
       
   122   
       
   123   print "Processing: $iLog\n";
       
   124 
       
   125   my $iParser = XML::Parser->new(Style => 'Subs', Pkg => 'MySubs' , ErrorContext => 2,
       
   126                                  Handlers => {Char => \&char_handler});
       
   127 
       
   128   # Supply the XML Parser the data source
       
   129   eval {
       
   130     $iParser->parsefile($iLog);
       
   131   };
       
   132  
       
   133   #Set current component and command to special values to record log processing errors/warnings/etc
       
   134   $component = 'sbsv2scanlog';    
       
   135   $command = 'sbsv2scanlog';
       
   136  
       
   137   #Check for parse errors
       
   138   if ($@)
       
   139   {
       
   140     #Generate error in log as the file time stamps are duff
       
   141     &do_error($iLog, "No_linenumer", "XML Parse error:$@");
       
   142     $Components{$component} = '0';
       
   143     $Commands{$command} ='0';
       
   144   }
       
   145   
       
   146   # Calculate the Total Duration
       
   147   # $currentfiletime is set from the info tags at the end of the log.
       
   148   $duration += $currentfiletime;  
       
   149 
       
   150   #Clear current component and command
       
   151   $component = '';    
       
   152   $command = ''; 
       
   153 }
       
   154 
       
   155 
       
   156 # PrintResults
       
   157 #
       
   158 # Inputs
       
   159 # $iTitle (Title for Log file)
       
   160 #
       
   161 # Outputs
       
   162 #
       
   163 # Description
       
   164 # This function prints all the data as HTML
       
   165 sub PrintResults
       
   166 {
       
   167   my ($iTitle) = @_;
       
   168   
       
   169   my $title;
       
   170 
       
   171   # Print Heading of Log File
       
   172   my $heading ="Overall";
       
   173   print HTML qq{<h1>$iTitle</h1>\n};
       
   174   print HTML qq{<h2>$heading</h2>\n};
       
   175 
       
   176   # Calculate the total number of remarks messages
       
   177 	$remarkcount = 0;
       
   178 	foreach $component (sort {lc $a cmp lc $b} keys %remarks)
       
   179 		{
       
   180 		$remarkcount += scalar(@{$remarks{$component}});
       
   181 		}
       
   182   # Calculate the Total number of errors
       
   183   	$errorcount = 0;
       
   184 	foreach $component (sort {lc $a cmp lc $b} keys %errors)
       
   185 		{
       
   186 		$errorcount += scalar(@{$errors{$component}});
       
   187 		}
       
   188   # Calculate the total number of warnings
       
   189 	$warningcount = 0;
       
   190 	foreach $component (sort {lc $a cmp lc $b} keys %warnings)
       
   191 		{
       
   192 		$warningcount += scalar(@{$warnings{$component}});
       
   193 		}
       
   194   
       
   195   # Calculate the total number of migration notes
       
   196   $migrationNoteCount=0;
       
   197   foreach $component (sort {lc $a cmp lc $b} keys %migrationNotes)
       
   198     {
       
   199     $migrationNoteCount += scalar(@{$migrationNotes{$component}});
       
   200   }
       
   201   
       
   202   # Calculate the total number of Advisory notes
       
   203   $AdvisoryNoteCount=0;
       
   204   foreach $component (sort {lc $a cmp lc $b} keys %AdvisoryNotes)
       
   205   {
       
   206     $AdvisoryNoteCount += scalar(@{$AdvisoryNotes{$component}});
       
   207   }
       
   208   
       
   209   # Start the Table
       
   210   &StartHTMLTable();
       
   211 
       
   212   # Print the Totals
       
   213   &HTMLTableRow($heading,"Total", $duration, $errorcount, $warningcount, $AdvisoryNoteCount, $remarkcount, $migrationNoteCount);
       
   214 
       
   215   # End the Table
       
   216   print HTML qq{</table>\n};
       
   217 
       
   218 
       
   219 
       
   220   # By Component
       
   221   print HTML qq{<h2>By Component</h2>\n};
       
   222 
       
   223   # Start the Table
       
   224   $title="Component";
       
   225   &StartHTMLTable($title);
       
   226 
       
   227   # Print the by Component Data
       
   228     foreach $component (sort {lc $a cmp lc $b} keys %Components)
       
   229     {
       
   230       # Calculate the number errors and warnings
       
   231       my $totalerrors;
       
   232       my $totalwarnings;
       
   233       my $totalremarks;
       
   234       my $totalMigrationNotes;
       
   235       my $totalAdvisoryNotes;
       
   236       if (!defined $remarks{$component})
       
   237       {
       
   238         # No Remarks were recorded, set total to zero
       
   239         $totalremarks = 0;
       
   240       } else {
       
   241         $totalremarks = scalar(@{$remarks{$component}});
       
   242       }
       
   243       if (!defined $errors{$component})
       
   244       {
       
   245         # No errors were recorded, set total to zero
       
   246         $totalerrors = 0;
       
   247       } else {
       
   248         $totalerrors = scalar(@{$errors{$component}});
       
   249       }
       
   250       if (!defined $warnings{$component})
       
   251       {
       
   252         # No Warnings were recorded, set total to zero
       
   253         $totalwarnings = 0;
       
   254       } else {
       
   255         $totalwarnings = scalar(@{$warnings{$component}});
       
   256       }
       
   257       
       
   258       if (!defined $migrationNotes{$component})
       
   259         {
       
   260         # No MigrationNotes were recorded, set total to zero
       
   261         $totalMigrationNotes=0;
       
   262         }
       
   263       else
       
   264         {
       
   265         $totalMigrationNotes = scalar(@{$migrationNotes{$component}});
       
   266         }
       
   267 
       
   268       if (!defined $AdvisoryNotes{$component})
       
   269         {
       
   270         # No AdvisoryNotes were recorded, set total to zero
       
   271         $totalAdvisoryNotes=0;
       
   272         }
       
   273       else
       
   274         {
       
   275         $totalAdvisoryNotes = scalar(@{$AdvisoryNotes{$component}});
       
   276         }
       
   277 	
       
   278 
       
   279 
       
   280       # Print the Table Row
       
   281       &HTMLTableRow($title,$component, $Components{$component}, $totalerrors, $totalwarnings, $totalAdvisoryNotes,$totalremarks, $totalMigrationNotes);
       
   282 
       
   283     }
       
   284 
       
   285   # End the Table
       
   286   print HTML qq{</table>\n};
       
   287 
       
   288   # By Command
       
   289   print HTML qq{<h2>By Command</h2>\n};
       
   290 
       
   291   # Start the Table
       
   292   $title="Command";
       
   293   &StartHTMLTable($title);
       
   294 
       
   295   # Print the by Command Data
       
   296     foreach $command (sort {lc $a cmp lc $b} keys %Commands)
       
   297 	{
       
   298       # Calculate the number errors, warnings and remarks
       
   299       my $totalerrors;
       
   300       my $totalwarnings;
       
   301       my $totalremarks;
       
   302       my $totalMigrationNotes;
       
   303       my $totalAdvisoryNotes;
       
   304       if (!defined $CmdRemarks{$command})
       
   305       {
       
   306         # No Remarks were recorded, set total to zero
       
   307         $totalremarks = 0;
       
   308       } else {
       
   309         $totalremarks = scalar(@{$CmdRemarks{$command}});
       
   310       }
       
   311       if (!defined $CmdErrors{$command})
       
   312       {
       
   313         # No errors were recorded, set total to zero
       
   314         $totalerrors = 0;
       
   315       } else {
       
   316         $totalerrors = scalar(@{$CmdErrors{$command}});
       
   317       }
       
   318       if (!defined $CmdWarnings{$command})
       
   319       {
       
   320         # No Warnings were recorded, set total to zero
       
   321         $totalwarnings = 0;
       
   322       } else {
       
   323         $totalwarnings = scalar(@{$CmdWarnings{$command}});
       
   324       }
       
   325       
       
   326       if (!defined $CmdMigrationNotes{$command})
       
   327         {
       
   328         # No MigrationNotes were recorded, set total to zero
       
   329         $totalMigrationNotes=0;
       
   330         }
       
   331       else
       
   332         {
       
   333         $totalMigrationNotes = scalar(@{$CmdMigrationNotes{$command}});
       
   334         }
       
   335 
       
   336       if (!defined $CmdAdvisoryNotes{$command})
       
   337         {
       
   338         # No AdvisoryNotes were recorded, set total to zero
       
   339         $totalAdvisoryNotes=0;
       
   340         }
       
   341       else
       
   342         {
       
   343         $totalAdvisoryNotes = scalar(@{$CmdAdvisoryNotes{$command}});
       
   344         }
       
   345 
       
   346       # Print the Table Row
       
   347 	  &HTMLTableRow($title,$command, $Commands{$command}, $totalerrors, $totalwarnings, $totalAdvisoryNotes, $totalremarks, $totalMigrationNotes);
       
   348 	}
       
   349 
       
   350 
       
   351   # End the Table
       
   352   print HTML qq{</table>\n};
       
   353 
       
   354   # Print Things Missing
       
   355   if (scalar %missing)
       
   356 	{
       
   357 	my $count = scalar keys %missing;
       
   358 	print HTML qq{<h2>Things Missing ($count)</h2>\n};
       
   359 	print HTML "Don't know how to make...\n";
       
   360 	foreach my $file (sort {lc $a cmp lc $b} keys %missing)
       
   361 		{
       
   362 		printf HTML "%d\t%s</BR>\n", $missing{$file}, $file;
       
   363 		}
       
   364 	}
       
   365   print HTML qq{</BR>\n};
       
   366 
       
   367   # Print Things Not Built
       
   368   if (scalar %not_built)
       
   369 	{
       
   370 	my $count = scalar keys %not_built;
       
   371 	print HTML qq{<h2>Things Not Built ($count)</h2>\n};
       
   372 	foreach my $file (sort {lc $a cmp lc $b} keys %not_built)
       
   373 		{
       
   374 		print HTML "MISSING: $file ($not_built{$file})</BR>\n";
       
   375 		}
       
   376 	}
       
   377 
       
   378 
       
   379   # Print the Actual Errors by Component
       
   380   if ($iVerbose > 0)
       
   381   {
       
   382     # Only Print the header if there are some errors
       
   383     if (scalar(keys %errors))
       
   384     {
       
   385       print HTML qq{<h2><a name="errorsByOverall_Total">Error Details by Component</a></h2>\n};
       
   386 	  foreach $component (sort {lc $a cmp lc $b} keys %errors)
       
   387 		{
       
   388 			my ($HTML) = $component;
       
   389 			$HTML =~ s/\s+$//;
       
   390 			encode_entities($HTML);
       
   391 			my $count = scalar @{$errors{$component}};
       
   392 			print HTML qq{<h3><a name="errorsByComponent_$HTML">$HTML</a> ($count)</h3>\n};
       
   393 			foreach $line (@{$errors{$component}})
       
   394 				{
       
   395 				encode_entities($line);
       
   396 				print HTML $line.qq{</BR>};
       
   397 				}
       
   398 			print HTML qq{</BR>\n};
       
   399 		}
       
   400     }
       
   401   }
       
   402 
       
   403   # Print the Actual Warning by Component
       
   404   if ($iVerbose > 1)
       
   405   {
       
   406     # Only Print the header if there are some warnings
       
   407     if (scalar(keys %warnings))
       
   408     {
       
   409       print HTML qq{<h2><a name="warningsByOverall_Total">Warning Details by Component</a></h2>\n};
       
   410       foreach $component (sort {lc $a cmp lc $b} keys %warnings)
       
   411         {
       
   412           my ($HTML) = $component;
       
   413           $HTML =~ s/\s+$//;
       
   414           encode_entities($HTML);
       
   415 		  my $count = scalar @{$warnings{$component}};
       
   416           print HTML qq{<h3><a name="warningsByComponent_$HTML">$HTML</a> ($count)</h3>\n};
       
   417           foreach $line (@{$warnings{$component}})
       
   418             {
       
   419             encode_entities($line);
       
   420             print HTML $line.qq{</BR>};
       
   421             }
       
   422           print HTML qq{</BR>\n};
       
   423         }
       
   424     }
       
   425   }
       
   426 
       
   427   # Print the Actual Advisory Notes by Component
       
   428   if ($iVerbose > 1)
       
   429   {
       
   430     # Only Print the header if there are some warnings
       
   431     if (scalar(keys %AdvisoryNotes))
       
   432     {
       
   433       print HTML qq{<h2><a name="AdvisoryNotesByOverall_Total">Advisory Note Details by Component</a></h2>\n};
       
   434       foreach $component (sort {lc $a cmp lc $b} keys %AdvisoryNotes)
       
   435         {
       
   436           my ($HTML) = $component;
       
   437           $HTML =~ s/\s+$//;
       
   438           encode_entities($HTML);
       
   439 		     my $count = scalar @{$AdvisoryNotes{$component}};
       
   440           print HTML qq{<h3><a name="AdvisoryNotesByComponent_$HTML">$HTML</a> ($count)</h3>\n};
       
   441           foreach $line (@{$AdvisoryNotes{$component}})
       
   442             {
       
   443             encode_entities($line);
       
   444             print HTML $line.qq{</BR>};
       
   445             }
       
   446           print HTML qq{</BR>\n};
       
   447         }
       
   448     }
       
   449   }  
       
   450  
       
   451   # Print the Actual Remarks by Component
       
   452   if ($iVerbose > 1)
       
   453   {
       
   454     # Only Print the header if there are some errors
       
   455     if (scalar(keys %remarks))
       
   456     {
       
   457       print HTML qq{<h2><a name="remarksByOverall_Total">Remarks Details by Component</a></h2>\n};
       
   458 	  foreach $component (sort {lc $a cmp lc $b} keys %remarks)
       
   459 		{
       
   460 			my ($HTML) = $component;
       
   461 			$HTML =~ s/\s+$//;
       
   462 			encode_entities($HTML);
       
   463 			my $count = scalar @{$remarks{$component}};
       
   464 			print HTML qq{<h3><a name="remarksByComponent_$HTML">$HTML</a> ($count)</h3>\n};
       
   465 			foreach $line (@{$remarks{$component}})
       
   466 				{
       
   467 				encode_entities($line);
       
   468 				print HTML $line.qq{</BR>};
       
   469 				}
       
   470 			print HTML qq{</BR>\n};
       
   471 		}
       
   472     }
       
   473   }
       
   474 
       
   475    # Print the Actual Migration Notes by Component
       
   476 if ($iVerbose > 1)
       
   477   {
       
   478     # Only Print the header if there are some warnings
       
   479     if (scalar(keys %migrationNotes))
       
   480     {
       
   481       print HTML qq{<h2><a name="migrationNotesByOverall_Total">Migration Note Details by Component</a></h2>\n};
       
   482       foreach $component (sort {lc $a cmp lc $b} keys %migrationNotes)
       
   483         {
       
   484           my ($HTML) = $component;
       
   485           $HTML =~ s/\s+$//;
       
   486           encode_entities($HTML);
       
   487 		     my $count = scalar @{$migrationNotes{$component}};
       
   488           print HTML qq{<h3><a name="migrationNotesByComponent_$HTML">$HTML</a> ($count)</h3>\n};
       
   489           foreach $line (@{$migrationNotes{$component}})
       
   490             {
       
   491             encode_entities($line);
       
   492             print HTML $line.qq{</BR>};
       
   493             }
       
   494           print HTML qq{</BR>\n};
       
   495         }
       
   496     }
       
   497   }
       
   498   
       
   499   # Print the Actual Errors by Command
       
   500   if ($iVerbose > 0)
       
   501   {
       
   502     # Only Print the header if there are some errors
       
   503     if (scalar(keys %CmdErrors))
       
   504     {
       
   505       print HTML qq{<h2>Error Details by Command</h2>\n};
       
   506 	  foreach $command (sort {lc $a cmp lc $b} keys %CmdErrors)
       
   507 		{
       
   508 			my ($HTML) = $command;
       
   509 			$HTML =~ s/\s+$//;
       
   510 			encode_entities($HTML);
       
   511 			print HTML qq{<h3><a name="errorsByCommand_$HTML">$HTML</a></h3>\n};
       
   512 			foreach $line (@{$CmdErrors{$command}})
       
   513 				{
       
   514 				encode_entities($line);
       
   515 				print HTML $line.qq{</BR>};
       
   516 				}
       
   517 			print HTML qq{</BR>\n};
       
   518 		}
       
   519     }
       
   520   }
       
   521 
       
   522   # Print the Actual Warning by Command
       
   523   if ($iVerbose > 1)
       
   524   {
       
   525     # Only Print the header if there are some warnings
       
   526     if (scalar(keys %CmdWarnings))
       
   527     {
       
   528       print HTML qq{<h2>Warning Details by Command</h2>\n};
       
   529 	  foreach $command (sort {lc $a cmp lc $b} keys %CmdWarnings)
       
   530 		{
       
   531 			my ($HTML) = $command;
       
   532 			$HTML =~ s/\s+$//;
       
   533 			encode_entities($HTML);
       
   534 			print HTML qq{<h3><a name="warningsByCommand_$HTML">$HTML</a></h3>\n};
       
   535 			foreach $line (@{$CmdWarnings{$command}})
       
   536 				{
       
   537 				encode_entities($line);
       
   538 				print HTML $line.qq{</BR>};
       
   539 				}
       
   540 			print HTML qq{</BR>\n};
       
   541 		}
       
   542     }
       
   543   }
       
   544 
       
   545   # Print the Actual Advisory Notes by Command
       
   546   if ($iVerbose >1)
       
   547     {
       
   548     # Only Print the header if there are some errors
       
   549     if (scalar(keys %CmdAdvisoryNotes))
       
   550       {
       
   551       print HTML qq{<h2>Advisory Note Details by Command</h2>\n};
       
   552       
       
   553       foreach $command (sort {lc $a cmp lc $b} keys %CmdAdvisoryNotes)
       
   554         {
       
   555      	  my ($HTML) = $command;
       
   556         $HTML =~ s/\s+$//;
       
   557         encode_entities($HTML);
       
   558         print HTML qq{<h3><a name="AdvisoryNotesByCommand_$HTML">$HTML</a></h3>\n};
       
   559         foreach $line (@{$CmdAdvisoryNotes{$command}})
       
   560 				  {
       
   561 				  encode_entities($line);
       
   562 				  print HTML $line.qq{</BR>};
       
   563 				  }
       
   564         print HTML qq{</BR>\n}
       
   565         }
       
   566       }
       
   567     }
       
   568 
       
   569   # Print the Actual Remarks by Command
       
   570   if ($iVerbose > 1)
       
   571   {
       
   572     # Only Print the header if there are some errors
       
   573     if (scalar(keys %CmdRemarks))
       
   574     {
       
   575       print HTML qq{<h2>Remarks Details by Command</h2>\n};
       
   576 	  foreach $command (sort {lc $a cmp lc $b} keys %CmdRemarks)
       
   577 		{
       
   578 			my ($HTML) = $command;
       
   579 			$HTML =~ s/\s+$//;
       
   580 			encode_entities($HTML);
       
   581 			print HTML qq{<h3><a name="remarksByCommand_$HTML">$HTML</a></h3>\n};
       
   582 			foreach $line (@{$CmdRemarks{$command}})
       
   583 				{
       
   584 				encode_entities($line);
       
   585 				print HTML $line.qq{</BR>};
       
   586 				}
       
   587 			print HTML qq{</BR>\n};
       
   588 		}
       
   589     }
       
   590   }
       
   591 
       
   592   # Print the Actual Migration Notes by Command
       
   593   if ($iVerbose >1)
       
   594     {
       
   595     # Only Print the header if there are some errors
       
   596     if (scalar(keys %CmdMigrationNotes))
       
   597       {
       
   598       print HTML qq{<h2>Migration Note Details by Command</h2>\n};
       
   599       
       
   600       foreach $command (sort {lc $a cmp lc $b} keys %CmdMigrationNotes)
       
   601         {
       
   602      	  my ($HTML) = $command;
       
   603         $HTML =~ s/\s+$//;
       
   604         encode_entities($HTML);
       
   605         print HTML qq{<h3><a name="migrationNotesByCommand_$HTML">$HTML</a></h3>\n};
       
   606         foreach $line (@{$CmdMigrationNotes{$command}})
       
   607 				  {
       
   608 				  encode_entities($line);
       
   609 				  print HTML $line.qq{</BR>};
       
   610 				  }
       
   611         print HTML qq{</BR>\n}
       
   612         }
       
   613       }
       
   614     }
       
   615  
       
   616  
       
   617 }
       
   618 
       
   619 
       
   620 # StartHTMLTable
       
   621 #
       
   622 # Inputs
       
   623 # $iC1Title (Column 1 Title)
       
   624 #
       
   625 # Outputs
       
   626 #
       
   627 # Description
       
   628 # This function prints the start of the HTML Table
       
   629 sub StartHTMLTable
       
   630 {
       
   631   my ($iC1Title) = @_;
       
   632 
       
   633   if ($iC1Title eq '')
       
   634   {
       
   635     $iC1Title = "&nbsp;";
       
   636   } else {
       
   637     encode_entities($iC1Title);
       
   638   }
       
   639 
       
   640   # Start the Table
       
   641   print HTML qq{<table border="1" cellpadding="0" cellspacing="0" width="100%">\n};
       
   642 
       
   643   # Print the Header Row
       
   644   print HTML qq{<tr>\n};
       
   645   print HTML qq{\t<th width="50%">$iC1Title</th>\n};
       
   646   print HTML qq{\t<th width="15%">Time</th>\n};
       
   647   print HTML qq{\t<th width="8%">Errors</th>\n};
       
   648   print HTML qq{\t<th width="8%">Warnings</th>\n};
       
   649   print HTML qq{\t<th width="8%">Advisory Notes</th>\n};
       
   650   print HTML qq{\t<th width="8%">Remarks</th>\n};
       
   651   print HTML qq{\t<th width="8%">Migration Notes</th>\n};
       
   652 
       
   653   print HTML qq{</tr>\n};
       
   654 }
       
   655 
       
   656 # HTMLTableCell
       
   657 #
       
   658 # Inputs
       
   659 # $iType	(errors,warnings,remarks,migration_notes)
       
   660 # $iCount	(number of errors)
       
   661 # $iLink	(empty string or linktype)
       
   662 #
       
   663 # Outputs
       
   664 # Returns HTML table data element with appropriate link & background color
       
   665 #
       
   666 # Description
       
   667 # Constructs HTML table element - used by HTMLTableRow to handle the formatting
       
   668 # of the data cells, complete with colouring and links where appropriate.
       
   669 sub HTMLTableCell
       
   670 {
       
   671    my ($iType,$iCount,$iLink)= @_;
       
   672    my $td = qq{td width="8%" align="center"};	# implied by the TH elements already? 
       
   673    if ($iCount != 0)
       
   674       {
       
   675 	  $td = "$td BGCOLOR=$htmlColours{$iType}";
       
   676       }
       
   677    if ($iLink eq "" || $iCount == 0)
       
   678       {
       
   679       return qq{<$td>$iCount</td>};
       
   680       }
       
   681    $iLink = $iType."By".$iLink;
       
   682    return qq{<$td><a href="#$iLink">$iCount</a></td>};
       
   683 }
       
   684 
       
   685 # HTMLTableRow
       
   686 #
       
   687 # Inputs
       
   688 # $iTitle (Need to differentiate between command and component to provide correct anchors)
       
   689 # $iC1Data(Column 1 Data)
       
   690 # $iC2Data(Column 2 Data) (Time in seconds)
       
   691 # $iC3Data(Column 3 Data) (Number of errors)
       
   692 # $iC4Data(Column 4 Data) (Number of warnings)
       
   693 # $iC5Data(Column 5 Data) (Number of Advisory notes )
       
   694 # $iC6Data(Column 6 Data) (Number of remarks )
       
   695 # $iC7Data(Column 7 Data) (Number of migration notes )
       
   696 #
       
   697 # Outputs
       
   698 #
       
   699 # Description
       
   700 # This function prints a line of the HTML Table
       
   701 sub HTMLTableRow
       
   702 {
       
   703   my ($iTitle,$iC1Data, $iC2Data, $iC3Data, $iC4Data,$iC5Data, $iC6Data, $iC7Data) = @_;
       
   704 
       
   705   #print "$iC2Data\n";
       
   706 
       
   707   # Convert the seconds in hh:mm:ss format
       
   708   $iC2Data = &ConvertSeconds($iC2Data);
       
   709 
       
   710   # HTML encode the text
       
   711   encode_entities($iC1Data);
       
   712   encode_entities($iC2Data);
       
   713   encode_entities($iC3Data);
       
   714   encode_entities($iC4Data);
       
   715   encode_entities($iC5Data);
       
   716   encode_entities($iC6Data);
       
   717   encode_entities($iC7Data);
       
   718 
       
   719   my $linkname = "$iTitle"."_"."$iC1Data";
       
   720   
       
   721   # Print the Row, including summary in a script comment
       
   722   print HTML qq{<tr>\n};
       
   723   print HTML qq{<!--\t$linkname\t$iC2Data\t$iC3Data\t$iC4Data\t$iC5Data\t$iC6Data\t$iC7Data\t-->\n};
       
   724   print HTML qq{\t<td width="50%">$iC1Data</td>\n};
       
   725   print HTML qq{\t<td width="15%" align="center">$iC2Data</td>\n};
       
   726 
       
   727   print HTML "\t",&HTMLTableCell("errors",  $iC3Data,$linkname),"\n";
       
   728   print HTML "\t",&HTMLTableCell("warnings",$iC4Data,$linkname),"\n";
       
   729   print HTML "\t",&HTMLTableCell("AdvisoryNotes", $iC5Data,$linkname),"\n";
       
   730   print HTML "\t",&HTMLTableCell("remarks", $iC6Data,$linkname),"\n";
       
   731   print HTML "\t",&HTMLTableCell("migrationNotes", $iC7Data,$linkname),"\n";
       
   732 
       
   733 
       
   734   print HTML qq{</tr>\n};
       
   735 }
       
   736 
       
   737 # ConvertSeconds
       
   738 #
       
   739 # Inputs
       
   740 # $iSeconds
       
   741 #
       
   742 # Outputs
       
   743 # $iString (seconds in hh:mm:ss)
       
   744 #
       
   745 # Description
       
   746 # This function processes the commandline
       
   747 sub ConvertSeconds
       
   748 {
       
   749   my ($iSeconds) = @_;
       
   750   
       
   751   my ($iString);
       
   752   my ($ih) = int($iSeconds/3600);
       
   753   my ($im) = int(($iSeconds-($ih*3600))/60);
       
   754   my ($is) = $iSeconds-($ih*3600)-($im*60);
       
   755   # Print the correct format if the data is HiRes (has a decimal point in the string)
       
   756   if ($is =~ /\d+\.\d+/)
       
   757   {
       
   758     $iString = sprintf "%d:%02d:%06.3f", $ih, $im, $is;
       
   759   } else {
       
   760     $iString = sprintf "%d:%02d:%02d", $ih, $im, $is;
       
   761   }
       
   762   return $iString;
       
   763 }
       
   764 
       
   765 # ProcessCommandLine
       
   766 #
       
   767 # Inputs
       
   768 #
       
   769 # Outputs
       
   770 # $iOutput (Output filename)
       
   771 # $iVerbose (Verbose Level)
       
   772 # $iLogs (Log files to process)
       
   773 #
       
   774 # Description
       
   775 # This function processes the commandline
       
   776 
       
   777 sub ProcessCommandLine {
       
   778   my ($iHelp, @iLogs, $iOutput, $iTitle, $iVerbose);
       
   779   GetOptions('h' => \$iHelp, 'l=s' =>\@iLogs, 'o=s' => \$iOutput, 't=s' => \$iTitle, 'v+' => \$iVerbose);
       
   780 
       
   781   if (($iHelp) || (!defined @iLogs) || (!defined $iOutput))
       
   782   {
       
   783     Usage();
       
   784   } elsif (-e $iOutput) {
       
   785     die "$iOutput already exists";
       
   786   }
       
   787   
       
   788   foreach my $iLog (@iLogs)
       
   789   {
       
   790     warn "$iLog does not exist" if (! -e $iLog);
       
   791   }
       
   792 
       
   793   # Set default title
       
   794   if ($iTitle eq '')
       
   795   {
       
   796     $iTitle = "Log File Summary";
       
   797   }
       
   798 
       
   799   return($iOutput, $iTitle, $iVerbose, @iLogs);
       
   800 }
       
   801 
       
   802 # Usage
       
   803 #
       
   804 # Output Usage Information.
       
   805 #
       
   806 
       
   807 sub Usage {
       
   808   print <<USAGE_EOF;
       
   809 
       
   810     Usage: Scanlog.pl [options]
       
   811 
       
   812     options:
       
   813 
       
   814     -h  help
       
   815     -l  Log file to scan [Multiple allowed]
       
   816     -o  Output file
       
   817     -v  Increments Verbose level [Maximum Level = 2]
       
   818     -t  Title to add to the Summary    
       
   819 
       
   820 USAGE_EOF
       
   821 	exit 1;
       
   822 }
       
   823 
       
   824 # PrintHTMLHeader
       
   825 #
       
   826 # Inputs
       
   827 # $iTitle (Title for Log file)
       
   828 #
       
   829 # Outputs
       
   830 #
       
   831 # Description
       
   832 # This function print the HTML Header
       
   833 
       
   834 sub PrintHTMLHeader {
       
   835   my ($iTitle) = @_;
       
   836 
       
   837    print HTML <<HTML_EOF;
       
   838 <HTML>
       
   839 <HEAD>
       
   840 <TITLE>$iTitle</TITLE>
       
   841 </HEAD>
       
   842 <BODY BGCOLOR="FFFFFF">
       
   843 <FONT FACE="Courier New">
       
   844 HTML_EOF
       
   845 }
       
   846 
       
   847 # PrintHTMLFooter
       
   848 #
       
   849 # Inputs
       
   850 #
       
   851 # Outputs
       
   852 #
       
   853 # Description
       
   854 # This function print the HTML Footer
       
   855 
       
   856 sub PrintHTMLFooter {
       
   857    print HTML <<HTML_EOF;
       
   858 </FONT>
       
   859 </BODY>
       
   860 </HTML>
       
   861 HTML_EOF
       
   862 }
       
   863 
       
   864 sub do_remarks()
       
   865 {
       
   866 	my ($iLog, $iLineNumber, $line)= @_;
       
   867 	# Store remarks by Command
       
   868 	if (!defined $CmdRemarks{$command})
       
   869 		{
       
   870 		$CmdRemarks{$command} = ();
       
   871 		}
       
   872 	push @{$CmdRemarks{$command}}, "$iLog:$iLineNumber>$line";
       
   873 
       
   874 	# Store remarks by Component
       
   875 	if (!defined $remarks{$component})
       
   876 		{
       
   877 		$remarks{$component} = ();
       
   878 		}
       
   879 	push @{$remarks{$component}}, "$iLog:$iLineNumber>$line";
       
   880 }
       
   881 
       
   882 sub do_warning()
       
   883 {
       
   884 	my ($iLog, $iLineNumber, $line)= @_;
       
   885 	# Store warning by Command
       
   886 	if (!defined $CmdWarnings{$command})
       
   887 		{
       
   888 		$CmdWarnings{$command} = ();
       
   889 		}
       
   890 	push @{$CmdWarnings{$command}}, "$iLog:$iLineNumber>$line";
       
   891 
       
   892 	# Store warning by Component
       
   893 	if (!defined $warnings{$component})
       
   894 		{
       
   895 		$warnings{$component} = ();
       
   896 		}
       
   897 	push @{$warnings{$component}}, "$iLog:$iLineNumber>$line";
       
   898 }
       
   899 
       
   900 
       
   901 sub do_migrationNotes()
       
   902   {
       
   903   my ($iLog, $iLineNumber, $line)= @_;
       
   904   # Store Migration Notes by command
       
   905   if (!defined $CmdMigrationNotes{$command})
       
   906     {
       
   907     $CmdMigrationNotes{$command} = ();
       
   908     }
       
   909   push @{$CmdMigrationNotes{$command}}, "$iLog:$iLineNumber>$line";
       
   910   
       
   911   # Store Migration Notes by Component
       
   912   if (!defined $migrationNotes{$component})
       
   913     {
       
   914     $migrationNotes{$component} = ();
       
   915     }
       
   916   push @{$migrationNotes{$component}}, "$iLog:$iLineNumber>$line";
       
   917   
       
   918   }
       
   919 
       
   920 sub do_AdvisoryNotes()
       
   921   {
       
   922   my ($iLog, $iLineNumber, $line)= @_;
       
   923   # Store Advisory Notes by command
       
   924   if (!defined $CmdAdvisoryNotes{$command})
       
   925     {
       
   926     $CmdAdvisoryNotes{$command} = ();
       
   927     }
       
   928   push @{$CmdAdvisoryNotes{$command}}, "$iLog:$iLineNumber>$line";
       
   929   
       
   930   # Store Advisory Notes by Component
       
   931   if (!defined $AdvisoryNotes{$component})
       
   932     {
       
   933     $AdvisoryNotes{$component} = ();
       
   934     }
       
   935   push @{$AdvisoryNotes{$component}}, "$iLog:$iLineNumber>$line";
       
   936   
       
   937 }
       
   938 
       
   939 
       
   940 sub do_error()
       
   941 {
       
   942   my ($iLog, $iLineNumber, $line)= @_;
       
   943 	# Store Errors by Command
       
   944 	if (!defined $CmdErrors{$command})
       
   945 		{
       
   946 		$CmdErrors{$command} = ();
       
   947 		}
       
   948 	push @{$CmdErrors{$command}}, "$iLog:$iLineNumber>$line";
       
   949 
       
   950 	# Store Errors by Component
       
   951 	if (!defined $errors{$component})
       
   952 		{
       
   953 		$errors{$component} = ();
       
   954 		}
       
   955 	push @{$errors{$component}}, "$iLog:$iLineNumber>$line";
       
   956 }
       
   957 
       
   958 # Read a number of lines in the log ignoreing the content
       
   959 sub do_slurp()
       
   960 {
       
   961   my ($num_lines) =@_;
       
   962   for (my $i = 0; $i < $num_lines; $i++)
       
   963   {
       
   964     ;
       
   965   }
       
   966 }
       
   967 
       
   968 sub char_handler
       
   969 {
       
   970   my ($iExpat, $data) = @_;
       
   971   my ($iStatus);
       
   972   
       
   973   # Now Buffer it up for context data
       
   974   $iExpat->{cdata_buffer} .= $data;
       
   975   
       
   976   #Delay parsing until end of line is found or close xml tag or end of recipe
       
   977   return if ($inRecipe);
       
   978   if (!($data =~ /\n$/))
       
   979   {
       
   980     #Put in the line buffer until the rest of the line comes in or an element end causes a parseline call
       
   981     $iExpat->{line_buffer} .= $data;
       
   982     return;
       
   983   } else {
       
   984     #line ends in a \n
       
   985     #Add the $data to buffer(normally empty) and parse
       
   986     &parseline($iExpat,$iExpat->{line_buffer}.$data);
       
   987     #Empty the line buffer
       
   988     $iExpat->{line_buffer} =''; 
       
   989   }
       
   990 }
       
   991 
       
   992 sub parseline
       
   993 {
       
   994   my ($iExpat, $data,$iLineNumber) = @_;
       
   995   if (!($iLineNumber =~ /\d+/))
       
   996   {
       
   997     #If no linenumber is passed the set to the current line in the parse
       
   998     $iLineNumber = $iExpat->current_line;
       
   999   }
       
  1000   my $CheckForComponentExitCodesToMigrate = 0;
       
  1001   
       
  1002   #Set some defaults if $component and $command are empty
       
  1003   if ($component eq '')
       
  1004   {
       
  1005     $component = "anonymous component";
       
  1006     $Components{$component} = '0';
       
  1007 
       
  1008   }
       
  1009   if ($command eq '')
       
  1010   {
       
  1011     $command = "anonymous command";
       
  1012     $Commands{$command} ='0';
       
  1013   }
       
  1014 
       
  1015     # Lines to Ignore
       
  1016     $iStatus =&sbsv2scanlog::CheckForIgnore($data);
       
  1017     if($iStatus)
       
  1018     {
       
  1019       return;
       
  1020     }
       
  1021 
       
  1022     # AdvisoryNotes
       
  1023     ($iStatus) =&sbsv2scanlog::CheckForAdvisoryNotes($data);
       
  1024     if ($iStatus)
       
  1025     {
       
  1026       if ($RetryInProgress)
       
  1027       {
       
  1028         #A retry is in progress so downgrade to a remark
       
  1029         &do_remarks($iLog, $iLineNumber, $data);
       
  1030         return;
       
  1031       } else {
       
  1032       &do_AdvisoryNotes($iLog, $iLineNumber, $data);
       
  1033       return;
       
  1034       }
       
  1035     }
       
  1036 
       
  1037 
       
  1038     #CheckForComponentExitCodesToMigrate
       
  1039     $CheckForComponentExitCodesToMigrate = &sbsv2scanlog::CheckForComponentExitCodesToMigrate($data,$component);
       
  1040     if ($CheckForComponentExitCodesToMigrate )
       
  1041     {
       
  1042       $MigrateNextExitCode = 1;
       
  1043     }
       
  1044 
       
  1045     # Migration Notes
       
  1046     $iStatus = &sbsv2scanlog::CheckForMigrationNotes($data,$component);
       
  1047     if ($iStatus)
       
  1048     {
       
  1049       if ($RetryInProgress)
       
  1050       {
       
  1051         #A retry is in progress so downgrade to a remark
       
  1052         &do_remarks($iLog, $iLineNumber, $data);
       
  1053         return;
       
  1054       } else {
       
  1055         &do_migrationNotes($iLog, $iLineNumber, $data);
       
  1056         #Setup global $warningmigrated flag so warning_ function can ignore the warning element that this migration note was in
       
  1057         $warningmigrated = 1;
       
  1058         return;
       
  1059       }
       
  1060     }
       
  1061 
       
  1062     # Remarks
       
  1063     ($iStatus) =&sbsv2scanlog::CheckForRemarks($data);
       
  1064     if ($iStatus)
       
  1065     {
       
  1066       &do_remarks($iLog, $iLineNumber, $data);
       
  1067       return;
       
  1068     }
       
  1069     
       
  1070     # Errors
       
  1071     ($iStatus) =&sbsv2scanlog::CheckForErrors($data);
       
  1072     if ($iStatus)
       
  1073     {
       
  1074       if ($RetryInProgress)
       
  1075       {
       
  1076         #A retry is in progress so downgrade to a remark
       
  1077         &do_remarks($iLog, $iLineNumber, $data);
       
  1078         return;
       
  1079       } else {
       
  1080         &do_error($iLog, $iLineNumber, $data);
       
  1081         return;
       
  1082       }
       
  1083     }
       
  1084 
       
  1085     
       
  1086     # Warnings
       
  1087     ($iStatus) =&sbsv2scanlog::CheckForWarnings($data);
       
  1088     if ($iStatus)
       
  1089     {
       
  1090       if ($RetryInProgress)
       
  1091       {
       
  1092         #A retry is in progress so downgrade to a remark
       
  1093         &do_remarks($iLog, $iLineNumber, $data);
       
  1094         return;
       
  1095       } else {
       
  1096         &do_warning($iLog, $iLineNumber, $data);
       
  1097         return;
       
  1098       }
       
  1099     }
       
  1100     return;
       
  1101 }
       
  1102 
       
  1103 {
       
  1104   package MySubs;
       
  1105   # recipe
       
  1106   #
       
  1107   # Inputs
       
  1108   #
       
  1109   # Outputs
       
  1110   #
       
  1111   # Description
       
  1112   # This function handles the recipe tag in the XML
       
  1113   sub recipe
       
  1114   {
       
  1115     my $iExpat = shift; my $iElement = shift;
       
  1116     
       
  1117     #empty cdata buffer
       
  1118     $iExpat->{cdata_buffer} = '';
       
  1119     
       
  1120     #Set global flag to change char data handling to the end of the recipe
       
  1121     #So that errors/warnings/migration notes can be down grade to remarks
       
  1122     #if a retry is signalled
       
  1123     $inRecipe = 1;
       
  1124   
       
  1125     my (%iAttr);
       
  1126   
       
  1127     # Read the attributes
       
  1128     while (@_) {
       
  1129       my $iAtt = shift;
       
  1130       my $iVal = shift;
       
  1131       $iAttr{$iAtt} = $iVal;
       
  1132     }
       
  1133     
       
  1134     #print "recipe name =".$iAttr{'name'}."\n";
       
  1135     if ($iAttr{'component'} ne '')
       
  1136     {
       
  1137       $component = $iAttr{'component'};
       
  1138     } else {
       
  1139       #Try using the bld.inf as unique component identifier
       
  1140       $component = $iAttr{'bldinf'};
       
  1141     }
       
  1142     
       
  1143     $command = $iAttr{'name'}." ".$iAttr{'platform'};
       
  1144   }
       
  1145   
       
  1146   sub recipe_
       
  1147   {
       
  1148     my $iExpat = shift;
       
  1149     
       
  1150     #Handle all recipe text that was inside this element
       
  1151     
       
  1152     #Split the multiline cdata_buffer in to single lines
       
  1153     my @lines = split /\n/,$iExpat->{cdata_buffer};
       
  1154     for (my $buffnum = 0 ; $buffnum < scalar (@lines); $buffnum++)
       
  1155     {
       
  1156       #Parse each line
       
  1157       
       
  1158       #Calculate the actual line number subtracking status and time element lines (2) and position in array from end
       
  1159       my $linenum = ($iExpat->current_line) - 2 - (scalar (@lines) - $buffnum);
       
  1160       &main::parseline($iExpat, $lines[$buffnum],$linenum);
       
  1161     }
       
  1162 
       
  1163     #Clear $inRecipe flag
       
  1164     $inRecipe = 0;
       
  1165     
       
  1166     #Clear $RetryInProgress flag as a retry cannot out live a recipe
       
  1167     $RetryInProgress = 0;
       
  1168     
       
  1169     #Clear all data set by recipe start
       
  1170     $component = '';
       
  1171     $command = '';
       
  1172     
       
  1173     #empty cdata buffer
       
  1174     $iExpat->{cdata_buffer} = '';
       
  1175   }
       
  1176   
       
  1177   sub time
       
  1178   {
       
  1179     my $iExpat = shift; my $iElement = shift;
       
  1180   
       
  1181     my (%iAttr);
       
  1182   
       
  1183     # Read the attributes
       
  1184     while (@_) {
       
  1185       my $iAtt = shift;
       
  1186       my $iVal = shift;
       
  1187       $iAttr{$iAtt} = $iVal;
       
  1188     }
       
  1189     
       
  1190     #Elapsed time and Total up for Command
       
  1191     $Commands{$command} += $iAttr{'elapsed'};
       
  1192     #Elapsed time and Total up for Component
       
  1193     $Components{$component} += $iAttr{'elapsed'};
       
  1194   }
       
  1195   
       
  1196   sub time_
       
  1197   {
       
  1198     #Do nothing
       
  1199   }
       
  1200   
       
  1201   sub info
       
  1202   {
       
  1203     my $iExpat = shift; my $iElement = shift;
       
  1204     #empty cdata buffer
       
  1205     $iExpat->{cdata_buffer} = '';
       
  1206     
       
  1207     $component = 'SBS: Info';    
       
  1208     $command = 'SBS: Info';
       
  1209     $Components{$component} = '0';
       
  1210     $Commands{$command} ='0';
       
  1211   }
       
  1212   
       
  1213   sub info_
       
  1214   {
       
  1215     my $iExpat = shift; my $iElement = shift;
       
  1216     
       
  1217     #Handle any unhandle text that was inside this element
       
  1218     if ($iExpat->{line_buffer} =~ /.+/)
       
  1219     {
       
  1220       &main::parseline($iExpat, $iExpat->{line_buffer});
       
  1221       $iExpat->{line_buffer} =''; 
       
  1222     }
       
  1223     
       
  1224     #Clear all data set by info start
       
  1225     $component = '';
       
  1226     $command = '';
       
  1227 	if ($iExpat->{cdata_buffer} =~ /Run time (.*?) seconds/)
       
  1228     {
       
  1229       ($currentfiletime) =$1;
       
  1230     }
       
  1231     
       
  1232     #empty cdata buffer
       
  1233     $iExpat->{cdata_buffer} = '';
       
  1234   }
       
  1235   
       
  1236   sub warning
       
  1237   {
       
  1238     my $iExpat = shift; my $iElement = shift;
       
  1239     #empty cdata buffer
       
  1240     $iExpat->{cdata_buffer} = '';
       
  1241     #reset $warningmigrated flag
       
  1242     $warningmigrated = 0;
       
  1243     
       
  1244     $component = 'SBS: Warning';    
       
  1245     $command = 'SBS: Warning';
       
  1246     $Components{$component} = '0';
       
  1247     $Commands{$command} ='0';
       
  1248   }
       
  1249   
       
  1250   sub warning_
       
  1251   {
       
  1252     my $iExpat = shift; my $iElement = shift;
       
  1253     
       
  1254     #Handle any unhandle text that was inside this element
       
  1255     if ($iExpat->{line_buffer} =~ /.+/)
       
  1256     {
       
  1257       &main::parseline($iExpat, $iExpat->{line_buffer});
       
  1258       $iExpat->{line_buffer} =''; 
       
  1259     }
       
  1260     
       
  1261     my ($iLineNumber) = $iExpat->current_line;
       
  1262   
       
  1263     if ($warningmigrated != 1)
       
  1264     {
       
  1265       #Record error in its own right for the error xml element
       
  1266       &main::do_warning($iLog, $iLineNumber, $iExpat->{cdata_buffer});
       
  1267     }
       
  1268     
       
  1269     #Clear all data set by info start
       
  1270     $component = '';
       
  1271     $command = '';
       
  1272     
       
  1273     #empty cdata buffer
       
  1274     $iExpat->{cdata_buffer} = '';
       
  1275   }
       
  1276   
       
  1277   sub error
       
  1278   {
       
  1279     my $iExpat = shift; my $iElement = shift;
       
  1280     #empty cdata buffer
       
  1281     $iExpat->{cdata_buffer} = '';
       
  1282     
       
  1283     #Set generic component and command names so that these don't get allocated to a empty component
       
  1284     $component = 'SBS: Error';    
       
  1285     $command = 'SBS: Error';
       
  1286     $Components{$component} = '0';
       
  1287     $Commands{$command} ='0';
       
  1288   }
       
  1289   
       
  1290   sub error_
       
  1291   {
       
  1292     my $iExpat = shift; my $iElement = shift;
       
  1293     
       
  1294     #Handle any unhandle text that was inside this element
       
  1295     if ($iExpat->{line_buffer} =~ /.+/)
       
  1296     {
       
  1297       &main::parseline($iExpat, $iExpat->{line_buffer});
       
  1298       $iExpat->{line_buffer} =''; 
       
  1299     }
       
  1300 
       
  1301     my ($iLineNumber) = $iExpat->current_line;
       
  1302   
       
  1303     #Record error in its own right for the error xml element
       
  1304     &main::do_error($iLog, $iLineNumber, $iExpat->{cdata_buffer});
       
  1305     
       
  1306     #Clear all data set by info start
       
  1307     $component = '';
       
  1308     $command = '';
       
  1309     
       
  1310     #empty cdata buffer
       
  1311     $iExpat->{cdata_buffer} = '';
       
  1312   }
       
  1313   
       
  1314   sub status
       
  1315   {
       
  1316     my $iExpat = shift; my $iElement = shift;
       
  1317 
       
  1318     my (%iAttr);
       
  1319   
       
  1320     # Read the attributes
       
  1321     while (@_) {
       
  1322       my $iAtt = shift;
       
  1323       my $iVal = shift;
       
  1324       $iAttr{$iAtt} = $iVal;
       
  1325     }
       
  1326 
       
  1327     my ($iLineNumber) = $iExpat->current_line;
       
  1328 
       
  1329     if ($iAttr{'exit'} eq 'retry')
       
  1330     {
       
  1331       $RetryInProgress = 1;
       
  1332       #Record retry as a remark
       
  1333       &main::do_remarks($iLog, $iLineNumber, "$component retried on $command with ".$iAttr{'code'});
       
  1334       return;
       
  1335     } elsif ($iAttr{'exit'} ne 'ok') {
       
  1336       #Record as migration note for non ok exit because a previous line has triggered this flag
       
  1337       if ($MigrateNextExitCode)
       
  1338       {
       
  1339         &main::do_migrationNotes($iLog, $iLineNumber, "$component failed on $command with ".$iAttr{'code'});
       
  1340       } else {
       
  1341         #Record error in its own right for the non 'ok' exit status
       
  1342         &main::do_error($iLog, $iLineNumber, "$component failed on $command with ".$iAttr{'code'});
       
  1343       }
       
  1344     }
       
  1345     
       
  1346     #Resest the Migrate exit code flag because a previous line has triggered this flag
       
  1347     $MigrateNextExitCode =0;
       
  1348   }
       
  1349   
       
  1350   sub status_
       
  1351   {
       
  1352     my $iExpat = shift; my $iElement = shift;
       
  1353     # Nothing to do
       
  1354   }
       
  1355   
       
  1356   sub debug
       
  1357   {
       
  1358     my $iExpat = shift; my $iElement = shift;
       
  1359     # Nothing to do
       
  1360   }
       
  1361   
       
  1362     sub debug_
       
  1363   {
       
  1364     my $iExpat = shift; my $iElement = shift;
       
  1365     # Nothing to do
       
  1366   }
       
  1367 }