Script 'mail_helper' called by obssrc Hello community, here is the log from the commit of package mksusecd for openSUSE:Factory checked in at 2024-08-17 12:41:22 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Comparing /work/SRC/openSUSE:Factory/mksusecd (Old) and /work/SRC/openSUSE:Factory/.mksusecd.new.2698 (New) ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Package is "mksusecd" Sat Aug 17 12:41:22 2024 rev:83 rq:1194333 version:3.0 Changes: -------- --- /work/SRC/openSUSE:Factory/mksusecd/mksusecd.changes 2024-07-18 19:19:29.478649613 +0200 +++ /work/SRC/openSUSE:Factory/.mksusecd.new.2698/mksusecd.changes 2024-08-17 12:41:43.760721662 +0200 @@ -1,0 +2,12 @@ +Fri Aug 16 15:54:15 UTC 2024 - wfe...@opensuse.org + +- merge gh#openSUSE/mksusecd#76 +- make some compression settings configurable (bsc#1223982, + jsc#PED-8374) +- update documentation +- fix UEFI image rebuild detection (bsc#1227668) +- allow updating kernel in live initrd +- allow updating kernel in live root, support resizing live root +- 3.0 + +-------------------------------------------------------------------- Old: ---- mksusecd-2.19.tar.xz New: ---- mksusecd-3.0.tar.xz ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Other differences: ------------------ ++++++ mksusecd.spec ++++++ --- /var/tmp/diff_new_pack.50KP1B/_old 2024-08-17 12:41:45.744804167 +0200 +++ /var/tmp/diff_new_pack.50KP1B/_new 2024-08-17 12:41:45.748804333 +0200 @@ -18,7 +18,7 @@ Name: mksusecd -Version: 2.19 +Version: 3.0 Release: 0 Summary: Tool to create SUSE Linux installation ISOs License: GPL-3.0+ ++++++ mksusecd-2.19.tar.xz -> mksusecd-3.0.tar.xz ++++++ diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/mksusecd-2.19/VERSION new/mksusecd-3.0/VERSION --- old/mksusecd-2.19/VERSION 2024-07-17 21:02:32.000000000 +0200 +++ new/mksusecd-3.0/VERSION 2024-08-16 17:54:15.000000000 +0200 @@ -1 +1 @@ -2.19 +3.0 diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/mksusecd-2.19/changelog new/mksusecd-3.0/changelog --- old/mksusecd-2.19/changelog 2024-07-17 21:02:32.000000000 +0200 +++ new/mksusecd-3.0/changelog 2024-08-16 17:54:15.000000000 +0200 @@ -1,3 +1,12 @@ +2024-08-16: 3.0 + - merge gh#openSUSE/mksusecd#76 + - make some compression settings configurable (bsc#1223982, + jsc#PED-8374) + - update documentation + - fix UEFI image rebuild detection (bsc#1227668) + - allow updating kernel in live initrd + - allow updating kernel in live root, support resizing live root + 2024-07-17: 2.19 - merge gh#openSUSE/mksusecd#75 - update El-Torito UEFI image to match 'EFI' directory (bsc#1227668) diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/mksusecd-2.19/mksusecd new/mksusecd-3.0/mksusecd --- old/mksusecd-2.19/mksusecd 2024-07-17 21:02:32.000000000 +0200 +++ new/mksusecd-3.0/mksusecd 2024-08-16 17:54:15.000000000 +0200 @@ -211,6 +211,8 @@ sub get_initrd_modules; sub build_module_list; sub add_modules_to_initrd; +sub add_modules_to_instsys; +sub update_no_compression_settings; sub replace_kernel_mods; sub new_products_xml; sub prepare_addon; @@ -291,7 +293,8 @@ my $opt_instsys_in_repo = 1; my $opt_create_repo; my $opt_signature_file; - +my $opt_no_compression; +my $opt_instsys_size; Getopt::Long::Configure("gnu_compat"); @@ -329,6 +332,7 @@ 'filesystem=s' => \$opt_crypto_fs, 'no-iso' => \$opt_no_iso, 'size=s' => \$opt_size, + 'instsys-size|live-root-size=s' => \$opt_instsys_size, 'protective-mbr' => sub { $opt_no_prot_mbr = 0 }, 'no-protective-mbr' => \$opt_no_prot_mbr, 'mbr-code' => sub { $opt_no_mbr_code = 0 }, @@ -336,9 +340,10 @@ 'mbr-chs' => sub { $opt_no_mbr_chs = 0 }, 'no-mbr-chs' => \$opt_no_mbr_chs, 'initrd=s' => \@opt_initrds, - 'instsys=s' => \@opt_instsys, + 'instsys|live-root=s' => \@opt_instsys, 'rescue=s' => \@opt_rescue, - 'rebuild-initrd' => \$opt_rebuild_initrd, + 'rebuild-initrd' => sub { $opt_rebuild_initrd = 2 }, + 'no-rebuild-initrd' => sub { $opt_rebuild_initrd = 0 }, 'boot=s' => \$opt_boot_options, 'grub2' => sub { $opt_loader = "grub" }, 'isolinux' => sub { $opt_loader = "isolinux" }, @@ -371,6 +376,7 @@ 'list-repos' => \$opt_list_repos, 'include-repos=s' => \$opt_include_repos, 'enable-repos=s' => \$opt_enable_repos, + 'no-compression=s' => sub { @$opt_no_compression{split /,/, $_[1]} = ( 1 .. 8 ) }, 'save-temp' => \$opt_save_temp, 'verbose|v' => sub { $opt_verbose++ }, 'version' => sub { print "$VERSION\n"; exit 0 }, @@ -382,12 +388,29 @@ usage 1 if defined($opt_digest) && $opt_digest !~ '^(md5|sha1|sha224|sha256|sha384|sha512)$'; usage 1 if defined($opt_enable_repos) && $opt_enable_repos !~ /^(0|1|no|yes|auto|ask)$/i; +for (keys %$opt_no_compression) { + die "Option --no-compression only accepts firmware, modules, or squashfs\n" if !/^(firmware|modules|squashfs)$/; +} + +if(@opt_kernel_rpms && ! defined $opt_rebuild_initrd) { + $opt_rebuild_initrd = 1; +} + +if(@opt_kernel_modules && !@opt_kernel_rpms) { + die "No kernel packages specified. Use --kernel together with --modules.\n"; +} + die "no password\n" if $opt_crypto && $opt_crypto_password eq ""; $ENV{PATH} = "/usr/bin:/bin:/usr/sbin:/sbin"; -if($opt_rebuild_initrd && $>) { - die "mksusecd must be run with root permissions when --rebuild-initrd is used\n" +if($>) { + if($opt_rebuild_initrd == 2) { + die "mksusecd must be run with root permissions when --rebuild-initrd is used\n" + } + if($opt_rebuild_initrd == 1) { + die "mksusecd must be run with root permissions to update kernel config.\nOr use --no-rebuild-initrd.\n" + } } if(open my $f, "$ENV{HOME}/.mksusecdrc") { @@ -460,6 +483,8 @@ my $media_style = 'suse'; my $media_variant = 'install'; my $detected_signature_file; +my $orig_initrd_00_lib; +my $instsys_size; my $progress_start = 0; my $progress_end = 100; @@ -473,6 +498,17 @@ if(defined $opt_size) { $image_size = eval_size $opt_size; die "$opt_size: invalid size\n" unless $image_size; + printf "target image size: %.2f GiB ($image_size blocks)\n", $image_size / (1 << 21); +} + +if(defined $opt_instsys_size) { + $instsys_size = eval_size $opt_instsys_size; + die "$opt_instsys_size: invalid size\n" unless defined $instsys_size; + + # add at least an empty directory if we are going to resize the live root file system + if(!@opt_instsys) { + push @opt_instsys, $tmp->dir(); + } } if($opt_sign_pass_file) { @@ -764,122 +800,132 @@ General options: - --verbose Show more detailed messages. Can be repeated to log even more. - --version Show mksusecd version. - --save-temp Keep temporary files. - --help Write this help text. + --verbose Show more detailed messages. Can be repeated to log even more. + --version Show mksusecd version. + --save-temp Keep temporary files. + --help Write this help text. Show available repositories: - --list-repos List all available repositories in SOURCES. + --list-repos List all available repositories in SOURCES. Create new image: - -c, --create FILE Create ISO or disk image FILE from SOURCES. + -c, --create FILE Create ISO or disk image FILE from SOURCES. Media type related options: - --micro Create image with just enough files to run the installer (for testing). - --nano Create image with just enough files for a network based installation. - --pico Even less than --nano, keep just the bootloader (for testing). + --micro Create image with just enough files to run the installer (for testing). + --nano Create image with just enough files for a network based installation. + --pico Even less than --nano, keep just the bootloader (for testing). Media integrity related options: - --check Tag ISO to be verified before starting the installation. - --no-check Don't tag ISO (default). - --digest DIGEST Embed DIGEST to verify ISO integrity (default: sha256). - --no-digest Don't embed any digest to verify ISO integrity. - --sign-image Embed signature for entire image. - --no-sign-image Don't embed signature for entire image. (default) - --signature-file FILE Store embedded signature in FILE. (default: /.signature) - --sign Re-sign '/CHECKSUMS' if it has changed (default). - --no-sign Don't re-sign '/CHECKSUMS'. - --sign-key KEY_FILE Use this key file instead of generating a transient key. - --sign-key-id KEY_ID Use this key id instead of generating a transient key. - --sign-pass-file Use the password stored in this file to open the key. + --check Tag ISO to be verified before starting the installation. + --no-check Don't tag ISO (default). + --digest DIGEST Embed DIGEST to verify ISO integrity (default: sha256). + --no-digest Don't embed any digest to verify ISO integrity. + --sign-image Embed signature for entire image. + --no-sign-image Don't embed signature for entire image. (default) + --signature-file FILE Store embedded signature in FILE. (default: /.signature) + --sign Re-sign '/CHECKSUMS' if it has changed (default). + --no-sign Don't re-sign '/CHECKSUMS'. + --sign-key KEY_FILE Use this key file instead of generating a transient key. + --sign-key-id KEY_ID Use this key id instead of generating a transient key. + --sign-pass-file Use the password stored in this file to open the key. Initrd/instsys update related options: - --initrd DIR|RPM|DUD Add content of DIR, RPM, or DUD to initrd (can be repeated). - --rebuild-initrd Rebuild the entire initrd instead of appending changes. - --instsys DIR|RPM Add content of DIR or RPM to installation system or root file - system for Live media (can be repeated). - --rescue DIR|RPM Add content of DIR or RPM to rescue system (can be repeated). - --no-docs Don't include package doc files (default). - --keep-docs Include package doc files. + --initrd DIR|RPM|DUD Add content of DIR, RPM, or DUD to initrd (can be repeated). + --rebuild-initrd Rebuild the entire initrd instead of appending changes. + --no-rebuild-initrd Append changes to the initrd instead of rebuilding. + --instsys DIR|RPM Add content of DIR or RPM to installation system or root file + system for Live media (can be repeated). + --live-root DIR|RPM Alias for --instsys. + --rescue DIR|RPM Add content of DIR or RPM to rescue system (can be repeated). + --instsys-size SIZE_SPEC Resize Live root file system. + --live-root-size SIZE_SPEC Alias for --instsys-size. + --no-docs Don't include package doc files (default). + --keep-docs Include package doc files. Kernel/module update related options: - --kernel KERNEL_RPMS Replace kernel and modules used for booting using KERNEL_RPMS. - --modules MODULE_LIST A list of modules to be included additionally in the initrd. + --kernel RPM_LIST Replace kernel, kernel modules, and kernel firmware used for booting. + RPM_LIST is a list of kernel or firmware packages. + Note: this option expects a variable number of arguments. + Note also: implies --rebuild-initrd since mksusecd 3.0. + --modules MODULE_LIST A list of modules to be added to the initrd. + To be used together with --kernel. + Note: this option expects a variable number of arguments. + --no-compression LIST A comma-separated list of: firmware, modules, squashfs. Add-on related options: - --addon RPM_LIST A list of RPMs that should be made available as add-on. - --addon-name NAME Use NAME as the add-on name. - --addon-alias ALIAS Set repo alias to ALIAS. - --addon-prio NUM Set add-on repository priority to NUM (default: 60). + --addon RPM_LIST A list of RPMs that should be made available as add-on. + --addon-name NAME Use NAME as the add-on name. + --addon-alias ALIAS Set repo alias to ALIAS. + --addon-prio NUM Set add-on repository priority to NUM (default: 60). ISO file system related options: - --joliet Use Joliet extensions (default). - --no-joliet Don't use Joliet extensions. - --volume VOLUME_ID Set ISO volume id to VOLUME_ID. - --vendor VENDOR_ID Set ISO publisher id to VENDOR_ID. - --preparer PREPARER_ID Set ISO data preparer id to PREPARER_ID. - --application APP_ID Set ISO application id to APP_ID. - --volume1 VOLUME_ID Specify ISO volume id of the entire image - in case it should differ - from the ISO volume id used for the partition. + --joliet Use Joliet extensions (default). + --no-joliet Don't use Joliet extensions. + --volume VOLUME_ID Set ISO volume id to VOLUME_ID. + --vendor VENDOR_ID Set ISO publisher id to VENDOR_ID. + --preparer PREPARER_ID Set ISO data preparer id to PREPARER_ID. + --application APP_ID Set ISO application id to APP_ID. + --volume1 VOLUME_ID Specify ISO volume id of the entire image - in case it should differ + from the ISO volume id used for the partition. General image layout related options: - --uefi Make ISO UEFI bootable (default). - --no-uefi Don't make ISO UEFI bootable. - --zipl Make image zIPL bootable (default on s390x). - --no-zipl Don't make image zIPL bootable (default if not on s390x). - --gpt Add GPT when in isohybrid mode. - --mbr Add MBR when in isohybrid mode (default). - --prot-mbr When writing a GPT, write a protective MBR (default). - --no-prot-mbr When writing a GPT, don't write a protective MBR. - --mbr-code Include x86 MBR boot code (default). - --no-mbr-code Don't include x86 MBR boot code. - --mbr-chs Fill in sensible CHS values in MBR partition table (default). - --no-mbr-chs Use 0xffffff instead of CHS values in MBR partition table. - --no-iso Don't make image accessible as ISO9660 file system. - --hybrid Create an image which is both an ISO and a disk (default). - --no-hybrid Create a regular ISO image without extra gimmicks. - --hybrid-fs FS Use file system FS for the disk partition created in hybrid mode. - --fat Create an image that's suitable to be put on a USB disk. - --size SIZE_SPEC The intended size of the disk image when using a FAT file. + --uefi Make ISO UEFI bootable (default). + --no-uefi Don't make ISO UEFI bootable. + --zipl Make image zIPL bootable (default on s390x). + --no-zipl Don't make image zIPL bootable (default if not on s390x). + --gpt Add GPT when in isohybrid mode. + --mbr Add MBR when in isohybrid mode (default). + --prot-mbr When writing a GPT, write a protective MBR (default). + --no-prot-mbr When writing a GPT, don't write a protective MBR. + --mbr-code Include x86 MBR boot code (default). + --no-mbr-code Don't include x86 MBR boot code. + --mbr-chs Fill in sensible CHS values in MBR partition table (default). + --no-mbr-chs Use 0xffffff instead of CHS values in MBR partition table. + --no-iso Don't make image accessible as ISO9660 file system. + --hybrid Create an image which is both an ISO and a disk (default). + --no-hybrid Create a regular ISO image without extra gimmicks. + --hybrid-fs FS Use file system FS for the disk partition created in hybrid mode. + --fat Create an image that's suitable to be put on a USB disk. + --size SIZE_SPEC The intended size of the disk image when using a FAT file. Media repository related options: - --merge-repos Create a common media.1/products file (default). - --no-merge-repos Skip the special treatment of repositories and just merge all SOURCES. - --include-repos LIST Comma-separated list of repository names to include in the final image. - --enable-repos WHEN Whether to enable repos. WHEN can be 'auto', 'yes', 'ask', or 'no' (default: no). - --create-repo Re-create and sign the repository (default: don't). + --merge-repos Create a common media.1/products file (default). + --no-merge-repos Skip the special treatment of repositories and just merge all SOURCES. + --include-repos LIST Comma-separated list of repository names to include in the final image. + --enable-repos WHEN Whether to enable repos. WHEN can be 'auto', 'yes', 'ask', or 'no' (default: no). + --create-repo Re-create and sign the repository (default: don't). Repository location related options: - --net URL Use URL as default network repository. - --instsys-url URL Load the installation system from the specified URL. - --instsys-in-repo Load installation system from repository (default). - --no-instsys-in-repo Do not load installation system from repository but from local disks. - --defaultrepo URL_LIST URL_LIST is a list of comma (',') separated URLs the installer will try in turn. + --net URL Use URL as default network repository. + --instsys-url URL Load the installation system from the specified URL. + --instsys-in-repo Load installation system from repository (default). + --no-instsys-in-repo Do not load installation system from repository but from local disks. + --defaultrepo URL_LIST URL_LIST is a list of comma (',') separated URLs the installer will try in turn. Boot menu related options: - --boot OPTIONS Add OPTIONS to default boot options. - --add-entry BOOT_ENTRY Create a new boot entry with name BOOT_ENTRY. + --boot OPTIONS Add OPTIONS to default boot options. + --add-entry BOOT_ENTRY Create a new boot entry with name BOOT_ENTRY. Image encryption related options: - --crypto If set, an encrypted disk image is created. - --password PASSWORD Use PASSWORD for encrypting the disk image. - --title TITLE The password query screen uses TITLE as title (default: openSUSE). - --top-dir DIR The installation files are placed into subdir DIR. - --filesystem FS Use file system FS for the encrypted image (default: ext4). + --crypto If set, an encrypted disk image is created. + --password PASSWORD Use PASSWORD for encrypting the disk image. + --title TITLE The password query screen uses TITLE as title (default: openSUSE). + --top-dir DIR The installation files are placed into subdir DIR. + --filesystem FS Use file system FS for the encrypted image (default: ext4). More information is available in the mksusecd(1) manual page. = = = = = = = = @@ -1181,7 +1227,7 @@ my $x = $legacy_eltorito[0]{eltorito}{base}; push @$todo, $legacy_eltorito[0]; if(@legacy_eltorito > 1) { - print "More than one El Torito legacy boot entry detected, choosing /$x\n"; + print "more than one El Torito legacy boot entry detected, choosing /$x\n"; } } @@ -1373,7 +1419,7 @@ elsif($opt_efi && $t eq 'efi') { $has_efi = 1; my $f = fname($_->{$t}{base}); - if(!$f || ! -s $f || rebuild_efi_image) { + if(!$f || ! -s $f || rebuild_efi_image($_->{$t}{base})) { create_efi_image $_->{$t}{base}; $f = fname($_->{$t}{base}); } @@ -2286,9 +2332,16 @@ my $tmp_dir = $tmp->dir(); if($opt_rebuild_initrd) { + print "initrd: complete rebuild\n" if $opt_verbose >= 1; unpack_orig_initrd if !$orig_initrd; die "initrd unpacking failed\n" if !$orig_initrd; $tmp_dir = $orig_initrd; + + if($kernel->{initrd_layout} ne 'install') { + # remove old modules and firmware trees + system "rm -rf $orig_initrd/$kernel->{target_lib_dir}/modules/$kernel->{orig_version}"; + system "rm -rf $orig_initrd/$kernel->{target_lib_dir}/firmware"; + } } for my $i (@opt_initrds) { @@ -2315,9 +2368,11 @@ } my $compr = 'cat'; - $compr = "xz --quiet --check=crc32 -9 -c" if $initrd_format eq "xz"; - $compr = "gzip --quiet -9c" if $initrd_format eq "gz"; - $compr = "zstd --quiet -c -T0" if $initrd_format eq "zst"; + # don't go for -9 with xz as it doesn't lead to noticeably reduced size + # but substancially limits multithreading + $compr = "xz --quiet --threads=0 --check=crc32 -c" if $initrd_format eq "xz"; + $compr = "gzip --quiet -9 -c" if $initrd_format eq "gz"; + $compr = "zstd --quiet --threads=0 -19 -c" if $initrd_format eq "zst"; chmod 0755, $tmp_dir; @@ -2434,7 +2489,7 @@ my $image_fname = copy_file $image_location; - print "Identified root file system: $image_location\n"; + print "identified root file system: $image_location\n"; my $new_files = prepare_new_instsys_files $file_list; @@ -2443,7 +2498,7 @@ my $err = susystem "unsquashfs -no-progress -dest $tmp_root/root $image_fname >/dev/null"; die "extracting root file system failed\n" if $err; - susystem "sh -c 'tar -C $new_files -cf - . | tar -C $tmp_root/root -xpf -'"; + susystem "sh -c 'tar -C $new_files -cf - . | tar -C $tmp_root/root --keep-directory-symlink -xpf -'"; # mksquashfs expects the image *not* to exist unlink $image_fname or die "$image_fname: $!\n"; @@ -2493,10 +2548,57 @@ susystem "chown -R $< $tmp_live/root"; susystem "chmod 644 $image_new"; + if(defined $instsys_size) { + my $root_size = -s "$tmp_live/root/LiveOS/rootfs.img"; + $root_size >>= 9; + $instsys_size += $root_size if $opt_instsys_size =~ /^\+/; + $instsys_size = $root_size - $instsys_size if $opt_instsys_size =~ /^\-/; + + die "target live root fs size too small: $instsys_size blocks\n" if $instsys_size <= 0; + + printf "target live root file system size: %.2f GiB\n", $instsys_size / (1 << 21); + + if($instsys_size > $root_size) { + if(open my $f, "+<", "$tmp_live/root/LiveOS/rootfs.img") { + truncate $f, $instsys_size << 9; + close $f; + } + + $err = susystem "resize2fs -f $tmp_live/root/LiveOS/rootfs.img >/dev/null 2>&1"; + die "resizing live root fs failed\n" if $err; + } + + if($instsys_size < $root_size) { + my $log = $tmp->file(); + $err = susystem "resize2fs -f $tmp_live/root/LiveOS/rootfs.img ${instsys_size}s >$log 2>&1"; + if($err) { + my $r = `cat $log`; + $r = $r =~ /No space left on device/ ? " (no space left on device)" : ""; + die "resizing live root fs failed$r\n"; + } + + if(open my $f, "+<", "$tmp_live/root/LiveOS/rootfs.img") { + truncate $f, $instsys_size << 9; + close $f; + } + } + } + my $tmp_mnt = $tmp->dir(); die "\nLiveOS mount failed\n" if susystem "mount -oloop '$tmp_live/root/LiveOS/rootfs.img' $tmp_mnt"; - susystem "sh -c 'tar -C $new_files --owner=0 --group=0 -cf - . | tar -C $tmp_mnt -xpf -'"; + if($opt_rebuild_initrd) { + susystem "rm -rf $tmp_mnt/$kernel->{target_lib_dir}/modules/$kernel->{orig_version}"; + susystem "rm -rf $tmp_mnt/$kernel->{target_lib_dir}/firmware" unless $kernel->{keep_firmware}; + } + + susystem "sh -c 'tar -C $new_files --owner=0 --group=0 -cf - . | tar -C $tmp_mnt --keep-directory-symlink -xpf -'"; + susystem "chmod 0755 $tmp_mnt"; + + for my $i (glob "$tmp_mnt/boot/* $tmp_mnt/boot/.*") { + susystem "rm -f '$i'" unless -e $i; + } + susystem "umount $tmp_mnt"; my $err = susystem "mksquashfs $tmp_live/root $image_new -comp xz -all-root -noappend -no-progress >/dev/null 2>&1"; @@ -4330,7 +4432,7 @@ } elsif($_ eq 'tar') { $cmd = "cat '$file'" if !$cmd; - $cmd .= " | tar -C '$dir' -xpf - 2>/dev/null"; + $cmd .= " | tar -C '$dir' --keep-directory-symlink -xpf - 2>/dev/null"; last; } elsif($_ eq 'cpio') { @@ -4407,20 +4509,45 @@ { my $unpack_dir = $tmp->dir(); + # kernel package layout expected in initrd + if(-d "$orig_initrd/usr/lib/modules") { + $kernel->{target_usrmerge} = 1; + $kernel->{target_lib_dir} = "usr/lib"; + } + else { + $kernel->{target_usrmerge} = 0; + $kernel->{target_lib_dir} = "lib"; + } + if(-l "$orig_initrd/modules") { $_ = readlink "$orig_initrd/modules"; if(m#/modules/([^/]+)#) { $kernel->{orig_version} = $1; } } + elsif(opendir my $d, "$orig_initrd/$kernel->{target_lib_dir}/modules") { + for my $v (readdir $d) { + $kernel->{orig_version} = $v if $v =~ /^\d/; + } + closedir $d; + } die "oops, incompatible initrd layout\n" unless $kernel->{orig_version}; + # Note: + # if($kernel->{initrd_layout} == 'install') is atm the same as if($initrd_has_parts) + # There might turn up other layouts in future, though. + # if(-f "$orig_initrd/parts/00_lib") { + $kernel->{initrd_layout} = 'install'; rmdir $unpack_dir; if(system "unsquashfs -n -d $unpack_dir $orig_initrd/parts/00_lib >/dev/null 2>&1") { die "parts/00_lib: failed to unpack squashfs image - squashfs tools too old?\n"; } + $orig_initrd_00_lib = $unpack_dir; + } + else { + $kernel->{initrd_layout} = 'live'; } File::Find::find({ @@ -4434,10 +4561,10 @@ } }, no_chdir => 1 - }, "$orig_initrd/modules/", $unpack_dir); + }, "$orig_initrd/$kernel->{target_lib_dir}/modules/$kernel->{orig_version}", $unpack_dir); die "no initrd modules?\n" if !$kernel->{initrd_modules}; - die "no module config?\n" if !$kernel->{initrd_module_config}; + die "no module config?\n" if $kernel->{initrd_layout} eq 'install' && !$kernel->{initrd_module_config}; } @@ -4456,14 +4583,19 @@ unpack_archive $type, $_, $kernel->{dir}; } - # kernel package layout expected in initrd - if(-d "$orig_initrd/usr/lib/modules") { - $kernel->{target_usrmerge} = 1; - $kernel->{target_lib_dir} = "usr/lib"; - } - else { - $kernel->{target_usrmerge} = 0; - $kernel->{target_lib_dir} = "lib"; + # if kernel and firmware have different ideas about usrmerge, move firmware files to match kernel package layout + if(! -l "$kernel->{dir}/lib") { + if(-d "$kernel->{dir}/lib/modules" && -d "$kernel->{dir}/usr/lib/firmware") { + system "tar -C $kernel->{dir}/usr/lib -cf - firmware | tar -C $kernel->{dir}/lib --keep-directory-symlink -xpf -"; + system "rm -rf $kernel->{dir}/usr/lib/firmware"; + rmdir "$kernel->{dir}/usr/lib"; + rmdir "$kernel->{dir}/usr"; + } + elsif(-d "$kernel->{dir}/usr/lib/modules" && -d "$kernel->{dir}/lib/firmware") { + system "tar -C $kernel->{dir}/lib -cf - firmware | tar -C $kernel->{dir}/usr/lib --keep-directory-symlink -xpf -"; + system "rm -rf $kernel->{dir}/lib/firmware"; + rmdir "$kernel->{dir}/lib"; + } } # kernel package layout in new kernel rpms @@ -4514,6 +4646,7 @@ for my $name ( qw ( vmlinuz Image image vmlinux ) ) { if( -f "$kernel->{dir}/$kernel_location/$name$kernel_name_suffix" ) { $kernel->{image} = "$kernel->{dir}/$kernel_location/$name$kernel_name_suffix"; + $kernel->{name} = $name; last; } } @@ -4521,11 +4654,35 @@ die "no module dir?\n" if $kernel->{version} eq ""; die "no kernel?\n" if !$kernel->{image}; + # if no firmware packages were specified and we have to build a completely + # new initrd, keep existing firmware files + if($opt_rebuild_initrd && ! -d "$kernel->{dir}/$lib_dir/firmware") { + $kernel->{keep_firmware} = 1; + if($kernel->{initrd_layout} eq 'install') { + if($orig_initrd_00_lib && -d "$orig_initrd_00_lib/$target_lib_dir/firmware") { + print "kernel firmware: keep existing version\n"; + system "cp -r $orig_initrd_00_lib/$target_lib_dir/firmware $kernel->{dir}/$lib_dir"; + } + else { + print "kernel firmware: original firmware files missing\n"; + } + } + else { + if(-d "$orig_initrd/$target_lib_dir/firmware") { + print "kernel firmware: keep existing version\n"; + system "cp -r $orig_initrd/$target_lib_dir/firmware $kernel->{dir}/$lib_dir"; + } + else { + print "kernel firmware: original firmware files missing\n"; + } + } + } + for (glob "$kernel->{dir}/$lib_dir/modules/*") { s#.*/##; next if $_ eq $kernel->{version}; print "warning: kmp version mismatch, adjusting: $_ --> $kernel->{version}\n"; - system "tar -C '$kernel->{dir}/$lib_dir/modules/$_' -cf - . | tar -C '$kernel->{dir}/$lib_dir/modules/$kernel->{version}' -xf -"; + system "tar -C '$kernel->{dir}/$lib_dir/modules/$_' -cf - . | tar -C '$kernel->{dir}/$lib_dir/modules/$kernel->{version}' --keep-directory-symlink -xf -"; } # compat symlink needed for depmod @@ -4621,11 +4778,23 @@ $kernel->{new_dir} = $tmp->dir(); - File::Path::make_path "$kernel->{new_dir}/$target_lib_dir/modules/$kernel->{version}/initrd"; + chmod 0755, $kernel->{new_dir}; + + if($kernel->{initrd_layout} eq 'install') { + File::Path::make_path "$kernel->{new_dir}/$target_lib_dir/modules/$kernel->{version}/initrd"; + } + else { + File::Path::make_path "$kernel->{new_dir}/$target_lib_dir"; + } for (sort keys %{$kernel->{initrd_modules}}) { if($kernel->{modules}{$_} && !$mods_remove{$_}) { - system "cp $kernel->{dir}/$lib_dir/modules/$kernel->{version}/$kernel->{modules}{$_} $kernel->{new_dir}/$target_lib_dir/modules/$kernel->{version}/initrd"; + if($kernel->{initrd_layout} eq 'install') { + system "cp $kernel->{dir}/$lib_dir/modules/$kernel->{version}/$kernel->{modules}{$_} $kernel->{new_dir}/$target_lib_dir/modules/$kernel->{version}/initrd"; + } + else { + system "cd $kernel->{dir}/$lib_dir && cp --parents modules/$kernel->{version}/$kernel->{modules}{$_} $kernel->{new_dir}/$target_lib_dir"; + } push @{$kernel->{added}}, $_ if $kernel->{initrd_modules}{$_} > 1; } else { @@ -4639,16 +4808,21 @@ system "cp -f $kernel->{dir}/$lib_dir/modules/$kernel->{version}/modules.builtin{,.modinfo} $kernel->{new_dir}/$target_lib_dir/modules/$kernel->{version}/"; } - if(open my $f, "$kernel->{dir}/$lib_dir/modules/$kernel->{version}/modules.order") { - if(open my $w, ">$kernel->{new_dir}/$target_lib_dir/modules/$kernel->{version}/modules.order") { - while(<$f>) { - chomp; - s#.*/#initrd/#; - print $w "$_\n" if -f "$kernel->{new_dir}/$lib_dir/modules/$kernel->{version}/$_"; + if($kernel->{initrd_layout} eq 'install') { + if(open my $f, "$kernel->{dir}/$lib_dir/modules/$kernel->{version}/modules.order") { + if(open my $w, ">$kernel->{new_dir}/$target_lib_dir/modules/$kernel->{version}/modules.order") { + while(<$f>) { + chomp; + s#.*/#initrd/#; + print $w "$_\n" if -f "$kernel->{new_dir}/$lib_dir/modules/$kernel->{version}/$_"; + } + close $w; } - close $w; + close $f; } - close $f; + } + else { + system "cp $kernel->{dir}/$lib_dir/modules/$kernel->{version}/modules.order $kernel->{new_dir}/$target_lib_dir/modules/$kernel->{version}"; } # compat symlink needed for depmod @@ -4660,6 +4834,18 @@ symlink("../lib", "$kernel->{new_dir}/usr/lib"); } + if($opt_no_compression->{modules}) { + my $dir = "$kernel->{new_dir}/$target_lib_dir/modules"; + + if(-d $dir) { + print "uncompressing kernel modules...\n"; + + system "find $dir -type f -name \\*.ko.zst -exec zstd -d --quiet --rm '{}' \\;"; + system "find $dir -type f -name \\*.ko.xz -exec xz -d '{}' \\;"; + system "find $dir -type f -name \\*.ko.gz -exec gzip -d '{}' \\;"; + } + } + system "depmod -a -b $kernel->{new_dir} $kernel->{version}"; if($kernel->{target_usrmerge}) { @@ -4674,19 +4860,21 @@ my %fw; - for my $m (glob("$kernel->{new_dir}/$target_lib_dir/modules/$kernel->{version}/initrd/*${kext_glob}")) { - chomp $m; - - next unless -f $m; - - my @l; - chomp(@l = `modinfo -F firmware $m`); + File::Find::find({ + wanted => sub { + return if -l || ! -f; # no links, only files + if(m#([^/]+)${kext_regexp}$#) { + my @l; + chomp(@l = `modinfo -F firmware $_`); - $m =~ s#.*/##; - $m =~ s#${kext_regexp}$##; + s#.*/##; + s#${kext_regexp}$##; - $fw{$m} = [ @l ] if @l; - } + $fw{$_} = [ @l ] if @l; + } + }, + no_chdir => 1 + }, "$kernel->{new_dir}/$target_lib_dir/modules/$kernel->{version}"); my $kv = $kernel->{version}; my $fw_dir = "$kernel->{dir}/$lib_dir/firmware"; @@ -4712,6 +4900,26 @@ } } + if($opt_no_compression->{firmware}) { + my $dir = "$kernel->{new_dir}/$target_lib_dir/firmware"; + + if(-d $dir) { + print "uncompressing kernel firmware...\n"; + + # rename symlinks + for my $suffix ("zst", "xz", "gz") { + system "find $dir -type l -name \\*.$suffix -exec rename -sl .$suffix '' '{}' \\; -exec rename -l .$suffix '' '{}' \\;"; + } + + system "find $dir -type f -name \\*.zst -exec zstd -d --quiet --rm '{}' \\;"; + system "find $dir -type f -name \\*.xz -exec xz -d '{}' \\;"; + system "find $dir -type f -name \\*.gz -exec gzip -d '{}' \\;"; + + my $broken = `find $dir -follow -type l`; + print STDERR "firmware uncompressing left broken symlinks:\n$broken\n" if $broken ne ""; + } + } + printf "kernel firmware: %d/%d files updated\n", scalar(keys %fw_ok), scalar(keys %fw_ok) + scalar(keys %fw_missing); # print Dumper(\%fw); @@ -4773,9 +4981,18 @@ } } - my $err = system "mksquashfs $kernel->{new_dir} $tmp_dir/parts/$p" . - ($mksquashfs_has_comp ? " -comp xz" : "") . - " -noappend -no-progress >/dev/null 2>&1"; + my $comp = $mksquashfs_has_comp ? "-comp xz" : ""; + + if($opt_no_compression->{squashfs}) { + if(!$mksquashfs_has_comp) { + die "mksquashfs version too old to allow setting compression algorithm\n"; + } + else { + $comp = "-no-compression"; + } + } + + my $err = system "mksquashfs $kernel->{new_dir} $tmp_dir/parts/$p $comp -noappend -no-progress >/dev/null 2>&1"; die "mksquashfs failed\n" if $err; } else { @@ -4783,29 +5000,108 @@ } # add module symlink + if($kernel->{initrd_layout} eq 'install') { + symlink "$target_lib_dir/modules/$kernel->{version}/initrd", "$tmp_dir/modules"; - symlink "$target_lib_dir/modules/$kernel->{version}/initrd", "$tmp_dir/modules"; + my $cmd = "Exec:\t\tln -snf $lib_dir/modules/`uname -r`/initrd /modules\n"; - my $cmd = "Exec:\t\tln -snf $lib_dir/modules/`uname -r`/initrd /modules\n"; + if(open my $f, "$orig_initrd/linuxrc.config") { + my $cmd_found; + my @lines; + while(<$f>) { + push @lines, $_; + $cmd_found = 1 if $_ eq $cmd; + } + close $f; - if(open my $f, "$orig_initrd/linuxrc.config") { - my $cmd_found; - my @lines; - while(<$f>) { - push @lines, $_; - $cmd_found = 1 if $_ eq $cmd; + if(!$cmd_found) { + open my $f, ">$tmp_dir/linuxrc.config"; + print $f $cmd; + print $f @lines; + close $f; + } + } + } + + push @opt_initrds, $tmp_dir; +} + + +# - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +# add_modules_to_instsys() +# +# Add new kernel modules and firmware to instsys. +# +sub add_modules_to_instsys +{ + return if $kernel->{initrd_layout} eq 'install'; + + if(! -d "$kernel->{dir}/boot") { + mkdir "$kernel->{dir}/boot", 0755; + + my $k_dir = "$kernel->{lib_dir}/modules/$kernel->{version}"; + + for my $i ("System.map", "config", "sysctl.conf", $kernel->{name}) { + symlink "../$k_dir/$i", "$kernel->{dir}/boot/$i-$kernel->{version}"; + } + symlink "../$k_dir/.$kernel->{name}.hmac", "$kernel->{dir}/boot/.$kernel->{name}-$kernel->{version}.hmac" if -f "$kernel->{dir}/$k_dir/.$kernel->{name}.hmac"; + } + + symlink "$kernel->{name}-$kernel->{version}", "$kernel->{dir}/boot/$kernel->{name}"; + + unshift @opt_instsys, $kernel->{dir}; +} + + +# - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +# update_no_compression_settings() +# +# Merge $opt_no_compression with .no_compression setting in initrd and +# update initrd if necessary. +# +sub update_no_compression_settings +{ + die "oops: initrd not unpacked?\n" if !$orig_initrd; + + my $has_setting = 0; + my $has_opt_setting = $opt_no_compression ? 1 : 0; + + if(open my $f, "$orig_initrd/.no_compression") { + $has_setting = 1; + if(!$opt_no_compression) { + chomp (my $no_comp = <$f>); + for my $c (split /,/, $no_comp) { + $opt_no_compression->{$c} = 1; + } } close $f; + } - if(!$cmd_found) { - open my $f, ">$tmp_dir/linuxrc.config"; - print $f $cmd; - print $f @lines; - close $f; + my @keys = qw (firmware modules squashfs); + my $comp_str; + + for my $i (@keys) { + if($opt_no_compression->{$i}) { + $comp_str .= "," if $comp_str ne ""; + $comp_str .= "$i"; } } - push @opt_initrds, $tmp_dir; + if(($has_opt_setting || $has_setting) && $comp_str ne "") { + print "no compression for: $comp_str\n"; + + # change only if necessary + if($has_opt_setting) { + my $tmp_dir = $tmp->dir(); + + if(open my $f, ">$tmp_dir/.no_compression") { + print $f "$comp_str\n"; + close $f; + } + + push @opt_initrds, $tmp_dir; + } + } } @@ -4826,6 +5122,8 @@ die "initrd unpacking failed\n" if !$orig_initrd; + update_no_compression_settings; + get_initrd_modules; unpack_kernel_rpms; @@ -4846,6 +5144,8 @@ add_modules_to_initrd; + add_modules_to_instsys; + # now replace kernel if(my $x = get_kernel_initrd) { @@ -5011,11 +5311,15 @@ # size_string is either a numerical size like '64G' or a file or block # device name. In this case the size of the file or block device is used. # +# An optional '+' or '-' at the beginning is ignored. +# sub eval_size { my $size = $_[0]; my $unit = { b => 9 - 9, k => 10 - 9, m => 20 - 9, g => 30 - 9, t => 40 - 9 }; + $size =~ s/^[+\-]//; + return undef unless $size; if($size =~ /^(\d+)\s*([bkmgt]?)/i) { @@ -5043,8 +5347,6 @@ $size = undef; } - printf "target image size: %.2f GiB ($size blocks)\n", $size / (1 << 21); - return $size; } @@ -5728,7 +6030,7 @@ # copy everything except the efi config - it's already on the efi system # partition - system "${sudo}tar -C $iso_mount --exclude EFI -cf - . | ${sudo}tar -C $crypt_mount/$top_dir -xpf -"; + system "${sudo}tar -C $iso_mount --exclude EFI -cf - . | ${sudo}tar -C $crypt_mount/$top_dir --keep-directory-symlink -xpf -"; show_progress 90; @@ -5968,7 +6270,7 @@ { return unless fname "EFI"; - print "updating UEFI image $_[0]\n"; + print "updating UEFI image: $_[0]\n"; my $file = copy_or_new_file($_[0]); @@ -5976,7 +6278,7 @@ for my $x (sort keys %$files) { if($x =~ m#^EFI($|/)#) { - system "tar -C '$files->{$x}' --mode=u+w -cf - '$x' | tar -C '$efi_dir' -xpf -"; + system "tar -C '$files->{$x}' --mode=u+w -cf - '$x' | tar -C '$efi_dir' --keep-directory-symlink -xpf -"; } } @@ -5995,7 +6297,9 @@ # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -# rebuild_efi_image() +# rebuild_efi_image(efi_image_name) +# +# - efi_image_name: efi image file name (in ISO image) # # Check whether there were changes to the 'EFI' directory and we need to # rebuild the el-torito efi image. @@ -6004,8 +6308,12 @@ # sub rebuild_efi_image { + my $efi_image_name = $_[0]; + my $source_list; + $source_list->{$files->{$efi_image_name}} = 1 if $files->{$efi_image_name}; + for my $x (sort keys %$files) { if($x =~ m#^EFI($|/)#) { $source_list->{$files->{$x}} = 1; diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/mksusecd-2.19/mksusecd_man.adoc new/mksusecd-3.0/mksusecd_man.adoc --- old/mksusecd-2.19/mksusecd_man.adoc 2024-07-17 21:02:32.000000000 +0200 +++ new/mksusecd-3.0/mksusecd_man.adoc 2024-08-16 17:54:15.000000000 +0200 @@ -125,14 +125,32 @@ *--rebuild-initrd*:: Rebuild the entire initrd instead of appending changes. + -This makes the initrd smaller but requires to run mksusecd with root permissions. +This makes the initrd smaller but requires to run mksusecd with root permissions. + +See *Kernel update notes* below. + +*--no-rebuild-initrd*:: +Append changes to the initrd instead of rebuilding. + +This makes the initrd larger but does not require to run mksusecd with root permissions. + +See *Kernel update notes* below. *--instsys*=_DIR_|_RPM_:: Add content of _DIR_ or _RPM_ to installation system or root file system for Live media (can be repeated). +*--live.root*=_DIR_|_RPM_:: +Alias for *--instsys*. + *--rescue*=_DIR_|_RPM_:: Add content of _DIR_ or _RPM_ to rescue system (can be repeated). +*--instsys-size*=_SIZE_SPEC_:: +Resize Live root file system. +_SIZE_SPEC_ can be a number, optionally followed by a unit ('k', +'m', 'g', 't') indicating kiB, MiB, GiB, or TiB, respectively. +If _SIZE_SPEC_ starts with a '+' or '-', the size is increased or decreased, respectively. + +*--live-root-size*=_SIZE_SPEC_:: +Aias for *--instsys-size*. + *--no-docs*:: Don't include package documentation files (default). @@ -141,21 +159,26 @@ === Kernel/module update related options -*--kernel*=_KERNEL_RPMS_:: -Replace kernel and modules used for booting. _KERNEL_RPMS_ is -a list of RPMs that contain the new kernel, modules, and -firmware files. + +*--kernel*=_RPM_LIST_:: +Replace kernel, kernel modules, and kernel firmware used for booting. _RPM_LIST_ is +a list of kernel or firmware packages. + *Note*: this option takes a variable number of arguments. So -it may be necessary to terminate the arg list with an explicit '--'. +it may be necessary to terminate the arg list with an explicit '--'. + +*Note also*: since mksusecd 3.0 this option automatically implies *--rebuild-initrd*. Use *--no-rebuild-inintrd* to revert this. + +See *Kernel update notes* below. *--modules*=_MODULE_LIST_:: -A list of modules to be included additionally to the initrd. +A list of modules to be added to the initrd. Use this in combination with *--kernel*. You can prefix module names with '-' to have them removed instead. + _MODULE_LIST_ may be space or comma separated. + *Note*: this option takes a variable number of arguments. So it may be necessary to terminate the arg list with an explicit '--'. +*--no-compression*=_LIST_:: +A comma-separated list of: firmware, modules, squashfs. + +See *Kernel compression notes* below. + === Add-on related options *--addon*=_RPM_LIST_:: @@ -206,10 +229,12 @@ === General image layout related options *--uefi*:: -Make ISO UEFI bootable (default). +Make ISO UEFI bootable (default). + +See *UEFI boot notes* below. *--no-uefi*:: -Don't make ISO UEFI bootable. +Don't make ISO UEFI bootable. + +See *UEFI boot notes* below. *--zipl*:: Make image zIPL bootable (default on s390x). @@ -360,9 +385,9 @@ Sources can be - existing installation media -- skelcd-installer-<PRODUCT> packages (RPMs) -- tftpboot-installation-<PRODUCT> packages (RPMs) -- additional or modified files that should be added/merged into the image +- skelcd-installer-<PRODUCT> packages +- tftpboot-installation-<PRODUCT> packages +- directories with additional or modified files that should be added/merged into the image either as image/RPM file or unpacked into a directory. @@ -371,7 +396,8 @@ If you pass a skelcd-installer-<PRODUCT> or tftpboot-installation-<PRODUCT> RPM (or a directory with the same layout) - mksusecd will handle these -specially and extract the relevant parts. +specially. These packaged contain the complete installation system and mksusecd +willl extract the relevant parts to update the installer on the medium. === Hybrid mode notes @@ -449,6 +475,89 @@ the image is not the default and you have to explicitly request it with *--sign-image*. You can also add a signature later using *tagmedia*. +=== Kernel update notes + +Normally, the *--kernel* option will do what you expect but there are +situations where it may subtly go wrong. So here is a more in-depth explanation +how kernel updates work. + +The *--kernel* option accepts a mix of kernel packages and kernel firmware +packages. That is, you can update both kernel firmware and kernel modules. +But there must be at least one kernel package. + +As a special case if there are no kernel firmware packages +specified in *--kernel*, then the old kernel firmware files are kept (kernel firmware is typically not +kernel version dependent). + +The initrd typically uses a limited set of kernel modules. mksusecd will try to keep the exact list +of modules but that may not be possible due to kernel package changes. mksusecd output will +display the differences. + +If you have to adjust the kernel module list, use the *--modules* option. Kernel module +dependencies are automatically resolved. + +Note that there may be not just a single package containing kernel modules (e.g. kernel-default) +but several others (e.g. kernel-default-extra, kernel-default-optional) or even kmp packages with +individual modules. If you see missing modules, you might need some of these packages as well. + +mksusecd will not add all kernel firmware files to the initrd but only those that are required by +the kernel modules used in the initrd. + +For Live media, kernel modules and firmware are also present in the Live root file system. Kernel modules +and firmware are also updated there but the complete packages are used. + +There are two cases: 1. the 'normal' case (*--rebuild-initrd* is active) and 2. *--no-rebuild-initrd* is active. + +Note that since mksusecd 3.0 *--rebuild-initrd* is automatically acivated if *--kernel* is used. + +1. Old kernel modules / firmware files are removed and only files from packages specified +in *--kernel* are used. This makes initrd and Live root smaller and exactly reproduces the original +initrd and Live root file system layouts. + +This also means that if you forgot to add sufficient kernel firmware packages in *--kernel*, kernel +firmware files might be missing. + +2. New kernel modules / firmware files are added to initrd and Live root. This means your initrd and Live root file system contain +both the old kernel tree and the new one (making it noticeably larger). + +If you included kernel firmware packages in *--kernel* then kernel firmware files from these packages +are added as well, possibly replacing old kernel firmware files with the same name. + +In both cases, if you run out of space in the Live root file system, use *--instsys-size* to increase the +file system size as needed. + +Note on usrmerge kernels: kernel packages (and kernel firmware packages) come in two variants: older packages +with files stored in '/lib' and (typically) newer packages with files stored in '/usr/lib'. +mksusecd will accept both and adjust the package layout to the one expected in initrd and Live root. + +=== Kernel compression notes + +For SUSE installation media, kernel modules and firmware files are kept in a +separate squashfs image ('parts/00_lib') within the initrd. + +Usually, kernel firmware files and kernel modules are compressed to reduce size. + +In certain situations it may be better to keep individual kernel modules or +kernel firmware files uncompressed and rely on the squashfs file system compression instead. + +Or use no squashfs file system compression and rely on the initrd compression. + +To fine-tune this, use the *--no-compression* option. + +Setting it to 'modules' will uncompress all kernel modules. 'firmware' will uncompress +firmware files and 'squashfs' will turn off squashfs file system compression. + +The current setting is stored in the '.no_compression' file the initrd. + +For example, *--no-compression=firmware,modules,squashfs* turns off compression +everywhere. This results in the smallest compressed initrd size - but it also results in +the largest uncompressed initrd size. + +Note that any new *--no-compression* setting replaces the old setting entirely. +For example, *--no-compression=modules* will not additionally turn off compression for +kernel modules but means only kernel modules are uncompressed. + +Note also that you almost certainly want to use *--no-compression* together +with *--rebuild-initrd*. + === Add-on notes The add-on created here is just a repository, not a full add-on product. @@ -517,11 +626,8 @@ === Fedora/RHEL notes -Not all options apply to media with Fedora/RHEL layout. Major options that work, are: - -- *--boot* to add boot options -- *--initrd* to modify the initrd (stage1) -- *--instsys* to modify the Live installation system (stage2) +Not all options apply to media with Fedora/RHEL layout. It doesn't make +sense to add a SUSE driver update to a RHEL iso, for example. mksusecd will by default create media with a SUSE-like hybrid mode (MBR partition table with non-overlapping partitions). You can change that to @@ -538,6 +644,23 @@ - You can use other digests instead of MD5 using *--digest DIGEST* but checkisomd5 cannot verify these images. +=== UEFI boot notes + +There are two ways UEFI firmware finds boot files on our media: + +1. by running the boot loader located below the '/EFI' directory +2. by locating a FAT file system image via the El-Torito standard and running +the boot loader stored there; this FAT file system image contains the same '/EFI' directory structure + +The *--uefi* option refers to method 2. + +Note that this FAT file system image might not be visible on the medium (e.g. KIWI produced media hide the file). +If it is visible, it has names like '/boot/x86_64/efi', '/boot/x86_64/loader/efiboot.img', '/images/efiboot.img', or similar. + +If this FAT file system image is missing or files in the '/EFI' directory (on the medium) have changed, +mksusecd will create a new FAT file system image based on the updated '/EFI' directory content. +This generated FAT file system image will always be visible on the medium. + === Crypto notes The *--crypto* option allows you to create an encrypted installation disk. @@ -600,6 +723,9 @@ # create foo.iso from /foo_dir mksusecd --create foo.iso /foo_dir +# create foo.iso from bar.iso and integrate files from /foo_dir +mksusecd --create foo.iso bar.iso /foo_dir + # create foo.iso from /foo_dir, no hybrid mode mksusecd --create foo.iso --no-hybrid /foo_dir @@ -612,11 +738,25 @@ # create foo.iso from old.iso and add package bar to the initrd mksusecd --create foo.iso --initrd bar.rpm old.iso +# create foo.iso from old.iso and add a driver update to the initrd +mksusecd --create foo.iso --initrd bar.dud old.iso + # create foo.iso from old.iso and add package bar to rescue system mksusecd --create foo.iso --rescue bar.rpm old.iso # create foo.iso from live.iso and add package bar to Live system mksusecd --create foo.iso --instsys bar.rpm live.iso + +# create foo.iso from live.iso and update kernel to kernel-default.rpm +mksusecd --create foo.iso --kernel kernel-default.rpm -- live.iso + +# create foo.iso from live.iso and increase Live root file system by 1 GiB +mksusecd --create foo.iso --live-root-size +1G live.iso + +# create new iso from sles.iso taking an updated installer from tftpboot-installation-* package +mksusecd --create new.iso sles.iso tftpboot-installation-SLE.rpm + + ---- Find more usage examples here: https://github.com/openSUSE/mksusecd/blob/master/HOWTO.md