summaryrefslogblamecommitdiffstats
path: root/boot-env/OpenSLX/BootEnvironment/PREBOOT_CD.pm
blob: 994e6dd0ebfcdde319c21a9ffb9c75c99a519687 (plain) (tree)
1
2
3
4
5
6
7
8
9
10









                                                                               
                                

                                                                               
                                             





                                            
                    



                    
                                              

                   


















                                                                              
















































































































































































                                                                                                     
  
# Copyright (c) 2008 - OpenSLX GmbH
#
# This program is free software distributed under the GPL version 2.
# See http://openslx.org/COPYING
#
# If you have any feedback please consult http://openslx.org/feedback and
# send your suggestions, praise, or complaints to feedback@openslx.org
#
# General information about OpenSLX can be found at http://openslx.org/
# -----------------------------------------------------------------------------
# BootEnvironment::PREBOOT_CD.pm
#    - provides CD-specific implementation of the BootEnvironment API.
# -----------------------------------------------------------------------------
package OpenSLX::BootEnvironment::PREBOOT_CD;

use strict;
use warnings;

use base qw(OpenSLX::BootEnvironment::Base);

use Clone qw(clone);
use File::Basename;
use File::Path;

use OpenSLX::Basics;
use OpenSLX::MakeInitRamFS::Engine::PrebootCD;
use OpenSLX::Utils;

sub initialize
{
    my $self   = shift;
    my $params = shift;
    
    return if !$self->SUPER::initialize($params);

    $self->{'original-path'} = "$openslxConfig{'public-path'}/preboot-cd";
    $self->{'target-path'}   = "$openslxConfig{'public-path'}/preboot-cd.new";

    if (!$self->{'dry-run'}) {
        mkpath([$self->{'original-path'}]);
        rmtree($self->{'target-path'});
        mkpath("$self->{'target-path'}/client-config");
    }

    return 1;
}

sub finalize
{
    my $self   = shift;
    my $delete = shift;

    return if !$self->{prebootSystemInfo};

    return $self->SUPER::finalize($delete);
}

sub writeBootloaderMenuFor
{
    my $self             = shift;
    my $client           = shift;
    my $externalClientID = shift;
    my $systemInfos      = shift || [];

    my $prebootSystemInfo = clone($systemInfos->[0]);
    $self->_createImage($client, $prebootSystemInfo);

#    $self->_prepareBootloaderConfigFolder() 
#        unless $self->{preparedBootloaderConfigFolder};
#
#    my $pxePath       = $self->{'target-path'};
#    my $pxeConfigPath = "$pxePath/pxelinux.cfg";
#
#    my $pxeConfig    = $self->_getTemplate();
#    my $pxeFile      = "$pxeConfigPath/$externalClientID";
#    my $clientAppend = $client->{kernel_params} || '';
#    vlog(1, _tr("writing PXE-file %s", $pxeFile));
#
#    # set label for each system
#    foreach my $info (@$systemInfos) {
#        my $label = $info->{label} || '';
#        if (!length($label) || $label eq $info->{name}) {
#            if ($info->{name} =~ m{^(.+)::(.+)$}) {
#                my $system = $1;
#                my $exportType = $2;
#                $label = $system . ' ' x (40-length($system)) . $exportType;
#            } else {
#                $label = $info->{name};
#            }
#        }
#        $info->{label} = $label;
#    }
#    my $slxLabels = '';
#    foreach my $info (sort { $a->{label} cmp $b->{label} } @$systemInfos) {
#        my $vendorOSName = $info->{'vendor-os'}->{name};
#        my $kernelName   = basename($info->{'kernel-file'});
#        my $append       = $info->{kernel_params};
#        $append .= " initrd=$vendorOSName/$info->{'initramfs-name'}";
#        $append .= " $clientAppend";
#        $slxLabels .= "LABEL openslx-$info->{'external-id'}\n";
#        $slxLabels .= "\tMENU LABEL ^$info->{label}\n";
#        $slxLabels .= "\tKERNEL $vendorOSName/$kernelName\n";
#        $slxLabels .= "\tAPPEND $append\n";
#        $slxLabels .= "\tIPAPPEND 1\n";
#        my $helpText = $info->{description} || '';
#        if (length($helpText)) {
#            # make sure that text matches the given margin
#            my $margin = $openslxConfig{'pxe-theme-menu-margin'} || 0;
#            my $marginAsText = ' ' x $margin;
#            $helpText =~ s{^}{$marginAsText}gms;
#            $slxLabels .= "\tTEXT HELP\n$helpText\n\tENDTEXT\n";
#        }
#    }
#    # now add the slx-labels (inline or appended) and write the config file
#    if (!($pxeConfig =~ s{\@\@\@SLX_LABELS\@\@\@}{$slxLabels})) {
#        $pxeConfig .= $slxLabels;
#    }
#
#    # PXE uses 'cp850' (codepage 850) but our string is in utf-8, we have
#    # to convert in order to avoid showing gibberish on the client side...
#    spitFile($pxeFile, $pxeConfig, { 'io-layer' => 'encoding(cp850)' } );

    return 1;
}

sub _createImage
{
    my $self   = shift;
    my $client = shift;
    my $info   = shift;
    
    vlog(
        0, 
        _tr(
            "\ncreating CD-image for client %s (based on %s) ...", 
            $client->{name}, $info->{name}
        )
    );

    my $imageDir = "$openslxConfig{'public-path'}/images/$client->{name}";
    mkpath($imageDir)   unless $self->{'dry-run'};

    # copy static data and init script
    my $dataDir = "$openslxConfig{'base-path'}/share/boot-env/preboot-cd";
    slxsystem(qq{rsync -rlpt $dataDir/ "$imageDir/"})
        unless $self->{'dry-run'};

    # copy kernel (take the one from the given system info)
    my $kernelFile = $info->{'kernel-file'};
    my $kernelName = basename($kernelFile);
    slxsystem(qq{cp -p "$kernelFile" "$imageDir/iso/isolinux/vmlinuz"})
        unless $self->{'dry-run'};

    # create initramfs
    my $initramfsName = qq{"$imageDir/iso/isolinux/initramfs"};
    $self->_makePrebootInitRamFS($info, $initramfsName);

    my $mkisoCmd = unshiftHereDoc(<<"    End-of-Here");
        mkisofs 
            -o "$imageDir/../$client->{name}.iso"
            -b isolinux/isolinux.bin -no-emul-boot -boot-load-size 4 
            -r -J -l -boot-info-table -joliet-long
            -publisher "OpenSLX Project - http://www.openslx.org" 
            -p "OpenSLX Project - openslx-devel\@openslx.org" 
            -V "OpenSLX BootCD"
            -volset "OpenSLX Project - PreBoot CD for non PXE/TFTP start of a Linux Stateless Client"
            -c isolinux/boot.cat "$imageDir/iso"
    End-of-Here
    $mkisoCmd =~ s{\n\s*}{ }gms;
    my $logFile = "$imageDir/../$client->{name}.iso.log";
    if (slxsystem(qq{$mkisoCmd 2>"$logFile"})) {
        my $log = slurpFile($logFile);
        die _tr("unable to create ISO-image - log follows:\n%s", $log);
    }

    rmtree($imageDir);

    return 1;
}

sub _makePrebootInitRamFS
{
    my $self       = shift;
    my $info       = shift;
    my $initramfs  = shift;

    my $vendorOS = $info->{'vendor-os'};
    my $kernelFile = basename(followLink($info->{'kernel-file'}));

    my $attrs = clone($info->{attrs} || {});

    chomp(my $slxVersion = qx{slxversion});

    my $params = {
        'attrs'          => $attrs,
        'export-name'    => undef,
        'export-uri'     => undef,
        'initramfs'      => $initramfs,
        'kernel-params'  => [ split ' ', ($info->{kernel_params} || '') ],
        'kernel-version' => $kernelFile =~ m[-(.+)$] ? $1 : '',
        'plugins'        => '',
        'root-path'
            => "$openslxConfig{'private-path'}/stage1/$vendorOS->{name}",
        'slx-version'    => $slxVersion,
        'system-name'    => $info->{name},
    };

    # TODO: make debug-level an explicit attribute, it's used in many places!
    my $kernelParams = $info->{kernel_params} || '';
    if ($kernelParams =~ m{debug(?:=(\d+))?}) {
        my $debugLevel = defined $1 ? $1 : '1';
        $params->{'debug-level'} = $debugLevel;
    }

    my $makeInitRamFSEngine 
        = OpenSLX::MakeInitRamFS::Engine::PrebootCD->new($params);
    $makeInitRamFSEngine->execute($self->{'dry-run'});

    # copy back kernel-params, as they might have been changed (by plugins)
    $info->{kernel_params} = join ' ', $makeInitRamFSEngine->kernelParams();

    return;
}

1;