mirror of
				https://github.com/xcat2/xcat-core.git
				synced 2025-11-04 13:22:36 +00:00 
			
		
		
		
	
		
			
				
	
	
		
			5622 lines
		
	
	
		
			193 KiB
		
	
	
	
		
			Perl
		
	
	
	
	
	
			
		
		
	
	
			5622 lines
		
	
	
		
			193 KiB
		
	
	
	
		
			Perl
		
	
	
	
	
	
# IBM(c) 2007 EPL license http://www.eclipse.org/legal/epl-v10.html
 | 
						|
#-------------------------------------------------------
 | 
						|
 | 
						|
=head1
 | 
						|
  xCAT plugin package to handle Kit management
 | 
						|
=cut
 | 
						|
 | 
						|
#-------------------------------------------------------
 | 
						|
package xCAT_plugin::kit;
 | 
						|
 | 
						|
BEGIN
 | 
						|
{
 | 
						|
    $::XCATROOT = $ENV{'XCATROOT'} ? $ENV{'XCATROOT'} : '/opt/xcat';
 | 
						|
}
 | 
						|
use lib "$::XCATROOT/lib/perl";
 | 
						|
 | 
						|
use xCAT::Table;
 | 
						|
use xCAT::Utils;
 | 
						|
use xCAT::MsgUtils;
 | 
						|
use Getopt::Long;
 | 
						|
 | 
						|
#use Data::Dumper;
 | 
						|
use File::Basename;
 | 
						|
use File::Path;
 | 
						|
use Cwd;
 | 
						|
 | 
						|
my $kitconf = "kit.conf";
 | 
						|
 | 
						|
# kit framework version for this xcat.
 | 
						|
$::KITFRAMEWORK = "2";
 | 
						|
 | 
						|
# this code is compatible with other kits that are at framework 0 or 1.
 | 
						|
$::COMPATIBLE_KITFRAMEWORKS = "0,1,2";
 | 
						|
 | 
						|
my $debianflag = 0;
 | 
						|
my $tempstring = xCAT::Utils->osver(all);
 | 
						|
if ($tempstring =~ /debian/ || $tempstring =~ /ubuntu/) {
 | 
						|
    $debianflag = 1;
 | 
						|
 | 
						|
    #    print "debian";
 | 
						|
}
 | 
						|
 | 
						|
#-------------------------------------------------------
 | 
						|
 | 
						|
=head3  handled_commands
 | 
						|
 | 
						|
Return list of commands handled by this plugin
 | 
						|
 | 
						|
=cut
 | 
						|
 | 
						|
#-------------------------------------------------------
 | 
						|
 | 
						|
sub handled_commands
 | 
						|
{
 | 
						|
    return {
 | 
						|
        lskit            => "kit",
 | 
						|
        addkit           => "kit",
 | 
						|
        rmkit            => "kit",
 | 
						|
        lskitcomp        => "kit",
 | 
						|
        addkitcomp       => "kit",
 | 
						|
        rmkitcomp        => "kit",
 | 
						|
        chkkitcomp       => "kit",
 | 
						|
        lskitdeployparam => "kit",
 | 
						|
    };
 | 
						|
}
 | 
						|
 | 
						|
#-------------------------------------------------------
 | 
						|
 | 
						|
=head3  process_request
 | 
						|
 | 
						|
  Process the command
 | 
						|
 | 
						|
=cut
 | 
						|
 | 
						|
#-------------------------------------------------------
 | 
						|
sub process_request
 | 
						|
{
 | 
						|
 | 
						|
    my $request         = shift;
 | 
						|
    my $callback        = shift;
 | 
						|
    my $request_command = shift;
 | 
						|
    $::CALLBACK = $callback;
 | 
						|
    $::args     = $request->{arg};
 | 
						|
 | 
						|
    my $lock;
 | 
						|
    my $locked = xCAT::Utils->is_locked("kit", 1);
 | 
						|
    if (!locked) {
 | 
						|
        $lock = xCAT::Utils->acquire_lock("kit", 1);
 | 
						|
        unless ($lock) {
 | 
						|
            $callback->({ error => ["Can not acquire lock."], errorcode => [1] });
 | 
						|
            return 1;
 | 
						|
        }
 | 
						|
    } else {
 | 
						|
        if ($::PID and $::PID != $$) {
 | 
						|
            $callback->({ error => ["Can not acquire lock, another process is running."], errorcode => [1] });
 | 
						|
            return 1;
 | 
						|
        }
 | 
						|
 | 
						|
        $::PID = $$;
 | 
						|
    }
 | 
						|
 | 
						|
    my ($sysos, $sysver) = split /,/, $tempstring;
 | 
						|
    if ( ($sysos =~ /rh/) && ($sysver ge 8) ) {
 | 
						|
        $callback->({ error => ["KITs are not supported on rhel8 or above"], errorcode => [1] });
 | 
						|
        return 1;
 | 
						|
    }
 | 
						|
 | 
						|
    my $command = $request->{command}->[0];
 | 
						|
    my $rc;
 | 
						|
 | 
						|
    if ($command eq "lskit") {
 | 
						|
        $rc = lskit($request, $callback, $request_command);
 | 
						|
    } elsif ($command eq "addkit") {
 | 
						|
        $rc = addkit($request, $callback, $request_command);
 | 
						|
        system("rm -rf /tmp/tmpkit/");
 | 
						|
    } elsif ($command eq "rmkit") {
 | 
						|
        $rc = rmkit($request, $callback, $request_command);
 | 
						|
    } elsif ($command eq "lskitcomp") {
 | 
						|
        $rc = lskitcomp($request, $callback, $request_command);
 | 
						|
    } elsif ($command eq "addkitcomp") {
 | 
						|
        $rc = addkitcomp($request, $callback, $request_command);
 | 
						|
    } elsif ($command eq "rmkitcomp") {
 | 
						|
        $rc = rmkitcomp($request, $callback, $request_command);
 | 
						|
    } elsif ($command eq "chkkitcomp") {
 | 
						|
        $rc = chkkitcomp($request, $callback, $request_command);
 | 
						|
    } elsif ($command eq "lskitdeployparam") {
 | 
						|
        $rc = lskitdeployparam($request, $callback, $request_command);
 | 
						|
    } else {
 | 
						|
        $callback->({ error => ["Error: $command not found in this module."], errorcode => [1] });
 | 
						|
        xCAT::Utils->release_lock($lock, 1);
 | 
						|
        return 1;
 | 
						|
    }
 | 
						|
 | 
						|
    if ($lock) {
 | 
						|
        xCAT::Utils->release_lock($lock, 1);
 | 
						|
    }
 | 
						|
    return $rc;
 | 
						|
 | 
						|
}
 | 
						|
 | 
						|
#-------------------------------------------------------
 | 
						|
 | 
						|
=head3  get_highest_version
 | 
						|
 | 
						|
  Return the highest version and release for a list of
 | 
						|
  kit, kitrepo, or kitcomponent names.
 | 
						|
 | 
						|
  Input: @entries: the arrary contains all the data
 | 
						|
         $key: the key name in entries hash.
 | 
						|
         $version: compare version nums.
 | 
						|
         $release: compare release nums.
 | 
						|
 | 
						|
=cut
 | 
						|
 | 
						|
#-------------------------------------------------------
 | 
						|
sub get_highest_version
 | 
						|
{
 | 
						|
    my $key     = shift;
 | 
						|
    my $version = shift;
 | 
						|
    my $release = shift;
 | 
						|
    my @entries = @_;
 | 
						|
 | 
						|
    my $highest;
 | 
						|
 | 
						|
    foreach my $entry (@entries) {
 | 
						|
        $highest = $entry if (!$highest);
 | 
						|
 | 
						|
        my $rc = compare_version($highest, $entry, $key, $version, $release);
 | 
						|
        if ($rc == 1) {
 | 
						|
            $highest = $entry;
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    return $highest->{$key};
 | 
						|
}
 | 
						|
 | 
						|
#-------------------------------------------------------
 | 
						|
 | 
						|
=head3  compare_version
 | 
						|
 | 
						|
  Compare the version and release between two kit/kitrepo/kitcomp
 | 
						|
 | 
						|
  Input: $highest: the current highest version or release
 | 
						|
         $entry: the new entry
 | 
						|
         $key: the key name in entries hash.
 | 
						|
         $version: compare version nums.
 | 
						|
         $release: compare release nums.
 | 
						|
 | 
						|
=cut
 | 
						|
 | 
						|
#-------------------------------------------------------
 | 
						|
sub compare_version
 | 
						|
{
 | 
						|
    my $highest = shift;
 | 
						|
    my $entry   = shift;
 | 
						|
    my $key     = shift;
 | 
						|
    my $version = shift;
 | 
						|
    my $release = shift;
 | 
						|
 | 
						|
    my @a1 = split(/\./, $highest->{$version});
 | 
						|
    my @a2 = split(/\./, $entry->{$version});
 | 
						|
 | 
						|
    my ($len, $num1, $num2);
 | 
						|
    if (($release = 'release') &&
 | 
						|
        (defined $highest->{$release}) && (defined $entry->{$release})) {
 | 
						|
        $len = (scalar(@a1) > scalar(@a2) ? scalar(@a1) : scalar(@a2));
 | 
						|
    } else {
 | 
						|
        $len = (scalar(@a1) < scalar(@a2) ? scalar(@a1) : scalar(@a2));
 | 
						|
    }
 | 
						|
 | 
						|
    $#a1 = $len - 1;  # make the arrays the same length before appending release
 | 
						|
    $#a2 = $len - 1;
 | 
						|
 | 
						|
    if ($release = 'release') {
 | 
						|
        push @a1, split(/\./, $highest->{$release});
 | 
						|
        push @a2, split(/\./, $entry->{$release});
 | 
						|
    }
 | 
						|
 | 
						|
    $len = (scalar(@a1) < scalar(@a2) ? scalar(@a1) : scalar(@a2));
 | 
						|
 | 
						|
    $num1 = '';
 | 
						|
    $num2 = '';
 | 
						|
 | 
						|
    for (my $i = 0 ; $i < $len ; $i++)
 | 
						|
    {
 | 
						|
        my ($d1, $w1) = $a1[$i] =~ /^(\d*)(\w*)/;
 | 
						|
        my ($d2, $w2) = $a2[$i] =~ /^(\d*)(\w*)/;
 | 
						|
 | 
						|
 | 
						|
        my $diff = length($d1) - length($d2);
 | 
						|
        if ($diff > 0)    # pad d2
 | 
						|
        {
 | 
						|
            $num1 .= $d1;
 | 
						|
            $num2 .= ('0' x $diff) . $d2;
 | 
						|
        }
 | 
						|
        elsif ($diff < 0)    # pad d1
 | 
						|
        {
 | 
						|
            $num1 .= ('0' x abs($diff)) . $d1;
 | 
						|
            $num2 .= $d2;
 | 
						|
        }
 | 
						|
        else                 # they are the same length
 | 
						|
        {
 | 
						|
            $num1 .= $d1;
 | 
						|
            $num2 .= $d2;
 | 
						|
        }
 | 
						|
 | 
						|
        if ($w1 && $w2)
 | 
						|
        {
 | 
						|
            my ($w_to_d1, $w_to_d2) = comp_word($w1, $w2);
 | 
						|
            $num1 .= $w_to_d1;
 | 
						|
            $num2 .= $w_to_d2;
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    # Remove the leading 0s or perl will interpret the numbers as octal
 | 
						|
    $num1 =~ s/^0+//;
 | 
						|
    $num2 =~ s/^0+//;
 | 
						|
 | 
						|
    #SuSE Changes
 | 
						|
    # if $num1="", the "eval '$num1 $operator $num2'" will fail. So MUSTBE be sure that $num1 is not a "".
 | 
						|
    if (length($num1) == 0) { $num1 = 0; }
 | 
						|
    if (length($num2) == 0) { $num2 = 0; }
 | 
						|
 | 
						|
    return 1 if ($num2 > $num1);
 | 
						|
    return 0 if ($num2 == $num1);
 | 
						|
    return -1;
 | 
						|
}
 | 
						|
 | 
						|
#--------------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3    comp_word
 | 
						|
 | 
						|
        Compare version1 word and version2 word. This subroutine can only be used to compare
 | 
						|
        one section in version number, and this section cannot start with number.
 | 
						|
 | 
						|
        Arguments:
 | 
						|
                $w1:
 | 
						|
                $w2
 | 
						|
        Returns:
 | 
						|
                if $w1 > $w2, return (1,0)
 | 
						|
                if $w1 < $w2, return (0,1)
 | 
						|
                if $w1 == $w2, return (undef, undef)
 | 
						|
        Globals:
 | 
						|
                none
 | 
						|
 | 
						|
        Example:
 | 
						|
                if ($self->comp_word ( "adfadsfa","acc2")
 | 
						|
                return (0,1)
 | 
						|
        Comments:
 | 
						|
                the version word cannot contain ".", and cannot start with number.
 | 
						|
                For examples, following version words cannot be compared by this subroutine:
 | 
						|
                (123.321, 123.322)  You need use subroutine testVersion to do the version comparision
 | 
						|
                (123abc,12bcd)      You need use subroutine testVersion to do the version comparision
 | 
						|
 | 
						|
=cut
 | 
						|
 | 
						|
#--------------------------------------------------------------------------------
 | 
						|
 | 
						|
sub comp_word
 | 
						|
{
 | 
						|
    my $self = shift;
 | 
						|
 | 
						|
    my ($w1, $w2) = @_;
 | 
						|
 | 
						|
    return (undef, undef) if (!$w1 || !$w2);
 | 
						|
 | 
						|
    my @strList1 = unpack "C*", $w1;
 | 
						|
    my @strList2 = unpack "C*", $w2;
 | 
						|
 | 
						|
    my $len = scalar(@strList1) < scalar(@strList2) ? scalar(@strList1) : scalar(@strList2);
 | 
						|
 | 
						|
    for (my $i = 0 ; $i < $len ; $i++)
 | 
						|
    {
 | 
						|
        next if ($strList1[$i] == $strList2[$i]);
 | 
						|
        return (0, 1) if ($strList1[$i] < $strList2[$i]);
 | 
						|
        return (1, 0);
 | 
						|
    }
 | 
						|
    return (undef, undef);
 | 
						|
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
#-------------------------------------------------------
 | 
						|
 | 
						|
=head3 check_newinstall
 | 
						|
 | 
						|
  Check if the given kitcomp list are in NEW_INSTALL_LIST
 | 
						|
  or not.  If so, set $::noupgrade all other kitcomp
 | 
						|
  depending on this list will be put into NEW_INSTALL_LIST
 | 
						|
  also
 | 
						|
 | 
						|
=cut
 | 
						|
 | 
						|
#-------------------------------------------------------
 | 
						|
sub check_newinstall
 | 
						|
{
 | 
						|
    my $kitcomponents = shift;
 | 
						|
    my @lines         = @_;
 | 
						|
 | 
						|
    my @kitcomps = split /,/, $kitcomponents;
 | 
						|
 | 
						|
    foreach my $kitcomp (@kitcomps) {
 | 
						|
        last if ($::noupgrade);
 | 
						|
 | 
						|
        my $match_newinstall = 0;
 | 
						|
        foreach my $line (@lines) {
 | 
						|
            chomp($line);
 | 
						|
            if ($line =~ /^#NEW_INSTALL_LIST#$/) {
 | 
						|
                $match_newinstall = 1;
 | 
						|
            }
 | 
						|
            if ($line =~ /\/$kitcomp$/) {
 | 
						|
                if ($match_newinstall) {
 | 
						|
                    $::noupgrade = 1;
 | 
						|
                }
 | 
						|
                last;
 | 
						|
            }
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
#-------------------------------------------------------
 | 
						|
 | 
						|
=head3 get local otherpkgdir
 | 
						|
 | 
						|
  otherpkgdir can be mixed http source and local dir
 | 
						|
  Split otherpkgdir
 | 
						|
  get local otherpkgdir
 | 
						|
 | 
						|
=cut
 | 
						|
 | 
						|
#-------------------------------------------------------
 | 
						|
 | 
						|
sub get_local_otherpkgdir
 | 
						|
{
 | 
						|
    $otherpkgdir = shift;
 | 
						|
    my $localdir = "";
 | 
						|
    my @tempdirarray = split /,/, $otherpkgdir;
 | 
						|
    foreach my $tempdir (@tempdirarray) {
 | 
						|
        $tempdir =~ s/(^ +| +$)//g;
 | 
						|
        if ($tempdir !~ /^http.*/) {
 | 
						|
            $localdir = $tempdir;
 | 
						|
            last;
 | 
						|
        }
 | 
						|
    }
 | 
						|
    return $localdir;
 | 
						|
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
#-------------------------------------------------------
 | 
						|
 | 
						|
=head3 assign_to_osimage
 | 
						|
 | 
						|
  Assign a kit component to osimage
 | 
						|
 | 
						|
=cut
 | 
						|
 | 
						|
#-------------------------------------------------------
 | 
						|
sub assign_to_osimage
 | 
						|
{
 | 
						|
    my $osimage  = shift;
 | 
						|
    my $kitcomp  = shift;
 | 
						|
    my $callback = shift;
 | 
						|
    my $tabs     = shift;
 | 
						|
 | 
						|
    (my $kitcomptable) = $tabs->{kitcomponent}->getAttribs({ kitcompname => $kitcomp }, 'kitname', 'kitreponame', 'basename', 'kitcompdeps', 'kitpkgdeps', 'prerequisite', 'exlist', 'genimage_postinstall', 'postbootscripts', 'driverpacks');
 | 
						|
    (my $osimagetable) = $tabs->{osimage}->getAttribs({ imagename => $osimage }, 'provmethod', 'osarch', 'postbootscripts', 'kitcomponents', 'osvers');
 | 
						|
    (my $linuximagetable) = $tabs->{linuximage}->getAttribs({ imagename => $osimage }, 'rootimgdir', 'exlist', 'postinstall', 'otherpkglist', 'otherpkgdir', 'driverupdatesrc');
 | 
						|
 | 
						|
    # Reading installdir.
 | 
						|
    my $installdir = xCAT::TableUtils->getInstallDir();
 | 
						|
    unless ($installdir) {
 | 
						|
        $installdir = '/install';
 | 
						|
    }
 | 
						|
    $installdir =~ s/\/$//;
 | 
						|
 | 
						|
 | 
						|
    # Reading kitdir
 | 
						|
    my $kittable;
 | 
						|
    if ($kitcomptable and $kitcomptable->{kitname}) {
 | 
						|
        ($kittable) = $tabs->{kit}->getAttribs({ kitname => $kitcomptable->{kitname} }, 'kitdir', 'kitdeployparams');
 | 
						|
    }
 | 
						|
 | 
						|
    # Create osimage direcotry to save kit tmp files
 | 
						|
    mkpath("$installdir/osimages/$osimage/kits/");
 | 
						|
 | 
						|
    # Adding genimage_postinstall script to linuximage.postintall attribute for diskless image or osimage.postbootscripts for diskfull image.
 | 
						|
    if ($kitcomptable and $kitcomptable->{genimage_postinstall}) {
 | 
						|
        my @kitcompscripts = split ',', $kitcomptable->{genimage_postinstall};
 | 
						|
        foreach my $kitcompscript (@kitcompscripts) {
 | 
						|
            if ($osimagetable) {
 | 
						|
                my $otherpkgdir;
 | 
						|
                my $rootimgdir;
 | 
						|
                if ($linuximagetable and $linuximagetable->{otherpkgdir}) {
 | 
						|
                    $otherpkgdir = $linuximagetable->{otherpkgdir};
 | 
						|
 | 
						|
                    #support mixed otherpkgdir http and local dir
 | 
						|
                    $otherpkgdir = get_local_otherpkgdir($otherpkgdir);
 | 
						|
 | 
						|
                } else {
 | 
						|
                    $callback->({ error => ["Could not read otherpkgdir from osimage $osimage"], errorcode => [1] });
 | 
						|
                    return 1;
 | 
						|
                }
 | 
						|
 | 
						|
                if ($osimagetable->{provmethod} =~ /install/) {
 | 
						|
 | 
						|
                    # If the script is only for diskless node
 | 
						|
                    my $cmd = "grep \"#FLAG FOR DISKLESS ONLY#\" $installdir/postscripts/$kitcompscript";
 | 
						|
                    my $res = xCAT::Utils->runcmd($cmd, -1);
 | 
						|
                    if ($res eq "#FLAG FOR DISKLESS ONLY#") {
 | 
						|
                        next;
 | 
						|
                    }
 | 
						|
 | 
						|
                    # for diskfull node
 | 
						|
                    my $match = 0;
 | 
						|
                    my @scripts = split ',', $osimagetable->{postbootscripts};
 | 
						|
                    foreach my $script (@scripts) {
 | 
						|
                        if ($script =~ /^KIT_$osimage.postbootscripts/) {
 | 
						|
                            $match = 1;
 | 
						|
                            last;
 | 
						|
                        }
 | 
						|
                    }
 | 
						|
 | 
						|
                    if (!-e "$installdir/postscripts/KIT_$osimage.postbootscripts") {
 | 
						|
                        if (open(FILE, ">", "$installdir/postscripts/KIT_$osimage.postbootscripts")) {
 | 
						|
                            print FILE "#!/bin/sh\n\n";
 | 
						|
                            close(FILE);
 | 
						|
                            chmod(0755, "$installdir/postscripts/KIT_$osimage.postbootscripts");
 | 
						|
                        }
 | 
						|
                    }
 | 
						|
 | 
						|
                    my @postbootlines;
 | 
						|
                    if (open(POSTBOOTSCRIPTS, "<", "$installdir/postscripts/KIT_$osimage.postbootscripts")) {
 | 
						|
                        @postbootlines = <POSTBOOTSCRIPTS>;
 | 
						|
                        close(POSTBOOTSCRIPTS);
 | 
						|
                        if ($::VERBOSE) {
 | 
						|
                            $callback->({ data => ["\nCreating osimage postbootscripts file $installdir/postscripts/KIT_$osimage.postbootscripts"] });
 | 
						|
                        }
 | 
						|
                    }
 | 
						|
 | 
						|
                    unless (grep(/$kitcompscript/, @postbootlines)) {
 | 
						|
                        if (open(NEWLIST, ">>", "$installdir/postscripts/KIT_$osimage.postbootscripts")) {
 | 
						|
                            print NEWLIST "otherpkgdir=$otherpkgdir $kitcompscript\n";
 | 
						|
                            close(NEWLIST);
 | 
						|
                        }
 | 
						|
                    }
 | 
						|
 | 
						|
                    if (!$match) {
 | 
						|
                        $osimagetable->{postbootscripts} = "KIT_$osimage.postbootscripts," . $osimagetable->{postbootscripts};
 | 
						|
                        $osimagetable->{postbootscripts} =~ s/^,//;
 | 
						|
                    }
 | 
						|
 | 
						|
                } else {
 | 
						|
 | 
						|
                    # for diskless node
 | 
						|
 | 
						|
                    if ($linuximagetable and $linuximagetable->{rootimgdir}) {
 | 
						|
                        $rootimgdir = $linuximagetable->{rootimgdir} . "/rootimg";
 | 
						|
                    } else {
 | 
						|
                        $callback->({ error => ["Could not read rootimgdir from osimage $osimage"], errorcode => [1] });
 | 
						|
                        return 1;
 | 
						|
                    }
 | 
						|
 | 
						|
                    if (!-e "$installdir/osimages/$osimage/kits/KIT_COMPONENTS.postinstall") {
 | 
						|
                        if (open(FILE, ">", "$installdir/osimages/$osimage/kits/KIT_COMPONENTS.postinstall")) {
 | 
						|
                            print FILE "#!/bin/sh\n\n";
 | 
						|
                            close(FILE);
 | 
						|
                            chmod(0755, "$installdir/osimages/$osimage/kits/KIT_COMPONENTS.postinstall");
 | 
						|
                        }
 | 
						|
                    }
 | 
						|
 | 
						|
                    my @postinstalllines;
 | 
						|
                    if (open(POSTINSTALL, "<", "$installdir/osimages/$osimage/kits/KIT_COMPONENTS.postinstall")) {
 | 
						|
                        @postinstalllines = <POSTINSTALL>;
 | 
						|
                        close(POSTINSTALL);
 | 
						|
 | 
						|
                        if ($::VERBOSE) {
 | 
						|
                            $callback->({ data => ["\nReading osimage postinstall scripts file $installdir/osimages/$osimage/kits/KIT_COMPONENTS.postinstall"] });
 | 
						|
                        }
 | 
						|
                    }
 | 
						|
 | 
						|
                    unless (grep(/$kitcompscript/, @postinstalllines)) {
 | 
						|
                        my $deployparams;
 | 
						|
                        my @ls;
 | 
						|
                        if ($kittable and $kittable->{kitdeployparams} and $kittable->{kitdir}) {
 | 
						|
                            if (open(DEPLOYPARAM, "<", "$kittable->{kitdir}/other_files/$kittable->{kitdeployparams}")) {
 | 
						|
                                @ls = <DEPLOYPARAM>;
 | 
						|
                                close(DEPLOYPARAM);
 | 
						|
                            }
 | 
						|
                        }
 | 
						|
 | 
						|
                        my @newlines;
 | 
						|
                        foreach my $line (@ls) {
 | 
						|
                            if ($line =~ /^#ENV:.+=.+#$/) {
 | 
						|
                                chomp($line);
 | 
						|
                                $line =~ s/^#ENV://;
 | 
						|
                                $line =~ s/#$//;
 | 
						|
                                push @newlines, $line;
 | 
						|
                            }
 | 
						|
                        }
 | 
						|
 | 
						|
                        $deployparams = join ' ', @newlines;
 | 
						|
 | 
						|
                        if (open(NEWLIST, ">>", "$installdir/osimages/$osimage/kits/KIT_COMPONENTS.postinstall")) {
 | 
						|
                            if ($deployparams) {
 | 
						|
                                print NEWLIST "installroot=$rootimgdir otherpkgdir=$otherpkgdir $deployparams $installdir/postscripts/$kitcompscript\n";
 | 
						|
                            } else {
 | 
						|
                                print NEWLIST "installroot=$rootimgdir otherpkgdir=$otherpkgdir $installdir/postscripts/$kitcompscript\n";
 | 
						|
                            }
 | 
						|
                            close(NEWLIST);
 | 
						|
                        }
 | 
						|
                    }
 | 
						|
 | 
						|
                    my $match = 0;
 | 
						|
                    my @scripts = split ',', $linuximagetable->{postinstall};
 | 
						|
                    foreach my $script (@scripts) {
 | 
						|
                        if ($script =~ /KIT_COMPONENTS.postinstall/) {
 | 
						|
                            $match = 1;
 | 
						|
                            last;
 | 
						|
                        }
 | 
						|
                    }
 | 
						|
 | 
						|
                    if (!$match) {
 | 
						|
                        $linuximagetable->{postinstall} = $linuximagetable->{postinstall} . ",$installdir/osimages/$osimage/kits/KIT_COMPONENTS.postinstall";
 | 
						|
                    }
 | 
						|
                    $linuximagetable->{postinstall} =~ s/^,//;
 | 
						|
                }
 | 
						|
            }
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    # Adding postbootscrits to osimage.postbootscripts
 | 
						|
    if (!$::noscripts and $kitcomptable and $kitcomptable->{postbootscripts}) {
 | 
						|
        my @kitcompscripts = split ',', $kitcomptable->{postbootscripts};
 | 
						|
        foreach my $kitcompscript (@kitcompscripts) {
 | 
						|
 | 
						|
            my $formatedkitcomp = $kitcompscript;
 | 
						|
 | 
						|
            if ($osimagetable) {
 | 
						|
                if ($osimagetable->{postbootscripts}) {
 | 
						|
                    my $match = 0;
 | 
						|
                    my $added = 0;
 | 
						|
                    my @newscripts;
 | 
						|
                    my @scripts = split ',', $osimagetable->{postbootscripts};
 | 
						|
                    foreach my $script (@scripts) {
 | 
						|
                        if ($script =~ /^$formatedkitcomp$/) {
 | 
						|
                            $match = 1;
 | 
						|
                            last;
 | 
						|
                        }
 | 
						|
 | 
						|
                        if ($script !~ /^BASEXCAT_/ and $script !~ /^KIT_/) {
 | 
						|
                            unless ($added) {
 | 
						|
                                push @newscripts, $formatedkitcomp;
 | 
						|
                                $added = 1;
 | 
						|
                            }
 | 
						|
                        }
 | 
						|
 | 
						|
 | 
						|
                        push @newscripts, $script;
 | 
						|
 | 
						|
                    }
 | 
						|
 | 
						|
                    if ($match) {
 | 
						|
                        next;
 | 
						|
                    } elsif (!$added) {
 | 
						|
                        push @newscripts, $formatedkitcomp;
 | 
						|
                    }
 | 
						|
 | 
						|
                    my $osimagescripts = join ',', @newscripts;
 | 
						|
                    $osimagetable->{postbootscripts} = $osimagescripts;
 | 
						|
                } else {
 | 
						|
                    $osimagetable->{postbootscripts} = $formatedkitcomp;
 | 
						|
                }
 | 
						|
 | 
						|
            }
 | 
						|
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    # Adding kit component's repodir to osimage.otherpkgdir
 | 
						|
    if ($kitcomptable and $kitcomptable->{kitreponame}) {
 | 
						|
 | 
						|
        (my $kitrepotable) = $tabs->{kitrepo}->getAttribs({ kitreponame => $kitcomptable->{kitreponame} }, 'kitrepodir');
 | 
						|
        if ($kitrepotable and $kitrepotable->{kitrepodir}) {
 | 
						|
 | 
						|
            if ($linuximagetable and $linuximagetable->{otherpkgdir}) {
 | 
						|
                my $otherpkgdir = $linuximagetable->{otherpkgdir};
 | 
						|
 | 
						|
                #support mixed otherpkgdir http and local dir
 | 
						|
                $otherpkgdir = get_local_otherpkgdir($otherpkgdir);
 | 
						|
                my $kitrepodir = $kitrepotable->{kitrepodir};
 | 
						|
 | 
						|
                # Create otherpkgdir if it doesn't exist
 | 
						|
                unless (-d "$otherpkgdir") {
 | 
						|
                    mkpath("$otherpkgdir");
 | 
						|
                }
 | 
						|
 | 
						|
                # Consider the mixed environment
 | 
						|
                my $imagerhelflag = 0;
 | 
						|
                if ($osimagetable and $osimagetable->{osvers}) {
 | 
						|
                    if ($osimagetable->{osvers} =~ /rhel/) {
 | 
						|
                        $imagerhelflag = 1;
 | 
						|
                    }
 | 
						|
                }
 | 
						|
 | 
						|
 | 
						|
                if ($debianflag && $imagerhelflag)
 | 
						|
                {
 | 
						|
                    unless (-d "$otherpkgdir/$kitcomptable->{kitreponame}")
 | 
						|
                    {
 | 
						|
                        system("ln -sf $kitrepodir $otherpkgdir/$kitcomptable->{kitreponame} ");
 | 
						|
                    }
 | 
						|
                }
 | 
						|
 | 
						|
 | 
						|
                elsif ($debianflag)
 | 
						|
                {
 | 
						|
                    unless (-d "$otherpkgdir/$kitcomptable->{kitreponame}")
 | 
						|
                    {
 | 
						|
                        # system("mkdir -p $otherpkgdir/$kitcomptable->{kitreponame}");
 | 
						|
                        # print "mkdir -p $otherpkgdir/$kitcomptable->{kitreponame}";
 | 
						|
                        system("cp -Rf $kitrepodir $otherpkgdir/");
 | 
						|
                        print "cp -Rf $kitrepodir $otherpkgdir/";
 | 
						|
                    }
 | 
						|
                }
 | 
						|
                else
 | 
						|
                {
 | 
						|
                    # Create symlink if doesn't exist
 | 
						|
                    unless (-d "$otherpkgdir/$kitcomptable->{kitreponame}") {
 | 
						|
                        system("ln -sf $kitrepodir $otherpkgdir/$kitcomptable->{kitreponame} ");
 | 
						|
                    }
 | 
						|
                }
 | 
						|
            } else {
 | 
						|
                $callback->({ error => ["Cannot open linuximage table or otherpkgdir do not exist"], errorcode => [1] });
 | 
						|
                return 1;
 | 
						|
            }
 | 
						|
        } else {
 | 
						|
            $callback->({ error => ["Cannot open kit table or kitdir do not exist"], errorcode => [1] });
 | 
						|
            return 1;
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    # Adding kitcomponent.exlist to osimage.exlist
 | 
						|
    if ($kitcomptable and $kitcomptable->{exlist} and $kittable and $kittable->{kitdir}) {
 | 
						|
 | 
						|
        my @lines;
 | 
						|
        my $exlistfile = $kitcomptable->{exlist};
 | 
						|
        my $kitdir     = $kittable->{kitdir};
 | 
						|
 | 
						|
 | 
						|
        # Adding kit component exlist file to KIT_COMPONENTS.exlist file
 | 
						|
        mkpath("$installdir/osimages/$osimage/kits/");
 | 
						|
        if (-e "$installdir/osimages/$osimage/kits/KIT_COMPONENTS.exlist") {
 | 
						|
            if (open(EXLIST, "<", "$installdir/osimages/$osimage/kits/KIT_COMPONENTS.exlist")) {
 | 
						|
                @lines = <EXLIST>;
 | 
						|
                close(EXLIST);
 | 
						|
                if ($::VERBOSE) {
 | 
						|
                    $callback->({ data => ["\nReading kit component exlist file $installdir/osimages/$osimage/kits/KIT_COMPONENTS.exlist\n"] });
 | 
						|
                }
 | 
						|
            } else {
 | 
						|
                $callback->({ error => ["Could not open kit component exlist file $installdir/osimages/$osimage/kits/KIT_COMPONENTS.exlist"], errorcode => [1] });
 | 
						|
                return 1;
 | 
						|
            }
 | 
						|
        }
 | 
						|
        unless (grep(/^#INCLUDE:$kitdir\/other_files\/$exlistfile#$/, @lines)) {
 | 
						|
            if (open(NEWEXLIST, ">>", "$installdir/osimages/$osimage/kits/KIT_COMPONENTS.exlist")) {
 | 
						|
 | 
						|
                print NEWEXLIST "#INCLUDE:$kitdir/other_files/$exlistfile#\n";
 | 
						|
                close(NEWEXLIST);
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
        # Adding KIT_COMPONENTS.exlist file to osimage.exlist if not existing.
 | 
						|
        if ($linuximagetable) {
 | 
						|
            if ($linuximagetable->{exlist}) {
 | 
						|
                my $match = 0;
 | 
						|
                my @exlists = split ',', $linuximagetable->{exlist};
 | 
						|
                foreach my $exlist (@exlists) {
 | 
						|
                    if ($exlist =~ /^$installdir\/osimages\/$osimage\/kits\/KIT_COMPONENTS.exlist$/) {
 | 
						|
                        $match = 1;
 | 
						|
                        last;
 | 
						|
                    }
 | 
						|
                }
 | 
						|
                unless ($match) {
 | 
						|
                    $linuximagetable->{exlist} = $linuximagetable->{exlist} . ',' . "$installdir/osimages/$osimage/kits/KIT_COMPONENTS.exlist";
 | 
						|
                }
 | 
						|
            } else {
 | 
						|
                $linuximagetable->{exlist} = "$installdir/osimages/$osimage/kits/KIT_COMPONENTS.exlist";
 | 
						|
            }
 | 
						|
 | 
						|
        }
 | 
						|
 | 
						|
    }
 | 
						|
 | 
						|
    # Adding kitdeployparams to a otherpkglist file in osimage
 | 
						|
    my @kitdeployparams;
 | 
						|
    if ($kittable and $kittable->{kitdeployparams} and $kittable->{kitdir}) {
 | 
						|
 | 
						|
        # Creating kit deployparams file
 | 
						|
        my @lines;
 | 
						|
        mkpath("$installdir/osimages/$osimage/kits/");
 | 
						|
        if (-e "$installdir/osimages/$osimage/kits/KIT_DEPLOY_PARAMS.otherpkgs.pkglist") {
 | 
						|
            if (open(DEPLOYPARAM, "<", "$installdir/osimages/$osimage/kits/KIT_DEPLOY_PARAMS.otherpkgs.pkglist")) {
 | 
						|
                @lines = <DEPLOYPARAM>;
 | 
						|
                close(DEPLOYPARAM);
 | 
						|
                if ($::VERBOSE) {
 | 
						|
                    $callback->({ data => ["\nReading kit deployparams file $installdir/osimages/$osimage/kits/KIT_DEPLOY_PARAMS.otherpkgs.pkglist\n"] });
 | 
						|
                }
 | 
						|
            } else {
 | 
						|
                $callback->({ error => ["Could not open kit deployparams file $installdir/osimages/$osimage/kits/KIT_DEPLOY_PARAMS.otherpkgs.pkglist"], errorcode => [1] });
 | 
						|
                return 1;
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
        # Checking if the kit deployparams have been written in the generated kit deployparams file.
 | 
						|
        my @l;
 | 
						|
        my $matched = 0;
 | 
						|
        foreach my $line (@lines) {
 | 
						|
            chomp $line;
 | 
						|
            if ($line =~ m!$kittable->{kitdir}/other_files/$kittable->{kitdeployparams}!) {
 | 
						|
                $matched = 1;
 | 
						|
                last;
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
        unless ($matched) {
 | 
						|
            push @l, "#INCLUDE:$kittable->{kitdir}/other_files/$kittable->{kitdeployparams}#\n";
 | 
						|
        }
 | 
						|
 | 
						|
        # Write the missing lines to kit deployparams file
 | 
						|
        if (open(NEWDEPLOYPARAM, ">>", "$installdir/osimages/$osimage/kits/KIT_DEPLOY_PARAMS.otherpkgs.pkglist")) {
 | 
						|
            print NEWDEPLOYPARAM @l;
 | 
						|
            close(NEWDEPLOYPARAM);
 | 
						|
        }
 | 
						|
 | 
						|
        # Write this kit deployparams to osimage.otherpkglist if not existing.
 | 
						|
        if ($linuximagetable) {
 | 
						|
            if ($linuximagetable->{otherpkglist}) {
 | 
						|
                my $match = 0;
 | 
						|
                my @otherpkglists = split ',', $linuximagetable->{otherpkglist};
 | 
						|
                foreach my $otherpkglist (@otherpkglists) {
 | 
						|
                    if ($otherpkglist =~ /^$installdir\/osimages\/$osimage\/kits\/KIT_DEPLOY_PARAMS.otherpkgs.pkglist$/) {
 | 
						|
                        $match = 1;
 | 
						|
                        last;
 | 
						|
                    }
 | 
						|
                }
 | 
						|
                unless ($match) {
 | 
						|
                    $linuximagetable->{otherpkglist} = "$installdir/osimages/$osimage/kits/KIT_DEPLOY_PARAMS.otherpkgs.pkglist" . ',' . "$linuximagetable->{otherpkglist}";
 | 
						|
                }
 | 
						|
            } else {
 | 
						|
                $linuximagetable->{otherpkglist} = "$installdir/osimages/$osimage/kits/KIT_DEPLOY_PARAMS.otherpkgs.pkglist";
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
    }
 | 
						|
 | 
						|
    # Adding kit component basename to osimage.otherpkgs.pkglist
 | 
						|
    if ($kitcomptable and $kitcomptable->{basename} and $kitcomptable->{kitreponame}) {
 | 
						|
 | 
						|
        my @lines;
 | 
						|
        my $basename    = $kitcomptable->{basename};
 | 
						|
        my $kitreponame = $kitcomptable->{kitreponame};
 | 
						|
 | 
						|
        # Adding kit component basename to KIT_COMPONENTS.otherpkgs.pkglist file
 | 
						|
        mkpath("$installdir/osimages/$osimage/kits");
 | 
						|
        if (-e "$installdir/osimages/$osimage/kits/KIT_COMPONENTS.otherpkgs.pkglist") {
 | 
						|
            if (open(OTHERPKGLIST, "<", "$installdir/osimages/$osimage/kits/KIT_COMPONENTS.otherpkgs.pkglist")) {
 | 
						|
                @lines = <OTHERPKGLIST>;
 | 
						|
                close(OTHERPKGLIST);
 | 
						|
                if ($::VERBOSE) {
 | 
						|
                    $callback->({ data => ["\nReading kit component otherpkg file $installdir/osimages/$osimage/kits/KIT_COMPONENTS.otherpkgs.pkglist\n"] });
 | 
						|
                }
 | 
						|
            } else {
 | 
						|
                $callback->({ error => ["Could not open kit component otherpkg file $installdir/osimages/$osimage/kits/KIT_COMPONENTS.otherpkgs.pkglist"], errorcode => [1] });
 | 
						|
                return 1;
 | 
						|
            }
 | 
						|
        }
 | 
						|
        unless (grep(/^$kitreponame\/$basename$/, @lines)) {
 | 
						|
            if (open(NEWOTHERPKGLIST, ">", "$installdir/osimages/$osimage/kits/KIT_COMPONENTS.otherpkgs.pkglist")) {
 | 
						|
                if ($kitcomptable and $kitcomptable->{prerequisite}) {
 | 
						|
                    push @lines, "#NEW_INSTALL_LIST#\n";
 | 
						|
 | 
						|
                    if ($kittable and $kittable->{kitdeployparams} and $kittable->{kitdir}) {
 | 
						|
                        push @lines, "#INCLUDE:$kittable->{kitdir}/other_files/$kittable->{kitdeployparams}#\n";
 | 
						|
                    }
 | 
						|
                    push @lines, "$kitreponame/$kitcomptable->{prerequisite}\n";
 | 
						|
                    $::noupgrade = 1;
 | 
						|
                }
 | 
						|
 | 
						|
                # Check if this kitcomponent's kitcompdeps are in NEW_INSTALL_LIST or not.
 | 
						|
                # If so, set $::noupgrade to put this kitcomp in a new NEW_INSTALL_LIST
 | 
						|
                if ($kitcomptable and $kitcomptable->{kitcompdeps}) {
 | 
						|
                    check_newinstall($kitcomptable->{kitcompdeps}, @lines);
 | 
						|
                }
 | 
						|
 | 
						|
                if ($::noupgrade) {
 | 
						|
                    push @lines, "#NEW_INSTALL_LIST#\n";
 | 
						|
 | 
						|
                    if ($kittable and $kittable->{kitdeployparams} and $kittable->{kitdir}) {
 | 
						|
                        push @lines, "#INCLUDE:$kittable->{kitdir}/other_files/$kittable->{kitdeployparams}#\n";
 | 
						|
                    }
 | 
						|
 | 
						|
                    push @lines, "$kitreponame/$basename\n";
 | 
						|
                    print NEWOTHERPKGLIST @lines;
 | 
						|
                } else {
 | 
						|
                    print NEWOTHERPKGLIST "$kitreponame/$basename\n";
 | 
						|
                    print NEWOTHERPKGLIST @lines;
 | 
						|
                }
 | 
						|
 | 
						|
                close(NEWOTHERPKGLIST);
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
        # Write this kit component otherpkgs pkgfile to osimage.otherpkglist if not existing.
 | 
						|
        if ($linuximagetable) {
 | 
						|
            if ($linuximagetable->{otherpkglist}) {
 | 
						|
                my $match = 0;
 | 
						|
                my @otherpkglists = split ',', $linuximagetable->{otherpkglist};
 | 
						|
                foreach my $otherpkglist (@otherpkglists) {
 | 
						|
                    if ($otherpkglist =~ /^$installdir\/osimages\/$osimage\/kits\/KIT_COMPONENTS.otherpkgs.pkglist$/) {
 | 
						|
                        $match = 1;
 | 
						|
                        last;
 | 
						|
                    }
 | 
						|
                }
 | 
						|
                unless ($match) {
 | 
						|
                    $linuximagetable->{otherpkglist} = $linuximagetable->{otherpkglist} . ',' . "$installdir/osimages/$osimage/kits/KIT_COMPONENTS.otherpkgs.pkglist";
 | 
						|
                }
 | 
						|
            } else {
 | 
						|
                $linuximagetable->{otherpkglist} = "$installdir/osimages/$osimage/kits/KIT_COMPONENTS.otherpkgs.pkglist";
 | 
						|
            }
 | 
						|
 | 
						|
        }
 | 
						|
 | 
						|
        # Remove this component basename and pkgnames from KIT_RMPKGS.otherpkg.pkglist
 | 
						|
        my @lines = ();
 | 
						|
 | 
						|
        my @kitpkgdeps = split ',', $kitcomptable->{kitpkgdeps};
 | 
						|
 | 
						|
        # Remove prerequisite from KIT_RMPKGS.otherpkg.pkglist
 | 
						|
        if ($kitcomptable and $kitcomptable->{prerequisite}) {
 | 
						|
            my @kitpreps = split /,/, $kitcomptable->{prerequisite};
 | 
						|
            foreach my $kitprep (@kitpreps) {
 | 
						|
                push @kitpkgdeps, $kitprep;
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
        push @kitpkgdeps, $basename;
 | 
						|
 | 
						|
        my @l = ();
 | 
						|
        if (-e "$installdir/osimages/$osimage/kits/KIT_RMPKGS.otherpkgs.pkglist") {
 | 
						|
            if (open(RMOTHERPKGLIST, "<", "$installdir/osimages/$osimage/kits/KIT_RMPKGS.otherpkgs.pkglist")) {
 | 
						|
                @lines = <RMOTHERPKGLIST>;
 | 
						|
                close(RMOTHERPKGLIST);
 | 
						|
                if ($::VERBOSE) {
 | 
						|
                    $callback->({ data => ["\nReading kit component rmpkgs file $installdir/osimages/$osimage/kits/KIT_RMPKGS.otherpkgs.pkglist\n"] });
 | 
						|
                }
 | 
						|
            } else {
 | 
						|
                $callback->({ error => ["Could not open kit component rmpkgs file $installdir/osimages/$osimage/kits/KIT_RMPKGS.otherpkgs.pkglist"], errorcode => [1] });
 | 
						|
                return 1;
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
        my $changed = 0;
 | 
						|
        foreach my $line (@lines) {
 | 
						|
            chomp $line;
 | 
						|
            my $matched = 0;
 | 
						|
            foreach my $kitpkgdep (@kitpkgdeps) {
 | 
						|
                if ($line =~ /^-$kitpkgdep$/) {
 | 
						|
                    $matched = 1;
 | 
						|
                    $changed = 1;
 | 
						|
                    last;
 | 
						|
                }
 | 
						|
            }
 | 
						|
            if ($line =~ /^-prep_$basename$/) {
 | 
						|
                $matched = 1;
 | 
						|
                $changed = 1;
 | 
						|
            }
 | 
						|
            unless ($matched) {
 | 
						|
                push @l, "$line\n";
 | 
						|
            }
 | 
						|
 | 
						|
            my $lastline = pop @l;
 | 
						|
            while ($lastline =~ /^#NEW_INSTALL_LIST#$/) {
 | 
						|
                $lastline = pop @l;
 | 
						|
            }
 | 
						|
            push @l, $lastline if ($lastline);
 | 
						|
        }
 | 
						|
 | 
						|
        if ($changed) {
 | 
						|
            if (open(RMPKGLIST, ">", "$installdir/osimages/$osimage/kits/KIT_RMPKGS.otherpkgs.pkglist")) {
 | 
						|
                print RMPKGLIST @l;
 | 
						|
                close(RMPKGLIST);
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
    } else {
 | 
						|
        $callback->({ error => ["Could not open kit component table and read basename for kit component $kitcomp"], errorcode => [1] });
 | 
						|
        return 1;
 | 
						|
    }
 | 
						|
 | 
						|
    # Now writing kit component to osimage.kitcomponents
 | 
						|
    if ($::VERBOSE) {
 | 
						|
        $callback->({ data => ["\nAdding this kitcomponent to osimage.kitcomponents\n"] });
 | 
						|
    }
 | 
						|
    if ($osimagetable) {
 | 
						|
        if ($osimagetable->{kitcomponents}) {
 | 
						|
            $osimagetable->{kitcomponents} = join(',', $osimagetable->{kitcomponents}, $kitcomp);
 | 
						|
        } else {
 | 
						|
            $osimagetable->{kitcomponents} = $kitcomp;
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    # Adding driverpacks
 | 
						|
 | 
						|
    if ($linuximagetable and $linuximagetable->{driverupdatesrc}) {
 | 
						|
        if ($kitcomptable and $kitcomptable->{driverpacks}) {
 | 
						|
            my @driverpacks = split ',', $kitcomptable->{driverpacks};
 | 
						|
            my @driverupdatesrcs = split ',', $linuximagetable->{driverupdatesrc};
 | 
						|
 | 
						|
            my @newdriverupdatesrcs = @driverupdatesrcs;
 | 
						|
 | 
						|
            foreach my $driverpack (@driverpacks) {
 | 
						|
                my $matched = 0;
 | 
						|
                foreach my $driverupdatesrc (@driverupdatesrcs) {
 | 
						|
                    if ($driverpack eq $driverupdatesrc) {
 | 
						|
                        $matched = 1;
 | 
						|
                        last;
 | 
						|
                    }
 | 
						|
                }
 | 
						|
 | 
						|
                unless ($matched) {
 | 
						|
                    push @newdriverupdatesrcs, $driverpack;
 | 
						|
                }
 | 
						|
            }
 | 
						|
 | 
						|
            my $newdriverupdatesrc = join ',', @newdriverupdatesrcs;
 | 
						|
            $linuximagetable->{driverupdatesrc} = $newdriverupdatesrc;
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
 | 
						|
    # Write linuximage table with all the above udpates.
 | 
						|
    $tabs->{linuximage}->setAttribs({ imagename => $osimage }, \%{$linuximagetable});
 | 
						|
 | 
						|
    # Write osimage table with all the above udpates.
 | 
						|
    $tabs->{osimage}->setAttribs({ imagename => $osimage }, \%{$osimagetable});
 | 
						|
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
#-------------------------------------------------------
 | 
						|
 | 
						|
=head3 check_kit_config
 | 
						|
 | 
						|
  Check if this kit is suitable to add
 | 
						|
 | 
						|
=cut
 | 
						|
 | 
						|
#-------------------------------------------------------
 | 
						|
 | 
						|
sub check_kit_config
 | 
						|
{
 | 
						|
 | 
						|
    my $tabs        = shift;
 | 
						|
    my $kit         = shift;
 | 
						|
    my $kithash     = shift;
 | 
						|
    my $kitrepohash = shift;
 | 
						|
    my $kitcomphash = shift;
 | 
						|
 | 
						|
    #TODO:  add check to see the the attributes name are acceptable by xCAT DB.
 | 
						|
    #TODO: need to check if the files are existing or not, like exlist,
 | 
						|
 | 
						|
    unless (keys %{$kithash}) {
 | 
						|
        my %rsp;
 | 
						|
        push @{ $rsp{data} }, "Failed to add kit $kit because kit.conf is invalid";
 | 
						|
        xCAT::MsgUtils->message("E", \%rsp, $::CALLBACK);
 | 
						|
        return 1;
 | 
						|
    }
 | 
						|
 | 
						|
    if ($::INSPECTION) {
 | 
						|
        my %rsp;
 | 
						|
        push @{ $rsp{data} }, "kitname=$kithash->{kitname}";
 | 
						|
        push @{ $rsp{data} }, "    description=$kithash->{description}";
 | 
						|
        push @{ $rsp{data} }, "    version=$kithash->{version}";
 | 
						|
        push @{ $rsp{data} }, "    ostype=$kithash->{ostype}";
 | 
						|
        xCAT::MsgUtils->message("I", \%rsp, $::CALLBACK);
 | 
						|
        next;
 | 
						|
    }
 | 
						|
 | 
						|
    (my $ref1) = $tabs->{kit}->getAttribs({ kitname => $kithash->{kitname} }, 'basename');
 | 
						|
    if ($ref1 and $ref1->{'basename'}) {
 | 
						|
        my %rsp;
 | 
						|
        push @{ $rsp{data} }, "Failed to add kit $kithash->{kitname} because it is already existing";
 | 
						|
        xCAT::MsgUtils->message("E", \%rsp, $::CALLBACK);
 | 
						|
        return 1;
 | 
						|
    }
 | 
						|
 | 
						|
 | 
						|
    # Check if the kitcomponent is existing
 | 
						|
    my @kitcomps = $tabs->{kitcomponent}->getAllAttribs('kitcompname');
 | 
						|
    foreach my $kitcomp (@kitcomps) {
 | 
						|
        if ($kitcomp->{kitcompname}) {
 | 
						|
            foreach my $kitcompid (keys %{$kitcomphash}) {
 | 
						|
                if ($kitcomphash->{$kitcompid}->{kitcompname} and $kitcomphash->{$kitcompid}->{kitcompname} =~ /$kitcomp->{kitcompname}/) {
 | 
						|
                    my %rsp;
 | 
						|
                    push @{ $rsp{data} }, "Failed to add kitcomponent $kitcomp->{kitcompname} because it is already existing";
 | 
						|
                    xCAT::MsgUtils->message("E", \%rsp, $::CALLBACK);
 | 
						|
                    return 1;
 | 
						|
                }
 | 
						|
            }
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
#-------------------------------------------------------
 | 
						|
 | 
						|
=head3 read_kit_config
 | 
						|
 | 
						|
  Read kit configuration file
 | 
						|
 | 
						|
=cut
 | 
						|
 | 
						|
#-------------------------------------------------------
 | 
						|
 | 
						|
sub read_kit_config
 | 
						|
{
 | 
						|
 | 
						|
    my $fn    = shift;
 | 
						|
    my @lines = @$fn;
 | 
						|
 | 
						|
    my $sec;
 | 
						|
    my $kitname;
 | 
						|
    my $kitreponame;
 | 
						|
    my $kitcompname;
 | 
						|
    my $scripts;
 | 
						|
    my $kitrepoid = 0;
 | 
						|
    my $kitcompid = 0;
 | 
						|
 | 
						|
    my %kithash;
 | 
						|
    my %kitrepohash;
 | 
						|
    my %kitcomphash;
 | 
						|
 | 
						|
    foreach my $line (@lines) {
 | 
						|
 | 
						|
        # Read through each line of kit.conf.
 | 
						|
        my $key, $value;
 | 
						|
        chomp $line;
 | 
						|
        next if ($line =~ /^$/);
 | 
						|
        next if ($line =~ /^\s*#/);
 | 
						|
 | 
						|
        # Split the kit.conf to different parts: kit, kitrepo, kitcomponent.
 | 
						|
        if ($line =~ /kit:/) {
 | 
						|
            $sec = "KIT";
 | 
						|
            next;
 | 
						|
        } elsif ($line =~ /kitrepo:/) {
 | 
						|
            $sec       = "KITREPO";
 | 
						|
            $kitrepoid = $kitrepoid + 1;
 | 
						|
            next;
 | 
						|
        } elsif ($line =~ /kitcomponent:/) {
 | 
						|
            $sec       = "KITCOMPONENT";
 | 
						|
            $kitcompid = $kitcompid + 1;
 | 
						|
            next;
 | 
						|
        } else {
 | 
						|
            if ($line =~ /kitcompdeps/) {
 | 
						|
                $key   = $line;
 | 
						|
                $value = $line;
 | 
						|
                $key =~ s/\s+(\w+)\s+=.*$/$1/;
 | 
						|
                $key =~ s/\s+//g;
 | 
						|
                $value =~ s/$key\s+=(.*)$/$1/;
 | 
						|
                $key =~ s/\s+//g;
 | 
						|
                $value =~ s/\s+//g;
 | 
						|
            } else {
 | 
						|
                ($key, $value) = split(/=/, $line,2);
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
        # Remove spaces in each lines.
 | 
						|
        $key =~ s/^\s+|\s+$//g;
 | 
						|
        $value =~ s/^\s+|\s+$//g;
 | 
						|
 | 
						|
        # Add each attribute to different hash.
 | 
						|
        if ($sec =~ /KIT$/) {
 | 
						|
            $kithash{$key} = $value;
 | 
						|
        } elsif ($sec =~ /KITREPO$/) {
 | 
						|
            $kitrepohash{$kitrepoid}{$key} = $value;
 | 
						|
        } elsif ($sec =~ /KITCOMPONENT$/) {
 | 
						|
            if ($key =~ /postbootscripts/ or $key =~ /genimage_postinstall/) {
 | 
						|
                $scripts = $scripts . ',' . $value;
 | 
						|
                $kitcomphash{$kitcompid}{$key} = $value;
 | 
						|
            } else {
 | 
						|
                $kitcomphash{$kitcompid}{$key} = $value;
 | 
						|
            }
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    return (\%kithash, \%kitrepohash, \%kitcomphash, $scripts);
 | 
						|
 | 
						|
}
 | 
						|
 | 
						|
#-------------------------------------------------------
 | 
						|
 | 
						|
=head3 addkit
 | 
						|
 | 
						|
  Add Kits into xCAT
 | 
						|
 | 
						|
=cut
 | 
						|
 | 
						|
#-------------------------------------------------------
 | 
						|
sub addkit
 | 
						|
{
 | 
						|
    my $request         = shift;
 | 
						|
    my $callback        = shift;
 | 
						|
    my $request_command = shift;
 | 
						|
 | 
						|
    my $path;
 | 
						|
    my $rc;
 | 
						|
 | 
						|
    my $xusage = sub {
 | 
						|
        my %rsp;
 | 
						|
        push @{ $rsp{data} }, "Usage: addkit - Adds product software Kits to an xCAT cluster environment.";
 | 
						|
        push @{ $rsp{data} }, "\taddkit [-h|--help]";
 | 
						|
        push @{ $rsp{data} }, "\taddkit [-v|--version]";
 | 
						|
        push @{ $rsp{data} }, "\taddkit [-i|--inspection] <kitlist>]";
 | 
						|
        push @{ $rsp{data} }, "\taddkit [-V|--verbose] [-p|--path <path>] <kitlist>]";
 | 
						|
        xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
    };
 | 
						|
 | 
						|
    if ($^O ne 'linux') {
 | 
						|
        my $rsp = {};
 | 
						|
        push @{ $rsp->{data} }, "The addkit command is only supported on Linux.\n";
 | 
						|
        xCAT::MsgUtils->message("E", $rsp, $::CALLBACK);
 | 
						|
        return 1;
 | 
						|
    }
 | 
						|
 | 
						|
    unless (defined($request->{arg})) { $xusage->(1); return; }
 | 
						|
    @ARGV = @{ $request->{arg} };
 | 
						|
    if ($#ARGV == -1) {
 | 
						|
        $xusage->(1);
 | 
						|
        return;
 | 
						|
    }
 | 
						|
 | 
						|
    GetOptions(
 | 
						|
        'h|help'       => \$help,
 | 
						|
        'V|verbose'    => \$::VERBOSE,
 | 
						|
        'v|version'    => \$vers,
 | 
						|
        'i|inspection' => \$::INSPECTION,
 | 
						|
        'p|path=s'     => \$path,
 | 
						|
    );
 | 
						|
 | 
						|
    if ($help) {
 | 
						|
        $xusage->(0);
 | 
						|
        return;
 | 
						|
    }
 | 
						|
 | 
						|
    # Option -v for version
 | 
						|
    if (defined($vers)) {
 | 
						|
        create_version_response('addkit');
 | 
						|
        return 1;    # no usage - just exit
 | 
						|
    }
 | 
						|
 | 
						|
    my %tabs   = ();
 | 
						|
    my @tables = qw(kit kitrepo kitcomponent);
 | 
						|
    foreach my $t (@tables) {
 | 
						|
        $tabs{$t} = xCAT::Table->new($t, -create => 1, -autocommit => 1);
 | 
						|
 | 
						|
        if (!exists($tabs{$t})) {
 | 
						|
            my %rsp;
 | 
						|
            push @{ $rsp{data} }, "Could not open xCAT table $t";
 | 
						|
            xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
            return 1;
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    my $basename;
 | 
						|
    my $des = shift @ARGV;
 | 
						|
 | 
						|
    my @kits = split ',', $des;
 | 
						|
    my @kitnames;
 | 
						|
    my $hasplugin = 0;
 | 
						|
    foreach my $kit (@kits) {
 | 
						|
 | 
						|
        my $kitdir    = '';
 | 
						|
        my $kittmpdir = '';
 | 
						|
 | 
						|
        if ($kit =~ /NEED_PRODUCT_PKGS/) {
 | 
						|
            my %rsp;
 | 
						|
            push @{ $rsp{data} }, "Not allowed to add partial kit $kit";
 | 
						|
            xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
            return 1;
 | 
						|
        }
 | 
						|
 | 
						|
        # extract the Kit to kitdir
 | 
						|
        my $installdir = xCAT::TableUtils->getInstallDir();
 | 
						|
        unless ($installdir) {
 | 
						|
            $installdir = '/install';
 | 
						|
        }
 | 
						|
        $installdir =~ s/\/$//;
 | 
						|
 | 
						|
        my $dir = $request->{cwd};    #getcwd;
 | 
						|
        $dir = $dir->[0];
 | 
						|
 | 
						|
        unless (-r $kit) {
 | 
						|
            $kit = "$dir/$kit";
 | 
						|
        }
 | 
						|
 | 
						|
        unless (-r $kit) {
 | 
						|
            my %rsp;
 | 
						|
            push @{ $rsp{data} }, "Can not find $kit";
 | 
						|
            xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
            return 1;
 | 
						|
        }
 | 
						|
 | 
						|
 | 
						|
        if (-d "$kit") {
 | 
						|
 | 
						|
            # This is a directory.
 | 
						|
            # TODO: check if this is a valid kit directory.
 | 
						|
 | 
						|
            $kittmpdir = $kit;
 | 
						|
        } else {
 | 
						|
 | 
						|
            # should be a tar.bz2 file
 | 
						|
 | 
						|
            system("rm -rf /tmp/tmpkit/");
 | 
						|
            mkpath("/tmp/tmpkit/");
 | 
						|
 | 
						|
            if ($::VERBOSE) {
 | 
						|
                my %rsp;
 | 
						|
                push @{ $rsp{data} }, "Extract Kit $kit to /tmp/tmpkit";
 | 
						|
                xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
            }
 | 
						|
 | 
						|
            #support white space in the dir name
 | 
						|
            $kit =~ s/(\s)/\\$1/g;
 | 
						|
 | 
						|
            $rc = system("tar jxvf $kit -C /tmp/tmpkit/");
 | 
						|
 | 
						|
            opendir($dir, "/tmp/tmpkit/");
 | 
						|
            my @files = readdir($dir);
 | 
						|
 | 
						|
            foreach my $file (@files) {
 | 
						|
                next if ($file eq '.' || $file eq '..');
 | 
						|
                $kittmpdir = "/tmp/tmpkit/$file";
 | 
						|
                last;
 | 
						|
            }
 | 
						|
 | 
						|
            if (!$kittmpdir) {
 | 
						|
                my %rsp;
 | 
						|
                push @{ $rsp{data} }, "Could not find extracted kit.conf in /tmp/tmpkit";
 | 
						|
                xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                return 1;
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
 | 
						|
        if ($rc) {
 | 
						|
            my %rsp;
 | 
						|
            push @{ $rsp{data} }, "Failed to extract kit.conf from $kit, (Maybe there was no space left?)";
 | 
						|
            xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
            return 1;
 | 
						|
        }
 | 
						|
 | 
						|
 | 
						|
        # Read kit info from kit.conf
 | 
						|
        my @lines;
 | 
						|
        if (open(KITCONF, "<$kittmpdir/$kitconf")) {
 | 
						|
            @lines = <KITCONF>;
 | 
						|
            close(KITCONF);
 | 
						|
            if ($::VERBOSE) {
 | 
						|
                my %rsp;
 | 
						|
                push @{ $rsp{data} }, "Reading kit configuration file $kittmpdir/$kitconf";
 | 
						|
                xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
            }
 | 
						|
        } else {
 | 
						|
            my %rsp;
 | 
						|
            push @{ $rsp{data} }, "Could not open kit configuration file $kittmpdir/$kitconf";
 | 
						|
            xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
            return 1;
 | 
						|
        }
 | 
						|
 | 
						|
 | 
						|
        #
 | 
						|
        # check contents of kit.conf to make sure the framework
 | 
						|
        #       is compatible with this codes framework
 | 
						|
        if (&check_framework(\@lines)) {
 | 
						|
            return 1;
 | 
						|
        }
 | 
						|
 | 
						|
        # Read kit configuration file
 | 
						|
        my ($kithash, $kitrepohash, $kitcomphash, $scripts) = read_kit_config(\@lines);
 | 
						|
 | 
						|
        # Check if this kit is allowed to add.
 | 
						|
        if (&check_kit_config(\%tabs, $kit, $kithash, $kitrepohash, $kitcomphash)) {
 | 
						|
            return 1;
 | 
						|
        }
 | 
						|
 | 
						|
        my %rsp;
 | 
						|
        push @{ $rsp{data} }, "Adding Kit $kithash->{kitname}";
 | 
						|
        xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
 | 
						|
        # Moving kits from tmp directory to kitdir
 | 
						|
        if (!$path) {
 | 
						|
            $kitdir = $installdir . "/kits";
 | 
						|
        } else {
 | 
						|
            $kitdir = $path;
 | 
						|
        }
 | 
						|
 | 
						|
        $kitdir =~ s/\/$//;
 | 
						|
        $kitdir = $kitdir . "/" . $kithash->{kitname};
 | 
						|
 | 
						|
        if ($::VERBOSE) {
 | 
						|
            my %rsp;
 | 
						|
            push @{ $rsp{data} }, "Create Kit directory $kitdir";
 | 
						|
            xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
        }
 | 
						|
        mkpath($kitdir);
 | 
						|
 | 
						|
        # Set kitdir and kitrepodir
 | 
						|
        $kithash->{kitdir} = $kitdir;
 | 
						|
 | 
						|
        foreach my $kitrepoid (keys %{$kitrepohash}) {
 | 
						|
            $kitrepohash->{$kitrepoid}->{kitrepodir} = $kitdir . "/repos/" . $kitrepohash->{$kitrepoid}->{kitreponame};
 | 
						|
        }
 | 
						|
 | 
						|
        if ($::VERBOSE) {
 | 
						|
            my %rsp;
 | 
						|
            push @{ $rsp{data} }, "Copying Kit from $kittmpdir to $kitdir";
 | 
						|
            xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
            $rc = system("cp -rfv $kittmpdir/* $kitdir");
 | 
						|
        } else {
 | 
						|
            $rc = system("cp -rf $kittmpdir/* $kitdir");
 | 
						|
        }
 | 
						|
 | 
						|
        # Coying scripts to /installdir/postscripts/
 | 
						|
        if ($::VERBOSE) {
 | 
						|
            my %rsp;
 | 
						|
            push @{ $rsp{data} }, "Copying kit scripts from $kitdir/other_files/ to $installdir/postscripts";
 | 
						|
            xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
        }
 | 
						|
 | 
						|
        my @script = split ',', $scripts;
 | 
						|
        foreach (@script) {
 | 
						|
            next unless ($_);
 | 
						|
            if ($::VERBOSE) {
 | 
						|
                $rc = system("cp -rfv $kitdir/other_files/$_ $installdir/postscripts/");
 | 
						|
            } else {
 | 
						|
                $rc = system("cp -rf $kitdir/other_files/$_ $installdir/postscripts/");
 | 
						|
            }
 | 
						|
            if ($rc && !-e "$installdir/postscripts/$_") {
 | 
						|
                my %rsp;
 | 
						|
                push @{ $rsp{data} }, "Failed to copy scripts from $kitdir/scripts/ to $installdir/postscripts";
 | 
						|
                xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                return 1;
 | 
						|
            }
 | 
						|
            $rc = 0;
 | 
						|
            chmod(0755, "$installdir/postscripts/$_");
 | 
						|
        }
 | 
						|
 | 
						|
        # Copying plugins to /opt/xcat/lib/perl/xCAT_plugin/
 | 
						|
        if (-d "$kitdir/plugins/") {
 | 
						|
 | 
						|
            chmod(644, "$kitdir/plugins/*");
 | 
						|
 | 
						|
            opendir($dir, "$kitdir/plugins/");
 | 
						|
            if (grep { ($_ ne '.') && ($_ ne '..') } readdir($dir)) {
 | 
						|
                if ($::VERBOSE) {
 | 
						|
                    my %rsp;
 | 
						|
                    push @{ $rsp{data} }, "Copying kit plugins from $kitdir/plugins/ to $::XCATROOT/lib/perl/xCAT_plugin";
 | 
						|
                    xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
 | 
						|
                    $rc = system("cp -rfv $kitdir/plugins/* $::XCATROOT/lib/perl/xCAT_plugin/");
 | 
						|
                } else {
 | 
						|
                    $rc = system("cp -rf $kitdir/plugins/* $::XCATROOT/lib/perl/xCAT_plugin/");
 | 
						|
                }
 | 
						|
 | 
						|
                $hasplugin = 1;
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
        if ($rc) {
 | 
						|
            my %rsp;
 | 
						|
            push @{ $rsp{data} }, "Failed to copy plugins from $kitdir/plugins/ to $::XCATROOT/lib/perl/xCAT_plugin";
 | 
						|
            xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
            return 1;
 | 
						|
        }
 | 
						|
 | 
						|
        # Write to DB
 | 
						|
        if ($::VERBOSE) {
 | 
						|
            my %rsp;
 | 
						|
            push @{ $rsp{data} }, "Writing kit configuration into xCAT DB";
 | 
						|
            xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
        }
 | 
						|
 | 
						|
        $rc = $tabs{kit}->setAttribs({ kitname => $kithash->{kitname} }, $kithash);
 | 
						|
        if ($rc) {
 | 
						|
            my %rsp;
 | 
						|
            push @{ $rsp{data} }, "Failed to write kit object into xCAT DB";
 | 
						|
            xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
            return 1;
 | 
						|
        }
 | 
						|
 | 
						|
        foreach my $kitrepoid (keys %{$kitrepohash}) {
 | 
						|
            $rc = $tabs{kitrepo}->setAttribs({ kitreponame => $kitrepohash->{$kitrepoid}->{kitreponame} }, \%{ $kitrepohash->{$kitrepoid} });
 | 
						|
            if ($rc) {
 | 
						|
                my %rsp;
 | 
						|
                push @{ $rsp{data} }, "Failed to write kitrepo $kitrepohash->{$kitrepoid}->{kitreponame} into xCAT DB";
 | 
						|
                xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                return 1;
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
        foreach my $kitcompid (keys %{$kitcomphash}) {
 | 
						|
            $rc = $tabs{kitcomponent}->setAttribs({ kitcompname => $kitcomphash->{$kitcompid}->{kitcompname} }, \%{ $kitcomphash->{$kitcompid} });
 | 
						|
            if ($rc) {
 | 
						|
                my %rsp;
 | 
						|
                push @{ $rsp{data} }, "Failed to write kitcomponent $kitcomphash->{$kitcompid}->{kitcompname} xCAT DB";
 | 
						|
                xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                return 1;
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
        push @kitnames, $kithash->{kitname};
 | 
						|
    }
 | 
						|
 | 
						|
    unless ($::INSPECTION) {
 | 
						|
        my $kitlist = join ',', @kitnames;
 | 
						|
        my %rsp;
 | 
						|
        push @{ $rsp{data} }, "Kit $kitlist was successfully added.";
 | 
						|
        xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
 | 
						|
        if ($hasplugin) {
 | 
						|
 | 
						|
            # Issue rescanplugins to have xcatd load the new plugins
 | 
						|
            xCAT::Utils->runxcmd({ command => ['rescanplugins'], },
 | 
						|
                $request_command, 0, 1);
 | 
						|
 | 
						|
        }
 | 
						|
    }
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
#-------------------------------------------------------
 | 
						|
 | 
						|
=head3 rmkit
 | 
						|
 | 
						|
  Remove Kits from xCAT
 | 
						|
 | 
						|
=cut
 | 
						|
 | 
						|
#-------------------------------------------------------
 | 
						|
sub rmkit
 | 
						|
{
 | 
						|
    my $request         = shift;
 | 
						|
    my $callback        = shift;
 | 
						|
    my $request_command = shift;
 | 
						|
    my $kitdir;
 | 
						|
    my $rc;
 | 
						|
 | 
						|
    my $xusage = sub {
 | 
						|
        my %rsp;
 | 
						|
        push @{ $rsp{data} }, "Usage: rmkit - Remove Kits from xCAT.";
 | 
						|
        push @{ $rsp{data} }, "\trmkit [-h|--help]";
 | 
						|
        push @{ $rsp{data} }, "\trmkit [-v|--version]";
 | 
						|
        push @{ $rsp{data} }, "\trmkit [-V|--verbose] [-f|--force] [-t|--test] <kitlist>]";
 | 
						|
        xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
    };
 | 
						|
 | 
						|
    if ($^O ne 'linux') {
 | 
						|
        my $rsp = {};
 | 
						|
        push @{ $rsp->{data} }, "The rmkit command is only supported on Linux.\n";
 | 
						|
        xCAT::MsgUtils->message("E", $rsp, $::CALLBACK);
 | 
						|
        return 1;
 | 
						|
    }
 | 
						|
 | 
						|
    unless (defined($request->{arg})) { $xusage->(1); return; }
 | 
						|
    @ARGV = @{ $request->{arg} };
 | 
						|
    if ($#ARGV == -1) {
 | 
						|
        $xusage->(1);
 | 
						|
        return;
 | 
						|
    }
 | 
						|
 | 
						|
 | 
						|
    GetOptions(
 | 
						|
        'h|help'    => \$help,
 | 
						|
        'V|verbose' => \$::VERBOSE,
 | 
						|
        'v|version' => \$vers,
 | 
						|
        't|test'    => \$test,
 | 
						|
        'f|force'   => \$force
 | 
						|
    );
 | 
						|
 | 
						|
    # Option -v for version
 | 
						|
    if (defined($vers)) {
 | 
						|
        create_version_response('rmkit');
 | 
						|
        return 1;    # no usage - just exit
 | 
						|
    }
 | 
						|
 | 
						|
    if ($help) {
 | 
						|
        $xusage->(0);
 | 
						|
        return;
 | 
						|
    }
 | 
						|
 | 
						|
    my %tabs   = ();
 | 
						|
    my @tables = qw(kit kitrepo kitcomponent osimage);
 | 
						|
    foreach my $t (@tables) {
 | 
						|
        $tabs{$t} = xCAT::Table->new($t, -create => 1, -autocommit => 1);
 | 
						|
 | 
						|
        if (!exists($tabs{$t})) {
 | 
						|
            my %rsp;
 | 
						|
            push @{ $rsp{data} }, "Could not open xCAT table $t";
 | 
						|
            xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
            return 1;
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    # Convert to kitname if input is a basename
 | 
						|
    my %kitnames;
 | 
						|
    my $des    = shift @ARGV;
 | 
						|
    my @kits   = split ',', $des;
 | 
						|
    my $DBname = xCAT::Utils->get_DBName;    # support for DB2
 | 
						|
    foreach my $kit (@kits) {
 | 
						|
 | 
						|
        # Check if it is a kitname or basename
 | 
						|
 | 
						|
        (my $ref1) = $tabs{kit}->getAttribs({ kitname => $kit }, 'basename', 'isinternal');
 | 
						|
        if ($ref1 and $ref1->{'basename'}) {
 | 
						|
            if ($ref1->{'isinternal'} and !$force) {
 | 
						|
                my %rsp;
 | 
						|
                push @{ $rsp{data} }, "Kit $kit with isinterval attribute cannot be removed";
 | 
						|
                xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                return 1;
 | 
						|
            }
 | 
						|
            $kitnames{$kit} = 1;
 | 
						|
        } else {
 | 
						|
            my @entries;
 | 
						|
            if ($DBname =~ /^DB2/) {
 | 
						|
                @entries = $tabs{kit}->getAllAttribsWhere("\"basename\" = '$kit'", 'kitname', 'isinternal');
 | 
						|
            } else {
 | 
						|
                @entries = $tabs{kit}->getAllAttribsWhere("basename = '$kit'", 'kitname', 'isinternal');
 | 
						|
            }
 | 
						|
            unless (@entries) {
 | 
						|
                my %rsp;
 | 
						|
                push @{ $rsp{data} }, "Kit $kit could not be found in DB $t";
 | 
						|
                xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                return 1;
 | 
						|
            }
 | 
						|
            foreach my $entry (@entries) {
 | 
						|
                if ($entry->{'isinternal'} and !$force) {
 | 
						|
                    my %rsp;
 | 
						|
                    push @{ $rsp{data} }, "Kit $entry->{kitname} with isinterval attribute cannot be remoed";
 | 
						|
                    xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                    return 1;
 | 
						|
                }
 | 
						|
                $kitnames{ $entry->{kitname} } = 1;
 | 
						|
            }
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    # Remove each kit
 | 
						|
    my @entries = $tabs{'osimage'}->getAllAttribs('imagename', 'kitcomponents');
 | 
						|
    my @kitlist;
 | 
						|
    my $hasplugin;
 | 
						|
    my @kpinuse;
 | 
						|
 | 
						|
    foreach my $kitname (keys %kitnames) {
 | 
						|
 | 
						|
        if (!$test) {
 | 
						|
            my %rsp;
 | 
						|
            push @{ $rsp{data} }, "Removing kit $kitname";
 | 
						|
            xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
        }
 | 
						|
 | 
						|
        # Remove osimage.kitcomponents.
 | 
						|
 | 
						|
        # Find all the components in this kit.
 | 
						|
        my $kitcompnames;
 | 
						|
        my @kitcomphash;
 | 
						|
        if ($DBname =~ /^DB2/) {
 | 
						|
            @kitcomphash = $tabs{kitcomponent}->getAllAttribsWhere("\"kitname\" = '$kitname'", 'kitcompname', 'postbootscripts', 'genimage_postinstall');
 | 
						|
        } else {
 | 
						|
            @kitcomphash = $tabs{kitcomponent}->getAllAttribsWhere("kitname = '$kitname'", 'kitcompname', 'postbootscripts', 'genimage_postinstall');
 | 
						|
        }
 | 
						|
        if (@entries && (@entries > 0)) {
 | 
						|
 | 
						|
            if ($::VERBOSE and !$test) {
 | 
						|
                my %rsp;
 | 
						|
                push @{ $rsp{data} }, "Removing kit components from osimage.kitcomponents";
 | 
						|
                xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
            }
 | 
						|
 | 
						|
            foreach my $entry (@entries) {
 | 
						|
 | 
						|
                # Check osimage.kitcomponents
 | 
						|
                my @kitcomponents = split ',', $entry->{kitcomponents};
 | 
						|
                foreach my $kitcomponent (@kitcomponents) {
 | 
						|
                    chomp $kitcomponent;
 | 
						|
 | 
						|
                    # Compare with each component in osimage.kitcomponents list.
 | 
						|
                    foreach my $kitcomp (@kitcomphash) {
 | 
						|
                        my $kitcompname = $kitcomp->{kitcompname};
 | 
						|
 | 
						|
                        # Remove this component from osimage.kitcomponents if -f option.
 | 
						|
                        if ("$kitcompname" =~ /^$kitcomponent$/) {
 | 
						|
                            if ($test) {
 | 
						|
                                push @kpinuse, $kitcomponent;
 | 
						|
                                my %rsp;
 | 
						|
                                push @{ $rsp{data} }, "$kitcomponent is being used by osimage $entry->{imagename}";
 | 
						|
                                xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
                                next;
 | 
						|
                            }
 | 
						|
                            unless ($force) {
 | 
						|
                                my %rsp;
 | 
						|
                                push @{ $rsp{data} }, "Failed to remove kit component $kitcomponent because:$kitcomponent is being used by osimage $entry->{imagename}";
 | 
						|
                                xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                                return 1;
 | 
						|
                            }
 | 
						|
 | 
						|
                            # Remove this component from osimage.kitcomponents. Mark here.
 | 
						|
                            my $ret = xCAT::Utils->runxcmd({ command => ['rmkitcomp'], arg => [ '-f', '-i', $entry->{imagename}, $kitcompname ] }, $request_command, 0, 1);
 | 
						|
                            if ($::RUNCMD_RC) {
 | 
						|
                                my %rsp;
 | 
						|
                                push @{ $rsp{data} }, "Failed to remove kit component $kitcomponent from $entry->{imagename}";
 | 
						|
                                xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                                return 1;
 | 
						|
                            }
 | 
						|
                        }
 | 
						|
                    }
 | 
						|
                }
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
        if ($test) {
 | 
						|
            next;
 | 
						|
        }
 | 
						|
 | 
						|
        my $kitdir;
 | 
						|
        (my $ref1) = $tabs{kit}->getAttribs({ kitname => $kitname }, 'kitdir');
 | 
						|
        if ($ref1 and $ref1->{'kitdir'}) {
 | 
						|
 | 
						|
            $kitdir = $ref1->{'kitdir'};
 | 
						|
            chomp $kitdir;
 | 
						|
 | 
						|
            # remove kit plugins from /opt/xcat/lib/perl/xCAT_plugin
 | 
						|
            if ($::VERBOSE) {
 | 
						|
                my %rsp;
 | 
						|
                push @{ $rsp{data} }, "Removing kit plugins from $::XCATROOT/lib/perl/xCAT_plugin/";
 | 
						|
                xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
            }
 | 
						|
 | 
						|
            opendir($dir, $kitdir . "/plugins");
 | 
						|
            my @files = readdir($dir);
 | 
						|
            if (grep { ($_ ne '.') && ($_ ne '..') } @files) {
 | 
						|
                $hasplugin = 1;
 | 
						|
            }
 | 
						|
            foreach my $file (@files) {
 | 
						|
                if ($file eq '.' or $file eq '..') { next; }
 | 
						|
                if (-e "$::XCATROOT/lib/perl/xCAT_plugin/$file") {
 | 
						|
                    if ($::VERBOSE) {
 | 
						|
                        system("rm -rfv $::XCATROOT/lib/perl/xCAT_plugin/$file");
 | 
						|
                    } else {
 | 
						|
                        system("rm -rf $::XCATROOT/lib/perl/xCAT_plugin/$file");
 | 
						|
                    }
 | 
						|
                }
 | 
						|
            }
 | 
						|
 | 
						|
 | 
						|
            if ($::VERBOSE) {
 | 
						|
                my %rsp;
 | 
						|
                push @{ $rsp{data} }, "Removing kit scripts from /install/postscripts/";
 | 
						|
                xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
            }
 | 
						|
 | 
						|
            # remove kit scripts from /install/postscripts/
 | 
						|
            my $installdir = xCAT::TableUtils->getInstallDir();
 | 
						|
            unless ($installdir) {
 | 
						|
                $installdir = '/install';
 | 
						|
            }
 | 
						|
            $installdir =~ s/\/$//;
 | 
						|
 | 
						|
            my $scripts;
 | 
						|
            foreach my $kitcomp (@kitcomphash) {
 | 
						|
                $scripts = $scripts . "," . $kitcomp->{postbootscripts} if ($kitcomp->{postbootscripts});
 | 
						|
                $scripts = $scripts . "," . $kitcomp->{genimage_postinstall} if ($kitcomp->{genimage_postinstall});
 | 
						|
            }
 | 
						|
            $scripts =~ s/^,//;
 | 
						|
            my @files = split /,/, $scripts;
 | 
						|
            foreach my $file (@files) {
 | 
						|
                if ($file eq '.' or $file eq '..') { next; }
 | 
						|
                if (-e "$installdir/postscripts/$file") {
 | 
						|
                    if ($::VERBOSE) {
 | 
						|
                        system("rm -rfv $installdir/postscripts/$file");
 | 
						|
                    } else {
 | 
						|
                        system("rm -rf $installdir/postscripts/$file");
 | 
						|
                    }
 | 
						|
                }
 | 
						|
            }
 | 
						|
 | 
						|
            # remove kitdir from /install/kits/
 | 
						|
            if ($::VERBOSE) {
 | 
						|
                my %rsp;
 | 
						|
                push @{ $rsp{data} }, "Removing kitdir from installdir";
 | 
						|
                xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
                system("rm -rfv $kitdir");
 | 
						|
            } else {
 | 
						|
                system("rm -rf $kitdir");
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
 | 
						|
        if ($::VERBOSE) {
 | 
						|
            my %rsp;
 | 
						|
            push @{ $rsp{data} }, "Removing kit from xCAT DB";
 | 
						|
            xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
        }
 | 
						|
 | 
						|
        # Remove kitcomponent
 | 
						|
        foreach my $kitcomp (@kitcomphash) {
 | 
						|
            my $kitcompname = $kitcomp->{kitcompname};
 | 
						|
            $tabs{kitcomponent}->delEntries({ kitcompname => $kitcompname });
 | 
						|
        }
 | 
						|
 | 
						|
        # Remove kitrepo
 | 
						|
        my @kitrepohash;
 | 
						|
        if ($DBname =~ /^DB2/) {
 | 
						|
            @kitrepohash = $tabs{kitrepo}->getAllAttribsWhere("\"kitname\" = '$kitname'", 'kitreponame');
 | 
						|
        } else {
 | 
						|
            @kitrepohash = $tabs{kitrepo}->getAllAttribsWhere("kitname = '$kitname'", 'kitreponame');
 | 
						|
        }
 | 
						|
        foreach my $kitrepo (@kitrepohash) {
 | 
						|
            my $kitreponame = $kitrepo->{kitreponame};
 | 
						|
            $tabs{kitrepo}->delEntries({ kitreponame => $kitreponame });
 | 
						|
        }
 | 
						|
 | 
						|
        # Remove kit
 | 
						|
        $tabs{kit}->delEntries({ kitname => $kitname });
 | 
						|
 | 
						|
        push @kitlist, $kitname;
 | 
						|
 | 
						|
    }
 | 
						|
 | 
						|
    if ($test) {
 | 
						|
        if (scalar(@kpinuse)) {
 | 
						|
            my $kp = join ',', @kpinuse;
 | 
						|
            my %rsp;
 | 
						|
            push @{ $rsp{data} }, "Following kitcomponents are in use: $kp";
 | 
						|
            xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
        } else {
 | 
						|
            my %rsp;
 | 
						|
            push @{ $rsp{data} }, "No kitcomponents are in use";
 | 
						|
            xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
        }
 | 
						|
        return 0;
 | 
						|
    }
 | 
						|
 | 
						|
    my $kits = join ',', @kitlist;
 | 
						|
    my %rsp;
 | 
						|
    push @{ $rsp{data} }, "Kit $kits was successfully removed.";
 | 
						|
    xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
 | 
						|
    if ($hasplugin) {
 | 
						|
 | 
						|
        # Issue rescanplugins to have xcatd load the new plugins
 | 
						|
        xCAT::Utils->runxcmd({ command => ['rescanplugins'], },
 | 
						|
            $request_command, 0, 1);
 | 
						|
    }
 | 
						|
 | 
						|
}
 | 
						|
 | 
						|
sub check_minorversion
 | 
						|
{
 | 
						|
    my $kitminor = shift;
 | 
						|
    my $osminor = shift;
 | 
						|
 | 
						|
    if ($kitminor eq $osminor) {
 | 
						|
        return 0;
 | 
						|
    }
 | 
						|
 | 
						|
    if (($kitminor =~ />/) || ($kitminor =~ /</) || ($kitminor =~ /==/)) {
 | 
						|
        if (eval ($osminor. $kitminor)) {
 | 
						|
            return 0;
 | 
						|
        }
 | 
						|
    }
 | 
						|
    return 1;
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
#-------------------------------------------------------
 | 
						|
 | 
						|
=head3 validate_os
 | 
						|
 | 
						|
  Validate if the input OS fit to the osimage or not.
 | 
						|
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------
 | 
						|
 | 
						|
sub validate_os {
 | 
						|
 | 
						|
    my $os      = shift;
 | 
						|
    my $osimage = shift;
 | 
						|
    my $kitcomp = shift;
 | 
						|
 | 
						|
    # Validate each attribute in kitcomp.
 | 
						|
    my $catched = 0;
 | 
						|
    my @osbasename = split ',', $kitcomp->{osbasename};
 | 
						|
    foreach (@osbasename) {
 | 
						|
        if ($osimage->{basename} eq $_) {
 | 
						|
            $catched = 1;
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    unless ($catched) {
 | 
						|
 | 
						|
        #        my %rsp;
 | 
						|
        #        push@{ $rsp{data} }, "osimage $os is not compatible with kit component $kitcomp->{kitcompname} with attribute OS";
 | 
						|
        #        xCAT::MsgUtils->message( "E", \%rsp, $::CALLBACK );
 | 
						|
        return 1;
 | 
						|
    }
 | 
						|
 | 
						|
    if ($osimage->{majorversion} ne $kitcomp->{osmajorversion}) {
 | 
						|
 | 
						|
        #        my %rsp;
 | 
						|
        #        push@{ $rsp{data} }, "osimage $os is not compatible with kit component $kitcomp->{kitcompname} with attribute majorversion";
 | 
						|
        #        xCAT::MsgUtils->message( "E", \%rsp, $::CALLBACK );
 | 
						|
        return 1;
 | 
						|
    }
 | 
						|
 | 
						|
    if ($kitcomp->{osminorversion}) {
 | 
						|
        if (check_minorversion($kitcomp->{osminorversion}, $osimage->{minorversion}))
 | 
						|
        {
 | 
						|
            return 1;
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    if ($osimage->{arch} ne $kitcomp->{osarch} && $kitcomp->{osarch} ne 'noarch') {
 | 
						|
 | 
						|
        #        my %rsp;
 | 
						|
        #        push@{ $rsp{data} }, "osimage $os is not compatible with kit component $kitcomp->{kitcompname} with attribute arch";
 | 
						|
        #        xCAT::MsgUtils->message( "E", \%rsp, $::CALLBACK );
 | 
						|
        return 1;
 | 
						|
    }
 | 
						|
 | 
						|
    if ($osimage->{type} ne $kitcomp->{ostype}) {
 | 
						|
 | 
						|
        #        my %rsp;
 | 
						|
        #        push@{ $rsp{data} }, "osimage $os is not compatible with kit component $kitcomp->{kitcompname} with attribute type";
 | 
						|
        #        xCAT::MsgUtils->message( "E", \%rsp, $::CALLBACK );
 | 
						|
        return 1;
 | 
						|
    }
 | 
						|
    if ($osimage->{serverrole}) {
 | 
						|
        my $match               = 0;
 | 
						|
        my @os_serverroles      = split /,/, $osimage->{serverrole};
 | 
						|
        my @kitcomp_serverroles = split /,/, $kitcomp->{serverroles};
 | 
						|
        foreach my $os_serverrole (@os_serverroles) {
 | 
						|
            foreach my $kitcomp_serverrole (@kitcomp_serverroles) {
 | 
						|
                if ($os_serverrole eq $kitcomp_serverrole) {
 | 
						|
                    $match = 1;
 | 
						|
                    last;
 | 
						|
                }
 | 
						|
            }
 | 
						|
 | 
						|
            if ($match) {
 | 
						|
                last;
 | 
						|
            }
 | 
						|
        }
 | 
						|
        if (!$match) {
 | 
						|
 | 
						|
            #            my %rsp;
 | 
						|
            #            push@{ $rsp{data} }, "osimage $os is not compatible with kit component $kitcomp->{kitcompname} with attribute serverrole";
 | 
						|
            #            xCAT::MsgUtils->message( "E", \%rsp, $::CALLBACK );
 | 
						|
            return 1;
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
 | 
						|
    return 0;
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
#-------------------------------------------------------
 | 
						|
 | 
						|
=head3 addkitcomp
 | 
						|
 | 
						|
  Assign Kit component to osimage
 | 
						|
 | 
						|
=cut
 | 
						|
 | 
						|
#-------------------------------------------------------
 | 
						|
sub addkitcomp
 | 
						|
{
 | 
						|
    my $request         = shift;
 | 
						|
    my $callback        = shift;
 | 
						|
    my $request_command = shift;
 | 
						|
    my $kitdir;
 | 
						|
    my $rc;
 | 
						|
 | 
						|
    my $xusage = sub {
 | 
						|
        my $ret = shift;
 | 
						|
        my %rsp;
 | 
						|
        push @{ $rsp{data} }, "Usage: addkitcomp - Add a Kit component to an xCAT osimage.";
 | 
						|
        push @{ $rsp{data} }, "\taddkitcomp [-h|--help]";
 | 
						|
        push @{ $rsp{data} }, "\taddkitcomp [-v|--version]";
 | 
						|
        push @{ $rsp{data} }, "\taddkitcomp [-V|--verbose] [-a|--adddeps] [-f|--force] \n\t\t[-n|--noupgrade] [--noscripts] -i <osimage> <kitcompname_list>";
 | 
						|
        xCAT::MsgUtils->message("I", \%rsp, $callback, $ret);
 | 
						|
    };
 | 
						|
 | 
						|
    if ($^O ne 'linux') {
 | 
						|
        my $rsp = {};
 | 
						|
        push @{ $rsp->{data} }, "The addkitcomp command is only supported on Linux.\n";
 | 
						|
        xCAT::MsgUtils->message("E", $rsp, $::CALLBACK);
 | 
						|
        return 1;
 | 
						|
    }
 | 
						|
 | 
						|
    unless (defined($request->{arg})) { $xusage->(1); return; }
 | 
						|
    @ARGV = @{ $request->{arg} };
 | 
						|
    if ($#ARGV == -1) {
 | 
						|
        $xusage->(1);
 | 
						|
        return;
 | 
						|
    }
 | 
						|
 | 
						|
    GetOptions(
 | 
						|
        'h|help'      => \$help,
 | 
						|
        'V|verbose'   => \$::VERBOSE,
 | 
						|
        'v|version'   => \$vers,
 | 
						|
        'a|adddeps'   => \$adddeps,
 | 
						|
        'f|force'     => \$force,
 | 
						|
        'n|noupgrade' => \$::noupgrade,
 | 
						|
        'noscripts'   => \$::noscripts,
 | 
						|
        'i=s'         => \$osimage
 | 
						|
    );
 | 
						|
 | 
						|
    if ($help) {
 | 
						|
        $xusage->(0);
 | 
						|
        return;
 | 
						|
    }
 | 
						|
 | 
						|
    # Option -v for version
 | 
						|
    if (defined($vers)) {
 | 
						|
        create_version_response('addkitcomp');
 | 
						|
        return 1;    # no usage - just exit
 | 
						|
    }
 | 
						|
 | 
						|
    unless (scalar @ARGV)
 | 
						|
    {
 | 
						|
        $xusage->(1);
 | 
						|
        return 1;
 | 
						|
    }
 | 
						|
 | 
						|
    my $DBname = xCAT::Utils->get_DBName;    # support for DB2
 | 
						|
    my %tabs   = ();
 | 
						|
    my @tables = qw(kit kitrepo kitcomponent osimage osdistro linuximage);
 | 
						|
    foreach my $t (@tables) {
 | 
						|
        $tabs{$t} = xCAT::Table->new($t, -create => 1, -autocommit => 1);
 | 
						|
 | 
						|
        if (!exists($tabs{$t})) {
 | 
						|
            my %rsp;
 | 
						|
            push @{ $rsp{data} }, "Could not open xCAT table $t";
 | 
						|
            xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
            return 1;
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    # Check if all the kitcomponents are existing before processing
 | 
						|
 | 
						|
    if ($::VERBOSE) {
 | 
						|
        my %rsp;
 | 
						|
        push @{ $rsp{data} }, "Checking if kitcomponents are valid";
 | 
						|
        xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
    }
 | 
						|
 | 
						|
    my %kitcomps;
 | 
						|
    my $des = shift @ARGV;
 | 
						|
    my @kitcomponents = split ',', $des;
 | 
						|
    foreach my $kitcomponent (@kitcomponents) {
 | 
						|
 | 
						|
        # Check if it is a kitcompname or basename
 | 
						|
        (my $kitcomptable) = $tabs{kitcomponent}->getAttribs({ kitcompname => $kitcomponent }, 'kitname', 'basename');
 | 
						|
        if ($kitcomptable and $kitcomptable->{'basename'}) {
 | 
						|
            $kitcomps{$kitcomponent}{name}     = $kitcomponent;
 | 
						|
            $kitcomps{$kitcomponent}{basename} = $kitcomptable->{'basename'};
 | 
						|
        } else {
 | 
						|
            my @entries;
 | 
						|
            if ($DBname =~ /^DB2/) {
 | 
						|
                @entries = $tabs{kitcomponent}->getAllAttribsWhere("\"basename\" = '$kitcomponent'", 'kitcompname', 'version', 'release');
 | 
						|
            } else {
 | 
						|
                @entries = $tabs{kitcomponent}->getAllAttribsWhere("basename = '$kitcomponent'", 'kitcompname', 'version', 'release');
 | 
						|
            }
 | 
						|
            unless (@entries) {
 | 
						|
                my %rsp;
 | 
						|
                push @{ $rsp{data} }, "$kitcomponent kitcomponent does not exist";
 | 
						|
                xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                return 1;
 | 
						|
            }
 | 
						|
 | 
						|
            my $highest = get_highest_version('kitcompname', 'version', 'release', @entries);
 | 
						|
            $kitcomps{$highest}{name}     = $highest;
 | 
						|
            $kitcomps{$highest}{basename} = $kitcomponent;
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    # Verify if the kitcomponents fitting to the osimage or not.
 | 
						|
 | 
						|
    if ($::VERBOSE) {
 | 
						|
        my %rsp;
 | 
						|
        push @{ $rsp{data} }, "Verifying if kitcomponents fit to osimage";
 | 
						|
        xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
    }
 | 
						|
 | 
						|
    my %os;
 | 
						|
    my $osdistrotable;
 | 
						|
    (my $osimagetable) = $tabs{osimage}->getAttribs({ imagename => $osimage }, 'osdistroname', 'serverrole', 'kitcomponents', 'osname', 'osvers', 'osarch');
 | 
						|
    if ($osimagetable and $osimagetable->{'osdistroname'}) {
 | 
						|
        ($osdistrotable) = $tabs{osdistro}->getAttribs({ osdistroname => $osimagetable->{'osdistroname'} }, 'basename', 'majorversion', 'minorversion', 'arch', 'type');
 | 
						|
        if (!$osdistrotable or !$osdistrotable->{basename}) {
 | 
						|
            my %rsp;
 | 
						|
            push @{ $rsp{data} }, "$osdistroname osdistro does not exist";
 | 
						|
            xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
            return 1;
 | 
						|
        }
 | 
						|
 | 
						|
        # Read basename,majorversion,minorversion,arch,type, from osdistro table
 | 
						|
        $os{$osimage}{basename}     = lc($osdistrotable->{basename});
 | 
						|
        $os{$osimage}{majorversion} = lc($osdistrotable->{majorversion});
 | 
						|
        $os{$osimage}{minorversion} = lc($osdistrotable->{minorversion});
 | 
						|
        $os{$osimage}{arch}         = lc($osdistrotable->{arch});
 | 
						|
        $os{$osimage}{type}         = lc($osdistrotable->{type});
 | 
						|
 | 
						|
        # Read serverrole from osimage.
 | 
						|
        $os{$osimage}{serverrole} = lc($osimagetable->{'serverrole'});
 | 
						|
 | 
						|
    } elsif (!$osimagetable) {
 | 
						|
        my %rsp;
 | 
						|
        push @{ $rsp{data} }, "osimage $osimage does not exist";
 | 
						|
        xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
        return 1;
 | 
						|
    } elsif (!$osimagetable->{'osname'}) {
 | 
						|
        my %rsp;
 | 
						|
        push @{ $rsp{data} }, "osimage $osimage does not contain a valid 'osname' attribute";
 | 
						|
        xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
        return 1;
 | 
						|
    } elsif (!$osimagetable->{'osvers'}) {
 | 
						|
        my %rsp;
 | 
						|
        push @{ $rsp{data} }, "osimage $osimage does not contain a valid 'osvers' attribute";
 | 
						|
        xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
        return 1;
 | 
						|
    } elsif (!$osimagetable->{'osarch'}) {
 | 
						|
        my %rsp;
 | 
						|
        push @{ $rsp{data} }, "osimage $osimage does not contain a valid 'osarch' attribute";
 | 
						|
        xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
        return 1;
 | 
						|
    } else {
 | 
						|
        $os{$osimage}{type}       = lc($osimagetable->{'osname'});
 | 
						|
        $os{$osimage}{arch}       = lc($osimagetable->{'osarch'});
 | 
						|
        $os{$osimage}{serverrole} = lc($osimagetable->{'serverrole'});
 | 
						|
 | 
						|
        my ($basename, $majorversion, $minorversion) = $osimagetable->{'osvers'} =~ /^(\D+)(\d+)\W+(\d+)/;
 | 
						|
        $os{$osimage}{basename}     = lc($basename);
 | 
						|
        $os{$osimage}{majorversion} = lc($majorversion);
 | 
						|
        $os{$osimage}{minorversion} = lc($minorversion);
 | 
						|
    }
 | 
						|
 | 
						|
 | 
						|
    foreach my $kitcomp (keys %kitcomps) {
 | 
						|
        (my $kitcomptable) = $tabs{kitcomponent}->getAttribs({ kitcompname => $kitcomp }, 'kitname', 'kitreponame', 'serverroles', 'kitcompdeps');
 | 
						|
        if ($kitcomptable and $kitcomptable->{'kitname'} and $kitcomptable->{'kitreponame'}) {
 | 
						|
 | 
						|
            # Read serverroles from kitcomponent table
 | 
						|
            $kitcomps{$kitcomp}{serverroles} = lc($kitcomptable->{'serverroles'});
 | 
						|
 | 
						|
            # Read ostype from kit table
 | 
						|
            (my $kittable) = $tabs{kit}->getAttribs({ kitname => $kitcomptable->{'kitname'} }, 'ostype');
 | 
						|
            if ($kittable and $kittable->{ostype}) {
 | 
						|
                $kitcomps{$kitcomp}{ostype} = lc($kittable->{ostype});
 | 
						|
            } else {
 | 
						|
                my %rsp;
 | 
						|
                push @{ $rsp{data} }, "$kitcomptable->{'kitname'} ostype does not exist";
 | 
						|
                xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                return 1;
 | 
						|
            }
 | 
						|
 | 
						|
            # Read osbasename, osmajorversion,osminorversion,osarch,compat_osbasenames from kitrepo table
 | 
						|
            (my $kitrepotable) = $tabs{kitrepo}->getAttribs({ kitreponame => $kitcomptable->{'kitreponame'} }, 'osbasename', 'osmajorversion', 'osminorversion', 'osarch', 'compat_osbasenames');
 | 
						|
            if ($kitrepotable and $kitrepotable->{osbasename} and $kitrepotable->{osmajorversion} and $kitrepotable->{osarch}) {
 | 
						|
                if ($kitrepotable->{compat_osbasenames}) {
 | 
						|
                    $kitcomps{$kitcomp}{osbasename} = lc($kitrepotable->{osbasename}) . ',' . lc($kitrepotable->{compat_osbasenames});
 | 
						|
                } else {
 | 
						|
                    $kitcomps{$kitcomp}{osbasename} = lc($kitrepotable->{osbasename});
 | 
						|
                }
 | 
						|
 | 
						|
                $kitcomps{$kitcomp}{osmajorversion} = lc($kitrepotable->{osmajorversion});
 | 
						|
                $kitcomps{$kitcomp}{osminorversion} = lc($kitrepotable->{osminorversion});
 | 
						|
                $kitcomps{$kitcomp}{osarch} = lc($kitrepotable->{osarch});
 | 
						|
            } else {
 | 
						|
                my %rsp;
 | 
						|
                push @{ $rsp{data} }, "$kitcomp osbasename,osmajorversion,osminorversion or osarch does not exist";
 | 
						|
                xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                return 1;
 | 
						|
            }
 | 
						|
 | 
						|
        } else {
 | 
						|
            my %rsp;
 | 
						|
            push @{ $rsp{data} }, "$kitcomp kitname or kitrepo name does not exist";
 | 
						|
            xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
            return 1;
 | 
						|
        }
 | 
						|
 | 
						|
        if (!$force) {
 | 
						|
 | 
						|
            # Validate each attribute in kitcomp.
 | 
						|
            my $catched = 0;
 | 
						|
            my @osbasename = split ',', $kitcomps{$kitcomp}{osbasename};
 | 
						|
            foreach (@osbasename) {
 | 
						|
                if ($os{$osimage}{basename} eq $_) {
 | 
						|
                    $catched = 1;
 | 
						|
                }
 | 
						|
            }
 | 
						|
 | 
						|
            unless ($catched) {
 | 
						|
                my %rsp;
 | 
						|
                push @{ $rsp{data} }, "osimage $osimage is not compatible with kit component $kitcomp with attribute OS";
 | 
						|
                xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                return 1;
 | 
						|
            }
 | 
						|
 | 
						|
            if ($os{$osimage}{majorversion} ne $kitcomps{$kitcomp}{osmajorversion}) {
 | 
						|
                my %rsp;
 | 
						|
                push @{ $rsp{data} }, "osimage $osimage is not compatible with kit component $kitcomp with attribute majorversion";
 | 
						|
                xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                return 1;
 | 
						|
            }
 | 
						|
 | 
						|
            if ($kitcomps{$kitcomp}{osminorversion}) {
 | 
						|
                if (check_minorversion($kitcomps{$kitcomp}{osminorversion}, $os{$osimage}{minorversion}))
 | 
						|
                {
 | 
						|
                    my %rsp;
 | 
						|
                    push @{ $rsp{data} }, "osimage $osimage is not compatible with kit component $kitcomp with attribute minorversion";
 | 
						|
                    xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                    return 1;
 | 
						|
                }
 | 
						|
            }
 | 
						|
 | 
						|
            if ($os{$osimage}{arch} ne $kitcomps{$kitcomp}{osarch} && $kitcomps{$kitcomp}{osarch} ne 'noarch') {
 | 
						|
                my %rsp;
 | 
						|
                push @{ $rsp{data} }, "osimage $osimage is not compatible with kit component $kitcomp with attribute arch";
 | 
						|
                xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                return 1;
 | 
						|
            }
 | 
						|
 | 
						|
            if ($os{$osimage}{type} ne $kitcomps{$kitcomp}{ostype}) {
 | 
						|
                my %rsp;
 | 
						|
                push @{ $rsp{data} }, "osimage $osimage is not compatible with kit component $kitcomp with attribute type";
 | 
						|
                xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                return 1;
 | 
						|
            }
 | 
						|
 | 
						|
            if ($os{$osimage}{serverrole}) {
 | 
						|
                my $match = 0;
 | 
						|
                my @os_serverroles = split /,/, $os{$osimage}{serverrole};
 | 
						|
                my @kitcomp_serverroles = split /,/, $kitcomps{$kitcomp}{serverroles};
 | 
						|
                foreach my $os_serverrole (@os_serverroles) {
 | 
						|
                    foreach my $kitcomp_serverrole (@kitcomp_serverroles) {
 | 
						|
                        if ($os_serverrole eq $kitcomp_serverrole) {
 | 
						|
                            $match = 1;
 | 
						|
                            last;
 | 
						|
                        }
 | 
						|
                    }
 | 
						|
 | 
						|
                    if ($match) {
 | 
						|
                        last;
 | 
						|
                    }
 | 
						|
                }
 | 
						|
                if (!$match) {
 | 
						|
                    my %rsp;
 | 
						|
                    push @{ $rsp{data} }, "osimage $osimage is not compatible with kit component $kitcomp with attribute serverrole";
 | 
						|
                    xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                    return 1;
 | 
						|
                }
 | 
						|
            }
 | 
						|
 | 
						|
            if ($kitcomptable and $kitcomptable->{'kitcompdeps'}) {
 | 
						|
                my @kitcompdeps = split ',', $kitcomptable->{'kitcompdeps'};
 | 
						|
                foreach my $kitcompdependency (@kitcompdeps) {
 | 
						|
                    my ($kitcompdep, $vers) = split /<=|>=|=|<|>/, $kitcompdependency;
 | 
						|
                    my @entries;
 | 
						|
                    if ($DBname =~ /^DB2/) {
 | 
						|
                        @entries = $tabs{kitcomponent}->getAllAttribsWhere("\"basename\" = '$kitcompdep'", 'kitreponame', 'kitname', 'kitcompname', 'serverroles', 'kitcompdeps', 'version', 'prerequisite', 'release');
 | 
						|
                    } else {
 | 
						|
                        @entries = $tabs{kitcomponent}->getAllAttribsWhere("basename = '$kitcompdep'", 'kitreponame', 'kitname', 'kitcompname', 'serverroles', 'kitcompdeps', 'version', 'prerequisite', 'release');
 | 
						|
                    }
 | 
						|
                    unless (@entries) {
 | 
						|
                        my %rsp;
 | 
						|
                        push @{ $rsp{data} }, "Cannot find any matched kit component for kit component $kitcomp dependency $kitcompdep";
 | 
						|
                        xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                        return 1;
 | 
						|
                    }
 | 
						|
 | 
						|
                    my $highest;
 | 
						|
                    if ($vers) {
 | 
						|
                        my @valid_kitcomp;
 | 
						|
                        my $tmpkitcomp;
 | 
						|
                        my ($vers, $rel) = split /-/, $vers;
 | 
						|
                        $tmpkitcomp->{version} = $vers;
 | 
						|
                        $tmpkitcomp->{release} = $rel;
 | 
						|
                        foreach my $entry (@entries) {
 | 
						|
                            my $rc = &compare_version($entry, $tmpkitcomp, 'kitcompname', 'version', 'release');
 | 
						|
                            if (($rc == -1 and $kitcompdependency =~ />/)
 | 
						|
                                || ($rc == 1 and $kitcompdependency =~ /</)
 | 
						|
                                || ($rc == 0 and $kitcompdependency =~ /=/)) {
 | 
						|
 | 
						|
 | 
						|
                                # Check if this kitcomp fits to the osimage
 | 
						|
                                (my $krtable) = $tabs{kitrepo}->getAttribs({ kitreponame => $entry->{'kitreponame'} }, 'osbasename', 'osmajorversion', 'osminorversion', 'osarch', 'compat_osbasenames');
 | 
						|
                                if ($krtable->{compat_osbasenames}) {
 | 
						|
                                    $entry->{osbasename} = lc($krtable->{osbasename}) . ',' . lc($krtable->{compat_osbasenames});
 | 
						|
                                } else {
 | 
						|
                                    $entry->{osbasename} = lc($krtable->{osbasename});
 | 
						|
                                }
 | 
						|
 | 
						|
                                $entry->{osmajorversion} = lc($krtable->{osmajorversion});
 | 
						|
                                $entry->{osminorversion} = lc($krtable->{osminorversion});
 | 
						|
                                $entry->{osarch} = lc($krtable->{osarch});
 | 
						|
 | 
						|
                                (my $ktable) = $tabs{kit}->getAttribs({ kitname => $entry->{'kitname'} }, 'ostype');
 | 
						|
                                $entry->{ostype} = lc($ktable->{ostype});
 | 
						|
 | 
						|
                                unless (&validate_os($osimage, $os{$osimage}, $entry)) {
 | 
						|
                                    push @valid_kitcomp, $entry;
 | 
						|
                                }
 | 
						|
 | 
						|
                            }
 | 
						|
                        }
 | 
						|
 | 
						|
                        if (scalar(@valid_kitcomp)) {
 | 
						|
                            $highest = get_highest_version('kitcompname', 'version', 'release', @valid_kitcomp);
 | 
						|
                        } else {
 | 
						|
                            my %rsp;
 | 
						|
                            push @{ $rsp{data} }, "Cannot find any kit component could match for kit component $kitcomp dependency $kitcompdep";
 | 
						|
                            xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                        }
 | 
						|
 | 
						|
                    } else {
 | 
						|
                        my @valid_kitcomp;
 | 
						|
 | 
						|
                        foreach my $entry (@entries) {
 | 
						|
 | 
						|
                            # Check if this kitcomp fits to the osimage
 | 
						|
                            (my $krtable) = $tabs{kitrepo}->getAttribs({ kitreponame => $entry->{'kitreponame'} }, 'osbasename', 'osmajorversion', 'osminorversion', 'osarch', 'compat_osbasenames');
 | 
						|
                            if ($krtable->{compat_osbasenames}) {
 | 
						|
                                $entry->{osbasename} = lc($krtable->{osbasename}) . ',' . lc($krtable->{compat_osbasenames});
 | 
						|
                            } else {
 | 
						|
                                $entry->{osbasename} = lc($krtable->{osbasename});
 | 
						|
                            }
 | 
						|
 | 
						|
                            $entry->{osmajorversion} = lc($krtable->{osmajorversion});
 | 
						|
                            $entry->{osminorversion} = lc($krtable->{osminorversion});
 | 
						|
                            $entry->{osarch} = lc($krtable->{osarch});
 | 
						|
 | 
						|
                            (my $ktable) = $tabs{kit}->getAttribs({ kitname => $entry->{'kitname'} }, 'ostype');
 | 
						|
                            $entry->{ostype} = lc($ktable->{ostype});
 | 
						|
 | 
						|
 | 
						|
                            unless (&validate_os($osimage, $os{$osimage}, $entry)) {
 | 
						|
                                push @valid_kitcomp, $entry;
 | 
						|
                            }
 | 
						|
                        }
 | 
						|
                        $highest = get_highest_version('kitcompname', 'version', 'release', @valid_kitcomp);
 | 
						|
 | 
						|
                    }
 | 
						|
 | 
						|
                    if ($adddeps and $highest) {
 | 
						|
                        my $catched = 0;
 | 
						|
                        if ($osimagetable and $osimagetable->{'kitcomponents'}) {
 | 
						|
                            my @oskitcomps = split ',', $osimagetable->{'kitcomponents'};
 | 
						|
                            foreach my $oskitcomp (@oskitcomps) {
 | 
						|
                                if ($highest eq $oskitcomp) {
 | 
						|
                                    $catched = 1;
 | 
						|
                                    last;
 | 
						|
                                }
 | 
						|
                            }
 | 
						|
                        }
 | 
						|
 | 
						|
 | 
						|
                        if (!$catched) {
 | 
						|
 | 
						|
                            # Add dependencies recursive
 | 
						|
                            my $ret = xCAT::Utils->runxcmd({ command => ['addkitcomp'], arg => [ '-a', '-i', $osimage, $highest ] }, $request_command, 0, 1);
 | 
						|
                            if ($::RUNCMD_RC) {
 | 
						|
                                my %rsp;
 | 
						|
                                push @{ $rsp{data} }, "Failed to add dependency $highest to osimage $osimage";
 | 
						|
                                xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                                return 1;
 | 
						|
                            }
 | 
						|
 | 
						|
 | 
						|
                        }
 | 
						|
                    } else {
 | 
						|
 | 
						|
                        my $catched = 0;
 | 
						|
                        if ($osimagetable and $osimagetable->{'kitcomponents'}) {
 | 
						|
                            my @oskitcomps = split ',', $osimagetable->{'kitcomponents'};
 | 
						|
                            foreach my $oskitcomp (@oskitcomps) {
 | 
						|
                                if ($highest eq $oskitcomp) {
 | 
						|
                                    $catched = 1;
 | 
						|
                                    last;
 | 
						|
                                }
 | 
						|
                            }
 | 
						|
                        }
 | 
						|
 | 
						|
                        foreach my $k (keys %kitcomps) {
 | 
						|
                            if ($kitcomps{$k}{basename} and $kitcompdep eq $kitcomps{$k}{basename}) {
 | 
						|
                                $catched = 1;
 | 
						|
                                last;
 | 
						|
                            }
 | 
						|
                        }
 | 
						|
 | 
						|
                        if (!$catched) {
 | 
						|
                            my %rsp;
 | 
						|
                            push @{ $rsp{data} }, "kit component dependency $highest for kit component $kitcomp is not existing in osimage or specified in command line";
 | 
						|
                            xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                            return 1;
 | 
						|
                        }
 | 
						|
                    }
 | 
						|
                }
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
        if ($::VERBOSE) {
 | 
						|
            my %rsp;
 | 
						|
            push @{ $rsp{data} }, "kitcomponent $kitcomp fits to osimage $osimage";
 | 
						|
            xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    # Now assign each component to the osimage
 | 
						|
 | 
						|
    if ($::VERBOSE) {
 | 
						|
        my %rsp;
 | 
						|
        push @{ $rsp{data} }, "Assigning kitcomponent to osimage";
 | 
						|
        xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
    }
 | 
						|
 | 
						|
    my @kitcomps;
 | 
						|
    my @oskitcomps;
 | 
						|
    my $catched = 0;
 | 
						|
    my @kitlist;
 | 
						|
 | 
						|
    if ($osimagetable and $osimagetable->{'kitcomponents'}) {
 | 
						|
        @oskitcomps = split ',', $osimagetable->{'kitcomponents'};
 | 
						|
    }
 | 
						|
 | 
						|
    my @newkitcomps = keys %kitcomps;
 | 
						|
    foreach (keys %kitcomps) {
 | 
						|
        my $kitcomp = shift @newkitcomps;
 | 
						|
 | 
						|
        my %rsp;
 | 
						|
        push @{ $rsp{data} }, "Assigning kit component $kitcomp to osimage $osimage";
 | 
						|
        xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
 | 
						|
        # Check if this component is existing in osimage.kitcomponents
 | 
						|
        foreach my $oskitcomp (@oskitcomps) {
 | 
						|
            if ($kitcomp eq $oskitcomp) {
 | 
						|
                my %rsp;
 | 
						|
                push @{ $rsp{data} }, "$kitcomp kit component is already in osimage $osimage";
 | 
						|
                xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
                $catched = 1;
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
        # No matching kitcomponent name in osimage.kitcomponents, now checking their basenames.
 | 
						|
        if (!$catched) {
 | 
						|
 | 
						|
            my $add = 0;
 | 
						|
            foreach my $oskitcomp (@oskitcomps) {
 | 
						|
 | 
						|
                # Compare this kit component's basename with basenames in osimage.kitcomponents
 | 
						|
                (my $kitcomptable) = $tabs{kitcomponent}->getAttribs({ kitcompname => $kitcomp }, 'basename', 'version', 'release');
 | 
						|
                if (!$kitcomptable or !$kitcomptable->{'basename'}) {
 | 
						|
                    my %rsp;
 | 
						|
                    push @{ $rsp{data} }, "$kitcomp kit component does not have basename";
 | 
						|
                    xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                    return 1;
 | 
						|
                }
 | 
						|
                (my $oskitcomptable) = $tabs{kitcomponent}->getAttribs({ kitcompname => $oskitcomp }, 'basename', 'version', 'release');
 | 
						|
                if (!$oskitcomptable or !$oskitcomptable->{'basename'}) {
 | 
						|
                    my %rsp;
 | 
						|
                    push @{ $rsp{data} }, "$oskitcomp kit component does not have basename";
 | 
						|
                    xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
                    next;
 | 
						|
                }
 | 
						|
 | 
						|
                if ($kitcomptable->{'basename'} eq $oskitcomptable->{'basename'}) {
 | 
						|
                    my $rc = compare_version($oskitcomptable, $kitcomptable, 'kitcompname', 'version', 'release');
 | 
						|
                    if ($rc == 1 and !$::noupgrade) {
 | 
						|
                        my %rsp;
 | 
						|
                        push @{ $rsp{data} }, "Upgrading kit component $oskitcomp to $kitcomp";
 | 
						|
                        xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
                        my $ret = xCAT::Utils->runxcmd({ command => ['rmkitcomp'], arg => [ '-f', '-i', $osimage, $oskitcomp ] }, $request_command, -2, 1);
 | 
						|
                        if (!$ret) {
 | 
						|
                            my %rsp;
 | 
						|
                            push @{ $rsp{data} }, "Failed to remove kit component $kitcomp from $osimage";
 | 
						|
                            xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                            return 1;
 | 
						|
                        }
 | 
						|
                        $add = 1;
 | 
						|
                    } elsif ($rc == 0) {
 | 
						|
                        my %rsp;
 | 
						|
                        push @{ $rsp{data} }, "Do nothing since kit component $oskitcomp in osimage $osimage has the same basename/version and release with kit component $kitcomp";
 | 
						|
                        xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
                        next;
 | 
						|
                    } elsif (!$::noupgrade) {
 | 
						|
                        my %rsp;
 | 
						|
                        push @{ $rsp{data} }, "kit component $oskitcomp is already in osimage $osimage, and has a newer release/version than $kitcomp.  Downgrading kit component is not supported";
 | 
						|
                        xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                        return 1;
 | 
						|
                    }
 | 
						|
                }
 | 
						|
            }
 | 
						|
 | 
						|
            # Now assign this component to osimage
 | 
						|
            my $rc = assign_to_osimage($osimage, $kitcomp, $callback, \%tabs);
 | 
						|
        }
 | 
						|
 | 
						|
        push @kitlist, $kitcomp;
 | 
						|
    }
 | 
						|
 | 
						|
    my $kitnames = join ',', @kitlist;
 | 
						|
    my %rsp;
 | 
						|
    push @{ $rsp{data} }, "Kit components $kitnames were added to osimage $osimage successfully";
 | 
						|
    xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
 | 
						|
    return;
 | 
						|
}
 | 
						|
 | 
						|
#-------------------------------------------------------
 | 
						|
 | 
						|
=head3 rmkitcomp
 | 
						|
 | 
						|
  Remove Kit component from osimage
 | 
						|
 | 
						|
=cut
 | 
						|
 | 
						|
#-------------------------------------------------------
 | 
						|
sub rmkitcomp
 | 
						|
{
 | 
						|
 | 
						|
    my $request         = shift;
 | 
						|
    my $callback        = shift;
 | 
						|
    my $request_command = shift;
 | 
						|
    my $kitdir;
 | 
						|
    my $rc;
 | 
						|
 | 
						|
    my $xusage = sub {
 | 
						|
        my $ret = shift;
 | 
						|
        my %rsp;
 | 
						|
        push @{ $rsp{data} }, "Usage: rmkitcomp - Remove Kit components from an xCAT osimage.";
 | 
						|
        push @{ $rsp{data} }, "\trmkitcomp [-h|--help]";
 | 
						|
        push @{ $rsp{data} }, "\trmkitcomp [-v|--version]";
 | 
						|
        push @{ $rsp{data} }, "\trmkitcomp [-V|--verbose] [-u|--uninstall] [-f|--force] [--noscripts] \n\t\t-i <osimage> <kitcompname_list>";
 | 
						|
        xCAT::MsgUtils->message("I", \%rsp, $callback, $ret);
 | 
						|
    };
 | 
						|
 | 
						|
    if ($^O ne 'linux') {
 | 
						|
        my $rsp = {};
 | 
						|
        push @{ $rsp->{data} }, "The rmkitcomp command is only supported on Linux.\n";
 | 
						|
        xCAT::MsgUtils->message("E", $rsp, $::CALLBACK);
 | 
						|
        return 1;
 | 
						|
    }
 | 
						|
 | 
						|
    unless (defined($request->{arg})) { $xusage->(1); return; }
 | 
						|
    @ARGV = @{ $request->{arg} };
 | 
						|
    if ($#ARGV == -1) {
 | 
						|
        $xusage->(1);
 | 
						|
        return;
 | 
						|
    }
 | 
						|
 | 
						|
 | 
						|
    GetOptions(
 | 
						|
        'h|help'      => \$help,
 | 
						|
        'V|verbose'   => \$::VERBOSE,
 | 
						|
        'v|version'   => \$vers,
 | 
						|
        'u|uninstall' => \$uninstall,
 | 
						|
        'f|force'     => \$force,
 | 
						|
        'noscripts'   => \$noscripts,
 | 
						|
        'i=s'         => \$osimage
 | 
						|
    );
 | 
						|
 | 
						|
    if ($help) {
 | 
						|
        $xusage->(0);
 | 
						|
        return;
 | 
						|
    }
 | 
						|
 | 
						|
    # Option -v for version
 | 
						|
    if (defined($vers)) {
 | 
						|
        create_version_response('rmkitcomp');
 | 
						|
        return 1;    # no usage - just exit
 | 
						|
    }
 | 
						|
 | 
						|
    unless (scalar @ARGV)
 | 
						|
    {
 | 
						|
        $xusage->(1);
 | 
						|
        return 1;
 | 
						|
    }
 | 
						|
 | 
						|
    my $DBname = xCAT::Utils->get_DBName;    # support for DB2
 | 
						|
    my %tabs   = ();
 | 
						|
    my @tables = qw(kit kitrepo kitcomponent osimage osdistro linuximage);
 | 
						|
    foreach my $t (@tables) {
 | 
						|
        $tabs{$t} = xCAT::Table->new($t, -create => 1, -autocommit => 1);
 | 
						|
 | 
						|
        if (!exists($tabs{$t})) {
 | 
						|
            my %rsp;
 | 
						|
            push @{ $rsp{data} }, "Could not open xCAT table $t";
 | 
						|
            xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
            return 1;
 | 
						|
            return 1;
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
 | 
						|
    # Check if all the kitcomponents are existing before processing
 | 
						|
 | 
						|
    if ($::VERBOSE) {
 | 
						|
        my %rsp;
 | 
						|
        push @{ $rsp{data} }, "Checking if kitcomponents are valid";
 | 
						|
        xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
    }
 | 
						|
 | 
						|
    my %kitcomps;
 | 
						|
    my @remove_kitcomps_by_basename;
 | 
						|
    my $des = shift @ARGV;
 | 
						|
    my @kitcomponents = split ',', $des;
 | 
						|
    foreach my $kitcomponent (@kitcomponents) {
 | 
						|
 | 
						|
        # Check if it is a kitcompname or basename
 | 
						|
        (my $kitcomptable) = $tabs{kitcomponent}->getAttribs({ kitcompname => $kitcomponent }, 'kitname', 'kitpkgdeps', 'prerequisite', 'postbootscripts', 'genimage_postinstall', 'kitreponame', 'exlist', 'basename', 'driverpacks');
 | 
						|
        if ($kitcomptable and $kitcomptable->{'kitname'}) {
 | 
						|
            $kitcomps{$kitcomponent}{name}       = $kitcomponent;
 | 
						|
            $kitcomps{$kitcomponent}{kitname}    = $kitcomptable->{kitname};
 | 
						|
            $kitcomps{$kitcomponent}{kitpkgdeps} = $kitcomptable->{kitpkgdeps};
 | 
						|
            $kitcomps{$kitcomponent}{prerequisite} = $kitcomptable->{prerequisite};
 | 
						|
            $kitcomps{$kitcomponent}{basename} = $kitcomptable->{basename};
 | 
						|
            $kitcomps{$kitcomponent}{exlist}   = $kitcomptable->{exlist};
 | 
						|
            $kitcomps{$kitcomponent}{postbootscripts} = $kitcomptable->{postbootscripts};
 | 
						|
            $kitcomps{$kitcomponent}{kitreponame} = $kitcomptable->{kitreponame};
 | 
						|
            $kitcomps{$kitcomponent}{driverpacks} = $kitcomptable->{driverpacks};
 | 
						|
            $kitcomps{$kitcomponent}{genimage_postinstall} = $kitcomptable->{genimage_postinstall};
 | 
						|
        } else {
 | 
						|
            my @entries;
 | 
						|
            if ($DBname =~ /^DB2/) {
 | 
						|
                @entries = $tabs{kitcomponent}->getAllAttribsWhere("\"basename\" = '$kitcomponent'", 'kitcompname', 'version', 'release');
 | 
						|
            } else {
 | 
						|
                @entries = $tabs{kitcomponent}->getAllAttribsWhere("basename = '$kitcomponent'", 'kitcompname', 'version', 'release');
 | 
						|
            }
 | 
						|
            unless (@entries) {
 | 
						|
                my %rsp;
 | 
						|
                push @{ $rsp{data} }, "$kitcomponent kitcomponent does not exist";
 | 
						|
                xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                return 1;
 | 
						|
            }
 | 
						|
            push(@remove_kitcomps_by_basename, $kitcomponent);
 | 
						|
            foreach $basename_entry (@entries) {
 | 
						|
                my $this_entry = $basename_entry->{kitcompname};
 | 
						|
                $kitcomps{$this_entry}{name} = $this_entry;
 | 
						|
                (my $kitcomptable) = $tabs{kitcomponent}->getAttribs({ kitcompname => $this_entry }, 'kitname', 'kitpkgdeps', 'prerequisite', 'postbootscripts', 'genimage_postinstall', 'kitreponame', 'exlist', 'basename', 'driverpacks');
 | 
						|
                $kitcomps{$this_entry}{kitname} = $kitcomptable->{kitname};
 | 
						|
                $kitcomps{$this_entry}{kitpkgdeps} = $kitcomptable->{kitpkgdeps};
 | 
						|
                $kitcomps{$this_entry}{prerequisite} = $kitcomptable->{prerequisite};
 | 
						|
                $kitcomps{$this_entry}{basename} = $kitcomptable->{basename};
 | 
						|
                $kitcomps{$this_entry}{exlist}   = $kitcomptable->{exlist};
 | 
						|
                $kitcomps{$this_entry}{postbootscripts} = $kitcomptable->{postbootscripts};
 | 
						|
                $kitcomps{$this_entry}{kitreponame} = $kitcomptable->{kitreponame};
 | 
						|
                $kitcomps{$this_entry}{driverpacks} = $kitcomptable->{driverpacks};
 | 
						|
                $kitcomps{$this_entry}{genimage_postinstall} = $kitcomptable->{genimage_postinstall};
 | 
						|
                $kitcomps{$this_entry}{remove_by_basename} = '1';
 | 
						|
            }
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    # Check if the kitcomponents are existing in osimage.kitcomponents attribute.
 | 
						|
 | 
						|
    (my $osimagetable) = $tabs{osimage}->getAttribs({ imagename => $osimage }, 'kitcomponents', 'postbootscripts', 'provmethod');
 | 
						|
    if (!$osimagetable or !$osimagetable->{'kitcomponents'}) {
 | 
						|
        my %rsp;
 | 
						|
        push @{ $rsp{data} }, "$osimage osimage does not exist or not includes any kit components";
 | 
						|
        xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
        return 1;
 | 
						|
    }
 | 
						|
 | 
						|
    if (!$osimagetable->{'provmethod'}) {
 | 
						|
        my %rsp;
 | 
						|
        push @{ $rsp{data} }, "$osimage osimage is missing provmethod";
 | 
						|
        xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
        return 1;
 | 
						|
    }
 | 
						|
    my @osikitcomps = split ',', $osimagetable->{'kitcomponents'};
 | 
						|
    foreach my $osikitcomp (@osikitcomps) {
 | 
						|
        if (exists($kitcomps{$osikitcomp})) {
 | 
						|
            $kitcomps{$osikitcomp}{matched} = 1;
 | 
						|
        }
 | 
						|
    }
 | 
						|
    my $invalidkitcomp = '';
 | 
						|
    foreach my $kitcomp (keys %kitcomps) {
 | 
						|
        if (!$kitcomps{$kitcomp}{matched}) {
 | 
						|
            if ($kitcomps{$kitcomp}{remove_by_basename}) {
 | 
						|
                delete($kitcomps{$kitcomp});
 | 
						|
            } else {
 | 
						|
                if (!$invalidkitcomp) {
 | 
						|
                    $invalidkitcomp = $kitcomp;
 | 
						|
                } else {
 | 
						|
                    $invalidkitcomp = join(',', $invalidkitcomp, $kitcomp);
 | 
						|
                }
 | 
						|
            }
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    foreach $basename_to_remove (@remove_kitcomps_by_basename) {
 | 
						|
        my $removing_at_least_one = 0;
 | 
						|
        foreach my $kitcomponent (keys %kitcomps) {
 | 
						|
            if ($basename_to_remove eq $kitcomps{$kitcomponent}{basename}) {
 | 
						|
                $removing_at_least_one = 1;
 | 
						|
                last;
 | 
						|
            }
 | 
						|
        }
 | 
						|
        if (!$removing_at_least_one) {
 | 
						|
            if (!$invalidkitcomp) {
 | 
						|
                $invalidkitcomp = $basename_to_remove;
 | 
						|
            } else {
 | 
						|
                $invalidkitcomp = join(',', $invalidkitcomp, $basename_to_remove);
 | 
						|
            }
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
 | 
						|
    if ($invalidkitcomp) {
 | 
						|
        my %rsp;
 | 
						|
        push @{ $rsp{data} }, "$invalidkitcomp kit components are not assigned to osimage $osimage";
 | 
						|
        xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
        return 1;
 | 
						|
    }
 | 
						|
 | 
						|
 | 
						|
    # Now check if there is any other kitcomponent depending on this one.
 | 
						|
 | 
						|
    foreach my $kitcomponent (keys %kitcomps) {
 | 
						|
        foreach my $osikitcomp (@osikitcomps) {
 | 
						|
            (my $kitcomptable) = $tabs{kitcomponent}->getAttribs({ kitcompname => $osikitcomp }, 'kitcompdeps');
 | 
						|
            if ($kitcomptable and $kitcomptable->{'kitcompdeps'}) {
 | 
						|
 | 
						|
                my @kitcompdeps = split(',', $kitcomptable->{'kitcompdeps'});
 | 
						|
                foreach my $kitcompdependency (@kitcompdeps) {
 | 
						|
 | 
						|
                    my ($kitcompdep, $vers) = split /<=|>=|=|<|>/, $kitcompdependency;
 | 
						|
 | 
						|
                    # Get the kit component full name from basename.
 | 
						|
                    my @entries;
 | 
						|
                    if ($DBname =~ /^DB2/) {
 | 
						|
                        @entries = $tabs{kitcomponent}->getAllAttribsWhere("\"basename\" = '$kitcompdep'", 'kitcompname', 'version', 'release');
 | 
						|
                    } else {
 | 
						|
                        @entries = $tabs{kitcomponent}->getAllAttribsWhere("basename = '$kitcompdep'", 'kitcompname', 'version', 'release');
 | 
						|
                    }
 | 
						|
                    unless (@entries) {
 | 
						|
                        my %rsp;
 | 
						|
                        push @{ $rsp{data} }, "kitcomponent $kitcompdep basename does not exist";
 | 
						|
                        xCAT::MsgUtils->message("W", \%rsp, $callback);
 | 
						|
                    }
 | 
						|
 | 
						|
                    my $kitcompdepname = get_highest_version('kitcompname', 'version', 'release', @entries);
 | 
						|
 | 
						|
                    if (($kitcomponent eq $kitcompdepname) and !$force and !exists($kitcomps{$osikitcomp})) {
 | 
						|
 | 
						|
                        # There is other kitcomponent depending on this one and there is no --force option
 | 
						|
                        my %rsp;
 | 
						|
                        push @{ $rsp{data} }, "Failed to remove kitcomponent $kitcomponent because $osikitcomp is still depending on it.  Use -f option to remove it anyway";
 | 
						|
                        xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                        return 1;
 | 
						|
                    }
 | 
						|
                }
 | 
						|
            }
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
 | 
						|
    # Reading installdir
 | 
						|
    my $installdir = xCAT::TableUtils->getInstallDir();
 | 
						|
    unless ($installdir) {
 | 
						|
        $installdir = '/install';
 | 
						|
    }
 | 
						|
    $installdir =~ s/\/$//;
 | 
						|
 | 
						|
 | 
						|
    # Remove each kitcomponent from osimage.
 | 
						|
 | 
						|
    my @newosikitcomps;
 | 
						|
    foreach my $osikitcomp (@osikitcomps) {
 | 
						|
        my $match = 0;
 | 
						|
        foreach my $kitcomponent (keys %kitcomps) {
 | 
						|
            if ($kitcomponent eq $osikitcomp) {
 | 
						|
                $match = 1;
 | 
						|
                last;
 | 
						|
            }
 | 
						|
        }
 | 
						|
        if (!$match) {
 | 
						|
            push @newosikitcomps, $osikitcomp;
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    my $newosikitcomp = join ',', @newosikitcomps;
 | 
						|
    $osimagetable->{'kitcomponents'} = $newosikitcomp;
 | 
						|
 | 
						|
 | 
						|
    # Remove kitcomponent.postbootscripts and kitcomponent.genimage_postinstall from osimage.postbootscripts.
 | 
						|
 | 
						|
    my @osimagescripts;
 | 
						|
    my @newosimagescripts;
 | 
						|
    if ($osimagetable and $osimagetable->{'postbootscripts'}) {
 | 
						|
        @osimagescripts = split(',', $osimagetable->{'postbootscripts'});
 | 
						|
    }
 | 
						|
 | 
						|
    foreach my $osimagescript (@osimagescripts) {
 | 
						|
        my $match = 0;
 | 
						|
        foreach my $kitcomponent (keys %kitcomps) {
 | 
						|
            my @kitcompscripts = split(',', $kitcomps{$kitcomponent}{postbootscripts});
 | 
						|
            foreach my $kitcompscript (@kitcompscripts) {
 | 
						|
                if ($osimagescript =~ /^$kitcompscript/) {
 | 
						|
                    $match = 1;
 | 
						|
                    last;
 | 
						|
                }
 | 
						|
            }
 | 
						|
 | 
						|
            last if ($match);
 | 
						|
        }
 | 
						|
 | 
						|
        if (!$match or $noscripts) {
 | 
						|
            push @newosimagescripts, $osimagescript;
 | 
						|
        }
 | 
						|
 | 
						|
        #Remove genimage_postinstall from osimage.postbootscripts
 | 
						|
        if ($osimagescript =~ /KIT_$osimage.postbootscripts/ and -e "$installdir/postscripts/KIT_$osimage.postbootscripts") {
 | 
						|
            foreach my $kitcomponent (keys %kitcomps) {
 | 
						|
 | 
						|
                my @postbootlines;
 | 
						|
                my @newlines;
 | 
						|
                if (open(POSTBOOTSCRIPTS, "<", "$installdir/postscripts/KIT_$osimage.postbootscripts")) {
 | 
						|
                    @postbootlines = <POSTBOOTSCRIPTS>;
 | 
						|
                    close(POSTBOOTSCRIPTS);
 | 
						|
                }
 | 
						|
 | 
						|
                my $match = 0;
 | 
						|
                my @kitcompscripts = split(',', $kitcomps{$kitcomponent}{genimage_postinstall});
 | 
						|
                foreach my $line (@postbootlines) {
 | 
						|
                    chomp $line;
 | 
						|
                    foreach my $kitcompscript (@kitcompscripts) {
 | 
						|
                        if (grep(/$kitcompscript/, $line)) {
 | 
						|
                            $match = 1;
 | 
						|
                        }
 | 
						|
                    }
 | 
						|
 | 
						|
                    if (!$match) {
 | 
						|
                        push @newlines, $line . "\n";
 | 
						|
                    }
 | 
						|
                }
 | 
						|
 | 
						|
                # Now write the new postbootscripts file.
 | 
						|
                if (open(NEWEXLIST, ">", "$installdir/postscripts/KIT_$osimage.postbootscripts")) {
 | 
						|
                    print NEWEXLIST @newlines;
 | 
						|
                    close(NEWEXLIST);
 | 
						|
                }
 | 
						|
            }
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    my $newosimagescript = join ',', @newosimagescripts;
 | 
						|
    $osimagetable->{'postbootscripts'} = $newosimagescript;
 | 
						|
 | 
						|
    # Remove symlink from osimage.otherpkgdir.
 | 
						|
 | 
						|
    # Read all the kitcomponents assigned to all the osimage to make sure the repo used by other osimage
 | 
						|
    # will not be deleted.
 | 
						|
 | 
						|
    my @allosikitcomps = $tabs{osimage}->getAllAttribs('imagename', 'kitcomponents');
 | 
						|
 | 
						|
    (my $linuximagetable) = $tabs{linuximage}->getAttribs({ imagename => $osimage }, 'postinstall', 'exlist', 'otherpkglist', 'otherpkgdir', 'driverupdatesrc');
 | 
						|
    if ($linuximagetable and $linuximagetable->{otherpkgdir}) {
 | 
						|
 | 
						|
        my $otherpkgdir = $linuximagetable->{otherpkgdir};
 | 
						|
 | 
						|
        #support mixed otherpkgdir http and local dir
 | 
						|
        $otherpkgdir = get_local_otherpkgdir($otherpkgdir);
 | 
						|
        foreach my $kitcomponent (keys %kitcomps) {
 | 
						|
 | 
						|
            my %newosikitcomponents;
 | 
						|
            foreach my $allosikitcomp (@allosikitcomps) {
 | 
						|
                if ($allosikitcomp->{kitcomponents} and $allosikitcomp->{imagename}) {
 | 
						|
                    (my $allosiotherpkgdir) = $tabs{linuximage}->getAttribs({ imagename => $allosikitcomp->{imagename} }, 'otherpkgdir');
 | 
						|
 | 
						|
                    my @allkitcomps = split /,/, $allosikitcomp->{kitcomponents};
 | 
						|
                    foreach my $allkitcomp (@allkitcomps) {
 | 
						|
                        if ((($allosikitcomp->{imagename} ne $osimage) and
 | 
						|
                                ($allosiotherpkgdir->{otherpkgdir} eq $otherpkgdir))
 | 
						|
                            or ($allkitcomp ne $kitcomponent)) {
 | 
						|
                            $newosikitcomponents{$allkitcomp} = 1;
 | 
						|
                        }
 | 
						|
                    }
 | 
						|
                }
 | 
						|
            }
 | 
						|
 | 
						|
            if ($kitcomps{$kitcomponent}{kitreponame}) {
 | 
						|
                if (-d "$otherpkgdir/$kitcomps{$kitcomponent}{kitreponame}") {
 | 
						|
 | 
						|
                    # Check if this repo is used by other kitcomponent before removing the link
 | 
						|
                    my $match = 0;
 | 
						|
                    foreach my $osikitcomp (keys %newosikitcomponents) {
 | 
						|
 | 
						|
                        my $depkitrepodir;
 | 
						|
                        (my $kitcomptable) = $tabs{kitcomponent}->getAttribs({ kitcompname => $osikitcomp }, 'kitreponame');
 | 
						|
                        if ($kitcomptable and $kitcomptable->{kitreponame}) {
 | 
						|
                            $depkitrepodir = "$otherpkgdir/$kitcomptable->{kitreponame}";
 | 
						|
                        }
 | 
						|
                        if ($depkitrepodir =~ /^$otherpkgdir\/$kitcomps{$kitcomponent}{kitreponame}$/) {
 | 
						|
                            $match = 1;
 | 
						|
                        }
 | 
						|
                    }
 | 
						|
                    if (!$match) {
 | 
						|
                        if ($debianflag)
 | 
						|
                        {
 | 
						|
                            #Now we do not use moun --bind for kitrepo dir to otherpkgdir
 | 
						|
                            #leave this line is support old way when using mount
 | 
						|
                            system("umount -f $otherpkgdir/$kitcomps{$kitcomponent}{kitreponame} > /dev/null");
 | 
						|
                        }
 | 
						|
                        system("rm -rf $otherpkgdir/$kitcomps{$kitcomponent}{kitreponame}");
 | 
						|
                    }
 | 
						|
                }
 | 
						|
            }
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    # Remove genimage_postinstall from linuximage table
 | 
						|
    if ($linuximagetable->{postinstall}) {
 | 
						|
        my @scripts = split ',', $linuximagetable->{postinstall};
 | 
						|
        foreach my $script (@scripts) {
 | 
						|
            if ($script =~ /KIT_COMPONENTS.postinstall/ and -e "$installdir/osimages/$osimage/kits/KIT_COMPONENTS.postinstall") {
 | 
						|
 | 
						|
                foreach my $kitcomponent (keys %kitcomps) {
 | 
						|
 | 
						|
                    my @postinstalllines;
 | 
						|
                    my @newlines;
 | 
						|
                    if (open(POSTINSTALLSCRIPTS, "<", "$installdir/osimages/$osimage/kits/KIT_COMPONENTS.postinstall")) {
 | 
						|
                        @postinstalllines = <POSTINSTALLSCRIPTS>;
 | 
						|
                        close(POSTINSTALLSCRIPTS);
 | 
						|
                    }
 | 
						|
 | 
						|
                    my @kitcompscripts = split(',', $kitcomps{$kitcomponent}{genimage_postinstall});
 | 
						|
                    foreach my $line (@postinstalllines) {
 | 
						|
                        chomp $line;
 | 
						|
                        my $match = 0;
 | 
						|
                        foreach my $kitcompscript (@kitcompscripts) {
 | 
						|
 | 
						|
                            if (grep(/$kitcompscript/, $line)) {
 | 
						|
                                $match = 1;
 | 
						|
                                last;
 | 
						|
                            }
 | 
						|
                        }
 | 
						|
                        if (!$match) {
 | 
						|
                            push @newlines, $line . "\n";
 | 
						|
                        }
 | 
						|
                    }
 | 
						|
 | 
						|
                    # Now write the new postbootscripts file.
 | 
						|
                    if (open(NEWEXLIST, ">", "$installdir/osimages/$osimage/kits/KIT_COMPONENTS.postinstall")) {
 | 
						|
                        print NEWEXLIST @newlines;
 | 
						|
                        close(NEWEXLIST);
 | 
						|
                    }
 | 
						|
                }
 | 
						|
            }
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    # Remove kitcomponent exlist,otherpkglist and deploy_params from osimage
 | 
						|
 | 
						|
    my @kitlist;
 | 
						|
    foreach my $kitcomponent (keys %kitcomps) {
 | 
						|
 | 
						|
        my %rsp;
 | 
						|
        push @{ $rsp{data} }, "Removing kitcomponent $kitcomponent from osimage $osimage";
 | 
						|
        xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
 | 
						|
        if (!exists($kitcomps{$kitcomponent}{kitname})) {
 | 
						|
            my %rsp;
 | 
						|
            push @{ $rsp{data} }, "Could not find kit object for kitcomponent $kitcomponent";
 | 
						|
            xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
            return 1;
 | 
						|
        }
 | 
						|
 | 
						|
        # Reading kitdir
 | 
						|
        my $kitdir     = '';
 | 
						|
        my $exlistfile = '';
 | 
						|
        my $kitname    = $kitcomps{$kitcomponent}{kitname};
 | 
						|
        (my $kittable) = $tabs{kit}->getAttribs({ kitname => $kitname }, 'kitdir', 'kitdeployparams');
 | 
						|
 | 
						|
 | 
						|
        # Removing exlist
 | 
						|
 | 
						|
        if ($linuximagetable and $linuximagetable->{exlist}) {
 | 
						|
            my $match = 0;
 | 
						|
            my @exlists = split ',', $linuximagetable->{exlist};
 | 
						|
            foreach my $exlist (@exlists) {
 | 
						|
                if ($exlist =~ /^$installdir\/osimages\/$osimage\/kits\/KIT_COMPONENTS.exlist$/) {
 | 
						|
                    $match = 1;
 | 
						|
                    last;
 | 
						|
                }
 | 
						|
            }
 | 
						|
 | 
						|
            my @lines = ();
 | 
						|
            if ($match and -e "$installdir/osimages/$osimage/kits/KIT_COMPONENTS.exlist") {
 | 
						|
                if (open(EXLIST, "<", "$installdir/osimages/$osimage/kits/KIT_COMPONENTS.exlist")) {
 | 
						|
                    @lines = <EXLIST>;
 | 
						|
                    if ($::VERBOSE) {
 | 
						|
                        my %rsp;
 | 
						|
                        push @{ $rsp{data} }, "Reading kit component exlist file $installdir/osimages/$osimage/kits/KIT_COMPONENTS.exlist";
 | 
						|
                        xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
                    }
 | 
						|
                } else {
 | 
						|
                    my %rsp;
 | 
						|
                    push @{ $rsp{data} }, "Could not open kit component exlist file $installdir/osimages/$osimage/kits/KIT_COMPONENTS.exlist";
 | 
						|
                    xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                    return 1;
 | 
						|
                }
 | 
						|
 | 
						|
                if ($kittable and $kittable->{kitdir}) {
 | 
						|
                    $kitdir = $kittable->{kitdir};
 | 
						|
                }
 | 
						|
 | 
						|
                if (exists($kitcomps{$kitcomponent}{exlist})) {
 | 
						|
                    $exlistfile = $kitcomps{$kitcomponent}{exlist};
 | 
						|
                }
 | 
						|
 | 
						|
                my @newlines = ();
 | 
						|
                foreach my $line (@lines) {
 | 
						|
                    chomp $line;
 | 
						|
                    if ($line =~ /^#INCLUDE:$kitdir\/other_files\/$exlistfile#$/) {
 | 
						|
                        next;
 | 
						|
                    }
 | 
						|
                    push @newlines, $line . "\n";
 | 
						|
                }
 | 
						|
                if (open(NEWEXLIST, ">", "$installdir/osimages/$osimage/kits/KIT_COMPONENTS.exlist")) {
 | 
						|
                    print NEWEXLIST @newlines;
 | 
						|
                    close(NEWEXLIST);
 | 
						|
                }
 | 
						|
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
        # Removing otherpkglist
 | 
						|
 | 
						|
        if ($linuximagetable and $linuximagetable->{otherpkglist}) {
 | 
						|
            my $match = 0;
 | 
						|
            my @lines = ();
 | 
						|
 | 
						|
            my @otherpkglists = split ',', $linuximagetable->{otherpkglist};
 | 
						|
            foreach my $otherpkglist (@otherpkglists) {
 | 
						|
                if ($otherpkglist =~ /^$installdir\/osimages\/$osimage\/kits\/KIT_COMPONENTS.otherpkgs.pkglist$/) {
 | 
						|
                    $match = 1;
 | 
						|
                    last;
 | 
						|
                }
 | 
						|
            }
 | 
						|
 | 
						|
            if ($match and -e "$installdir/osimages/$osimage/kits/KIT_COMPONENTS.otherpkgs.pkglist") {
 | 
						|
                if (open(OTHERPKGLIST, "<", "$installdir/osimages/$osimage/kits/KIT_COMPONENTS.otherpkgs.pkglist")) {
 | 
						|
                    @lines = <OTHERPKGLIST>;
 | 
						|
                    if ($::VERBOSE) {
 | 
						|
                        my %rsp;
 | 
						|
                        push @{ $rsp{data} }, "Reading kit component otherpkg pkglist $installdir/osimages/$osimage/kits/KIT_COMPONENTS.otherpkgs.pkglist";
 | 
						|
                        xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
                    }
 | 
						|
                } else {
 | 
						|
                    my %rsp;
 | 
						|
                    push @{ $rsp{data} }, "Could not open kit component exlist file $installdir/osimages/$osimage/kits/KIT_COMPONENTS.exlist";
 | 
						|
                    xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                    return 1;
 | 
						|
                }
 | 
						|
 | 
						|
                my $basename = '';
 | 
						|
                if (exists($kitcomps{$kitcomponent}{basename}) and exists($kitcomps{$kitcomponent}{kitreponame})) {
 | 
						|
                    $basename = $kitcomps{$kitcomponent}{basename};
 | 
						|
                    my $kitreponame = $kitcomps{$kitcomponent}{kitreponame};
 | 
						|
 | 
						|
                    my @newlines = ();
 | 
						|
                    my $num      = 0;
 | 
						|
                    my $inlist   = 0;
 | 
						|
                    foreach my $line (@lines) {
 | 
						|
                        chomp $line;
 | 
						|
 | 
						|
                        if ($line =~ /^#NEW_INSTALL_LIST#/) {
 | 
						|
                            $num    = 1;
 | 
						|
                            $inlist = 1;
 | 
						|
                        }
 | 
						|
                        if ($kitcomps{$kitcomponent}{prerequisite}) {
 | 
						|
                            if (($line =~ /^$kitreponame\/prep_$basename$/) ||
 | 
						|
                                ($line =~ /^$kitreponame\/prep-$basename$/)) {
 | 
						|
                                if ($inlist) {
 | 
						|
                                    $num--;
 | 
						|
                                    foreach (1 .. $num) {
 | 
						|
                                        pop @newlines;
 | 
						|
                                    }
 | 
						|
                                }
 | 
						|
                                next;
 | 
						|
                            }
 | 
						|
                        }
 | 
						|
                        if ($line =~ /^$kitreponame\/$basename$/) {
 | 
						|
                            if ($inlist) {
 | 
						|
                                $num--;
 | 
						|
                                foreach (1 .. $num) {
 | 
						|
                                    pop @newlines;
 | 
						|
                                }
 | 
						|
                            }
 | 
						|
                            next;
 | 
						|
                        }
 | 
						|
                        push @newlines, $line . "\n";
 | 
						|
                        $num++;
 | 
						|
                    }
 | 
						|
 | 
						|
                    if (open(NEWOTHERPKGLIST, ">", "$installdir/osimages/$osimage/kits/KIT_COMPONENTS.otherpkgs.pkglist")) {
 | 
						|
                        print NEWOTHERPKGLIST @newlines;
 | 
						|
                        close(NEWOTHERPKGLIST);
 | 
						|
                    }
 | 
						|
                }
 | 
						|
            }
 | 
						|
 | 
						|
            # Add this component basename and pkgnames to KIT_RMPKGS.otherpkg.pkglist
 | 
						|
            if ($uninstall) {
 | 
						|
                my @lines = ();
 | 
						|
 | 
						|
                mkpath("$installdir/osimages/$osimage/kits/");
 | 
						|
 | 
						|
                if (-e "$installdir/osimages/$osimage/kits/KIT_RMPKGS.otherpkgs.pkglist") {
 | 
						|
                    if (open(RMOTHERPKGLIST, "<", "$installdir/osimages/$osimage/kits/KIT_RMPKGS.otherpkgs.pkglist")) {
 | 
						|
                        @lines = <RMOTHERPKGLIST>;
 | 
						|
                        close(RMOTHERPKGLIST);
 | 
						|
                        if ($::VERBOSE) {
 | 
						|
                            my %rsp;
 | 
						|
                            push @{ $rsp{data} }, "Reading kit component rmpkgs file $installdir/osimages/$osimage/kits/KIT_RMPKGS.otherpkgs.pkglist";
 | 
						|
                            xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
                        }
 | 
						|
                    } else {
 | 
						|
                        my %rsp;
 | 
						|
                        push @{ $rsp{data} }, "Could not open kit component rmpkgs file $installdir/osimages/$osimage/kits/KIT_RMPKGS.otherpkgs.pkglist";
 | 
						|
                        xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                        return 1;
 | 
						|
                    }
 | 
						|
                }
 | 
						|
 | 
						|
                my @l           = @lines;
 | 
						|
                my $basename    = '';
 | 
						|
                my $kitreponame = '';
 | 
						|
                my @kitpkgdeps  = ();
 | 
						|
 | 
						|
                if (exists($kitcomps{$kitcomponent}{basename}) and exists($kitcomps{$kitcomponent}{kitreponame})) {
 | 
						|
                    $basename    = $kitcomps{$kitcomponent}{basename};
 | 
						|
                    $kitreponame = $kitcomps{$kitcomponent}{kitreponame};
 | 
						|
                } else {
 | 
						|
                    my %rsp;
 | 
						|
                    push @{ $rsp{data} }, "Could not open kit component table and read basename for kit component $kitcomp";
 | 
						|
                    xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                    return 1;
 | 
						|
                }
 | 
						|
 | 
						|
                if (exists($kitcomps{$kitcomponent}{kitpkgdeps})) {
 | 
						|
                    @kitpkgdeps = split ',', $kitcomps{$kitcomponent}{kitpkgdeps};
 | 
						|
                }
 | 
						|
 | 
						|
                #  Add prerequisite to  KIT_RMPKGS.otherpkg.pkglist
 | 
						|
                if ($kitcomps{$kitcomponent}{prerequisite}) {
 | 
						|
                    my @kitpreps = split /,/, $kitcomps{$kitcomponent}{prerequisite};
 | 
						|
                    foreach my $kitprep (@kitpreps) {
 | 
						|
                        push @kitpkgdeps, $kitprep;
 | 
						|
                    }
 | 
						|
                }
 | 
						|
 | 
						|
                push @kitpkgdeps, $basename;
 | 
						|
 | 
						|
                my $update = 0;
 | 
						|
 | 
						|
                foreach my $kitpkgdep (@kitpkgdeps) {
 | 
						|
                    next if ($kitpkgdep =~ /^$/);
 | 
						|
                    my $matched = 0;
 | 
						|
                    foreach my $line (@lines) {
 | 
						|
                        chomp $line;
 | 
						|
                        if ($line =~ /^-$kitpkgdep$/) {
 | 
						|
                            $matched = 1;
 | 
						|
                            last;
 | 
						|
                        }
 | 
						|
                    }
 | 
						|
 | 
						|
                    unless ($matched) {
 | 
						|
                        unshift @l, "-$kitpkgdep\n";
 | 
						|
                        $update = 1;
 | 
						|
                    }
 | 
						|
 | 
						|
                }
 | 
						|
 | 
						|
 | 
						|
                if ($update and open(RMPKGLIST, ">", "$installdir/osimages/$osimage/kits/KIT_RMPKGS.otherpkgs.pkglist")) {
 | 
						|
                    print RMPKGLIST @l;
 | 
						|
                    close(RMPKGLIST);
 | 
						|
                }
 | 
						|
 | 
						|
                if ($linuximagetable and $linuximagetable->{otherpkglist}) {
 | 
						|
                    my $match = 0;
 | 
						|
                    my @otherpkglists = split ',', $linuximagetable->{otherpkglist};
 | 
						|
                    foreach my $otherpkglist (@otherpkglists) {
 | 
						|
                        if ($otherpkglist =~ /^$installdir\/osimages\/$osimage\/kits\/KIT_RMPKGS.otherpkgs.pkglist$/) {
 | 
						|
                            $match = 1;
 | 
						|
                            last;
 | 
						|
                        }
 | 
						|
                    }
 | 
						|
 | 
						|
                    if (!$match and -e "$installdir/osimages/$osimage/kits/KIT_RMPKGS.otherpkgs.pkglist") {
 | 
						|
                        $linuximagetable->{otherpkglist} = $linuximagetable->{otherpkglist} . ",$installdir/osimages/$osimage/kits/KIT_RMPKGS.otherpkgs.pkglist"
 | 
						|
                    }
 | 
						|
                }
 | 
						|
            }
 | 
						|
 | 
						|
        }
 | 
						|
 | 
						|
        # Removing deploy parameters
 | 
						|
 | 
						|
        if ($kittable and $kittable->{kitdeployparams} and $kittable->{kitdir}) {
 | 
						|
 | 
						|
            my $kitdir        = $kittable->{kitdir};
 | 
						|
            my $kitdeployfile = $kittable->{kitdeployparams};
 | 
						|
 | 
						|
            # Check if there is other kitcomponent in the same kit.
 | 
						|
            my $match = 0;
 | 
						|
            if (exists($kitcomps{$kitcomponent}{kitname})) {
 | 
						|
                my $kitname = $kitcomps{$kitcomponent}{kitname};
 | 
						|
 | 
						|
                foreach my $osikitcomp (@osikitcomps) {
 | 
						|
                    (my $kitcomptable) = $tabs{kitcomponent}->getAttribs({ kitcompname => $osikitcomp }, 'kitname');
 | 
						|
 | 
						|
                    if ($kitcomptable and $kitcomptable->{kitname} and $kitcomptable->{kitname} eq $kitname and !exists($kitcomps{$osikitcomp}{name})) {
 | 
						|
                        $match = 1;
 | 
						|
                        last;
 | 
						|
                    }
 | 
						|
                }
 | 
						|
 | 
						|
                unless ($match) {
 | 
						|
                    my @contents = ();
 | 
						|
                    if (-e "$kitdir/other_files/$kitdeployfile") {
 | 
						|
                        if (open(KITDEPLOY, "<", "$kitdir/other_files/$kitdeployfile")) {
 | 
						|
                            @contents = <KITDEPLOY>;
 | 
						|
                            close(KITDEPLOY);
 | 
						|
                            if ($::VERBOSE) {
 | 
						|
                                my %rsp;
 | 
						|
                                push @{ $rsp{data} }, "Reading kit deployparams from $kitdir/other_files/$kitdeployfile";
 | 
						|
                                xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
                            }
 | 
						|
                        } else {
 | 
						|
                            my %rsp;
 | 
						|
                            push @{ $rsp{data} }, "Could not open kit deployparams file $kitdir/other_files/$kitdeployfile";
 | 
						|
                            xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                            return 1;
 | 
						|
                        }
 | 
						|
 | 
						|
                        push @contents, "#INCLUDE:$kitdir/other_files/$kitdeployfile#";
 | 
						|
                    }
 | 
						|
 | 
						|
                    my @lines = ();
 | 
						|
                    if (-e "$installdir/osimages/$osimage/kits/KIT_DEPLOY_PARAMS.otherpkgs.pkglist") {
 | 
						|
 | 
						|
                        system("cp $installdir/osimages/$osimage/kits/KIT_DEPLOY_PARAMS.otherpkgs.pkglist $installdir/osimages/$osimage/kits/KIT_DEPLOY_PARAMS.otherpkgs.pkglist.orig");
 | 
						|
 | 
						|
                        if (open(DEPLOYPARAM, "<", "$installdir/osimages/$osimage/kits/KIT_DEPLOY_PARAMS.otherpkgs.pkglist")) {
 | 
						|
                            @lines = <DEPLOYPARAM>;
 | 
						|
                            close(DEPLOYPARAM);
 | 
						|
                            if ($::VERBOSE) {
 | 
						|
                                my %rsp;
 | 
						|
                                push @{ $rsp{data} }, "Reading kit deployparams file $installdir/osimages/$osimage/kits/KIT_DEPLOY_PARAMS.otherpkgs.pkglist";
 | 
						|
                                xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
                            }
 | 
						|
                        } else {
 | 
						|
                            my %rsp;
 | 
						|
                            push @{ $rsp{data} }, "Could not open kit deployparams file $installdir/osimages/$osimage/kits/KIT_DEPLOY_PARAMS.otherpkgs.pkglist";
 | 
						|
                            xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                            return 1;
 | 
						|
                        }
 | 
						|
                    }
 | 
						|
 | 
						|
                    # Check if each deploy parameter is used by other kitcomponent.
 | 
						|
                    my @otherlines = ();
 | 
						|
                    foreach my $osikitcomp (@osikitcomps) {
 | 
						|
                        next if (exists($kitcomps{$osikitcomp}{name}));
 | 
						|
 | 
						|
                        (my $kitcomptable) = $tabs{kitcomponent}->getAttribs({ kitcompname => $osikitcomp }, 'kitname');
 | 
						|
                        if ($kitcomptable and $kitcomptable->{kitname}) {
 | 
						|
                            (my $kittable) = $tabs{kit}->getAttribs({ kitname => $kitcomptable->{kitname} }, 'kitdir', 'kitdeployparams');
 | 
						|
                            if ($kittable and $kittable->{kitdeployparams} and $kittable->{kitdir}) {
 | 
						|
                                my @otherdeployparams;
 | 
						|
                                my $deployparam_file = $kittable->{kitdir} . "/other_files/" . $kittable->{kitdeployparams};
 | 
						|
                                if (-e "$deployparam_file") {
 | 
						|
 | 
						|
                                    if (open(OTHERDEPLOYPARAM, "<", "$deployparam_file")) {
 | 
						|
                                        @otherdeployparams = <OTHERDEPLOYPARAM>;
 | 
						|
                                        close(OTHERDEPLOYPARAM);
 | 
						|
                                    }
 | 
						|
 | 
						|
                                    foreach (@otherdeployparams) {
 | 
						|
                                        push @otherlines, $_;
 | 
						|
                                    }
 | 
						|
 | 
						|
                                    push @otherlines, "#INCLUDE:$deployparam_file#";
 | 
						|
                                }
 | 
						|
                            }
 | 
						|
                        }
 | 
						|
                    }
 | 
						|
 | 
						|
 | 
						|
                    my @newcontents = ();
 | 
						|
                    foreach my $line (@lines) {
 | 
						|
                        chomp $line;
 | 
						|
                        my $found = 0;
 | 
						|
 | 
						|
                        #check if the parameter is used by other kitcomponent
 | 
						|
                        foreach my $otherline (@otherlines) {
 | 
						|
                            chomp $otherline;
 | 
						|
                            if ($otherline && $line =~ m!$otherline!) {
 | 
						|
                                $found = 1;
 | 
						|
                                last;
 | 
						|
                            }
 | 
						|
                        }
 | 
						|
 | 
						|
                        if ($found) {
 | 
						|
                            push @newcontents, $line . "\n";
 | 
						|
                        } else {
 | 
						|
                            foreach my $content (@contents) {
 | 
						|
                                chomp $content;
 | 
						|
                                if ($content && $line =~ m!$content!) {
 | 
						|
                                    $found = 1;
 | 
						|
                                    last;
 | 
						|
                                }
 | 
						|
                            }
 | 
						|
 | 
						|
                            unless ($found) {
 | 
						|
                                push @newcontents, $line . "\n";
 | 
						|
                            }
 | 
						|
                        }
 | 
						|
                    }
 | 
						|
 | 
						|
                    # Write the updated lines to kit deployparams file
 | 
						|
                    if (open(NEWDEPLOYPARAM, ">", "$installdir/osimages/$osimage/kits/KIT_DEPLOY_PARAMS.otherpkgs.pkglist")) {
 | 
						|
                        print NEWDEPLOYPARAM @newcontents;
 | 
						|
                        close(NEWDEPLOYPARAM);
 | 
						|
                    }
 | 
						|
                }
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
 | 
						|
        # Remove driverpacks from linuximage
 | 
						|
 | 
						|
        if ($linuximagetable and $linuximagetable->{driverupdatesrc}) {
 | 
						|
            if (exists($kitcomps{$kitcomponent}{driverpacks})) {
 | 
						|
                my @driverpacks = split ',', $kitcomps{$kitcomponent}{driverpacks};
 | 
						|
                my @driverupdatesrcs = split ',', $linuximagetable->{driverupdatesrc};
 | 
						|
 | 
						|
                my @newdriverupdatesrcs = ();
 | 
						|
 | 
						|
                foreach my $driverupdatesrc (@driverupdatesrcs) {
 | 
						|
                    my $matched = 0;
 | 
						|
                    foreach my $driverpack (@driverpacks) {
 | 
						|
                        if ($driverpack eq $driverupdatesrc) {
 | 
						|
                            $matched = 1;
 | 
						|
                            last;
 | 
						|
                        }
 | 
						|
                    }
 | 
						|
 | 
						|
                    unless ($matched) {
 | 
						|
                        push @newdriverupdatesrcs, $driverupdatesrc;
 | 
						|
                    }
 | 
						|
                }
 | 
						|
 | 
						|
                my $newdriverupdatesrc = join ',', @newdriverupdatesrcs;
 | 
						|
                $linuximagetable->{driverupdatesrc} = $newdriverupdatesrc;
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
        push @kitlist, $kitcomponent;
 | 
						|
 | 
						|
    }
 | 
						|
 | 
						|
    my $kitcompnames = join ',', @kitlist;
 | 
						|
    my %rsp;
 | 
						|
    push @{ $rsp{data} }, "kitcomponents $kitcompnames were removed from osimage $osimage successfully";
 | 
						|
    xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
 | 
						|
    # Write linuximage table with all the above udpates.
 | 
						|
    $tabs{linuximage}->setAttribs({ imagename => $osimage }, \%{$linuximagetable});
 | 
						|
 | 
						|
    # Write osimage table with all the above udpates.
 | 
						|
    $tabs{osimage}->setAttribs({ imagename => $osimage }, \%{$osimagetable});
 | 
						|
 | 
						|
    #After all the data updated in osimage and linuximage table
 | 
						|
    #check if these kitcomponents are assigned to other osimage
 | 
						|
    #if these kitcomponents are not used by other osimage, find their kitrepo and kitrepo directory under otherpkg dir
 | 
						|
    #delete these kitrepo
 | 
						|
    my @allosikitcomps = $tabs{osimage}->getAllAttribs('imagename', 'kitcomponents');
 | 
						|
 | 
						|
    (my $linuximagetable) = $tabs{linuximage}->getAttribs({ imagename => $osimage }, 'postinstall', 'exlist', 'otherpkglist', 'otherpkgdir', 'driverupdatesrc');
 | 
						|
    if ($linuximagetable and $linuximagetable->{otherpkgdir}) {
 | 
						|
 | 
						|
        my $otherpkgdir = $linuximagetable->{otherpkgdir};
 | 
						|
        $otherpkgdir = get_local_otherpkgdir($otherpkgdir);
 | 
						|
 | 
						|
        foreach my $kitcomponent (keys %kitcomps) {
 | 
						|
 | 
						|
            my %newosikitcomponents;
 | 
						|
            foreach my $allosikitcomp (@allosikitcomps) {
 | 
						|
                if ($allosikitcomp->{kitcomponents} and $allosikitcomp->{imagename}) {
 | 
						|
                    my @allkitcomps = split /,/, $allosikitcomp->{kitcomponents};
 | 
						|
                    foreach my $allkitcomp (@allkitcomps) {
 | 
						|
                        if ($allosikitcomp->{imagename} ne $osimage or $allkitcomp ne $kitcomponent) {
 | 
						|
                            $newosikitcomponents{$allkitcomp} = 1;
 | 
						|
                        }
 | 
						|
                    }
 | 
						|
                }
 | 
						|
            }
 | 
						|
 | 
						|
            if ($kitcomps{$kitcomponent}{kitreponame}) {
 | 
						|
                if (-d "$otherpkgdir/$kitcomps{$kitcomponent}{kitreponame}") {
 | 
						|
 | 
						|
                    # Check if this repo is used by other kitcomponent before removing the link
 | 
						|
                    my $match = 0;
 | 
						|
                    foreach my $osikitcomp (keys %newosikitcomponents) {
 | 
						|
 | 
						|
                        my $depkitrepodir;
 | 
						|
                        (my $kitcomptable) = $tabs{kitcomponent}->getAttribs({ kitcompname => $osikitcomp }, 'kitreponame');
 | 
						|
                        if ($kitcomptable and $kitcomptable->{kitreponame}) {
 | 
						|
                            $depkitrepodir = "$otherpkgdir/$kitcomptable->{kitreponame}";
 | 
						|
                        }
 | 
						|
                        if ($depkitrepodir =~ /^$otherpkgdir\/$kitcomps{$kitcomponent}{kitreponame}$/) {
 | 
						|
                            $match = 1;
 | 
						|
                        }
 | 
						|
                    }
 | 
						|
                    if (!$match) {
 | 
						|
                        if ($debianflag)
 | 
						|
                        {
 | 
						|
                            system("umount -f $otherpkgdir/$kitcomps{$kitcomponent}{kitreponame} > /dev/null");
 | 
						|
                        }
 | 
						|
                        system("rm -rf $otherpkgdir/$kitcomps{$kitcomponent}{kitreponame}");
 | 
						|
                    }
 | 
						|
                }
 | 
						|
            }
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
 | 
						|
 | 
						|
    return;
 | 
						|
}
 | 
						|
 | 
						|
#-------------------------------------------------------
 | 
						|
 | 
						|
=head3  chkkitcomp
 | 
						|
 | 
						|
    Check if the kit components fits to osimage
 | 
						|
 | 
						|
=cut
 | 
						|
 | 
						|
#-------------------------------------------------------
 | 
						|
sub chkkitcomp
 | 
						|
{
 | 
						|
    my $request         = shift;
 | 
						|
    my $callback        = shift;
 | 
						|
    my $request_command = shift;
 | 
						|
 | 
						|
    my $xusage = sub {
 | 
						|
        my %rsp;
 | 
						|
        push @{ $rsp{data} }, "Usage: chkkitcomp - Check if a Kit component is compatible with an xCAT osimage.";
 | 
						|
        push @{ $rsp{data} }, "\tchkkitcomp [-h|--help]";
 | 
						|
        push @{ $rsp{data} }, "\tchkkitcomp [-v|--version]";
 | 
						|
        push @{ $rsp{data} }, "\tchkkitcomp [-V|--verbose] -i <osimage> <kitcompname_list>";
 | 
						|
        xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
    };
 | 
						|
 | 
						|
    if ($^O ne 'linux') {
 | 
						|
        my $rsp = {};
 | 
						|
        push @{ $rsp->{data} }, "The chkkitcomp command is only supported on Linux.\n";
 | 
						|
        xCAT::MsgUtils->message("E", $rsp, $::CALLBACK);
 | 
						|
        return 1;
 | 
						|
    }
 | 
						|
 | 
						|
    unless (defined($request->{arg})) { $xusage->(1); return; }
 | 
						|
    @ARGV = @{ $request->{arg} };
 | 
						|
    if ($#ARGV == -1) {
 | 
						|
        $xusage->(1);
 | 
						|
        return;
 | 
						|
    }
 | 
						|
 | 
						|
    GetOptions(
 | 
						|
        'h|help'    => \$help,
 | 
						|
        'V|verbose' => \$::VERBOSE,
 | 
						|
        'v|version' => \$vers,
 | 
						|
        'i=s'       => \$osimage
 | 
						|
    );
 | 
						|
 | 
						|
    if ($help) {
 | 
						|
        $xusage->(0);
 | 
						|
        return;
 | 
						|
    }
 | 
						|
 | 
						|
    # Option -v for version
 | 
						|
    if (defined($vers)) {
 | 
						|
        create_version_response('chkkitcomp');
 | 
						|
        return 1;    # no usage - just exit
 | 
						|
    }
 | 
						|
    my $DBname = xCAT::Utils->get_DBName;    # support for DB2
 | 
						|
    my %tabs   = ();
 | 
						|
    my @tables = qw(kit kitrepo kitcomponent osimage osdistro linuximage);
 | 
						|
    foreach my $t (@tables) {
 | 
						|
        $tabs{$t} = xCAT::Table->new($t, -create => 1, -autocommit => 1);
 | 
						|
 | 
						|
        if (!exists($tabs{$t})) {
 | 
						|
            my %rsp;
 | 
						|
            push @{ $rsp{data} }, "Could not open xCAT table $t";
 | 
						|
            xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
            return 1;
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    # Check if all the kitcomponents are existing before processing
 | 
						|
 | 
						|
    my %kitcomps;
 | 
						|
    my %kitcompbasename;
 | 
						|
    my $des = shift @ARGV;
 | 
						|
    my @kitcomponents = split ',', $des;
 | 
						|
    foreach my $kitcomponent (@kitcomponents) {
 | 
						|
 | 
						|
        # Check if it is a kitcompname or basename
 | 
						|
        (my $kitcomptable) = $tabs{kitcomponent}->getAttribs({ kitcompname => $kitcomponent }, 'kitname', 'kitcompdeps', 'kitpkgdeps', 'kitreponame', 'basename', 'serverroles');
 | 
						|
        if ($kitcomptable and $kitcomptable->{'kitname'}) {
 | 
						|
            $kitcomps{$kitcomponent}{name}       = $kitcomponent;
 | 
						|
            $kitcomps{$kitcomponent}{kitname}    = $kitcomptable->{kitname};
 | 
						|
            $kitcomps{$kitcomponent}{kitpkgdeps} = $kitcomptable->{kitpkgdeps};
 | 
						|
            $kitcomps{$kitcomponent}{kitcompdeps} = $kitcomptable->{kitcompdeps};
 | 
						|
            $kitcomps{$kitcomponent}{basename} = $kitcomptable->{basename};
 | 
						|
            $kitcomps{$kitcomponent}{kitreponame} = $kitcomptable->{kitreponame};
 | 
						|
            $kitcomps{$kitcomponent}{serverroles} = $kitcomptable->{serverroles};
 | 
						|
            $kitcompbasename{ $kitcomptable->{basename} } = 1;
 | 
						|
        } else {
 | 
						|
            my @entries;
 | 
						|
            if ($DBname =~ /^DB2/) {
 | 
						|
                @entries = $tabs{kitcomponent}->getAllAttribsWhere("\"basename\" = '$kitcomponent'", 'kitcompname', 'version', 'release');
 | 
						|
            } else {
 | 
						|
                @entries = $tabs{kitcomponent}->getAllAttribsWhere("basename = '$kitcomponent'", 'kitcompname', 'version', 'release');
 | 
						|
            }
 | 
						|
            unless (@entries) {
 | 
						|
                my %rsp;
 | 
						|
                push @{ $rsp{data} }, "$kitcomponent kitcomponent does not exist";
 | 
						|
                xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                return 1;
 | 
						|
            }
 | 
						|
 | 
						|
            my $highest = get_highest_version('kitcompname', 'version', 'release', @entries);
 | 
						|
            $kitcomps{$highest}{name} = $highest;
 | 
						|
            (my $kitcomptable) = $tabs{kitcomponent}->getAttribs({ kitcompname => $highest }, 'kitname', 'kitpkgdeps', 'kitcompdeps', 'kitreponame', 'basename', 'serverroles');
 | 
						|
            $kitcomps{$highest}{kitname}     = $kitcomptable->{kitname};
 | 
						|
            $kitcomps{$highest}{kitpkgdeps}  = $kitcomptable->{kitpkgdeps};
 | 
						|
            $kitcomps{$highest}{kitcompdeps} = $kitcomptable->{kitcompdeps};
 | 
						|
            $kitcomps{$highest}{basename}    = $kitcomptable->{basename};
 | 
						|
            $kitcomps{$highest}{kitreponame} = $kitcomptable->{kitreponame};
 | 
						|
            $kitcomps{$highest}{serverroles} = $kitcomptable->{serverroles};
 | 
						|
            $kitcompbasename{$kitcomponent}  = 1;
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    # Verify if the kitcomponents fitting to the osimage or not.
 | 
						|
    my %os;
 | 
						|
    my $osdistrotable;
 | 
						|
    (my $osimagetable) = $tabs{osimage}->getAttribs({ imagename => $osimage }, 'osdistroname', 'serverrole', 'kitcomponents', 'osname', 'osvers', 'osarch');
 | 
						|
    if ($osimagetable and $osimagetable->{'osdistroname'}) {
 | 
						|
        ($osdistrotable) = $tabs{osdistro}->getAttribs({ osdistroname => $osimagetable->{'osdistroname'} }, 'basename', 'majorversion', 'minorversion', 'arch', 'type');
 | 
						|
        if (!$osdistrotable or !$osdistrotable->{basename}) {
 | 
						|
            my %rsp;
 | 
						|
            push @{ $rsp{data} }, "$osdistroname osdistro does not exist";
 | 
						|
            xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
            return 1;
 | 
						|
        }
 | 
						|
 | 
						|
        # Read basename,majorversion,minorversion,arch,type, from osdistro table
 | 
						|
        $os{$osimage}{basename}     = lc($osdistrotable->{basename});
 | 
						|
        $os{$osimage}{majorversion} = lc($osdistrotable->{majorversion});
 | 
						|
        $os{$osimage}{minorversion} = lc($osdistrotable->{minorversion});
 | 
						|
        $os{$osimage}{arch}         = lc($osdistrotable->{arch});
 | 
						|
        $os{$osimage}{type}         = lc($osdistrotable->{type});
 | 
						|
 | 
						|
        # Read serverrole from osimage.
 | 
						|
        $os{$osimage}{serverrole} = lc($osimagetable->{'serverrole'});
 | 
						|
 | 
						|
    } elsif (!$osimagetable) {
 | 
						|
        my %rsp;
 | 
						|
        push @{ $rsp{data} }, "osimage $osimage does not exist";
 | 
						|
        xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
        return 1;
 | 
						|
    } elsif (!$osimagetable->{'osname'}) {
 | 
						|
        my %rsp;
 | 
						|
        push @{ $rsp{data} }, "osimage $osimage does not contain a valid 'osname' attribute";
 | 
						|
        xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
        return 1;
 | 
						|
    } elsif (!$osimagetable->{'osvers'}) {
 | 
						|
        my %rsp;
 | 
						|
        push @{ $rsp{data} }, "osimage $osimage does not contain a valid 'osvers' attribute";
 | 
						|
        xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
        return 1;
 | 
						|
    } elsif (!$osimagetable->{'osarch'}) {
 | 
						|
        my %rsp;
 | 
						|
        push @{ $rsp{data} }, "osimage $osimage does not contain a valid 'osarch' attribute";
 | 
						|
        xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
        return 1;
 | 
						|
    } else {
 | 
						|
        $os{$osimage}{type}       = lc($osimagetable->{'osname'});
 | 
						|
        $os{$osimage}{arch}       = lc($osimagetable->{'osarch'});
 | 
						|
        $os{$osimage}{serverrole} = lc($osimagetable->{'serverrole'});
 | 
						|
 | 
						|
        my ($basename, $majorversion, $minorversion) = $osimagetable->{'osvers'} =~ /^(\D+)(\d+)\W+(\d+)/;
 | 
						|
        $os{$osimage}{basename}     = lc($basename);
 | 
						|
        $os{$osimage}{majorversion} = lc($majorversion);
 | 
						|
        $os{$osimage}{minorversion} = lc($minorversion);
 | 
						|
    }
 | 
						|
 | 
						|
    my @kitcompnames;
 | 
						|
    foreach my $kitcomp (keys %kitcomps) {
 | 
						|
        if ($kitcomps{$kitcomp}{kitname} and $kitcomps{$kitcomp}{kitreponame}) {
 | 
						|
 | 
						|
            # Read ostype from kit table
 | 
						|
            (my $kittable) = $tabs{kit}->getAttribs({ kitname => $kitcomps{$kitcomp}{kitname} }, 'ostype');
 | 
						|
            if ($kittable and $kittable->{ostype}) {
 | 
						|
                $kitcomps{$kitcomp}{ostype} = lc($kittable->{ostype});
 | 
						|
            } else {
 | 
						|
                my %rsp;
 | 
						|
                push @{ $rsp{data} }, "$kitcomp ostype does not exist";
 | 
						|
                xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                return 1;
 | 
						|
            }
 | 
						|
 | 
						|
            # Read osbasename, osmajorversion,osminorversion,osarch,compat_osbasenames from kitrepo table
 | 
						|
            (my $kitrepotable) = $tabs{kitrepo}->getAttribs({ kitreponame => $kitcomps{$kitcomp}{kitreponame} }, 'osbasename', 'osmajorversion', 'osminorversion', 'osarch', 'compat_osbasenames');
 | 
						|
            if ($kitrepotable and $kitrepotable->{osbasename} and $kitrepotable->{osmajorversion} and $kitrepotable->{osarch}) {
 | 
						|
                if ($kitrepotable->{compat_osbasenames}) {
 | 
						|
                    $kitcomps{$kitcomp}{osbasename} = lc($kitrepotable->{osbasename}) . ',' . lc($kitrepotable->{compat_osbasenames});
 | 
						|
                } else {
 | 
						|
                    $kitcomps{$kitcomp}{osbasename} = lc($kitrepotable->{osbasename});
 | 
						|
                }
 | 
						|
 | 
						|
                $kitcomps{$kitcomp}{osmajorversion} = lc($kitrepotable->{osmajorversion});
 | 
						|
                $kitcomps{$kitcomp}{osminorversion} = lc($kitrepotable->{osminorversion});
 | 
						|
                $kitcomps{$kitcomp}{osarch} = lc($kitrepotable->{osarch});
 | 
						|
            } else {
 | 
						|
                my %rsp;
 | 
						|
                push @{ $rsp{data} }, "$kitcomp osbasename,osmajorversion,osminorversion or osarch does not exist";
 | 
						|
                xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                return 1;
 | 
						|
            }
 | 
						|
 | 
						|
        } else {
 | 
						|
            my %rsp;
 | 
						|
            push @{ $rsp{data} }, "$kitcomp kitname $kitcomptable->{'kitname'} or kitrepo name $kitcomptable->{'kitreponame'} or serverroles $kitcomps{$kitcomp}{serverroles} does not exist";
 | 
						|
            xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
            return 1;
 | 
						|
        }
 | 
						|
 | 
						|
        # Validate each attribute in kitcomp.
 | 
						|
        my $catched = 0;
 | 
						|
        my @osbasename = split ',', $kitcomps{$kitcomp}{osbasename};
 | 
						|
        foreach (@osbasename) {
 | 
						|
            if ($os{$osimage}{basename} eq $_) {
 | 
						|
                $catched = 1;
 | 
						|
            }
 | 
						|
        }
 | 
						|
        unless ($catched) {
 | 
						|
            my %rsp;
 | 
						|
            push @{ $rsp{data} }, "kit component $kitcomp is not compatible with osimage $osimage with attribute OS";
 | 
						|
            xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
            return 1;
 | 
						|
        }
 | 
						|
 | 
						|
        if ($os{$osimage}{majorversion} ne $kitcomps{$kitcomp}{osmajorversion}) {
 | 
						|
            my %rsp;
 | 
						|
            push @{ $rsp{data} }, "kit component $kitcomp is not compatible with osimage $osimage with attribute majorversion";
 | 
						|
            xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
            return 1;
 | 
						|
        }
 | 
						|
 | 
						|
        if ($kitcomps{$kitcomp}{osminorversion} ) {
 | 
						|
            if (check_minorversion($kitcomps{$kitcomp}{osminorversion}, $os{$osimage}{minorversion}))
 | 
						|
            {
 | 
						|
                my %rsp;
 | 
						|
                push @{ $rsp{data} }, "kit component $kitcomp is not compatible with osimage $osimage with attribute minorversion";
 | 
						|
                xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                return 1;
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
        if ($os{$osimage}{arch} ne $kitcomps{$kitcomp}{osarch} && $kitcomps{$kitcomp}{osarch} ne 'noarch') {
 | 
						|
            my %rsp;
 | 
						|
            push @{ $rsp{data} }, "kit component $kitcomp is not compatible with osimage $osimage with attribute arch";
 | 
						|
            xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
            return 1;
 | 
						|
        }
 | 
						|
 | 
						|
        if ($os{$osimage}{type} ne $kitcomps{$kitcomp}{ostype}) {
 | 
						|
            my %rsp;
 | 
						|
            push @{ $rsp{data} }, "kit component $kitcomp is not compatible with osimage $osimage with attribute type";
 | 
						|
            xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
            return 1;
 | 
						|
        }
 | 
						|
 | 
						|
        if ($os{$osimage}{serverrole}) {
 | 
						|
            my $match = 0;
 | 
						|
            my @os_serverroles = split /,/, $os{$osimage}{serverrole};
 | 
						|
            my @kitcomp_serverroles = split /,/, $kitcomps{$kitcomp}{serverroles};
 | 
						|
            foreach my $os_serverrole (@os_serverroles) {
 | 
						|
                foreach my $kitcomp_serverrole (@kitcomp_serverroles) {
 | 
						|
                    if ($os_serverrole eq $kitcomp_serverrole) {
 | 
						|
                        $match = 1;
 | 
						|
                        last;
 | 
						|
                    }
 | 
						|
                }
 | 
						|
 | 
						|
                if ($match) {
 | 
						|
                    last;
 | 
						|
                }
 | 
						|
            }
 | 
						|
            if (!$match) {
 | 
						|
                my %rsp;
 | 
						|
                push @{ $rsp{data} }, "osimage $osimage is not compatible with kit component $kitcomp with attribute serverrole";
 | 
						|
                xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                return 1;
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
        # Check if this kit component's dependencies are in the kitcomponent list.
 | 
						|
        if ($kitcomps{$kitcomp}{kitcompdeps}) {
 | 
						|
            my ($kitcompdep, $vers) = split /<=|>=|=|<|>/, $kitcomps{$kitcomp}{kitcompdeps};
 | 
						|
            if (!exists($kitcompbasename{$kitcompdep})) {
 | 
						|
                my %rsp;
 | 
						|
                push @{ $rsp{data} }, "kit component $kitcomp dependency $kitcomps{$kitcomp}{kitcompdeps} doesn't exist";
 | 
						|
                xCAT::MsgUtils->message("E", \%rsp, $callback);
 | 
						|
                return 1;
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
        push @kitcompnames, $kitcomp;
 | 
						|
    }
 | 
						|
 | 
						|
    my $kitcompnamelist = join ',', @kitcompnames;
 | 
						|
 | 
						|
    my %rsp;
 | 
						|
    push @{ $rsp{data} }, "Kit components $kitcompnamelist are compatible with osimage $osimage";
 | 
						|
    xCAT::MsgUtils->message("I", \%rsp, $callback);
 | 
						|
 | 
						|
    return;
 | 
						|
}
 | 
						|
 | 
						|
#----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3  lskit_usage
 | 
						|
 | 
						|
        Display the lskit usage
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
 | 
						|
sub lskit_usage {
 | 
						|
    my $rsp;
 | 
						|
    push @{ $rsp->{data} },
 | 
						|
      "\nUsage: lskit - List infomation for one or more kits.\n";
 | 
						|
    push @{ $rsp->{data} },
 | 
						|
"\tlskit [-V|--verbose] [-x|--xml|--XML] [-K|--kitattr kitattr_names]\n\t[-R|--repoattr repoattr_names] [-C|--compattr compattr_names]\n\t[kit_names]\n ";
 | 
						|
    push @{ $rsp->{data} }, "\tlskit [-h|--help|-?]\n";
 | 
						|
    push @{ $rsp->{data} }, "\tlskit [-v|--version]\n ";
 | 
						|
    push @{ $rsp->{data} }, "\tlskit [-F|--framework] kit_path_name\n ";
 | 
						|
    xCAT::MsgUtils->message("I", $rsp, $::CALLBACK);
 | 
						|
    return 0;
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
#----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3  lskitcomp_usage
 | 
						|
 | 
						|
        Display the lskitcomp usage
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
 | 
						|
sub lskitcomp_usage {
 | 
						|
    my $rsp;
 | 
						|
    push @{ $rsp->{data} },
 | 
						|
      "\nUsage: lskitcomp - List information for one or more Kit components.";
 | 
						|
    push @{ $rsp->{data} }, "\tlskitcomp [-h|--help|-?]";
 | 
						|
    push @{ $rsp->{data} }, "\tlskitcomp [-v|--version]";
 | 
						|
    push @{ $rsp->{data} }, "\tlskitcomp [-V|--verbose] [-x|--xml|--XML] \n\t\t[-C|--compattr compattr_names] [-O|--osdistro os_distro]\n\t\t[-S|--serverrole server_role] [kitcomp_names]\n ";
 | 
						|
    xCAT::MsgUtils->message("I", $rsp, $::CALLBACK);
 | 
						|
    return 0;
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
#----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3  lskitdeployparam_usage
 | 
						|
 | 
						|
        Display the lskitdeployparam usage
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
 | 
						|
sub lskitdeployparam_usage {
 | 
						|
    my $rsp;
 | 
						|
    push @{ $rsp->{data} }, "\nUsage: lskitdeployparam - List the kit deployment parameters for full Kits or Kit components.";
 | 
						|
    push @{ $rsp->{data} }, "\tlskitdeployparam [-h|--help|-?]";
 | 
						|
    push @{ $rsp->{data} }, "\tlskitdeployparam [-v|--version]";
 | 
						|
    push @{ $rsp->{data} }, "\tlskitdeployparam [-V|--verbose] [-x|--xml|--XML] \n\t\t[-k|--kitname kit_names] [-c|--compname comp_names]\n";
 | 
						|
    xCAT::MsgUtils->message("I", $rsp, $::CALLBACK);
 | 
						|
    return 0;
 | 
						|
}
 | 
						|
 | 
						|
#----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3  create_version_response
 | 
						|
 | 
						|
        Create a response containing the command name and version
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
sub create_version_response {
 | 
						|
    my $command = shift;
 | 
						|
    my $rsp;
 | 
						|
    my $version = xCAT::Utils->Version();
 | 
						|
    push @{ $rsp->{data} }, "$command - xCAT $version";
 | 
						|
    push @{ $rsp->{data} }, "\tkitframework = $::KITFRAMEWORK";
 | 
						|
    push @{ $rsp->{data} }, "\tcompatible_frameworks = $::COMPATIBLE_KITFRAMEWORKS\n";
 | 
						|
    xCAT::MsgUtils->message("I", $rsp, $::CALLBACK);
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
#----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3  create_error_response
 | 
						|
 | 
						|
        Create a response containing a single error message
 | 
						|
        Arguments:  error message
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
sub create_error_response {
 | 
						|
    my $error_msg = shift;
 | 
						|
    my $rsp;
 | 
						|
    push @{ $rsp->{data} }, $error_msg;
 | 
						|
    xCAT::MsgUtils->message("E", $rsp, $::CALLBACK);
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
#----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3   lskit_processargs
 | 
						|
 | 
						|
        Process the lskit command line
 | 
						|
        Returns:
 | 
						|
                0 - OK
 | 
						|
                1 - just print version
 | 
						|
                2 - just print help
 | 
						|
                3 - error
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
sub lskit_processargs {
 | 
						|
    if (defined($::args) && @{$::args}) {
 | 
						|
        @ARGV = @{$::args};
 | 
						|
    }
 | 
						|
 | 
						|
    # parse the options
 | 
						|
    # options can be bundled up like -vV, flag unsupported options
 | 
						|
    Getopt::Long::Configure("bundling", "no_ignore_case", "no_pass_through");
 | 
						|
    my $getopt_success = Getopt::Long::GetOptions(
 | 
						|
        'help|h|?'      => \$::opt_h,
 | 
						|
        'kitattr|K=s'   => \$::opt_K,
 | 
						|
        'repoattr|R=s'  => \$::opt_R,
 | 
						|
        'compattr|C=s'  => \$::opt_C,
 | 
						|
        'framework|F=s' => \$::opt_F,
 | 
						|
        'verbose|V'     => \$::opt_V,
 | 
						|
        'version|v'     => \$::opt_v,
 | 
						|
        'xml|XML|x'     => \$::opt_x,
 | 
						|
    );
 | 
						|
 | 
						|
    if (!$getopt_success) {
 | 
						|
        return 3;
 | 
						|
    }
 | 
						|
 | 
						|
    # Option -h for Help
 | 
						|
    if (defined($::opt_h)) {
 | 
						|
        return 2;
 | 
						|
    }
 | 
						|
 | 
						|
    # Option -v for version
 | 
						|
    if (defined($::opt_v)) {
 | 
						|
        create_version_response('lskit');
 | 
						|
        return 1;    # no usage - just exit
 | 
						|
    }
 | 
						|
 | 
						|
    # Option -V for verbose output
 | 
						|
    if (defined($::opt_V)) {
 | 
						|
        $::VERBOSE = 1;
 | 
						|
    }
 | 
						|
 | 
						|
    # Option -K for kit attributes
 | 
						|
    if (defined($::opt_K)) {
 | 
						|
        $::kitattrs = split_comma_delim_str($::opt_K);
 | 
						|
        ensure_kitname_attr_in_list($::kitattrs);
 | 
						|
        if (check_attr_names_exist('kit', $::kitattrs) != 0) {
 | 
						|
            return 3;
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    # Option -R for kit repo attributes
 | 
						|
    if (defined($::opt_R)) {
 | 
						|
        $::kitrepoattrs = split_comma_delim_str($::opt_R);
 | 
						|
        ensure_kitname_attr_in_list($::kitrepoattrs);
 | 
						|
        if (check_attr_names_exist('kitrepo', $::kitrepoattrs) != 0) {
 | 
						|
            return 3;
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    # Option -C for kit component attributes
 | 
						|
    if (defined($::opt_C)) {
 | 
						|
        $::kitcompattrs = split_comma_delim_str($::opt_C);
 | 
						|
        ensure_kitname_attr_in_list($::kitcompattrs);
 | 
						|
        if (check_attr_names_exist('kitcomponent', $::kitcompattrs) != 0) {
 | 
						|
            return 3;
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    # Kit names
 | 
						|
    my $kitnames_str = shift(@ARGV);
 | 
						|
    if (defined($kitnames_str)) {
 | 
						|
        my @tmp = split(/,/, $kitnames_str);
 | 
						|
        $::kitnames = \@tmp;
 | 
						|
        if (check_attr_values_exist('kit', 'kitname', 'kit names', $::kitnames) != 0) {
 | 
						|
            return 3;
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    # Other attributes are not allowed
 | 
						|
    my $more_input = shift(@ARGV);
 | 
						|
    if (defined($more_input)) {
 | 
						|
        create_error_response("Invalid input: $more_input \n");
 | 
						|
        return 3;
 | 
						|
    }
 | 
						|
 | 
						|
    return 0;
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
#----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3   lskitcomp_processargs
 | 
						|
 | 
						|
        Process the lskitcomp command line
 | 
						|
        Returns:
 | 
						|
                0 - OK
 | 
						|
                1 - just print version
 | 
						|
                2 - just print help
 | 
						|
                3 - error
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
sub lskitcomp_processargs {
 | 
						|
 | 
						|
    if (defined($::args) && @{$::args}) {
 | 
						|
        @ARGV = @{$::args};
 | 
						|
    }
 | 
						|
 | 
						|
    # parse the options
 | 
						|
    # options can be bundled up like -vV, flag unsupported options
 | 
						|
    Getopt::Long::Configure("bundling", "no_ignore_case", "no_pass_through");
 | 
						|
    my $getopt_success = Getopt::Long::GetOptions(
 | 
						|
        'help|h|?'       => \$::opt_h,
 | 
						|
        'compattr|C=s'   => \$::opt_C,
 | 
						|
        'osdistro|O=s'   => \$::opt_O,
 | 
						|
        'serverrole|S=s' => \$::opt_S,
 | 
						|
        'verbose|V'      => \$::opt_V,
 | 
						|
        'version|v'      => \$::opt_v,
 | 
						|
        'xml|XML|x'      => \$::opt_x,
 | 
						|
    );
 | 
						|
 | 
						|
    if (!$getopt_success) {
 | 
						|
        return 3;
 | 
						|
    }
 | 
						|
 | 
						|
    # Option -h for Help
 | 
						|
    if (defined($::opt_h)) {
 | 
						|
        return 2;
 | 
						|
    }
 | 
						|
 | 
						|
    # Option -v for version
 | 
						|
    if (defined($::opt_v)) {
 | 
						|
        create_version_response('lskitcomp');
 | 
						|
        return 1;    # no usage - just exit
 | 
						|
    }
 | 
						|
 | 
						|
    # Option -V for verbose output
 | 
						|
    if (defined($::opt_V)) {
 | 
						|
        $::VERBOSE = 1;
 | 
						|
    }
 | 
						|
 | 
						|
    # Option -C for kit component attributes
 | 
						|
    if (defined($::opt_C)) {
 | 
						|
        $::kitcompattrs = split_comma_delim_str($::opt_C);
 | 
						|
        push(@{$::kitcompattrs}, "kitcompname");
 | 
						|
        ensure_kitname_attr_in_list($::kitcompattrs);
 | 
						|
        if (check_attr_names_exist('kitcomponent', $::kitcompattrs) != 0) {
 | 
						|
            return 3;
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    # Option -O for osdistro name
 | 
						|
    $::osdistroname = $::opt_O;
 | 
						|
    if (defined($::osdistroname)) {
 | 
						|
        if (check_attr_values_exist('osdistro', 'osdistroname', 'os distro', [$::osdistroname]) != 0) {
 | 
						|
            return 3;
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    # Option -S for server role
 | 
						|
    $::serverrole = $::opt_S;
 | 
						|
 | 
						|
    # Kit component names
 | 
						|
    my $kitcompnames_str = shift(@ARGV);
 | 
						|
    if (defined($kitcompnames_str)) {
 | 
						|
        my @tmp = split(/,/, $kitcompnames_str);
 | 
						|
        $::kitcompnames = \@tmp;
 | 
						|
        if (check_attr_values_exist('kitcomponent', 'kitcompname', 'kit component names', $::kitcompnames) != 0) {
 | 
						|
            return 3;
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    # Other attributes are not allowed
 | 
						|
    my $more_input = shift(@ARGV);
 | 
						|
    if (defined($more_input)) {
 | 
						|
        create_error_response("Invalid input: $more_input \n");
 | 
						|
        return 3;
 | 
						|
    }
 | 
						|
 | 
						|
    return 0;
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
#----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3   lskitdeployparam_processargs
 | 
						|
 | 
						|
        Process the lskitdeployparam command line
 | 
						|
        Returns:
 | 
						|
                0 - OK
 | 
						|
                1 - just print version
 | 
						|
                2 - just print help
 | 
						|
                3 - error
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
sub lskitdeployparam_processargs {
 | 
						|
 | 
						|
    if (defined($::args) && @{$::args}) {
 | 
						|
        @ARGV = @{$::args};
 | 
						|
    }
 | 
						|
 | 
						|
    # parse the options
 | 
						|
    # options can be bundled up like -vV, flag unsupported options
 | 
						|
    Getopt::Long::Configure("bundling", "no_ignore_case", "no_pass_through");
 | 
						|
    my $getopt_success = Getopt::Long::GetOptions(
 | 
						|
        'help|h|?'     => \$::opt_h,
 | 
						|
        'kitname|k=s'  => \$::opt_k,
 | 
						|
        'compname|c=s' => \$::opt_c,
 | 
						|
        'verbose|V'    => \$::opt_V,
 | 
						|
        'version|v'    => \$::opt_v,
 | 
						|
        'xml|XML|x'    => \$::opt_x,
 | 
						|
    );
 | 
						|
 | 
						|
    if (!$getopt_success) {
 | 
						|
        return 3;
 | 
						|
    }
 | 
						|
 | 
						|
    # Option -h for Help
 | 
						|
    if (defined($::opt_h)) {
 | 
						|
        return 2;
 | 
						|
    }
 | 
						|
 | 
						|
    # Option -v for version
 | 
						|
    if (defined($::opt_v)) {
 | 
						|
        create_version_response('lskitdeployparam');
 | 
						|
        return 1;    # no usage - just exit
 | 
						|
    }
 | 
						|
 | 
						|
    # Option -V for verbose output
 | 
						|
    if (defined($::opt_V)) {
 | 
						|
        $::VERBOSE = 1;
 | 
						|
    }
 | 
						|
 | 
						|
    # Ensure -k and -c option not used together
 | 
						|
    if (defined($::opt_k) && defined($::opt_c)) {
 | 
						|
        create_error_response("The -k and -c options cannot be used together.");
 | 
						|
        return 3;
 | 
						|
    }
 | 
						|
 | 
						|
    # Ensure -k or -c option are specified
 | 
						|
    if (!defined($::opt_k) && !defined($::opt_c)) {
 | 
						|
        create_error_response("The -k or -c option must be specified.");
 | 
						|
        return 3;
 | 
						|
    }
 | 
						|
 | 
						|
    # Option -k for kit names
 | 
						|
    if (defined($::opt_k)) {
 | 
						|
        $::kitnames = split_comma_delim_str($::opt_k);
 | 
						|
        if (check_attr_values_exist('kit', 'kitname', 'kit names', $::kitnames) != 0) {
 | 
						|
            return 3;
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    # Option -c for kitocmponent names
 | 
						|
    if (defined($::opt_c)) {
 | 
						|
        $::kitcompnames = split_comma_delim_str($::opt_c);
 | 
						|
        if (check_attr_values_exist('kitcomponent', 'kitcompname', 'kit component names', $::kitcompnames) != 0) {
 | 
						|
            return 3;
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    # Other attributes are not allowed
 | 
						|
    my $more_input = shift(@ARGV);
 | 
						|
    if (defined($more_input)) {
 | 
						|
        create_error_response("Invalid input: $more_input \n");
 | 
						|
        return 3;
 | 
						|
    }
 | 
						|
 | 
						|
    return 0;
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
#----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3  split_comma_delim_str
 | 
						|
 | 
						|
        Split comma-delimited list of strings into an array.
 | 
						|
 | 
						|
        Arguments: comma-delimited string
 | 
						|
        Returns:   Returns list of strings (ref)
 | 
						|
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
sub split_comma_delim_str {
 | 
						|
    my $input_str = shift;
 | 
						|
 | 
						|
    my @result = split(/,/, $input_str);
 | 
						|
    return \@result;
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
#----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3  ensure_kitname_attr_in_list
 | 
						|
 | 
						|
        Checks if 'kitname' attribute is in specified attribute list.
 | 
						|
        If not, then add it.
 | 
						|
 | 
						|
        Arguments: list of attribute names (ref)
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
sub ensure_kitname_attr_in_list {
 | 
						|
    my $attrs = shift;
 | 
						|
 | 
						|
    if (defined($attrs)) {
 | 
						|
        if (!grep(/^kitname$/, @$attrs)) {
 | 
						|
            push(@$attrs, "kitname");
 | 
						|
        }
 | 
						|
    }
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
#----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3  check_attr_names_exist
 | 
						|
 | 
						|
        Check if list of DB attribute names exist in a table
 | 
						|
        Arguments:  a table name
 | 
						|
                    a list of attribute names to check (ref)
 | 
						|
        Returns:
 | 
						|
                0 - OK
 | 
						|
                1 - error
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
sub check_attr_names_exist {
 | 
						|
 | 
						|
    my $tablename = shift;
 | 
						|
    my $attrs     = shift;
 | 
						|
    my @badattrs  = ();
 | 
						|
 | 
						|
    if (defined($attrs)) {
 | 
						|
        my $schema = xCAT::Table->getTableSchema($tablename);
 | 
						|
        my @cols   = @{ $schema->{cols} };
 | 
						|
        foreach my $attr (@{$attrs}) {
 | 
						|
            if (!grep { $_ eq $attr } @cols) {
 | 
						|
                push(@badattrs, $attr);
 | 
						|
            }
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    if (scalar @badattrs > 0) {
 | 
						|
        my $error = sprintf("The following %s attributes are not valid: %s.",
 | 
						|
            $tablename, join(",", @badattrs));
 | 
						|
        create_error_response($error);
 | 
						|
        return 1;
 | 
						|
    }
 | 
						|
    return 0;
 | 
						|
}
 | 
						|
 | 
						|
#----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3  check_attr_values_exist
 | 
						|
 | 
						|
        Check if a list of DB attribute values exist
 | 
						|
        Arguments:
 | 
						|
                table name
 | 
						|
                table attribute
 | 
						|
                table attribute desc (e.g. kit names), this string is added to error message
 | 
						|
                list of values to check (ref)
 | 
						|
        Returns:
 | 
						|
                0 - OK
 | 
						|
                1 - error
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
sub check_attr_values_exist {
 | 
						|
 | 
						|
    my $tablename       = shift;
 | 
						|
    my $tableattr       = shift;
 | 
						|
    my $tableattr_desc  = shift;
 | 
						|
    my $values_to_check = shift;
 | 
						|
    my @badvalues       = ();
 | 
						|
 | 
						|
    my $filter_stmt = db_build_filter_stmt({ $tableattr => $values_to_check });
 | 
						|
    my $rows = db_get_table_rows($tablename, [$tableattr], $filter_stmt);
 | 
						|
 | 
						|
    my @values_in_DB = map { $_->{$tableattr} } @$rows;
 | 
						|
    foreach my $value_to_check (@{$values_to_check}) {
 | 
						|
        if (!grep { $_ eq $value_to_check } @values_in_DB) {
 | 
						|
            push(@badvalues, $value_to_check);
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    if (scalar @badvalues > 0) {
 | 
						|
        my $error;
 | 
						|
        if ($tableattr_desc =~ /s$/) {
 | 
						|
            $error = sprintf("The following %s are not valid: %s.", $tableattr_desc, join(",", @badvalues));
 | 
						|
        } else {
 | 
						|
            $error = sprintf("The following %s is not valid: %s.", $tableattr_desc, join(",", @badvalues));
 | 
						|
        }
 | 
						|
        create_error_response($error);
 | 
						|
        return 1;
 | 
						|
    }
 | 
						|
 | 
						|
    return 0;
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
 | 
						|
#----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3  lskit
 | 
						|
 | 
						|
        Support for listing kits
 | 
						|
        Returns:
 | 
						|
                0 - OK
 | 
						|
                1 - help
 | 
						|
                2 - error
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
sub lskit {
 | 
						|
 | 
						|
    my $request         = shift;
 | 
						|
    my $callback        = shift;
 | 
						|
    my $request_command = shift;
 | 
						|
 | 
						|
    my $rc = 0;
 | 
						|
 | 
						|
    # process the command line
 | 
						|
    # 0=success, 1=version, 2=help, 3=error
 | 
						|
 | 
						|
    $rc = lskit_processargs(@_);
 | 
						|
    if ($rc != 0) {
 | 
						|
        if ($rc != 1) {
 | 
						|
            lskit_usage(@_);
 | 
						|
        }
 | 
						|
        return ($rc - 1);
 | 
						|
    }
 | 
						|
 | 
						|
    if ($^O ne 'linux') {
 | 
						|
        my $rsp = {};
 | 
						|
        push @{ $rsp->{data} }, "The lskit command is only supported on Linux.\n";
 | 
						|
        xCAT::MsgUtils->message("E", $rsp, $::CALLBACK);
 | 
						|
        return 1;
 | 
						|
    }
 | 
						|
 | 
						|
    if (defined($::opt_F)) {
 | 
						|
        if (defined($::opt_x) || defined($::opt_K) || defined($::opt_R) || defined($::opt_C)) {
 | 
						|
            my $rsp = {};
 | 
						|
            push @{ $rsp->{data} }, "\nThe \'-F\' option cannot be used with the x, R, K, or C options.\n";
 | 
						|
            xCAT::MsgUtils->message("E", $rsp, $::CALLBACK);
 | 
						|
            lskit_usage(1);
 | 
						|
            return 1;
 | 
						|
        }
 | 
						|
        my $tarpathname = $::opt_F;
 | 
						|
 | 
						|
        # check if full path
 | 
						|
        my $dir = $request->{cwd};    #getcwd;
 | 
						|
        my $cwd = $dir->[0];
 | 
						|
 | 
						|
        if ($tarpathname !~ /^\//)
 | 
						|
        {
 | 
						|
            my $fullpath = xCAT::Utils->full_path($tarpathname, $cwd);
 | 
						|
            if ($fullpath)
 | 
						|
            {
 | 
						|
                $tarpathname = $fullpath;
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
        unless (-e $tarpathname) {
 | 
						|
            my $rsp = {};
 | 
						|
            push @{ $rsp->{data} }, "Could not find $tarpathname.\n";
 | 
						|
            xCAT::MsgUtils->message("E", $rsp, $::CALLBACK);
 | 
						|
            return 1;
 | 
						|
        }
 | 
						|
 | 
						|
        #  create a unique  /tmp dir name name
 | 
						|
        my $thisdate     = `/bin/date +%s`;
 | 
						|
        my $tmp_dir_name = qq~/tmp/tmp_kit_$thisdate~;
 | 
						|
        $tmp_dir_name =~ s/\s*//g;    #remove blanks
 | 
						|
 | 
						|
        # extract the kit.conf file
 | 
						|
        my $rsp = {};
 | 
						|
        push @{ $rsp->{data} }, "\nExtracting the kit.conf file from $tarpathname. Please wait.\n";
 | 
						|
        xCAT::MsgUtils->message("I", $rsp, $::CALLBACK);
 | 
						|
 | 
						|
        my $tcmd = qq~/bin/mkdir -p $tmp_dir_name;/bin/tar -C $tmp_dir_name -jxvf $tarpathname --wildcards */kit.conf~;
 | 
						|
        my $kitconffile = xCAT::Utils->runcmd("$tcmd", -1);
 | 
						|
        if ($::RUNCMD_RC != 0) {
 | 
						|
            my $rsp = {};
 | 
						|
            push @{ $rsp->{data} }, "No kit.conf file was found.\n";
 | 
						|
            xCAT::MsgUtils->message("E", $rsp, $::CALLBACK);
 | 
						|
            return 1;
 | 
						|
        }
 | 
						|
 | 
						|
        # get the framework from the file
 | 
						|
        my $fcmd = "/bin/cat $tmp_dir_name/$kitconffile | grep 'kitframework '";
 | 
						|
        my $fline = xCAT::Utils->runcmd("$fcmd", -1);
 | 
						|
        if ($::RUNCMD_RC != 0) {
 | 
						|
            my $rsp = {};
 | 
						|
            push @{ $rsp->{data} }, "No kitframework value was found.\n";
 | 
						|
            xCAT::MsgUtils->message("E", $rsp, $::CALLBACK);
 | 
						|
            return 1;
 | 
						|
        }
 | 
						|
        my ($junk, $kitframework) = split(/=/, $fline);
 | 
						|
        $kitframework =~ s/\s*//g;    #remove blanks
 | 
						|
 | 
						|
        my $cfcmd = "/bin/cat $tmp_dir_name/$kitconffile | grep 'compatible_kitframeworks'";
 | 
						|
        my $cfline = xCAT::Utils->runcmd("$cfcmd", -1);
 | 
						|
        if ($::RUNCMD_RC != 0) {
 | 
						|
            my $rsp = {};
 | 
						|
            push @{ $rsp->{data} }, "No compatible_kitframeworks value was found.\n";
 | 
						|
            xCAT::MsgUtils->message("E", $rsp, $::CALLBACK);
 | 
						|
            return 1;
 | 
						|
        }
 | 
						|
        my ($junk, $compatframework) = split(/=/, $cfline);
 | 
						|
        $compatframework =~ s/\s*//g;    #remove blanks
 | 
						|
 | 
						|
        my $rcmd = qq~/bin/rm -Rf $tmp_dir_name 2>/dev/null~;
 | 
						|
        my $out = xCAT::Utils->runcmd("$rcmd", -1);
 | 
						|
        if ($::RUNCMD_RC != 0) {
 | 
						|
            my $rsp = {};
 | 
						|
            push @{ $rsp->{data} }, "Could not remove $tmp_dir_name.\n";
 | 
						|
            xCAT::MsgUtils->message("E", $rsp, $::CALLBACK);
 | 
						|
        }
 | 
						|
 | 
						|
        if ($kitframework && $compatframework) {
 | 
						|
            my $rsp = {};
 | 
						|
            push @{ $rsp->{data} }, "\tkitframework=$kitframework\n\tcompatible_kitframeworks=$compatframework\n";
 | 
						|
            xCAT::MsgUtils->message("I", $rsp, $::CALLBACK);
 | 
						|
            return 0;
 | 
						|
        } else {
 | 
						|
            my $rsp = {};
 | 
						|
            push @{ $rsp->{data} }, "Could not determine framework values for Kit $tarpathname.\n";
 | 
						|
            xCAT::MsgUtils->message("E", $rsp, $::CALLBACK);
 | 
						|
            return 1;
 | 
						|
        }
 | 
						|
        return 0;
 | 
						|
    }
 | 
						|
 | 
						|
    # Prepare the hash tables to pass to the output routines
 | 
						|
    my $kit_hash = get_kit_hash($::kitnames, $::kitattrs);
 | 
						|
    my $kitrepo_hash = get_kitrepo_hash($::kitnames, $::kitrepoattrs);
 | 
						|
    my $kitcomp_hash = get_kitcomp_hash($::kitnames, $::kitcompattrs);
 | 
						|
 | 
						|
 | 
						|
 | 
						|
    # Now display the output
 | 
						|
    my @kitnames = keys(%$kit_hash);
 | 
						|
    if (scalar @kitnames == 0) {
 | 
						|
        my $rsp = {};
 | 
						|
        push @{ $rsp->{data} }, "No kits were found.";
 | 
						|
        xCAT::MsgUtils->message("I", $rsp, $::CALLBACK);
 | 
						|
        return 0;
 | 
						|
    }
 | 
						|
    if (defined($::opt_K) || defined($::opt_R) || defined($::opt_C)) {
 | 
						|
 | 
						|
        if (!defined($::opt_x)) {
 | 
						|
            if (defined($::opt_K)) {
 | 
						|
                lskit_K($kit_hash);
 | 
						|
            }
 | 
						|
 | 
						|
            # Option -R for kit repo attributes
 | 
						|
            if (defined($::opt_R)) {
 | 
						|
                my @kitrepos = keys(%$kitrepo_hash);
 | 
						|
                if (scalar @kitrepos == 0) {
 | 
						|
                    my $rsp = {};
 | 
						|
                    push @{ $rsp->{data} }, "No kit repos were found.";
 | 
						|
                    xCAT::MsgUtils->message("I", $rsp, $::CALLBACK);
 | 
						|
                    return 0;
 | 
						|
                }
 | 
						|
                lskit_R($kit_hash, $kitrepo_hash);
 | 
						|
            }
 | 
						|
 | 
						|
            if (defined($::opt_C)) {
 | 
						|
                my @kitcomplist = keys(%$kitcomp_hash);
 | 
						|
                if (scalar @kitcomplist == 0) {
 | 
						|
                    my $rsp = {};
 | 
						|
                    push @{ $rsp->{data} }, "No kit components were found.";
 | 
						|
                    xCAT::MsgUtils->message("I", $rsp, $::CALLBACK);
 | 
						|
                    return 0;
 | 
						|
                }
 | 
						|
                lskit_C($kit_hash, $kitcomp_hash);
 | 
						|
            }
 | 
						|
        } else
 | 
						|
        {
 | 
						|
            if (defined($::opt_K)) {
 | 
						|
                create_lskit_K_xml_response($kit_hash);
 | 
						|
            }
 | 
						|
            if (defined($::opt_R)) {
 | 
						|
                create_lskit_R_xml_response($kit_hash, $kitrepo_hash);
 | 
						|
            }
 | 
						|
            if (defined($::opt_C)) {
 | 
						|
                create_lskit_C_xml_response($kit_hash, $kitcomp_hash);
 | 
						|
            }
 | 
						|
        }
 | 
						|
    }
 | 
						|
    else
 | 
						|
    {
 | 
						|
        if (defined($::opt_x)) {
 | 
						|
            create_lskit_xml_response($kit_hash, $kitrepo_hash, $kitcomp_hash);
 | 
						|
        } else {
 | 
						|
            create_lskit_stanza_response($kit_hash, $kitrepo_hash, $kitcomp_hash);
 | 
						|
        }
 | 
						|
    }
 | 
						|
    return 0;
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
#----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3  lskit_R
 | 
						|
 | 
						|
        Support for listing kit repo
 | 
						|
 | 
						|
        Arguments:
 | 
						|
        Returns:
 | 
						|
                0 - OK
 | 
						|
                1 - help
 | 
						|
                2 - error
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
 | 
						|
sub lskit_R {
 | 
						|
 | 
						|
    my $kit_hash     = shift;
 | 
						|
    my $kitrepo_hash = shift;
 | 
						|
    my $rsp          = {};
 | 
						|
    my $count        = 0;
 | 
						|
 | 
						|
 | 
						|
    for my $kitname (sort(keys(%$kit_hash))) {
 | 
						|
 | 
						|
        my $output .= "\nkit : $kitname\n----------------------------------------------------\n";
 | 
						|
 | 
						|
 | 
						|
        # Kit repository info
 | 
						|
        if (defined($kitrepo_hash->{$kitname})) {
 | 
						|
            for my $kitrepo (@{ $kitrepo_hash->{$kitname} }) {
 | 
						|
                $output .= "kitrepo:\n";
 | 
						|
                for my $kitrepo_attr (sort(keys(%$kitrepo))) {
 | 
						|
                    $output .= sprintf("    %s=%s\n", $kitrepo_attr, $kitrepo->{$kitrepo_attr});
 | 
						|
                }
 | 
						|
                $output .= "\n";
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
        push @{ $rsp->{data} }, $output;
 | 
						|
    }
 | 
						|
 | 
						|
    xCAT::MsgUtils->message("D", $rsp, $::CALLBACK);
 | 
						|
 | 
						|
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
#----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3  lskit_K
 | 
						|
 | 
						|
        Support for listing kit
 | 
						|
 | 
						|
        Arguments:
 | 
						|
        Returns:
 | 
						|
                0 - OK
 | 
						|
                1 - help
 | 
						|
                2 - error
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
 | 
						|
sub lskit_K {
 | 
						|
 | 
						|
    my $kit_hash = shift;
 | 
						|
    my $rsp      = {};
 | 
						|
    my $count    = 0;
 | 
						|
 | 
						|
 | 
						|
    for my $kitname (sort(keys(%$kit_hash))) {
 | 
						|
 | 
						|
        my $output .= "\nkit : $kitname\n----------------------------------------------------\n";
 | 
						|
 | 
						|
        # Kit info
 | 
						|
        if (defined($kit_hash->{$kitname})) {
 | 
						|
            my $kit = $kit_hash->{$kitname}->[0];
 | 
						|
            $output .= "kit:\n";
 | 
						|
            for my $kit_attr (sort(keys(%$kit))) {
 | 
						|
                $output .= sprintf("    %s=%s\n", $kit_attr, $kit->{$kit_attr});
 | 
						|
            }
 | 
						|
            $output .= "\n";
 | 
						|
        }
 | 
						|
 | 
						|
 | 
						|
        push @{ $rsp->{data} }, $output;
 | 
						|
    }
 | 
						|
 | 
						|
    xCAT::MsgUtils->message("D", $rsp, $::CALLBACK);
 | 
						|
 | 
						|
 | 
						|
}
 | 
						|
 | 
						|
#----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3  lskit_C
 | 
						|
 | 
						|
        Support for listing kitcomponent
 | 
						|
 | 
						|
        Arguments:
 | 
						|
        Returns:
 | 
						|
                0 - OK
 | 
						|
                1 - help
 | 
						|
                2 - error
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
 | 
						|
sub lskit_C {
 | 
						|
 | 
						|
    my $kit_hash     = shift;
 | 
						|
    my $kitcomp_hash = shift;
 | 
						|
    my $rsp          = {};
 | 
						|
    my $count        = 0;
 | 
						|
 | 
						|
 | 
						|
    for my $kitname (sort(keys(%$kit_hash))) {
 | 
						|
 | 
						|
        my $output .= "\nkit : $kitname\n----------------------------------------------------\n";
 | 
						|
 | 
						|
 | 
						|
        # Kit component info
 | 
						|
        if (defined($kitcomp_hash->{$kitname})) {
 | 
						|
            for my $kitcomp (@{ $kitcomp_hash->{$kitname} }) {
 | 
						|
                $output .= "kitcomponent:\n";
 | 
						|
                for my $kitcomp_attr (sort(keys(%$kitcomp))) {
 | 
						|
                    $output .= sprintf("    %s=%s\n", $kitcomp_attr, $kitcomp->{$kitcomp_attr});
 | 
						|
                }
 | 
						|
                $output .= "\n";
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
 | 
						|
        push @{ $rsp->{data} }, $output;
 | 
						|
    }
 | 
						|
 | 
						|
    xCAT::MsgUtils->message("D", $rsp, $::CALLBACK);
 | 
						|
 | 
						|
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
#----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3  lskitcomp
 | 
						|
 | 
						|
        Support for listing kit components
 | 
						|
 | 
						|
        Arguments:
 | 
						|
        Returns:
 | 
						|
                0 - OK
 | 
						|
                1 - help
 | 
						|
                2 - error
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
 | 
						|
 | 
						|
sub lskitcomp {
 | 
						|
 | 
						|
    my $rc = 0;
 | 
						|
 | 
						|
    # process the command line
 | 
						|
    # 0=success, 1=version, 2=help, 3=error
 | 
						|
 | 
						|
    if ($^O ne 'linux') {
 | 
						|
        my $rsp = {};
 | 
						|
        push @{ $rsp->{data} }, "The lskitcomp command is only supported on Linux.\n";
 | 
						|
        xCAT::MsgUtils->message("E", $rsp, $::CALLBACK);
 | 
						|
        return 1;
 | 
						|
    }
 | 
						|
 | 
						|
    $rc = lskitcomp_processargs(@_);
 | 
						|
    if ($rc != 0) {
 | 
						|
        if ($rc != 1) {
 | 
						|
            lskitcomp_usage(@_);
 | 
						|
        }
 | 
						|
        return ($rc - 1);
 | 
						|
    }
 | 
						|
 | 
						|
    # Get the list of kitcomponents to display
 | 
						|
 | 
						|
    ## Build the initial kitcomponent list, filtering the kitcomponents whose:
 | 
						|
    ##    - name matches one of the user-specified names
 | 
						|
    ##    - AND, reponame refers to a repo that is compatible with the user-specified osdistro
 | 
						|
 | 
						|
    my $compat_kitreponames = undef;
 | 
						|
    if (defined($::osdistroname)) {
 | 
						|
        $compat_kitreponames = get_compat_kitreponames($::osdistroname);
 | 
						|
    }
 | 
						|
    my $kitcomps = get_kitcomp_list($::kitcompnames, $compat_kitreponames, $::kitcompattrs);
 | 
						|
 | 
						|
 | 
						|
    ## Filter the kitcomponent list by user-specified server role
 | 
						|
    if (defined($::serverrole)) {
 | 
						|
        my @tmplist = ();
 | 
						|
        foreach my $kitcomp (@$kitcomps) {
 | 
						|
            if (defined($kitcomp->{serverroles})) {
 | 
						|
                my @serverroles = split(/,/, $kitcomp->{serverroles});
 | 
						|
                if (grep { $_ eq $::serverrole } @serverroles) {
 | 
						|
                    push(@tmplist, $kitcomp);
 | 
						|
                }
 | 
						|
            } else {
 | 
						|
 | 
						|
                # If kit component doesn't have server roles, it means
 | 
						|
                # it supports any server role.
 | 
						|
                push(@tmplist, $kitcomp);
 | 
						|
            }
 | 
						|
        }
 | 
						|
        @$kitcomps = @tmplist;
 | 
						|
    }
 | 
						|
 | 
						|
 | 
						|
    # Check if kit component list is empty
 | 
						|
 | 
						|
    if (scalar(@$kitcomps) == 0) {
 | 
						|
        my $rsp = {};
 | 
						|
        push @{ $rsp->{data} }, "No kit components were found.";
 | 
						|
        xCAT::MsgUtils->message("I", $rsp, $::CALLBACK);
 | 
						|
        return 0;
 | 
						|
    }
 | 
						|
 | 
						|
 | 
						|
    # Prepare the hash tables to pass to the output routines
 | 
						|
 | 
						|
    ## Kit hash table
 | 
						|
    my @kitnames = map { $_->{kitname} } @$kitcomps;
 | 
						|
    my $kit_hash = get_kit_hash(\@kitnames, ['kitname']);
 | 
						|
    ## Kit component hash table
 | 
						|
    my $kitcomp_hash = create_hash_from_table_rows($kitcomps, 'kitname');
 | 
						|
 | 
						|
 | 
						|
    ## Now display the output
 | 
						|
    if (defined($::opt_C)) {
 | 
						|
        if (defined($::opt_x)) {
 | 
						|
            create_lskitcomp_C_xml_response($kit_hash, $kitcomp_hash);
 | 
						|
        }
 | 
						|
        else
 | 
						|
        {
 | 
						|
            if (defined($::opt_C)) {
 | 
						|
                my @kitcomplist = keys(%$kitcomp_hash);
 | 
						|
                if (scalar @kitcomplist == 0) {
 | 
						|
                    my $rsp = {};
 | 
						|
                    push @{ $rsp->{data} }, "No kit components were found.";
 | 
						|
                    xCAT::MsgUtils->message("I", $rsp, $::CALLBACK);
 | 
						|
                    return 0;
 | 
						|
                }
 | 
						|
                lskitcomp_C($kit_hash, $kitcomp_hash);
 | 
						|
            }
 | 
						|
        }
 | 
						|
    }
 | 
						|
    else
 | 
						|
    {
 | 
						|
 | 
						|
        if (defined($::opt_x)) {
 | 
						|
            create_lskit_xml_response($kit_hash, {}, $kitcomp_hash);
 | 
						|
        }
 | 
						|
        else
 | 
						|
        {
 | 
						|
            create_lskit_stanza_response($kit_hash, {}, $kitcomp_hash);
 | 
						|
        }
 | 
						|
    }
 | 
						|
    return 0;
 | 
						|
}
 | 
						|
 | 
						|
#----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3  lskitcomp_C
 | 
						|
 | 
						|
        Support for listing kitcomponent
 | 
						|
 | 
						|
        Arguments:
 | 
						|
        Returns:
 | 
						|
                0 - OK
 | 
						|
                1 - help
 | 
						|
                2 - error
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
 | 
						|
sub lskitcomp_C {
 | 
						|
 | 
						|
    my $kit_hash     = shift;
 | 
						|
    my $kitcomp_hash = shift;
 | 
						|
    my $rsp          = {};
 | 
						|
    my $count        = 0;
 | 
						|
 | 
						|
 | 
						|
    for my $kitname (sort(keys(%$kit_hash))) {
 | 
						|
 | 
						|
        my $output .= "\n----------------------------------------------------\n";
 | 
						|
        $output .= "\nkit : $kitname:\n\n";
 | 
						|
 | 
						|
 | 
						|
        # Kit component info
 | 
						|
        if (defined($kitcomp_hash->{$kitname})) {
 | 
						|
 | 
						|
            for my $kitcomp (@{ $kitcomp_hash->{$kitname} }) {
 | 
						|
                $output .= "kitcomponent:\n";
 | 
						|
                for my $kitcomp_attr (sort(keys(%$kitcomp))) {
 | 
						|
                    $output .= sprintf("    %s=%s\n", $kitcomp_attr, $kitcomp->{$kitcomp_attr});
 | 
						|
                }
 | 
						|
                $output .= "\n";
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
 | 
						|
        push @{ $rsp->{data} }, $output;
 | 
						|
    }
 | 
						|
 | 
						|
    xCAT::MsgUtils->message("D", $rsp, $::CALLBACK);
 | 
						|
 | 
						|
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
#----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3  lskitdeployparam
 | 
						|
 | 
						|
        Support for listing kit deployment parameters
 | 
						|
 | 
						|
        Arguments:
 | 
						|
        Returns:
 | 
						|
                0 - OK
 | 
						|
                1 - help
 | 
						|
                2 - error
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
 | 
						|
 | 
						|
sub lskitdeployparam {
 | 
						|
 | 
						|
    my $rc = 0;
 | 
						|
 | 
						|
    # process the command line
 | 
						|
    # 0=success, 1=version, 2=help, 3=error
 | 
						|
 | 
						|
    if ($^O ne 'linux') {
 | 
						|
        my $rsp = {};
 | 
						|
        push @{ $rsp->{data} }, "The lskitdeployparam command is only supported on Linux.\n";
 | 
						|
        xCAT::MsgUtils->message("E", $rsp, $::CALLBACK);
 | 
						|
        return 1;
 | 
						|
    }
 | 
						|
 | 
						|
    $rc = lskitdeployparam_processargs(@_);
 | 
						|
    if ($rc != 0) {
 | 
						|
        if ($rc != 1) {
 | 
						|
            lskitdeployparam_usage(@_);
 | 
						|
        }
 | 
						|
        return ($rc - 1);
 | 
						|
    }
 | 
						|
 | 
						|
    # Get the kit deployment parameter files to read
 | 
						|
 | 
						|
    ## First get the list of kits
 | 
						|
    my $kitnames = undef;
 | 
						|
    if (defined($::kitnames)) {
 | 
						|
        $kitnames = $::kitnames;
 | 
						|
    } elsif (defined $::kitcompnames) {
 | 
						|
        my $kitcomps = get_kitcomp_list($::kitcompnames, undef, [ 'kitname', 'kitcompname' ]);
 | 
						|
        my @tmp = map { $_->{kitname} } @$kitcomps;
 | 
						|
        $kitnames = \@tmp;
 | 
						|
    } else {
 | 
						|
 | 
						|
        # unreachable code
 | 
						|
    }
 | 
						|
 | 
						|
    ## Then get the kit deployment parameter file for each kit
 | 
						|
    my $kits = get_kit_list($kitnames, [ 'kitname', 'kitdir', 'kitdeployparams' ]);
 | 
						|
 | 
						|
    # Read the kit deployment parameter files. The format is:
 | 
						|
    #        #ENV:KIT_KIT1_PARAM1=value11#
 | 
						|
    #        #ENV:KIT_KIT1_PARAM2=value12#
 | 
						|
    #        #ENV:KIT_KIT2_PARAM1=value21#
 | 
						|
    my $deployparam_hash = {};
 | 
						|
    foreach my $kit (@$kits) {
 | 
						|
        my $deployparam_file = $kit->{kitdir} . "/other_files/" . $kit->{kitdeployparams};
 | 
						|
 | 
						|
        my $tmpkitdeployparames = $kit->{kitdeployparams};
 | 
						|
 | 
						|
        if (defined($deployparam_file)) {
 | 
						|
 | 
						|
            # Check if there is kitdeployparam file or not
 | 
						|
            if (defined($tmpkitdeployparames))
 | 
						|
            {
 | 
						|
                open(my $fh, "<", $deployparam_file) || die sprintf("Failed to open file %s because: %s", $deployparam_file, $!);
 | 
						|
 | 
						|
                while (<$fh>) {
 | 
						|
                    chomp $_;
 | 
						|
                    if ($_ =~ /^#ENV:.+=.+#$/) {
 | 
						|
                        my $tmp = $_;
 | 
						|
                        $tmp =~ s/^#ENV://;
 | 
						|
                        $tmp =~ s/#$//;
 | 
						|
                        (my $name, my $value) = split(/=/, $tmp);
 | 
						|
                        $deployparam_hash->{$name} = $value;
 | 
						|
                    }
 | 
						|
                }
 | 
						|
                close($fh);
 | 
						|
            }
 | 
						|
            else {
 | 
						|
                my $rsp = {};
 | 
						|
                push @{ $rsp->{data} }, "There is no kitdeployparams file in $deployparam_file.\n";
 | 
						|
                xCAT::MsgUtils->message("W", $rsp, $::CALLBACK);
 | 
						|
 | 
						|
                return 1;
 | 
						|
            }
 | 
						|
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    # Now display the output
 | 
						|
 | 
						|
    my $rsp = {};
 | 
						|
 | 
						|
    if (defined($::opt_x)) {
 | 
						|
 | 
						|
        # Output XML format
 | 
						|
        foreach my $deployparam_key (sort(keys(%$deployparam_hash))) {
 | 
						|
            my $output_hash = { "kitdeployparam" => { "name" => "", "value" => "" } };
 | 
						|
            $output_hash->{kitdeployparam}->{name} = $deployparam_key;
 | 
						|
            $output_hash->{kitdeployparam}->{value} = $deployparam_hash->{$deployparam_key};
 | 
						|
            push @{ $rsp->{data} }, $output_hash;
 | 
						|
        }
 | 
						|
    } else {
 | 
						|
 | 
						|
        # Output Stanza format
 | 
						|
        foreach my $deployparam_key (sort(keys(%$deployparam_hash))) {
 | 
						|
            my $output = "kitdeployparam:\n";
 | 
						|
            $output .= sprintf("    name=%s\n", $deployparam_key);
 | 
						|
            $output .= sprintf("    value=%s\n", $deployparam_hash->{$deployparam_key});
 | 
						|
            push @{ $rsp->{data} }, $output;
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    xCAT::MsgUtils->message("D", $rsp, $::CALLBACK);
 | 
						|
 | 
						|
    return 0
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
1;
 | 
						|
 | 
						|
#----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3  get_kit_hash
 | 
						|
 | 
						|
        Returns a hash table containing kit entries indexed by kit name.
 | 
						|
        Arguments:
 | 
						|
            list of kit names (ref)
 | 
						|
            list of kit attribute names (ref)
 | 
						|
        Returns: hash table (ref)
 | 
						|
           { kitname1 => [{kitname1,basename1,...}],
 | 
						|
             kitname2 => [{kitname2,basename2,...}],
 | 
						|
             ...
 | 
						|
           }
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
 | 
						|
sub get_kit_hash {
 | 
						|
 | 
						|
    my $tablename = 'kit';
 | 
						|
    my $kitnames  = shift;
 | 
						|
    my $kitattrs  = shift;
 | 
						|
 | 
						|
    my $filter_hash = {};
 | 
						|
    if (defined($kitnames)) {
 | 
						|
        $filter_hash->{kitname} = $kitnames;
 | 
						|
    }
 | 
						|
 | 
						|
    my $filter_stmt = undef;
 | 
						|
    if (scalar(keys(%$filter_hash)) > 0) {
 | 
						|
        $filter_stmt = db_build_filter_stmt($filter_hash);
 | 
						|
    }
 | 
						|
 | 
						|
    my $rows = db_get_table_rows($tablename, $kitattrs, $filter_stmt);
 | 
						|
 | 
						|
    return create_hash_from_table_rows($rows, 'kitname');
 | 
						|
}
 | 
						|
 | 
						|
#----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3  get_kitrepo_hash
 | 
						|
 | 
						|
        Returns a hash table containing lists of kit repository entries
 | 
						|
        indexed by kit name.
 | 
						|
        Arguments:
 | 
						|
            list of kit names (ref)
 | 
						|
            list of kit repo attribute names (ref)
 | 
						|
        Returns: hash table (ref)
 | 
						|
           { kitname1 => [{kitrepo11,...},{kitrepo12,...}],
 | 
						|
             kitname2 => [{kitrepo21,...},{kitrepo22,...}],
 | 
						|
             ...
 | 
						|
           }
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
 | 
						|
sub get_kitrepo_hash {
 | 
						|
 | 
						|
    my $tablename    = 'kitrepo';
 | 
						|
    my $kitnames     = shift;
 | 
						|
    my $kitrepoattrs = shift;
 | 
						|
 | 
						|
    my $filter_hash = {};
 | 
						|
    if (defined($kitnames)) {
 | 
						|
        $filter_hash->{kitname} = $kitnames;
 | 
						|
    }
 | 
						|
 | 
						|
    my $filter_stmt = undef;
 | 
						|
    if (scalar(keys(%$filter_hash)) > 0) {
 | 
						|
        $filter_stmt = db_build_filter_stmt($filter_hash);
 | 
						|
    }
 | 
						|
    my $rows = db_get_table_rows($tablename, $kitrepoattrs, $filter_stmt);
 | 
						|
 | 
						|
    return create_hash_from_table_rows($rows, 'kitname');
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
#----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3  get_kitcomp_hash
 | 
						|
 | 
						|
        Returns a hash table containing lists of kit component entries
 | 
						|
        indexed by kit name.
 | 
						|
        Arguments:
 | 
						|
            list of kit names (ref)
 | 
						|
            list of kit component attribute names (ref)
 | 
						|
        Returns: hash table (ref)
 | 
						|
           { kitname1 => [{kitcomp11,...},{kitcomp12,...}],
 | 
						|
             kitname2 => [{kitcomp21,...},{kitcomp22,...}],
 | 
						|
             ...
 | 
						|
           }
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
 | 
						|
sub get_kitcomp_hash {
 | 
						|
 | 
						|
    my $tablename    = 'kitcomponent';
 | 
						|
    my $kitnames     = shift;
 | 
						|
    my $kitcompattrs = shift;
 | 
						|
 | 
						|
    my $filter_hash = {};
 | 
						|
    if (defined($kitnames)) {
 | 
						|
        $filter_hash->{kitname} = $kitnames;
 | 
						|
    }
 | 
						|
 | 
						|
    my $filter_stmt = undef;
 | 
						|
    if (scalar(keys(%$filter_hash)) > 0) {
 | 
						|
        $filter_stmt = db_build_filter_stmt($filter_hash);
 | 
						|
    }
 | 
						|
    my $rows = db_get_table_rows($tablename, $kitcompattrs, $filter_stmt);
 | 
						|
 | 
						|
    return create_hash_from_table_rows($rows, 'kitname');
 | 
						|
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
#----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3  get_kit_list
 | 
						|
 | 
						|
        Returns a list of kit, filtering the kits by:
 | 
						|
          - kit name
 | 
						|
 | 
						|
        Arguments:
 | 
						|
               list of kit attributes to query (ref)
 | 
						|
               list of kit names for filtering  (ref)
 | 
						|
 | 
						|
        Returns a list of kit(ref)
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
 | 
						|
sub get_kit_list {
 | 
						|
 | 
						|
    my $kitnames = shift;
 | 
						|
    my $kitattrs = shift;
 | 
						|
 | 
						|
    my $filter_hash = {};
 | 
						|
 | 
						|
    if (defined($kitnames)) {
 | 
						|
        $filter_hash->{kitname} = $kitnames;
 | 
						|
    }
 | 
						|
 | 
						|
    my $filter_stmt = undef;
 | 
						|
    if (scalar(keys(%$filter_hash)) > 0) {
 | 
						|
        $filter_stmt = db_build_filter_stmt($filter_hash);
 | 
						|
    }
 | 
						|
    return db_get_table_rows('kit', $kitattrs, $filter_stmt);
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
#----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3  get_kitcomp_list
 | 
						|
 | 
						|
        Returns a list of kit components, filtering the kit components by:
 | 
						|
          - kit component name
 | 
						|
          - kit repository name
 | 
						|
 | 
						|
        Arguments:
 | 
						|
               list of kit component names for filtering  (ref)
 | 
						|
               list of kit repo names for filtering (ref)
 | 
						|
               list of kit component attributes to query (ref)
 | 
						|
 | 
						|
        Returns a list of kit components (ref)
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
 | 
						|
sub get_kitcomp_list {
 | 
						|
 | 
						|
    my $kitcompnames = shift;
 | 
						|
    my $kitreponames = shift;
 | 
						|
    my $kitcompattrs = shift;
 | 
						|
 | 
						|
    my $filter_hash = {};
 | 
						|
 | 
						|
    if (defined($kitcompnames)) {
 | 
						|
        $filter_hash->{kitcompname} = $kitcompnames;
 | 
						|
    }
 | 
						|
 | 
						|
    if (defined($kitreponames)) {
 | 
						|
        $filter_hash->{kitreponame} = $kitreponames;
 | 
						|
    }
 | 
						|
 | 
						|
    my $filter_stmt = undef;
 | 
						|
    if (scalar(keys(%$filter_hash)) > 0) {
 | 
						|
        $filter_stmt = db_build_filter_stmt($filter_hash);
 | 
						|
    }
 | 
						|
    return db_get_table_rows('kitcomponent', $kitcompattrs, $filter_stmt);
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
#----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3  get_compat_kitreponames
 | 
						|
 | 
						|
        Returns a list of kitreponames which are compatible with the specified
 | 
						|
        osdistroname.
 | 
						|
 | 
						|
        Arguments:
 | 
						|
             osdistroname
 | 
						|
 | 
						|
        Returns:
 | 
						|
             List of kitreponames (ref)
 | 
						|
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
 | 
						|
sub get_compat_kitreponames {
 | 
						|
 | 
						|
    my $osdistroname    = shift;
 | 
						|
    my @compat_kitrepos = ();
 | 
						|
 | 
						|
    ## Get the osdistro info
 | 
						|
    my $filter_stmt = db_build_filter_stmt({ 'osdistroname' => [$osdistroname] });
 | 
						|
    my $osdistros = db_get_table_rows('osdistro', undef, $filter_stmt);
 | 
						|
    my $osdistro = $osdistros->[0];
 | 
						|
 | 
						|
    #print Dumper($osdistro);
 | 
						|
 | 
						|
    ## Get the kitrepos, which are compatible with the osdistro info
 | 
						|
    my $kitrepos = db_get_table_rows('kitrepo', undef, undef);
 | 
						|
 | 
						|
    foreach my $kitrepo (@$kitrepos) {
 | 
						|
        ## To check if kitrepo is compatible with an osdistro, the following 4 things
 | 
						|
        ## must be true:
 | 
						|
        ##     1) The kitrepo basename must be same as or compatible with osdistro basename.
 | 
						|
        ##     2) The kitrepo major verison must be same as osdistro major version.
 | 
						|
        ##     3) The kitrepo minor version must either:
 | 
						|
        ##           - Be same as osdistro minor version
 | 
						|
        ##           - OR, be empty which matches any osdistro minor version
 | 
						|
        ##     4) The kitrepo arch must be same as osdistro arch.
 | 
						|
        if (defined($kitrepo->{osbasename})) {
 | 
						|
            my @kitrepo_compat_basenames = ();
 | 
						|
            if (defined($kitrepo->{compat_osbasenames})) {
 | 
						|
                @kitrepo_compat_basenames = split(/,/, $kitrepo->{compat_osbasenames});
 | 
						|
            }
 | 
						|
            if ($kitrepo->{osbasename} ne $osdistro->{basename} &&
 | 
						|
                !grep { $_ eq $osdistro->{basename} } @kitrepo_compat_basenames) {
 | 
						|
                next;
 | 
						|
            }
 | 
						|
        }
 | 
						|
        if (defined($kitrepo->{osmajorversion}) && $kitrepo->{osmajorversion} ne $osdistro->{majorversion}) {
 | 
						|
            next;
 | 
						|
        }
 | 
						|
        if (defined($kitrepo->{osminorversion})) {
 | 
						|
            if (check_minorversion($kitrepo->{osminorversion},$osdistro->{minorversion}))
 | 
						|
            {
 | 
						|
                next;
 | 
						|
            }
 | 
						|
        }
 | 
						|
        if (defined($kitrepo->{osarch}) && $kitrepo->{osarch} ne $osdistro->{arch} && $kitrepo->{osarch} ne 'noarch') {
 | 
						|
            next;
 | 
						|
        }
 | 
						|
 | 
						|
        push(@compat_kitrepos, $kitrepo);
 | 
						|
    }
 | 
						|
 | 
						|
    #print Dumper(@compat_kitrepos);
 | 
						|
 | 
						|
    my @compat_kitreponames = map { $_->{kitreponame} } @compat_kitrepos;
 | 
						|
    return \@compat_kitreponames;
 | 
						|
 | 
						|
}
 | 
						|
 | 
						|
#----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3  db_build_filter_stmt
 | 
						|
 | 
						|
        Returns a SQL 'where' statement which is used to filter the
 | 
						|
        result of a kit, kit repository or kit component query.
 | 
						|
 | 
						|
        Arguments:
 | 
						|
             hash table
 | 
						|
                 - each entry represents a filter
 | 
						|
                 - each entry has a key <keyN>, and a list of values <valuesN>.
 | 
						|
                 - each entry is added to 'where' stmt as follows:
 | 
						|
                      <key1> in (comma-separated list of <values1>)
 | 
						|
                      <key2> in (comma-separated list of <values2>)
 | 
						|
                      ...
 | 
						|
        Returns: string containing SQL 'where' statement
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
 | 
						|
sub db_build_filter_stmt {
 | 
						|
 | 
						|
    my $filter_hash = shift;
 | 
						|
    my $filter_stmt = "";
 | 
						|
 | 
						|
    for my $filter_key (keys(%$filter_hash)) {
 | 
						|
        my $filter_values = $filter_hash->{$filter_key};
 | 
						|
        my $values_str = join ",", map { '\'' . $_ . '\'' } @$filter_values;
 | 
						|
        if ($filter_stmt eq "") {
 | 
						|
            $filter_stmt = sprintf("%s in (%s)", $filter_key, $values_str);
 | 
						|
        } else {
 | 
						|
            $filter_stmt .= sprintf(" AND %s in (%s)", $filter_key, $values_str);
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    return $filter_stmt;
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
#----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3  db_get_table_rows
 | 
						|
 | 
						|
        Returns a list of table rows.  Each table row is a hash table.
 | 
						|
 | 
						|
        Arguments:
 | 
						|
               table name
 | 
						|
               attribute list
 | 
						|
               where statement
 | 
						|
 | 
						|
        Returns: list of table rows (ref)
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
 | 
						|
sub db_get_table_rows {
 | 
						|
 | 
						|
    my $tablename   = shift;
 | 
						|
    my $attrs       = shift;
 | 
						|
    my $filter_stmt = shift;
 | 
						|
 | 
						|
    if (!defined($attrs)) {
 | 
						|
        @{$attrs} = ();
 | 
						|
        my $schema = xCAT::Table->getTableSchema($tablename);
 | 
						|
        foreach my $c (@{ $schema->{cols} }) {
 | 
						|
            push @{$attrs}, $c;
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    my $table      = xCAT::Table->new($tablename);
 | 
						|
    my @table_rows = ();
 | 
						|
 | 
						|
    # todo fix for DB2 support
 | 
						|
    if (defined($filter_stmt)) {
 | 
						|
        if (length($filter_stmt) > 0) {
 | 
						|
            @table_rows = $table->getAllAttribsWhere($filter_stmt, @{$attrs});
 | 
						|
        }
 | 
						|
    } else {
 | 
						|
        @table_rows = $table->getAllAttribs(@{$attrs});
 | 
						|
    }
 | 
						|
 | 
						|
    return \@table_rows;
 | 
						|
}
 | 
						|
 | 
						|
#----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3  create_hash_from_table_rows
 | 
						|
 | 
						|
        Returns a hash table containing table rows indexed by specified
 | 
						|
        table attribute.
 | 
						|
        Arguments:
 | 
						|
               list of table rows (each row is a hash table)
 | 
						|
               table attribute
 | 
						|
        Returns: hash table (ref)
 | 
						|
            { kitname1 => [row11,row12,...}],
 | 
						|
              kitname2 => [row21,row22,...}],
 | 
						|
              ...
 | 
						|
            }
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
 | 
						|
sub create_hash_from_table_rows {
 | 
						|
 | 
						|
    my $table_rows = shift;
 | 
						|
    my $table_attr = shift;
 | 
						|
 | 
						|
    my $result = {};
 | 
						|
    foreach my $row (@$table_rows) {
 | 
						|
        my $hash_key = $row->{$table_attr};
 | 
						|
        if (!defined($result->{$hash_key})) {
 | 
						|
            $result->{$hash_key} = [];
 | 
						|
        }
 | 
						|
        push(@{ $result->{$hash_key} }, $row);
 | 
						|
    }
 | 
						|
 | 
						|
    return $result;
 | 
						|
 | 
						|
}
 | 
						|
 | 
						|
#----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3  create_lskit_xml_response
 | 
						|
 | 
						|
        Prepare a response that returns the kit, kit repository, and
 | 
						|
        kit component info in XML format.
 | 
						|
 | 
						|
        Arguments:
 | 
						|
               kit hash table
 | 
						|
               kit repo hash table
 | 
						|
               kit component hash table
 | 
						|
 | 
						|
               Note: Hash tables are created by create_hash_from_table_rows()
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
 | 
						|
sub create_lskit_xml_response {
 | 
						|
 | 
						|
    my $kit_hash     = shift;
 | 
						|
    my $kitrepo_hash = shift;
 | 
						|
    my $kitcomp_hash = shift;
 | 
						|
 | 
						|
    my $rsp = {};
 | 
						|
 | 
						|
    for my $kitname (sort(keys(%$kit_hash))) {
 | 
						|
        my $output_hash = { "kitinfo" => { "kit" => [], "kitrepo" => [], "kitcomponent" => [] } };
 | 
						|
 | 
						|
        # Kit info
 | 
						|
        if (defined($kit_hash->{$kitname})) {
 | 
						|
            my $kit = $kit_hash->{$kitname}->[0];
 | 
						|
            push(@{ $output_hash->{kitinfo}->{kit} }, $kit);
 | 
						|
        }
 | 
						|
 | 
						|
        # Kit repository info
 | 
						|
        if (defined($kitrepo_hash->{$kitname})) {
 | 
						|
            for my $kitrepo (@{ $kitrepo_hash->{$kitname} }) {
 | 
						|
                push(@{ $output_hash->{kitinfo}->{kitrepo} }, $kitrepo);
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
        # Kit component info
 | 
						|
        if (defined($kitcomp_hash->{$kitname})) {
 | 
						|
            for my $kitcomp (@{ $kitcomp_hash->{$kitname} }) {
 | 
						|
                push(@{ $output_hash->{kitinfo}->{kitcomp} }, $kitcomp);
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
        push @{ $rsp->{data} }, $output_hash;
 | 
						|
    }
 | 
						|
 | 
						|
    xCAT::MsgUtils->message("D", $rsp, $::CALLBACK);
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
#----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3  create_lskit_K_xml_response
 | 
						|
 | 
						|
        Prepare a response that returns the kit info in XML format.
 | 
						|
 | 
						|
        Arguments:
 | 
						|
               kit hash table
 | 
						|
 | 
						|
               Note: Hash tables are created by create_hash_from_table_rows()
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
 | 
						|
sub create_lskit_K_xml_response {
 | 
						|
 | 
						|
    my $kit_hash = shift;
 | 
						|
 | 
						|
    my $rsp = {};
 | 
						|
 | 
						|
    for my $kitname (sort(keys(%$kit_hash))) {
 | 
						|
        my $output_hash = { "kitinfo" => { "kit" => [], "kitrepo" => [], "kitcomponent" => [] } };
 | 
						|
 | 
						|
        # Kit info
 | 
						|
        if (defined($kit_hash->{$kitname})) {
 | 
						|
            my $kit = $kit_hash->{$kitname}->[0];
 | 
						|
            push(@{ $output_hash->{kitinfo}->{kit} }, $kit);
 | 
						|
        }
 | 
						|
 | 
						|
        push @{ $rsp->{data} }, $output_hash;
 | 
						|
    }
 | 
						|
 | 
						|
    xCAT::MsgUtils->message("D", $rsp, $::CALLBACK);
 | 
						|
}
 | 
						|
 | 
						|
#----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3  create_lskit_R_xml_response
 | 
						|
 | 
						|
        Prepare a response that returns the kit repository
 | 
						|
        info in XML format.
 | 
						|
 | 
						|
        Arguments:
 | 
						|
               kit repo hash table
 | 
						|
 | 
						|
               Note: Hash tables are created by create_hash_from_table_rows()
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
 | 
						|
sub create_lskit_R_xml_response {
 | 
						|
 | 
						|
    my $kit_hash     = shift;
 | 
						|
    my $kitrepo_hash = shift;
 | 
						|
 | 
						|
    my $rsp = {};
 | 
						|
 | 
						|
    for my $kitname (sort(keys(%$kit_hash))) {
 | 
						|
        my $output_hash = { "kitinfo" => { "kit" => [], "kitrepo" => [], "kitcomponent" => [] } };
 | 
						|
 | 
						|
        # Kit repository info
 | 
						|
        if (defined($kitrepo_hash->{$kitname})) {
 | 
						|
            for my $kitrepo (@{ $kitrepo_hash->{$kitname} }) {
 | 
						|
                push(@{ $output_hash->{kitinfo}->{kitrepo} }, $kitrepo);
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
        push @{ $rsp->{data} }, $output_hash;
 | 
						|
    }
 | 
						|
 | 
						|
    xCAT::MsgUtils->message("D", $rsp, $::CALLBACK);
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
#----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3  create_lskit_C_xml_response
 | 
						|
 | 
						|
        Prepare a response that returns the
 | 
						|
        kit component info in XML format.
 | 
						|
 | 
						|
        Arguments:
 | 
						|
               kit hash table
 | 
						|
               kit component hash table
 | 
						|
 | 
						|
               Note: Hash tables are created by create_hash_from_table_rows()
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
 | 
						|
sub create_lskit_C_xml_response {
 | 
						|
 | 
						|
    my $kit_hash     = shift;
 | 
						|
    my $kitcomp_hash = shift;
 | 
						|
 | 
						|
    my $rsp = {};
 | 
						|
 | 
						|
    for my $kitname (sort(keys(%$kit_hash))) {
 | 
						|
        my $output_hash = { "kitinfo" => { "kit" => [], "kitrepo" => [], "kitcomponent" => [] } };
 | 
						|
 | 
						|
 | 
						|
        # Kit component info
 | 
						|
        if (defined($kitcomp_hash->{$kitname})) {
 | 
						|
            for my $kitcomp (@{ $kitcomp_hash->{$kitname} }) {
 | 
						|
                push(@{ $output_hash->{kitinfo}->{kitcomp} }, $kitcomp);
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
        push @{ $rsp->{data} }, $output_hash;
 | 
						|
    }
 | 
						|
 | 
						|
    xCAT::MsgUtils->message("D", $rsp, $::CALLBACK);
 | 
						|
}
 | 
						|
 | 
						|
#----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3  create_lskitcomp_C_xml_response
 | 
						|
 | 
						|
        Prepare a response that returns the
 | 
						|
        kit component info in XML format.
 | 
						|
 | 
						|
        Arguments:
 | 
						|
               kit hash table
 | 
						|
               kit component hash table
 | 
						|
 | 
						|
               Note: Hash tables are created by create_hash_from_table_rows()
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
 | 
						|
sub create_lskitcomp_C_xml_response {
 | 
						|
 | 
						|
    my $kit_hash     = shift;
 | 
						|
    my $kitcomp_hash = shift;
 | 
						|
 | 
						|
    my $rsp = {};
 | 
						|
 | 
						|
    for my $kitname (sort(keys(%$kit_hash))) {
 | 
						|
        my $output_hash = { "kitinfo" => { "kit" => [], "kitrepo" => [], "kitcomponent" => [] } };
 | 
						|
 | 
						|
 | 
						|
        # Kit component info
 | 
						|
        if (defined($kitcomp_hash->{$kitname})) {
 | 
						|
            for my $kitcomp (@{ $kitcomp_hash->{$kitname} }) {
 | 
						|
                push(@{ $output_hash->{kitinfo}->{kitcomp} }, $kitcomp);
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
        push @{ $rsp->{data} }, $output_hash;
 | 
						|
    }
 | 
						|
 | 
						|
    xCAT::MsgUtils->message("D", $rsp, $::CALLBACK);
 | 
						|
}
 | 
						|
 | 
						|
#----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3  create_lskit_stanza_response
 | 
						|
 | 
						|
        Prepare a response that returns the kit, kit repository, and
 | 
						|
        kit component info in stanza-like format.
 | 
						|
 | 
						|
        Arguments:
 | 
						|
               kit hash table
 | 
						|
               kit repo hash table
 | 
						|
               kit component hash table
 | 
						|
               Note: Hash tables are created by create_hash_from_table_rows()
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
sub create_lskit_stanza_response {
 | 
						|
 | 
						|
    my $kit_hash     = shift;
 | 
						|
    my $kitrepo_hash = shift;
 | 
						|
    my $kitcomp_hash = shift;
 | 
						|
 | 
						|
    my $rsp   = {};
 | 
						|
    my $count = 0;
 | 
						|
 | 
						|
    for my $kitname (sort(keys(%$kit_hash))) {
 | 
						|
        my $output .= "\n----------------------------------------------------\n";
 | 
						|
 | 
						|
        # Kit info
 | 
						|
        if (defined($kit_hash->{$kitname})) {
 | 
						|
            my $kit = $kit_hash->{$kitname}->[0];
 | 
						|
            $output .= "kit:\n";
 | 
						|
            for my $kit_attr (sort(keys(%$kit))) {
 | 
						|
                $output .= sprintf("    %s=%s\n", $kit_attr, $kit->{$kit_attr});
 | 
						|
            }
 | 
						|
            $output .= "\n";
 | 
						|
        }
 | 
						|
 | 
						|
        # Kit repository info
 | 
						|
        if (defined($kitrepo_hash->{$kitname})) {
 | 
						|
            for my $kitrepo (@{ $kitrepo_hash->{$kitname} }) {
 | 
						|
                $output .= "kitrepo:\n";
 | 
						|
                for my $kitrepo_attr (sort(keys(%$kitrepo))) {
 | 
						|
                    $output .= sprintf("    %s=%s\n", $kitrepo_attr, $kitrepo->{$kitrepo_attr});
 | 
						|
                }
 | 
						|
                $output .= "\n";
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
        # Kit component info
 | 
						|
        if (defined($kitcomp_hash->{$kitname})) {
 | 
						|
            for my $kitcomp (@{ $kitcomp_hash->{$kitname} }) {
 | 
						|
                $output .= "kitcomponent:\n";
 | 
						|
                for my $kitcomp_attr (sort(keys(%$kitcomp))) {
 | 
						|
                    $output .= sprintf("    %s=%s\n", $kitcomp_attr, $kitcomp->{$kitcomp_attr});
 | 
						|
                }
 | 
						|
                $output .= "\n";
 | 
						|
            }
 | 
						|
        }
 | 
						|
 | 
						|
 | 
						|
        push @{ $rsp->{data} }, $output;
 | 
						|
    }
 | 
						|
 | 
						|
    xCAT::MsgUtils->message("D", $rsp, $::CALLBACK);
 | 
						|
 | 
						|
}
 | 
						|
 | 
						|
1;
 | 
						|
 | 
						|
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3    check_framework
 | 
						|
 | 
						|
    Check the compatible frameworks of the kit to see if it is
 | 
						|
        compatible with the running code.
 | 
						|
 | 
						|
    If one of the compatible frameworks of the kit matches one of the
 | 
						|
        compatible frameworks of the running code then we're good.
 | 
						|
 | 
						|
    NOTE:  compatible_kitframeworks are the kitframeworks that I can add
 | 
						|
        and kit frameworks that I can be added to.
 | 
						|
 | 
						|
    Returns:
 | 
						|
        0 - OK
 | 
						|
        1 - error
 | 
						|
 | 
						|
    Example:
 | 
						|
        my $rc = &check_framework(\@lines);
 | 
						|
 | 
						|
=cut
 | 
						|
 | 
						|
#-----------------------------------------------------------------------------
 | 
						|
sub check_framework
 | 
						|
{
 | 
						|
    my $lines = shift;
 | 
						|
 | 
						|
    my @kitconflines = @$lines;
 | 
						|
 | 
						|
    my $kitbasename;
 | 
						|
    my $kitcompat;
 | 
						|
    my $section = '';
 | 
						|
    foreach my $l (@kitconflines) {
 | 
						|
 | 
						|
        # skip blank and comment lines
 | 
						|
        if ($l =~ /^\s*$/ || $l =~ /^\s*#/) {
 | 
						|
            next;
 | 
						|
        }
 | 
						|
 | 
						|
        if ($l =~ /^\s*(\w+)\s*:/) {
 | 
						|
            $section = $1;
 | 
						|
            next;
 | 
						|
        }
 | 
						|
 | 
						|
        if ($l =~ /^\s*(\w+)\s*=\s*(.*)\s*/) {
 | 
						|
            my $attr = $1;
 | 
						|
            my $val  = $2;
 | 
						|
            $attr =~ s/^\s*//;       # Remove any leading whitespace
 | 
						|
            $attr =~ s/\s*$//;       # Remove any trailing whitespace
 | 
						|
            $attr =~ tr/A-Z/a-z/;    # Convert to lowercase
 | 
						|
            $val =~ s/^\s*//;
 | 
						|
            $val =~ s/\s*$//;
 | 
						|
 | 
						|
            if ($section eq 'kitbuildinfo') {
 | 
						|
                if ($attr eq 'compatible_kitframeworks') {
 | 
						|
                    $kitcompat = $val;
 | 
						|
                }
 | 
						|
            }
 | 
						|
            if ($section eq 'kit') {
 | 
						|
                if ($attr eq 'basename') { $kitbasename = $val; }
 | 
						|
            }
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    if (!$kitcompat) {
 | 
						|
        my %rsp;
 | 
						|
        push @{ $rsp{data} }, "Could not determine the kit compatible framework values for \'$kitbasename\' from the kit.conf file. Continuing for now.";
 | 
						|
        xCAT::MsgUtils->message("I", \%rsp, $::CALLBACK);
 | 
						|
        return 0;
 | 
						|
    }
 | 
						|
 | 
						|
    my @kit_compat_list = split(',', $kitcompat);
 | 
						|
    my @my_compat_list  = split(',', $::COMPATIBLE_KITFRAMEWORKS);
 | 
						|
 | 
						|
    foreach my $myfw (@my_compat_list) {
 | 
						|
        chomp $myfw;
 | 
						|
        foreach my $kitfw (@kit_compat_list) {
 | 
						|
            chomp $kitfw;
 | 
						|
 | 
						|
            if ($myfw eq $kitfw) {
 | 
						|
                return 0;
 | 
						|
            }
 | 
						|
        }
 | 
						|
    }
 | 
						|
 | 
						|
    my %rsp;
 | 
						|
    push @{ $rsp{data} }, "The kit named \'$kitbasename\' is not compatible with this version of the buildkit command.  \'$kitbasename\' is compatible with \'$kitcompat\' and the buildkit command is compatible with \'$::COMPATIBLE_KITFRAMEWORKS\'";
 | 
						|
    xCAT::MsgUtils->message("E", \%rsp, $::CALLBACK);
 | 
						|
    return 1;
 | 
						|
}
 |