diff --git a/ncm-grub/src/main/pan/components/grub/schema.pan b/ncm-grub/src/main/pan/components/grub/schema.pan index e26de8f5eb..c3e67b5a7a 100755 --- a/ncm-grub/src/main/pan/components/grub/schema.pan +++ b/ncm-grub/src/main/pan/components/grub/schema.pan @@ -96,6 +96,8 @@ type grub_component = { @{pxeboot first: set the PXE boot device as first device. Only for supported platforms (e.g. UEFI)} 'pxeboot' ? boolean + @{Set arguments of default kernel also for next kernel(s) (to be picked up outside ncm-grub)} + 'for_next' ? boolean } with { if (exists(SELF['args']) && exists(SELF['arguments'])) { error("Only one of args or arguments can be set for the default kernel boot arguments"); diff --git a/ncm-grub/src/main/perl/grub.pm b/ncm-grub/src/main/perl/grub.pm index 8fcba8ae73..d67ff19e58 100755 --- a/ncm-grub/src/main/perl/grub.pm +++ b/ncm-grub/src/main/perl/grub.pm @@ -7,6 +7,7 @@ use CAF::FileWriter; use CAF::Process; use EDG::WP4::CCM::Path qw(unescape); +use File::Temp qw(tempdir); use Readonly; use parent qw(NCM::Component CAF::Path); our $EC = LC::Exception::Context->new->will_store_all; @@ -803,6 +804,8 @@ sub default_options my ($current, $currargs) = $self->get_current_arguments($default); + my @default_options; + # If we want full control of the arguments: if ($fullcontrol) { # Check if the arguments we want to add are the same we have @@ -846,12 +849,12 @@ sub default_options $arguments->{remove} = {}; }; - my @options = $self->grubby_arguments_options($arguments); - if (@options) { - if ($self->grubby(['--update-kernel', $default, @options], success => 1)) { - $self->info("fullcontrol set args with '@options' for default kernel $default"); + @default_options = $self->grubby_arguments_options($arguments); + if (@default_options) { + if ($self->grubby(['--update-kernel', $default, @default_options], success => 1)) { + $self->info("fullcontrol set args with '@default_options' for default kernel $default"); } else { - $self->error("fullcontrol cannot set args with '@options' for default kernel $default"); + $self->error("fullcontrol cannot set args with '@default_options' for default kernel $default"); return; } } else { @@ -860,12 +863,12 @@ sub default_options } } else { # If we want no full control of the arguments - my @options = $self->grubby_arguments_options($arguments); - if (@options) { - if ($self->grubby(['--update-kernel', $default, @options], success => 1)) { - $self->info("set args with '@options' for default kernel $default"); + @default_options = $self->grubby_arguments_options($arguments); + if (@default_options) { + if ($self->grubby(['--update-kernel', $default, @default_options], success => 1)) { + $self->info("set args with '@default_options' for default kernel $default"); } else { - $self->error("cannot set args with '@options' for default kernel $default"); + $self->error("cannot set args with '@default_options' for default kernel $default"); return; } } else { @@ -873,6 +876,20 @@ sub default_options } } + if ($tree->{for_next}) { + # Set default options for "next" kernel that will be installed with e.g. new rpm. + # This involves updating /etc/default/grub and /etc/kernel/cmdline + # As there is no direct way in grubby to only update these files, + # we use hack to pass ALL kernels and point to empty bootloader dir + my $bls_tmpdir = tempdir("ncm-grub-bls-XXXXXX", TMPDIR => 1, CLEANUP => 1); + if ($self->grubby(['--bls-directory', $bls_tmpdir, '--update-kernel', 'ALL', @default_options], success => 1)) { + $self->info("set args with '@default_options' for next kernel"); + } else { + $self->error("cannot set args with '@default_options' for next kernel"); + return; + } + } + return SUCCESS; } diff --git a/ncm-grub/src/test/perl/methods.t b/ncm-grub/src/test/perl/methods.t index 8d0b614879..5445a39517 100644 --- a/ncm-grub/src/test/perl/methods.t +++ b/ncm-grub/src/test/perl/methods.t @@ -381,10 +381,11 @@ ok($cmp->default_options({arguments => { b => {enable => 0}, escape("c_aa") => {enable => 1, value => 'xyz'}, escape("d.e.f") => {enable => 0, value => 'ghi'}, - }}, '/boot/vmlinuz-1.2.3.4'), "default_options returns success on non-fullcontrol"); + }, for_next => 1}, '/boot/vmlinuz-1.2.3.4'), "default_options returns success on non-fullcontrol"); ok(command_history_ok([ '/sbin/grubby --info /boot/vmlinuz-1.2.3.4', '/sbin/grubby --update-kernel /boot/vmlinuz-1.2.3.4 --args a c_aa=xyz --remove-args b d.e.f=ghi', + '/sbin/grubby --bls-directory /.*?/ncm-grub-bls-\w{6} --update-kernel ALL --args a c_aa=xyz --remove-args b d.e.f=ghi', ]), 'grubby commands from default options non-fullcontrol from arguments'); command_history_reset(); @@ -392,13 +393,26 @@ command_history_reset(); # but there are current args to remove first # settings args with a - with fullcontrol is pointless; all current args are removed first set_desired_output('/sbin/grubby --info /boot/vmlinuz-1.2.3.4', "blablah\nargs=\"something special\"\nkernel=/boot/vmlinuz-1.2.3.4\n"); -ok($cmp->default_options({fullcontrol => 1, args => 'a -b c'}, '/boot/vmlinuz-1.2.3.4'), "default_options returns success on fullcontrol"); +ok($cmp->default_options({fullcontrol => 1, args => 'a -b c', for_next => 1}, '/boot/vmlinuz-1.2.3.4'), "default_options returns success on fullcontrol"); ok(command_history_ok([ '/sbin/grubby --info /boot/vmlinuz-1.2.3.4', '/sbin/grubby --update-kernel /boot/vmlinuz-1.2.3.4 --remove-args something special', '/sbin/grubby --update-kernel /boot/vmlinuz-1.2.3.4 --args a c', # no remove opts, they make no sense + '/sbin/grubby --bls-directory /.*?/ncm-grub-bls-\w{6} --update-kernel ALL --args a c', ]), 'grubby commands from default options fullcontrol'); +command_history_reset(); +# fullcontrol, existing options will not match; no for_next +# but there are current args to remove first +# settings args with a - with fullcontrol is pointless; all current args are removed first +set_desired_output('/sbin/grubby --info /boot/vmlinuz-1.2.3.4', "blablah\nargs=\"something special\"\nkernel=/boot/vmlinuz-1.2.3.4\n"); +ok($cmp->default_options({fullcontrol => 1, args => 'a -b c'}, '/boot/vmlinuz-1.2.3.4'), "default_options returns success on fullcontrol without for_next"); +ok(command_history_ok([ + '/sbin/grubby --info /boot/vmlinuz-1.2.3.4', + '/sbin/grubby --update-kernel /boot/vmlinuz-1.2.3.4 --remove-args something special', + '/sbin/grubby --update-kernel /boot/vmlinuz-1.2.3.4 --args a c', # no remove opts, they make no sense +], ['bls-directtory']), 'grubby commands from default options fullcontrol without for_next'); + =head1 pxeboot