Thursday, 9 March 2017

findbadobjectfile script (learning)

#!/usr/bin/perl

@PURPOSE="Find bad compilation unit";
@SYNTAX="findbadobjectfile";
@NOTE="Uses scripts compileme, link.sh, and executeme. Also uses file object_names.";

# To use this script, create two directories: good_objects and bad_objects.
# Build the testcase twice. First build with good driver and move all the object files to good_objects directory.
# Build again with bad driver, and move all the object files to bad_objects directory.
# Create a script called link.sh which has the original link command. Remove all the object files from the link command.
# Create a file called object_names which lists all the object files, one per line.
# Create a script called executeme which runs the testcase and returns 0 for success.

sub link_program
{
  print "***Running link cmd\n";
  system("./temp_link.sh");
}

sub run_program
{
  print "****Running program\n";
  system("./executeme");
}

@obj_array = `cat object_names`;

use integer;

$lower = 0;
$size = @obj_array;
$upper = $size;
$lastgood = $size+1;

open (my $input, '<', 'link.sh');
$link = <$input>;
chomp ($link);

$j=0;
while( $lower < $upper-1 ) {
  $link_cmd = $link;

  my $link_file = "temp_link.sh";
  open (my $fh, '>',$link_file) or die "Could not open $link_file";
  system ("chmod +x temp_link.sh");

  $middle = ($lower + $upper) / 2;
  if($lower > 0){
    for($i=0;$i<$lower;$i++){
      chomp(@obj_array[$i]);
        $link_cmd = $link_cmd . " good_objects/".@obj_array[$i];
    }
  }
  for($i=$lower;$i<$middle;$i++){
    chomp(@obj_array[$i]);
    $link_cmd = $link_cmd . " good_objects/".@obj_array[$i];
  }
  for($i=$middle;$i<$upper;$i++){
    chomp(@obj_array[$i]);
    $link_cmd = $link_cmd . " bad_objects/".@obj_array[$i];
  }

  if($upper < $size){
    for($i=$upper;$i<$size;$i++){
      chomp(@obj_array[$i]);
        $link_cmd = $link_cmd . " good_objects/".@obj_array[$i];
    }
  }

  $link_cmd = $link_cmd."\n";
#   print $link_cmd;
  print $fh $link_cmd;
  close $fh;
  link_program;
  run_program;
  if($?==0){
    print "Passed round $j\n";
    $upper = $middle;
  }else{
    print "Failed round $j\n";
    $lower = $middle;
  }
  $j=$j+1;
  system("rm temp_link.sh");
}

print "Bad compilation unit: @obj_array[$lower]\n";

1 comment: