]> git.ipfire.org Git - thirdparty/dracut.git/blob - dracut.sh
fix(dracut): be more robust when using 'set -u'
[thirdparty/dracut.git] / dracut.sh
1 #!/bin/bash -p
2 #
3 # Generator script for a dracut initramfs
4
5 # Copyright 2005-2013 Red Hat, Inc. All rights reserved.
6 #
7 # This program is free software; you can redistribute it and/or modify
8 # it under the terms of the GNU General Public License as published by
9 # the Free Software Foundation; either version 2 of the License, or
10 # (at your option) any later version.
11 #
12 # This program is distributed in the hope that it will be useful,
13 # but WITHOUT ANY WARRANTY; without even the implied warranty of
14 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 # GNU General Public License for more details.
16 #
17 # You should have received a copy of the GNU General Public License
18 # along with this program. If not, see <http://www.gnu.org/licenses/>.
19 #
20
21 # store for logging
22
23 unset BASH_ENV
24 unset GZIP
25
26 # Verify bash version, current minimum is 4
27 if ((BASH_VERSINFO[0] < 4)); then
28 printf -- 'You need at least Bash 4 to use dracut, sorry.' >&2
29 exit 1
30 fi
31
32 dracut_args=("$@")
33 # shellcheck disable=SC2155
34 readonly dracut_cmd=$(readlink -f "$0")
35
36 set -o pipefail
37
38 usage() {
39 [[ $sysroot_l ]] && dracutsysrootdir="$sysroot_l"
40 [[ $dracutbasedir ]] || dracutbasedir="$dracutsysrootdir"/usr/lib/dracut
41 if [[ -f $dracutbasedir/dracut-version.sh ]]; then
42 # shellcheck source=./dracut-version.sh
43 . "$dracutbasedir"/dracut-version.sh
44 fi
45
46 # 80x25 linebreak here ^
47 cat << EOF
48 Usage: $dracut_cmd [OPTION]... [<initramfs> [<kernel-version>]]
49
50 Version: $DRACUT_VERSION
51
52 Creates initial ramdisk images for preloading modules
53
54 -h, --help Display all options
55
56 If a [LIST] has multiple arguments, then you have to put these in quotes.
57
58 For example:
59
60 # dracut --add-drivers "module1 module2" ...
61
62 EOF
63 }
64
65 long_usage() {
66 [[ $dracutbasedir ]] || dracutbasedir="$dracutsysrootdir"/usr/lib/dracut
67 if [[ -f $dracutbasedir/dracut-version.sh ]]; then
68 # shellcheck source=./dracut-version.sh
69 . "$dracutbasedir"/dracut-version.sh
70 fi
71
72 # 80x25 linebreak here ^
73 cat << EOF
74 Usage: $dracut_cmd [OPTION]... [<initramfs> [<kernel-version>]]
75
76 Version: $DRACUT_VERSION
77
78 Creates initial ramdisk images for preloading modules
79
80 --kver [VERSION] Set kernel version to [VERSION].
81 -f, --force Overwrite existing initramfs file.
82 -a, --add [LIST] Add a space-separated list of dracut modules.
83 --rebuild Append arguments to those of existing image and rebuild
84 -m, --modules [LIST] Specify a space-separated list of dracut modules to
85 call when building the initramfs. Modules are located
86 in /usr/lib/dracut/modules.d.
87 -o, --omit [LIST] Omit a space-separated list of dracut modules.
88 --force-add [LIST] Force to add a space-separated list of dracut modules
89 to the default set of modules, when -H is specified.
90 -d, --drivers [LIST] Specify a space-separated list of kernel modules to
91 exclusively include in the initramfs.
92 --add-drivers [LIST] Specify a space-separated list of kernel
93 modules to add to the initramfs.
94 --force-drivers [LIST] Specify a space-separated list of kernel
95 modules to add to the initramfs and make sure they
96 are tried to be loaded via modprobe same as passing
97 rd.driver.pre=DRIVER kernel parameter.
98 --omit-drivers [LIST] Specify a space-separated list of kernel
99 modules not to add to the initramfs.
100 --filesystems [LIST] Specify a space-separated list of kernel filesystem
101 modules to exclusively include in the generic
102 initramfs.
103 -k, --kmoddir [DIR] Specify the directory, where to look for kernel
104 modules
105 --fwdir [DIR] Specify additional directories, where to look for
106 firmwares, separated by :
107 --kernel-only Only install kernel drivers and firmware files
108 --no-kernel Do not install kernel drivers and firmware files
109 --print-cmdline Print the kernel command line for the given disk layout
110 --early-microcode Combine early microcode with ramdisk
111 --no-early-microcode Do not combine early microcode with ramdisk
112 --kernel-cmdline [PARAMETERS] Specify default kernel command line parameters
113 --strip Strip binaries in the initramfs
114 --aggresive-strip Strip more than just debug symbol and sections,
115 for a smaller initramfs build.
116 --nostrip Do not strip binaries in the initramfs
117 --hardlink Hardlink files in the initramfs
118 --nohardlink Do not hardlink files in the initramfs
119 --prefix [DIR] Prefix initramfs files with [DIR]
120 --noprefix Do not prefix initramfs files
121 --mdadmconf Include local /etc/mdadm.conf
122 --nomdadmconf Do not include local /etc/mdadm.conf
123 --lvmconf Include local /etc/lvm/lvm.conf
124 --nolvmconf Do not include local /etc/lvm/lvm.conf
125 --fscks [LIST] Add a space-separated list of fsck helpers.
126 --nofscks Inhibit installation of any fsck helpers.
127 --ro-mnt Mount / and /usr read-only by default.
128 -h, --help This message
129 --debug Output debug information of the build process
130 --profile Output profile information of the build process
131 -L, --stdlog [0-6] Specify logging level (to standard error)
132 0 - suppress any messages
133 1 - only fatal errors
134 2 - all errors
135 3 - warnings
136 4 - info
137 5 - debug info (here starts lots of output)
138 6 - trace info (and even more)
139 -v, --verbose Increase verbosity level
140 -q, --quiet Decrease verbosity level
141 -c, --conf [FILE] Specify configuration file to use.
142 Default: /etc/dracut.conf
143 --confdir [DIR] Specify configuration directory to use *.conf files
144 from. Default: /etc/dracut.conf.d
145 --tmpdir [DIR] Temporary directory to be used instead of default
146 ${TMPDIR:-/var/tmp}.
147 -r, --sysroot [DIR] Specify sysroot directory to collect files from.
148 -l, --local Local mode. Use modules from the current working
149 directory instead of the system-wide installed in
150 /usr/lib/dracut/modules.d.
151 Useful when running dracut from a git checkout.
152 -H, --hostonly Host-Only mode: Install only what is needed for
153 booting the local host instead of a generic host.
154 -N, --no-hostonly Disables Host-Only mode
155 --hostonly-mode <mode>
156 Specify the hostonly mode to use. <mode> could be
157 one of "sloppy" or "strict". "sloppy" mode is used
158 by default.
159 In "sloppy" hostonly mode, extra drivers and modules
160 will be installed, so minor hardware change won't make
161 the image unbootable (eg. changed keyboard), and the
162 image is still portable among similar hosts.
163 With "strict" mode enabled, anything not necessary
164 for booting the local host in its current state will
165 not be included, and modules may do some extra job
166 to save more space. Minor change of hardware or
167 environment could make the image unbootable.
168 DO NOT use "strict" mode unless you know what you
169 are doing.
170 --hostonly-cmdline Store kernel command line arguments needed
171 in the initramfs
172 --no-hostonly-cmdline Do not store kernel command line arguments needed
173 in the initramfs
174 --no-hostonly-default-device
175 Do not generate implicit host devices like root,
176 swap, fstab, etc. Use "--mount" or "--add-device"
177 to explicitly add devices as needed.
178 --hostonly-i18n Install only needed keyboard and font files according
179 to the host configuration (default).
180 --no-hostonly-i18n Install all keyboard and font files available.
181 --hostonly-nics [LIST]
182 Only enable listed NICs in the initramfs.
183 --persistent-policy [POLICY]
184 Use [POLICY] to address disks and partitions.
185 POLICY can be any directory name found in /dev/disk.
186 E.g. "by-uuid", "by-label"
187 --fstab Use /etc/fstab to determine the root device.
188 --add-fstab [FILE] Add file to the initramfs fstab
189 --mount "[DEV] [MP] [FSTYPE] [FSOPTS]"
190 Mount device [DEV] on mountpoint [MP] with filesystem
191 [FSTYPE] and options [FSOPTS] in the initramfs
192 --mount "[MP]" Same as above, but [DEV], [FSTYPE] and [FSOPTS] are
193 determined by looking at the current mounts.
194 --add-device "[DEV]" Bring up [DEV] in initramfs
195 -i, --include [SOURCE] [TARGET]
196 Include the files in the SOURCE directory into the
197 Target directory in the final initramfs.
198 If SOURCE is a file, it will be installed to TARGET
199 in the final initramfs.
200 -I, --install [LIST] Install the space separated list of files into the
201 initramfs.
202 --install-optional [LIST] Install the space separated list of files into the
203 initramfs, if they exist.
204 --gzip Compress the generated initramfs using gzip.
205 This will be done by default, unless another
206 compression option or --no-compress is passed.
207 --bzip2 Compress the generated initramfs using bzip2.
208 Make sure your kernel has bzip2 decompression support
209 compiled in, otherwise you will not be able to boot.
210 --lzma Compress the generated initramfs using lzma.
211 Make sure your kernel has lzma support compiled in,
212 otherwise you will not be able to boot.
213 --xz Compress the generated initramfs using xz.
214 Make sure that your kernel has xz support compiled
215 in, otherwise you will not be able to boot.
216 --lzo Compress the generated initramfs using lzop.
217 Make sure that your kernel has lzo support compiled
218 in, otherwise you will not be able to boot.
219 --lz4 Compress the generated initramfs using lz4.
220 Make sure that your kernel has lz4 support compiled
221 in, otherwise you will not be able to boot.
222 --zstd Compress the generated initramfs using Zstandard.
223 Make sure that your kernel has zstd support compiled
224 in, otherwise you will not be able to boot.
225 --compress [COMPRESSION] Compress the generated initramfs with the
226 passed compression program. Make sure your kernel
227 knows how to decompress the generated initramfs,
228 otherwise you will not be able to boot.
229 --no-compress Do not compress the generated initramfs. This will
230 override any other compression options.
231 --enhanced-cpio Attempt to reflink cpio file data using dracut-cpio.
232 --list-modules List all available dracut modules.
233 -M, --show-modules Print included module's name to standard output during
234 build.
235 --keep Keep the temporary initramfs for debugging purposes
236 --printsize Print out the module install size
237 --sshkey [SSHKEY] Add ssh key to initramfs (use with ssh-client module)
238 --logfile [FILE] Logfile to use (overrides configuration setting)
239 --reproducible Create reproducible images
240 --no-reproducible Do not create reproducible images
241 --loginstall [DIR] Log all files installed from the host to [DIR]
242 --uefi Create an UEFI executable with the kernel cmdline and
243 kernel combined
244 --no-uefi Disables UEFI mode
245 --uefi-stub [FILE] Use the UEFI stub [FILE] to create an UEFI executable
246 --uefi-splash-image [FILE]
247 Use [FILE] as a splash image when creating an UEFI
248 executable
249 --kernel-image [FILE] location of the kernel image
250 --regenerate-all Regenerate all initramfs images at the default location
251 for the kernel versions found on the system
252 --version Display version
253
254 If [LIST] has multiple arguments, then you have to put these in quotes.
255
256 For example:
257
258 # dracut --add-drivers "module1 module2" ...
259
260 EOF
261 }
262
263 long_version() {
264 [[ $dracutbasedir ]] || dracutbasedir="$dracutsysrootdir"/usr/lib/dracut
265 if [[ -f $dracutbasedir/dracut-version.sh ]]; then
266 # shellcheck source=./dracut-version.sh
267 . "$dracutbasedir"/dracut-version.sh
268 fi
269 echo "dracut $DRACUT_VERSION"
270 }
271
272 # Fills up host_devs stack variable and makes sure there are no duplicates
273 push_host_devs() {
274 local _dev
275 for _dev in "$@"; do
276 [[ " ${host_devs[*]} " == *" $_dev "* ]] && return
277 host_devs+=("$_dev")
278 done
279 }
280
281 # Little helper function for reading args from the commandline.
282 # it automatically handles -a b and -a=b variants, and returns 1 if
283 # we need to shift $3.
284 read_arg() {
285 # $1 = arg name
286 # $2 = arg value
287 # $3 = arg parameter
288 local rematch='^[^=]*=(.*)$'
289 if [[ $2 =~ $rematch ]]; then
290 read -r "$1" <<< "${BASH_REMATCH[1]}"
291 else
292 read -r "$1" <<< "$3"
293 # There is no way to shift our callers args, so
294 # return 1 to indicate they should do it instead.
295 return 1
296 fi
297 }
298
299 check_conf_file() {
300 if grep -H -e '^[^#]*[+]=\("[^ ]\|.*[^ ]"\)' "$@"; then
301 printf '\ndracut: WARNING: <key>+=" <values> ": <values> should have surrounding white spaces!\n' >&2
302 printf 'dracut: WARNING: This will lead to unwanted side effects! Please fix the configuration file.\n\n' >&2
303 fi
304 }
305
306 dropindirs_sort() {
307 local suffix=$1
308 shift
309 local -a files
310 local f d
311
312 for d in "$@"; do
313 for i in "$d/"*"$suffix"; do
314 if [[ -e $i ]]; then
315 printf "%s\n" "${i##*/}"
316 fi
317 done
318 done | sort -Vu | {
319 readarray -t files
320
321 for f in "${files[@]}"; do
322 for d in "$@"; do
323 if [[ -e "$d/$f" ]]; then
324 printf "%s\n" "$d/$f"
325 continue 2
326 fi
327 done
328 done
329 }
330 }
331
332 rearrange_params() {
333 # Workaround -i, --include taking 2 arguments
334 newat=()
335 for i in "$@"; do
336 if [[ $i == "-i" ]] || [[ $i == "--include" ]]; then
337 newat+=("++include") # Replace --include by ++include
338 else
339 newat+=("$i")
340 fi
341 done
342 set -- "${newat[@]}" # Set new $@
343
344 TEMP=$(
345 unset POSIXLY_CORRECT
346 getopt \
347 -o "a:m:o:d:I:k:c:r:L:fvqlHhMN" \
348 --long kver: \
349 --long add: \
350 --long force-add: \
351 --long add-drivers: \
352 --long force-drivers: \
353 --long omit-drivers: \
354 --long modules: \
355 --long omit: \
356 --long drivers: \
357 --long filesystems: \
358 --long install: \
359 --long install-optional: \
360 --long fwdir: \
361 --long libdirs: \
362 --long fscks: \
363 --long add-fstab: \
364 --long mount: \
365 --long device: \
366 --long add-device: \
367 --long nofscks \
368 --long ro-mnt \
369 --long kmoddir: \
370 --long conf: \
371 --long confdir: \
372 --long tmpdir: \
373 --long sysroot: \
374 --long stdlog: \
375 --long compress: \
376 --long prefix: \
377 --long rebuild: \
378 --long force \
379 --long kernel-only \
380 --long no-kernel \
381 --long print-cmdline \
382 --long kernel-cmdline: \
383 --long strip \
384 --long aggresive-strip \
385 --long nostrip \
386 --long hardlink \
387 --long nohardlink \
388 --long noprefix \
389 --long mdadmconf \
390 --long nomdadmconf \
391 --long lvmconf \
392 --long nolvmconf \
393 --long debug \
394 --long profile \
395 --long sshkey: \
396 --long logfile: \
397 --long verbose \
398 --long quiet \
399 --long local \
400 --long hostonly \
401 --long host-only \
402 --long no-hostonly \
403 --long no-host-only \
404 --long hostonly-mode: \
405 --long hostonly-cmdline \
406 --long no-hostonly-cmdline \
407 --long no-hostonly-default-device \
408 --long persistent-policy: \
409 --long fstab \
410 --long help \
411 --long bzip2 \
412 --long lzma \
413 --long xz \
414 --long lzo \
415 --long lz4 \
416 --long zstd \
417 --long no-compress \
418 --long gzip \
419 --long enhanced-cpio \
420 --long list-modules \
421 --long show-modules \
422 --long keep \
423 --long printsize \
424 --long regenerate-all \
425 --long noimageifnotneeded \
426 --long early-microcode \
427 --long no-early-microcode \
428 --long reproducible \
429 --long no-reproducible \
430 --long loginstall: \
431 --long uefi \
432 --long no-uefi \
433 --long uefi-stub: \
434 --long uefi-splash-image: \
435 --long kernel-image: \
436 --long no-hostonly-i18n \
437 --long hostonly-i18n \
438 --long hostonly-nics: \
439 --long no-machineid \
440 --long version \
441 -- "$@"
442 )
443
444 # shellcheck disable=SC2181
445 if (($? != 0)); then
446 usage
447 exit 1
448 fi
449 }
450
451 verbosity_mod_l=0
452 unset kernel
453 unset outfile
454
455 rearrange_params "$@"
456 eval set -- "$TEMP"
457
458 # parse command line args to check if '--rebuild' option is present
459 unset append_args_l
460 unset rebuild_file
461 while :; do
462 if [ "$1" == "--" ]; then
463 shift
464 break
465 fi
466 if [ "$1" == "--rebuild" ]; then
467 append_args_l="yes"
468 rebuild_file="$2"
469 if [ ! -e "$rebuild_file" ]; then
470 echo "Image file '$rebuild_file', for rebuild, does not exist!"
471 exit 1
472 fi
473 abs_rebuild_file=$(readlink -f "$rebuild_file") && rebuild_file="$abs_rebuild_file"
474 shift
475 continue
476 fi
477 shift
478 done
479
480 # get output file name and kernel version from command line arguments
481 while (($# > 0)); do
482 case ${1%%=*} in
483 ++include)
484 shift 2
485 ;;
486 *)
487 if ! [[ ${outfile+x} ]]; then
488 outfile=$1
489 elif ! [[ ${kernel+x} ]]; then
490 kernel=$1
491 else
492 printf "\nUnknown arguments: %s\n\n" "$*" >&2
493 usage
494 exit 1
495 fi
496 ;;
497 esac
498 shift
499 done
500
501 # extract input image file provided with rebuild option to get previous parameters, if any
502 if [[ $append_args_l == "yes" ]]; then
503 unset rebuild_param
504
505 # determine resultant file
506 if ! [[ $outfile ]]; then
507 outfile=$rebuild_file
508 fi
509
510 if ! rebuild_param=$(lsinitrd "$rebuild_file" '*lib/dracut/build-parameter.txt'); then
511 echo "Image '$rebuild_file' has no rebuild information stored"
512 exit 1
513 fi
514
515 # prepend previous parameters to current command line args
516 if [[ $rebuild_param ]]; then
517 TEMP="$rebuild_param $TEMP"
518 eval set -- "$TEMP"
519 rearrange_params "$@"
520 fi
521 fi
522
523 unset PARMS_TO_STORE
524 PARMS_TO_STORE=""
525
526 eval set -- "$TEMP"
527
528 while :; do
529 if [[ $1 != "--" ]] && [[ $1 != "--rebuild" ]]; then
530 PARMS_TO_STORE+=" $1"
531 fi
532 case $1 in
533 --kver)
534 kernel="$2"
535 PARMS_TO_STORE+=" '$2'"
536 shift
537 ;;
538 -a | --add)
539 add_dracutmodules_l+=("$2")
540 PARMS_TO_STORE+=" '$2'"
541 shift
542 ;;
543 --force-add)
544 force_add_dracutmodules_l+=("$2")
545 PARMS_TO_STORE+=" '$2'"
546 shift
547 ;;
548 --add-drivers)
549 add_drivers_l+=("$2")
550 PARMS_TO_STORE+=" '$2'"
551 shift
552 ;;
553 --force-drivers)
554 force_drivers_l+=("$2")
555 PARMS_TO_STORE+=" '$2'"
556 shift
557 ;;
558 --omit-drivers)
559 omit_drivers_l+=("$2")
560 PARMS_TO_STORE+=" '$2'"
561 shift
562 ;;
563 -m | --modules)
564 dracutmodules_l+=("$2")
565 PARMS_TO_STORE+=" '$2'"
566 shift
567 ;;
568 -o | --omit)
569 omit_dracutmodules_l+=("$2")
570 PARMS_TO_STORE+=" '$2'"
571 shift
572 ;;
573 -d | --drivers)
574 drivers_l+=("$2")
575 PARMS_TO_STORE+=" '$2'"
576 shift
577 ;;
578 --filesystems)
579 filesystems_l+=("$2")
580 PARMS_TO_STORE+=" '$2'"
581 shift
582 ;;
583 -I | --install)
584 install_items_l+=("$2")
585 PARMS_TO_STORE+=" '$2'"
586 shift
587 ;;
588 --install-optional)
589 install_optional_items_l+=("$2")
590 PARMS_TO_STORE+=" '$2'"
591 shift
592 ;;
593 --fwdir)
594 fw_dir_l+=("$2")
595 PARMS_TO_STORE+=" '$2'"
596 shift
597 ;;
598 --libdirs)
599 libdirs_l+=("$2")
600 PARMS_TO_STORE+=" '$2'"
601 shift
602 ;;
603 --fscks)
604 fscks_l+=("$2")
605 PARMS_TO_STORE+=" '$2'"
606 shift
607 ;;
608 --add-fstab)
609 add_fstab_l+=("$2")
610 PARMS_TO_STORE+=" '$2'"
611 shift
612 ;;
613 --mount)
614 fstab_lines+=("$2")
615 PARMS_TO_STORE+=" '$2'"
616 shift
617 ;;
618 --add-device | --device)
619 add_device_l+=("$2")
620 PARMS_TO_STORE+=" '$2'"
621 shift
622 ;;
623 --kernel-cmdline)
624 kernel_cmdline_l+=("$2")
625 PARMS_TO_STORE+=" '$2'"
626 shift
627 ;;
628 --nofscks) nofscks_l="yes" ;;
629 --ro-mnt) ro_mnt_l="yes" ;;
630 -k | --kmoddir)
631 drivers_dir_l="$2"
632 PARMS_TO_STORE+=" '$2'"
633 shift
634 ;;
635 -c | --conf)
636 conffile="$2"
637 PARMS_TO_STORE+=" '$2'"
638 shift
639 ;;
640 --confdir)
641 confdir="$2"
642 PARMS_TO_STORE+=" '$2'"
643 shift
644 ;;
645 --tmpdir)
646 tmpdir_l="$2"
647 PARMS_TO_STORE+=" '$2'"
648 shift
649 ;;
650 -r | --sysroot)
651 sysroot_l="$2"
652 PARMS_TO_STORE+=" '$2'"
653 shift
654 ;;
655 -L | --stdlog)
656 stdloglvl_l="$2"
657 PARMS_TO_STORE+=" '$2'"
658 shift
659 ;;
660 --compress)
661 compress_l="$2"
662 PARMS_TO_STORE+=" '$2'"
663 shift
664 ;;
665 --prefix)
666 prefix_l="$2"
667 PARMS_TO_STORE+=" '$2'"
668 shift
669 ;;
670 --loginstall)
671 loginstall_l="$2"
672 PARMS_TO_STORE+=" '$2'"
673 shift
674 ;;
675 --rebuild)
676 if [[ $rebuild_file == "$outfile" ]]; then
677 force=yes
678 fi
679 shift
680 ;;
681 -f | --force) force=yes ;;
682 --kernel-only)
683 kernel_only="yes"
684 no_kernel="no"
685 ;;
686 --no-kernel)
687 kernel_only="no"
688 no_kernel="yes"
689 ;;
690 --print-cmdline)
691 print_cmdline="yes"
692 hostonly_l="yes"
693 kernel_only="yes"
694 no_kernel="yes"
695 ;;
696 --early-microcode)
697 early_microcode_l="yes"
698 ;;
699 --no-early-microcode)
700 early_microcode_l="no"
701 ;;
702 --strip) do_strip_l="yes" ;;
703 --aggresive-strip) aggresive_strip_l="yes" ;;
704 --nostrip) do_strip_l="no" ;;
705 --hardlink) do_hardlink_l="yes" ;;
706 --nohardlink) do_hardlink_l="no" ;;
707 --noprefix) prefix_l="/" ;;
708 --mdadmconf) mdadmconf_l="yes" ;;
709 --nomdadmconf) mdadmconf_l="no" ;;
710 --lvmconf) lvmconf_l="yes" ;;
711 --nolvmconf) lvmconf_l="no" ;;
712 --debug) debug="yes" ;;
713 --profile) profile="yes" ;;
714 --sshkey)
715 sshkey="$2"
716 PARMS_TO_STORE+=" '$2'"
717 shift
718 ;;
719 --logfile)
720 logfile_l="$2"
721 shift
722 ;;
723 -v | --verbose) ((verbosity_mod_l++)) ;;
724 -q | --quiet) ((verbosity_mod_l--)) ;;
725 -l | --local)
726 allowlocal="yes"
727 [[ -f "$(readlink -f "${0%/*}")/dracut-init.sh" ]] \
728 && dracutbasedir="$(readlink -f "${0%/*}")"
729 ;;
730 -H | --hostonly | --host-only)
731 hostonly_l="yes"
732 ;;
733 -N | --no-hostonly | --no-host-only)
734 hostonly_l="no"
735 ;;
736 --hostonly-mode)
737 hostonly_mode_l="$2"
738 PARMS_TO_STORE+=" '$2'"
739 shift
740 ;;
741 --hostonly-cmdline)
742 hostonly_cmdline_l="yes"
743 ;;
744 --hostonly-i18n)
745 i18n_install_all_l="no"
746 ;;
747 --hostonly-nics)
748 hostonly_nics_l+=("$2")
749 PARMS_TO_STORE+=" '$2'"
750 shift
751 ;;
752 --no-hostonly-i18n)
753 i18n_install_all_l="yes"
754 ;;
755 --no-hostonly-cmdline)
756 hostonly_cmdline_l="no"
757 ;;
758 --no-hostonly-default-device)
759 hostonly_default_device="no"
760 ;;
761 --persistent-policy)
762 persistent_policy_l="$2"
763 PARMS_TO_STORE+=" '$2'"
764 shift
765 ;;
766 --fstab) use_fstab_l="yes" ;;
767 -h | --help)
768 long_usage
769 exit 1
770 ;;
771 --bzip2) compress_l="bzip2" ;;
772 --lzma) compress_l="lzma" ;;
773 --xz) compress_l="xz" ;;
774 --lzo) compress_l="lzo" ;;
775 --lz4) compress_l="lz4" ;;
776 --zstd) compress_l="zstd" ;;
777 --no-compress) _no_compress_l="cat" ;;
778 --gzip) compress_l="gzip" ;;
779 --enhanced-cpio) enhanced_cpio_l="yes" ;;
780 --list-modules) do_list="yes" ;;
781 -M | --show-modules)
782 show_modules_l="yes"
783 ;;
784 --keep) keep="yes" ;;
785 --printsize) printsize="yes" ;;
786 --regenerate-all) regenerate_all="yes" ;;
787 --noimageifnotneeded) noimageifnotneeded="yes" ;;
788 --reproducible) reproducible_l="yes" ;;
789 --no-reproducible) reproducible_l="no" ;;
790 --uefi) uefi_l="yes" ;;
791 --no-uefi) uefi_l="no" ;;
792 --uefi-stub)
793 uefi_stub_l="$2"
794 PARMS_TO_STORE+=" '$2'"
795 shift
796 ;;
797 --uefi-splash-image)
798 uefi_splash_image_l="$2"
799 PARMS_TO_STORE+=" '$2'"
800 shift
801 ;;
802 --kernel-image)
803 kernel_image_l="$2"
804 PARMS_TO_STORE+=" '$2'"
805 shift
806 ;;
807 --no-machineid)
808 machine_id_l="no"
809 ;;
810 --version)
811 long_version
812 exit 1
813 ;;
814 --)
815 shift
816 break
817 ;;
818
819 *) # should not even reach this point
820 printf "\n!Unknown option: '%s'\n\n" "$1" >&2
821 usage
822 exit 1
823 ;;
824 esac
825 shift
826 done
827
828 # getopt cannot handle multiple arguments, so just handle "-I,--include"
829 # the old fashioned way
830
831 while (($# > 0)); do
832 if [ "${1%%=*}" == "++include" ]; then
833 include_src+=("$2")
834 include_target+=("$3")
835 PARMS_TO_STORE+=" --include '$2' '$3'"
836 shift 2
837 fi
838 shift
839 done
840
841 [[ $sysroot_l ]] && dracutsysrootdir="$sysroot_l"
842
843 if [[ $regenerate_all == "yes" ]]; then
844 ret=0
845 if [[ $kernel ]]; then
846 printf -- "--regenerate-all cannot be called with a kernel version\n" >&2
847 exit 1
848 fi
849
850 if [[ $outfile ]]; then
851 printf -- "--regenerate-all cannot be called with a image file\n" >&2
852 exit 1
853 fi
854
855 ((len = ${#dracut_args[@]}))
856 for ((i = 0; i < len; i++)); do
857 [[ ${dracut_args[$i]} == "--regenerate-all" ]] \
858 && unset dracut_args["$i"]
859 done
860
861 cd "$dracutsysrootdir"/lib/modules || exit 1
862 for i in *; do
863 [[ -f $i/modules.dep ]] || [[ -f $i/modules.dep.bin ]] || continue
864 "$dracut_cmd" --kver="$i" "${dracut_args[@]}"
865 ((ret += $?))
866 done
867 exit "$ret"
868 fi
869
870 if ! [[ $kernel ]]; then
871 kernel=$(uname -r)
872 fi
873
874 export LC_ALL=C
875 export LANG=C
876 unset LC_MESSAGES
877 unset LC_CTYPE
878 unset LD_LIBRARY_PATH
879 unset LD_PRELOAD
880 unset GREP_OPTIONS
881
882 export DRACUT_LOG_LEVEL=warning
883 [[ $debug ]] && {
884 export DRACUT_LOG_LEVEL=debug
885 export PS4='${BASH_SOURCE}@${LINENO}(${FUNCNAME[0]-}): '
886 set -x
887 }
888
889 [[ $profile ]] && {
890 export PS4='+ $(date "+%s.%N") ${BASH_SOURCE}@${LINENO}: '
891 set -x
892 debug=yes
893 }
894
895 [[ $dracutbasedir ]] || dracutbasedir="$dracutsysrootdir"/usr/lib/dracut
896
897 # if we were not passed a config file, try the default one
898 if [[ -z $conffile ]]; then
899 if [[ $allowlocal ]]; then
900 conffile="$dracutbasedir/dracut.conf"
901 else
902 conffile="$dracutsysrootdir/etc/dracut.conf"
903 fi
904 elif [[ ! -f $conffile ]]; then
905 printf "%s\n" "dracut: Configuration file '$conffile' not found." >&2
906 exit 1
907 fi
908
909 if [[ -z $confdir ]]; then
910 if [[ $allowlocal ]]; then
911 confdir="$dracutbasedir/dracut.conf.d"
912 else
913 confdir="$dracutsysrootdir/etc/dracut.conf.d"
914 fi
915 elif [[ ! -d $confdir ]]; then
916 printf "%s\n" "dracut: Configuration directory '$confdir' not found." >&2
917 exit 1
918 fi
919
920 # source our config file
921 if [[ -f $conffile ]]; then
922 check_conf_file "$conffile"
923 # shellcheck disable=SC1090
924 . "$conffile"
925 fi
926
927 # source our config dir
928 for f in $(dropindirs_sort ".conf" "$confdir" "$dracutbasedir/dracut.conf.d"); do
929 check_conf_file "$f"
930 # shellcheck disable=SC1090
931 [[ -e $f ]] && . "$f"
932 done
933
934 DRACUT_PATH=${DRACUT_PATH:-/sbin /bin /usr/sbin /usr/bin}
935
936 for i in $DRACUT_PATH; do
937 rl=$i
938 if [ -L "$dracutsysrootdir$i" ]; then
939 rl=$(readlink -f "$dracutsysrootdir$i")
940 fi
941 rl="${rl#$dracutsysrootdir}"
942 if [[ $NPATH != *:$rl* ]]; then
943 NPATH+=":$rl"
944 fi
945 done
946 [[ -z $dracutsysrootdir ]] && export PATH="${NPATH#:}"
947 unset NPATH
948
949 export SYSTEMCTL=${SYSTEMCTL:-systemctl}
950
951 # these options add to the stuff in the config file
952 ((${#add_dracutmodules_l[@]})) && add_dracutmodules+=" ${add_dracutmodules_l[*]} "
953 ((${#omit_dracutmodules_l[@]})) && omit_dracutmodules+=" ${omit_dracutmodules_l[*]} "
954 ((${#force_add_dracutmodules_l[@]})) && force_add_dracutmodules+=" ${force_add_dracutmodules_l[*]} "
955 ((${#fscks_l[@]})) && fscks+=" ${fscks_l[*]} "
956 ((${#add_fstab_l[@]})) && add_fstab+=" ${add_fstab_l[*]} "
957 ((${#install_items_l[@]})) && install_items+=" ${install_items_l[*]} "
958 ((${#install_optional_items_l[@]})) && install_optional_items+=" ${install_optional_items_l[*]} "
959 ((${#hostonly_nics_l[@]})) && hostonly_nics+=" ${hostonly_nics_l[*]} "
960
961 # these options override the stuff in the config file
962 ((${#dracutmodules_l[@]})) && dracutmodules="${dracutmodules_l[*]}"
963 ((${#filesystems_l[@]})) && filesystems="${filesystems_l[*]}"
964 ((${#fw_dir_l[@]})) && fw_dir="${fw_dir_l[*]}"
965 ((${#libdirs_l[@]})) && libdirs="${libdirs_l[*]}"
966
967 [[ $stdloglvl_l ]] && stdloglvl=$stdloglvl_l
968 [[ ! $stdloglvl ]] && stdloglvl=4
969 stdloglvl=$((stdloglvl + verbosity_mod_l))
970 ((stdloglvl > 6)) && stdloglvl=6
971 ((stdloglvl < 0)) && stdloglvl=0
972
973 [[ $drivers_dir_l ]] && drivers_dir=$drivers_dir_l
974 [[ $do_strip_l ]] && do_strip=$do_strip_l
975 [[ $do_strip ]] || do_strip=yes
976 [[ $aggresive_strip_l ]] && aggresive_strip=$aggresive_strip_l
977 [[ $do_hardlink_l ]] && do_hardlink=$do_hardlink_l
978 [[ $do_hardlink ]] || do_hardlink=yes
979 [[ $prefix_l ]] && prefix=$prefix_l
980 [[ $prefix == "/" ]] && unset prefix
981 [[ $hostonly_l ]] && hostonly=$hostonly_l
982 [[ $hostonly_cmdline_l ]] && hostonly_cmdline=$hostonly_cmdline_l
983 [[ $hostonly_mode_l ]] && hostonly_mode=$hostonly_mode_l
984 [[ $hostonly == "yes" ]] && ! [[ $hostonly_cmdline ]] && hostonly_cmdline="yes"
985 # shellcheck disable=SC2034
986 [[ $i18n_install_all_l ]] && i18n_install_all=$i18n_install_all_l
987 # shellcheck disable=SC2034
988 [[ $persistent_policy_l ]] && persistent_policy=$persistent_policy_l
989 [[ $use_fstab_l ]] && use_fstab=$use_fstab_l
990 [[ $mdadmconf_l ]] && mdadmconf=$mdadmconf_l
991 [[ $lvmconf_l ]] && lvmconf=$lvmconf_l
992 [[ $dracutbasedir ]] || dracutbasedir="$dracutsysrootdir"/usr/lib/dracut
993 [[ $fw_dir ]] || fw_dir="$dracutsysrootdir/lib/firmware/updates:$dracutsysrootdir/lib/firmware:$dracutsysrootdir/lib/firmware/$kernel"
994 [[ $tmpdir_l ]] && tmpdir="$tmpdir_l"
995 [[ $tmpdir ]] || tmpdir="$TMPDIR"
996 [[ $tmpdir ]] || tmpdir="$dracutsysrootdir"/var/tmp
997 [[ $INITRD_COMPRESS ]] && compress=$INITRD_COMPRESS
998 [[ $compress_l ]] && compress=$compress_l
999 [[ $enhanced_cpio_l ]] && enhanced_cpio=$enhanced_cpio_l
1000 [[ $show_modules_l ]] && show_modules=$show_modules_l
1001 [[ $nofscks_l ]] && nofscks="yes"
1002 [[ $ro_mnt_l ]] && ro_mnt="yes"
1003 [[ $early_microcode_l ]] && early_microcode=$early_microcode_l
1004 [[ $early_microcode ]] || early_microcode=yes
1005 [[ $early_microcode_image_dir ]] || early_microcode_image_dir=('/boot')
1006 [[ $early_microcode_image_name ]] \
1007 || early_microcode_image_name=('intel-uc.img' 'intel-ucode.img' 'amd-uc.img' 'amd-ucode.img' 'early_ucode.cpio' 'microcode.cpio')
1008 [[ $logfile_l ]] && logfile="$logfile_l"
1009 [[ $reproducible_l ]] && reproducible="$reproducible_l"
1010 [[ $loginstall_l ]] && loginstall="$loginstall_l"
1011 [[ $uefi_l ]] && uefi=$uefi_l
1012 [[ $uefi_stub_l ]] && uefi_stub="$uefi_stub_l"
1013 [[ $uefi_splash_image_l ]] && uefi_splash_image="$uefi_splash_image_l"
1014 [[ $kernel_image_l ]] && kernel_image="$kernel_image_l"
1015 [[ $machine_id_l ]] && machine_id="$machine_id_l"
1016
1017 if ! [[ $outfile ]]; then
1018 if [[ $machine_id != "no" ]]; then
1019 [[ -f "$dracutsysrootdir"/etc/machine-id ]] && read -r MACHINE_ID < "$dracutsysrootdir"/etc/machine-id
1020 fi
1021
1022 if [[ $uefi == "yes" ]]; then
1023 # shellcheck disable=SC2154
1024 if [[ -n $uefi_secureboot_key && -z $uefi_secureboot_cert ]] || [[ -z $uefi_secureboot_key && -n $uefi_secureboot_cert ]]; then
1025 dfatal "Need 'uefi_secureboot_key' and 'uefi_secureboot_cert' both to be set."
1026 exit 1
1027 fi
1028
1029 if [[ -n $uefi_secureboot_key && -n $uefi_secureboot_cert ]] && ! command -v sbsign &> /dev/null; then
1030 dfatal "Need 'sbsign' to create a signed UEFI executable"
1031 exit 1
1032 fi
1033
1034 BUILD_ID=$(cat "$dracutsysrootdir"/etc/os-release "$dracutsysrootdir"/usr/lib/os-release \
1035 | while read -r line || [[ $line ]]; do
1036 [[ $line =~ BUILD_ID\=* ]] && eval "$line" && echo "$BUILD_ID" && break
1037 done)
1038 if [[ -z $dracutsysrootdir ]]; then
1039 if [[ -d /efi ]] && mountpoint -q /efi; then
1040 efidir=/efi/EFI
1041 else
1042 efidir=/boot/EFI
1043 if [[ -d $dracutsysrootdir/boot/efi/EFI ]]; then
1044 efidir=/boot/efi/EFI
1045 fi
1046 fi
1047 else
1048 efidir=/boot/EFI
1049 if [[ -d $dracutsysrootdir/boot/efi/EFI ]]; then
1050 efidir=/boot/efi/EFI
1051 fi
1052 fi
1053 mkdir -p "$dracutsysrootdir$efidir/Linux"
1054 outfile="$dracutsysrootdir$efidir/Linux/linux-$kernel${MACHINE_ID:+-${MACHINE_ID}}${BUILD_ID:+-${BUILD_ID}}.efi"
1055 else
1056 if [[ -e $dracutsysrootdir/boot/vmlinuz-$kernel ]]; then
1057 outfile="/boot/initramfs-$kernel.img"
1058 elif [[ $MACHINE_ID ]] && { [[ -d $dracutsysrootdir/boot/${MACHINE_ID} ]] || [[ -L $dracutsysrootdir/boot/${MACHINE_ID} ]]; }; then
1059 outfile="$dracutsysrootdir/boot/${MACHINE_ID}/$kernel/initrd"
1060 else
1061 outfile="$dracutsysrootdir/boot/initramfs-$kernel.img"
1062 fi
1063 fi
1064 fi
1065
1066 # eliminate IFS hackery when messing with fw_dir
1067 export DRACUT_FIRMWARE_PATH=${fw_dir// /:}
1068 fw_dir=${fw_dir//:/ }
1069
1070 # check for logfile and try to create one if it doesn't exist
1071 if [[ -n $logfile ]]; then
1072 if [[ ! -f $logfile ]]; then
1073 if touch "$logfile"; then
1074 printf "%s\n" "dracut: touch $logfile failed." >&2
1075 fi
1076 fi
1077 fi
1078
1079 # handle compression options.
1080 DRACUT_COMPRESS_BZIP2=${DRACUT_COMPRESS_BZIP2:-bzip2}
1081 DRACUT_COMPRESS_LBZIP2=${DRACUT_COMPRESS_LBZIP2:-lbzip2}
1082 DRACUT_COMPRESS_LZMA=${DRACUT_COMPRESS_LZMA:-lzma}
1083 DRACUT_COMPRESS_XZ=${DRACUT_COMPRESS_XZ:-xz}
1084 DRACUT_COMPRESS_GZIP=${DRACUT_COMPRESS_GZIP:-gzip}
1085 DRACUT_COMPRESS_PIGZ=${DRACUT_COMPRESS_PIGZ:-pigz}
1086 DRACUT_COMPRESS_LZOP=${DRACUT_COMPRESS_LZOP:-lzop}
1087 DRACUT_COMPRESS_ZSTD=${DRACUT_COMPRESS_ZSTD:-zstd}
1088 DRACUT_COMPRESS_LZ4=${DRACUT_COMPRESS_LZ4:-lz4}
1089 DRACUT_COMPRESS_CAT=${DRACUT_COMPRESS_CAT:-cat}
1090
1091 if [[ $_no_compress_l == "$DRACUT_COMPRESS_CAT" ]]; then
1092 compress="$DRACUT_COMPRESS_CAT"
1093 fi
1094
1095 [[ $hostonly == yes ]] && hostonly="-h"
1096 [[ $hostonly != "-h" ]] && unset hostonly
1097
1098 case $hostonly_mode in
1099 '')
1100 [[ $hostonly ]] && hostonly_mode="sloppy"
1101 ;;
1102 sloppy | strict)
1103 if [[ ! $hostonly ]]; then
1104 unset hostonly_mode
1105 fi
1106 ;;
1107 *)
1108 printf "%s\n" "dracut: Invalid hostonly mode '$hostonly_mode'." >&2
1109 exit 1
1110 ;;
1111 esac
1112
1113 [[ $reproducible == yes ]] && DRACUT_REPRODUCIBLE=1
1114
1115 case "${drivers_dir}" in
1116 '' | *lib/modules/${kernel} | *lib/modules/${kernel}/) ;;
1117 *)
1118 [[ "$DRACUT_KMODDIR_OVERRIDE" ]] || {
1119 printf "%s\n" 'dracut: -k/--kmoddir path must contain "lib/modules" as a parent of your kernel module directory,'
1120 printf "%s\n" "dracut: or modules may not be placed in the correct location inside the initramfs."
1121 printf "%s\n" "dracut: was given: ${drivers_dir}"
1122 printf "%s\n" "dracut: expected: $(dirname "${drivers_dir}")/lib/modules/${kernel}"
1123 printf "%s\n" "dracut: Please move your modules into the correct directory structure and pass the new location,"
1124 printf "%s\n" "dracut: or set DRACUT_KMODDIR_OVERRIDE=1 to ignore this check."
1125 exit 1
1126 }
1127 ;;
1128 esac
1129
1130 # shellcheck disable=SC2155
1131 readonly TMPDIR="$(realpath -e "$tmpdir")"
1132 [ -d "$TMPDIR" ] || {
1133 printf "%s\n" "dracut: Invalid tmpdir '$tmpdir'." >&2
1134 exit 1
1135 }
1136
1137 if findmnt --raw -n --target "$tmpdir" --output=options | grep -q noexec; then
1138 [[ $debug == yes ]] && printf "%s\n" "dracut: Tmpdir '$tmpdir' is mounted with 'noexec'."
1139 noexec=1
1140 fi
1141
1142 # shellcheck disable=SC2155
1143 readonly DRACUT_TMPDIR="$(mktemp -p "$TMPDIR/" -d -t dracut.XXXXXX)"
1144 [ -d "$DRACUT_TMPDIR" ] || {
1145 printf "%s\n" "dracut: mktemp -p '$TMPDIR/' -d -t dracut.XXXXXX failed." >&2
1146 exit 1
1147 }
1148
1149 # Cache file used to optimize get_maj_min()
1150 declare -x -r get_maj_min_cache_file="${DRACUT_TMPDIR}/majmin_cache"
1151 : > "$get_maj_min_cache_file"
1152
1153 # clean up after ourselves no matter how we die.
1154 trap '
1155 ret=$?;
1156 [[ $keep ]] && echo "Not removing $DRACUT_TMPDIR." >&2 || { [[ $DRACUT_TMPDIR ]] && rm -rf -- "$DRACUT_TMPDIR"; };
1157 if [[ ${FSFROZEN} ]]; then
1158 fsfreeze -u "${FSFROZEN}"
1159 fi
1160 exit $ret;
1161 ' EXIT
1162
1163 # clean up after ourselves no matter how we die.
1164 trap 'exit 1;' SIGINT
1165
1166 readonly initdir="${DRACUT_TMPDIR}/initramfs"
1167 mkdir -p "$initdir"
1168
1169 # shellcheck disable=SC2154
1170 if [[ $early_microcode == yes ]] || { [[ $acpi_override == yes ]] && [[ -d $acpi_table_dir ]]; }; then
1171 readonly early_cpio_dir="${DRACUT_TMPDIR}/earlycpio"
1172 mkdir "$early_cpio_dir"
1173 fi
1174
1175 [[ "$dracutsysrootdir" ]] || [[ "$noexec" ]] || export DRACUT_RESOLVE_LAZY="1"
1176
1177 if [[ $print_cmdline ]]; then
1178 stdloglvl=0
1179 sysloglvl=0
1180 fileloglvl=0
1181 kmsgloglvl=0
1182 fi
1183
1184 if [[ -f $dracutbasedir/dracut-version.sh ]]; then
1185 # shellcheck source=./dracut-version.sh
1186 . "$dracutbasedir"/dracut-version.sh
1187 fi
1188
1189 if systemd-detect-virt -c &> /dev/null; then
1190 export DRACUT_NO_MKNOD=1 DRACUT_NO_XATTR=1
1191 if [[ $hostonly ]]; then
1192 printf "%s\n" "dracut: WARNING: running in hostonly mode in a container!!"
1193 fi
1194 fi
1195
1196 if [[ -f $dracutbasedir/dracut-init.sh ]]; then
1197 # shellcheck source=./dracut-init.sh
1198 . "$dracutbasedir"/dracut-init.sh
1199 else
1200 printf "%s\n" "dracut: Cannot find $dracutbasedir/dracut-init.sh." >&2
1201 printf "%s\n" "dracut: Are you running from a git checkout?" >&2
1202 printf "%s\n" "dracut: Try passing -l as an argument to $dracut_cmd" >&2
1203 exit 1
1204 fi
1205
1206 if [[ $enhanced_cpio == "yes" ]]; then
1207 enhanced_cpio="$dracutbasedir/dracut-cpio"
1208 if [[ -x $enhanced_cpio ]]; then
1209 # align based on statfs optimal transfer size
1210 cpio_align=$(stat --file-system -c "%s" -- "$initdir")
1211 else
1212 dinfo "--enhanced-cpio ignored due to lack of dracut-cpio"
1213 unset enhanced_cpio
1214 fi
1215 else
1216 unset enhanced_cpio
1217 fi
1218
1219 # shellcheck disable=SC2154
1220 if [[ $no_kernel != yes ]] && ! [[ -d $srcmods ]]; then
1221 printf "%s\n" "dracut: Cannot find module directory $srcmods" >&2
1222 printf "%s\n" "dracut: and --no-kernel was not specified" >&2
1223 exit 1
1224 fi
1225
1226 if ! [[ $print_cmdline ]]; then
1227 inst "$DRACUT_TESTBIN"
1228 if ! $DRACUT_INSTALL ${initdir:+-D "$initdir"} ${dracutsysrootdir:+-r "$dracutsysrootdir"} -R "$DRACUT_TESTBIN" &> /dev/null; then
1229 unset DRACUT_RESOLVE_LAZY
1230 export DRACUT_RESOLVE_DEPS=1
1231 fi
1232 rm -fr -- "${initdir:?}"/*
1233 fi
1234
1235 dracutfunctions=$dracutbasedir/dracut-functions.sh
1236 export dracutfunctions
1237
1238 ((${#drivers_l[@]})) && drivers="${drivers_l[*]}"
1239 drivers=${drivers/-/_}
1240
1241 ((${#add_drivers_l[@]})) && add_drivers+=" ${add_drivers_l[*]} "
1242 add_drivers=${add_drivers/-/_}
1243
1244 ((${#force_drivers_l[@]})) && force_drivers+=" ${force_drivers_l[*]} "
1245 force_drivers=${force_drivers/-/_}
1246
1247 ((${#omit_drivers_l[@]})) && omit_drivers+=" ${omit_drivers_l[*]} "
1248 omit_drivers=${omit_drivers/-/_}
1249
1250 ((${#kernel_cmdline_l[@]})) && kernel_cmdline+=" ${kernel_cmdline_l[*]} "
1251
1252 omit_drivers_corrected=""
1253 for d in $omit_drivers; do
1254 [[ " $drivers $add_drivers " == *\ $d\ * ]] && continue
1255 [[ " $drivers $force_drivers " == *\ $d\ * ]] && continue
1256 omit_drivers_corrected+="$d|"
1257 done
1258 omit_drivers="${omit_drivers_corrected%|}"
1259 unset omit_drivers_corrected
1260
1261 # prepare args for logging
1262 for ((i = 0; i < ${#dracut_args[@]}; i++)); do
1263 [[ ${dracut_args[$i]} == *\ * ]] \
1264 && dracut_args[$i]="\"${dracut_args[$i]}\""
1265 #" keep vim happy
1266 done
1267
1268 dinfo "Executing: $dracut_cmd ${dracut_args[*]}"
1269
1270 [[ $do_list == yes ]] && {
1271 for mod in "$dracutbasedir"/modules.d/*; do
1272 [[ -d $mod ]] || continue
1273 [[ -e $mod/install || -e $mod/installkernel || -e \
1274 $mod/module-setup.sh ]] || continue
1275 printf "%s\n" "${mod##*/??}"
1276 done
1277 exit 0
1278 }
1279
1280 # This is kinda legacy -- eventually it should go away.
1281 case $dracutmodules in
1282 "" | auto) dracutmodules="all" ;;
1283 esac
1284
1285 abs_outfile=$(readlink -f "$outfile") && outfile="$abs_outfile"
1286
1287 [[ -d $dracutsysrootdir$systemdutildir ]] \
1288 || systemdutildir=$(pkg-config systemd --variable=systemdutildir 2> /dev/null)
1289
1290 if ! [[ -d $dracutsysrootdir$systemdutildir ]]; then
1291 [[ -e $dracutsysrootdir/lib/systemd/systemd-udevd ]] && systemdutildir=/lib/systemd
1292 [[ -e $dracutsysrootdir/usr/lib/systemd/systemd-udevd ]] && systemdutildir=/usr/lib/systemd
1293 fi
1294
1295 [[ -d $dracutsysrootdir$systemdutilconfdir ]] \
1296 || systemdutilconfdir=$(pkg-config systemd --variable=systemdutilconfdir 2> /dev/null)
1297
1298 [[ -d $dracutsysrootdir$systemdutilconfdir ]] || systemdutilconfdir=/etc/systemd
1299
1300 if [[ $no_kernel != yes ]] && [[ -d $srcmods ]]; then
1301 if ! [[ -f $srcmods/modules.dep ]]; then
1302 if [[ -n "$(find "$srcmods" -name '*.ko*')" ]]; then
1303 dfatal "$srcmods/modules.dep is missing. Did you run depmod?"
1304 exit 1
1305 else
1306 dwarn "$srcmods/modules.dep is missing. Did you run depmod?"
1307 fi
1308 fi
1309 fi
1310
1311 if [[ ! $print_cmdline ]]; then
1312 if [[ -f $outfile && ! $force ]]; then
1313 dfatal "Will not override existing initramfs ($outfile) without --force"
1314 exit 1
1315 fi
1316
1317 outdir=${outfile%/*}
1318 [[ $outdir ]] || outdir="/"
1319
1320 if [[ ! -d $outdir ]]; then
1321 dfatal "Can't write to $outdir: Directory $outdir does not exist or is not accessible."
1322 exit 1
1323 elif [[ ! -w $outdir ]]; then
1324 dfatal "No permission to write to $outdir."
1325 exit 1
1326 elif [[ -f $outfile && ! -w $outfile ]]; then
1327 dfatal "No permission to write $outfile."
1328 exit 1
1329 fi
1330
1331 if [[ $loginstall ]]; then
1332 if ! mkdir -p "$loginstall"; then
1333 dfatal "Could not create directory to log installed files to '$loginstall'."
1334 exit 1
1335 fi
1336 loginstall=$(readlink -f "$loginstall")
1337 fi
1338
1339 if [[ $uefi == yes ]]; then
1340 if ! command -v objcopy &> /dev/null; then
1341 dfatal "Need 'objcopy' to create a UEFI executable"
1342 exit 1
1343 fi
1344 unset EFI_MACHINE_TYPE_NAME
1345 case $(uname -m) in
1346 x86_64)
1347 EFI_MACHINE_TYPE_NAME=x64
1348 ;;
1349 i?86)
1350 EFI_MACHINE_TYPE_NAME=ia32
1351 ;;
1352 *)
1353 dfatal "Architecture '$(uname -m)' not supported to create a UEFI executable"
1354 exit 1
1355 ;;
1356 esac
1357
1358 if ! [[ -s $uefi_stub ]]; then
1359 uefi_stub="$dracutsysrootdir${systemdutildir}/boot/efi/linux${EFI_MACHINE_TYPE_NAME}.efi.stub"
1360 fi
1361
1362 if ! [[ -s $uefi_stub ]]; then
1363 dfatal "Can't find a uefi stub '$uefi_stub' to create a UEFI executable"
1364 exit 1
1365 fi
1366
1367 if ! [[ $kernel_image ]]; then
1368 for kernel_image in "$dracutsysrootdir/lib/modules/$kernel/vmlinuz" "$dracutsysrootdir/boot/vmlinuz-$kernel"; do
1369 [[ -s $kernel_image ]] || continue
1370 break
1371 done
1372 fi
1373 if ! [[ -s $kernel_image ]]; then
1374 dfatal "Can't find a kernel image '$kernel_image' to create a UEFI executable"
1375 exit 1
1376 fi
1377 fi
1378 fi
1379
1380 if [[ $acpi_override == yes ]] && ! (check_kernel_config CONFIG_ACPI_TABLE_UPGRADE || check_kernel_config CONFIG_ACPI_INITRD_TABLE_OVERRIDE); then
1381 dwarn "Disabling ACPI override, because kernel does not support it. CONFIG_ACPI_INITRD_TABLE_OVERRIDE!=y or CONFIG_ACPI_TABLE_UPGRADE!=y"
1382 unset acpi_override
1383 fi
1384
1385 if [[ $early_microcode == yes ]]; then
1386 if [[ $hostonly ]]; then
1387 if [[ $(get_cpu_vendor) == "AMD" ]]; then
1388 check_kernel_config CONFIG_MICROCODE_AMD || unset early_microcode
1389 elif [[ $(get_cpu_vendor) == "Intel" ]]; then
1390 check_kernel_config CONFIG_MICROCODE_INTEL || unset early_microcode
1391 else
1392 unset early_microcode
1393 fi
1394 else
1395 ! check_kernel_config CONFIG_MICROCODE_AMD \
1396 && ! check_kernel_config CONFIG_MICROCODE_INTEL \
1397 && unset early_microcode
1398 fi
1399 # Do not complain on non-x86 architectures as it makes no sense
1400 case $(uname -m) in
1401 x86_64 | i?86)
1402 [[ $early_microcode != yes ]] \
1403 && dwarn "Disabling early microcode, because kernel does not support it. CONFIG_MICROCODE_[AMD|INTEL]!=y"
1404 ;;
1405 *) ;;
1406 esac
1407 fi
1408
1409 # Need to be able to have non-root users read stuff (rpcbind etc)
1410 chmod 755 "$initdir"
1411
1412 if [[ $hostonly ]]; then
1413 for i in /sys /proc /run /dev; do
1414 if ! findmnt --target "$i" &> /dev/null; then
1415 dwarning "Turning off host-only mode: '$i' is not mounted!"
1416 unset hostonly
1417 fi
1418 done
1419 fi
1420
1421 declare -A host_fs_types
1422
1423 for line in "${fstab_lines[@]}"; do
1424 # shellcheck disable=SC2086
1425 set -- $line
1426 dev="$1"
1427 #dev mp fs fsopts
1428 case "$dev" in
1429 UUID=*)
1430 dev=$(blkid -l -t "UUID=${dev#UUID=}" -o device)
1431 ;;
1432 LABEL=*)
1433 dev=$(blkid -l -t "LABEL=${dev#LABEL=}" -o device)
1434 ;;
1435 PARTUUID=*)
1436 dev=$(blkid -l -t "PARTUUID=${dev#PARTUUID=}" -o device)
1437 ;;
1438 PARTLABEL=*)
1439 dev=$(blkid -l -t "PARTLABEL=${dev#PARTLABEL=}" -o device)
1440 ;;
1441 esac
1442 [ -z "$dev" ] && dwarn "Bad fstab entry $*" && continue
1443 if [[ $3 == btrfs ]]; then
1444 for mp in $(findmnt --source "$1" -o TARGET -n); do
1445 for i in $(btrfs_devs "$mp"); do
1446 push_host_devs "$i"
1447 done
1448 done
1449 fi
1450 push_host_devs "$dev"
1451 host_fs_types["$dev"]="$3"
1452 done
1453
1454 for f in $add_fstab; do
1455 [[ -e $f ]] || continue
1456 while read -r dev rest || [ -n "$dev" ]; do
1457 push_host_devs "$dev"
1458 done < "$f"
1459 done
1460
1461 for dev in $add_device; do
1462 push_host_devs "$dev"
1463 done
1464
1465 if ((${#add_device_l[@]})); then
1466 add_device+=" ${add_device_l[*]} "
1467 push_host_devs "${add_device_l[@]}"
1468 fi
1469
1470 if [[ $hostonly ]] && [[ $hostonly_default_device != "no" ]]; then
1471 # in hostonly mode, determine all devices, which have to be accessed
1472 # and examine them for filesystem types
1473
1474 for mp in \
1475 "/" \
1476 "/etc" \
1477 "/bin" \
1478 "/sbin" \
1479 "/lib" \
1480 "/lib64" \
1481 "/usr" \
1482 "/usr/bin" \
1483 "/usr/sbin" \
1484 "/usr/lib" \
1485 "/usr/lib64" \
1486 "/boot" \
1487 "/boot/efi" \
1488 "/boot/zipl"; do
1489 mp=$(readlink -f "$dracutsysrootdir$mp")
1490 mountpoint "$mp" > /dev/null 2>&1 || continue
1491 _dev=$(find_block_device "$mp")
1492 _bdev=$(readlink -f "/dev/block/$_dev")
1493 [[ -b $_bdev ]] && _dev=$_bdev
1494 [[ $mp == "/" ]] && root_devs+=("$_dev")
1495 push_host_devs "$_dev"
1496 if [[ $(find_mp_fstype "$mp") == btrfs ]]; then
1497 for i in $(btrfs_devs "$mp"); do
1498 [[ $mp == "/" ]] && root_devs+=("$i")
1499 push_host_devs "$i"
1500 done
1501 fi
1502 done
1503
1504 # TODO - with sysroot, /proc/swaps is not relevant
1505 if [[ -f /proc/swaps ]] && [[ -f $dracutsysrootdir/etc/fstab ]]; then
1506 while read -r dev type rest || [ -n "$dev" ]; do
1507 [[ -b $dev ]] || continue
1508 [[ $type == "partition" ]] || continue
1509
1510 while read -r _d _m _t _o _ || [ -n "$_d" ]; do
1511 [[ $_d == \#* ]] && continue
1512 [[ $_d ]] || continue
1513 [[ $_t != "swap" ]] && continue
1514 [[ $_m != "swap" ]] && [[ $_m != "none" ]] && continue
1515 [[ $_o == *noauto* ]] && continue
1516 _d=$(expand_persistent_dev "$_d")
1517 [[ $_d -ef $dev ]] || continue
1518
1519 if [[ -f $dracutsysrootdir/etc/crypttab ]]; then
1520 while read -r _mapper _ _p _o || [ -n "$_mapper" ]; do
1521 [[ $_mapper == \#* ]] && continue
1522 [[ $_d -ef /dev/mapper/"$_mapper" ]] || continue
1523 [[ "$_o" ]] || _o="$_p"
1524 # skip entries with password files
1525 [[ $_p == /* ]] && [[ -f $_p ]] && continue 2
1526 # skip mkswap swap
1527 [[ $_o == *swap* ]] && continue 2
1528 done < "$dracutsysrootdir"/etc/crypttab
1529 fi
1530
1531 _dev="$(readlink -f "$dev")"
1532 push_host_devs "$_dev"
1533 swap_devs+=("$_dev")
1534 break
1535 done < "$dracutsysrootdir"/etc/fstab
1536 done < /proc/swaps
1537 fi
1538
1539 # collect all "x-initrd.mount" entries from /etc/fstab
1540 if [[ -f $dracutsysrootdir/etc/fstab ]]; then
1541 while read -r _d _m _t _o _ || [ -n "$_d" ]; do
1542 [[ $_d == \#* ]] && continue
1543 [[ $_d ]] || continue
1544 [[ $_o != *x-initrd.mount* ]] && continue
1545 _dev=$(expand_persistent_dev "$_d")
1546 _dev="$(readlink -f "$_dev")"
1547 [[ -b $_dev ]] || continue
1548
1549 push_host_devs "$_dev"
1550 if [[ $_t == btrfs ]]; then
1551 for i in $(btrfs_devs "$_m"); do
1552 push_host_devs "$i"
1553 done
1554 fi
1555 done < "$dracutsysrootdir"/etc/fstab
1556 fi
1557 fi
1558
1559 unset m
1560 unset rest
1561
1562 _get_fs_type() {
1563 [[ $1 ]] || return
1564 if [[ -b /dev/block/$1 ]]; then
1565 ID_FS_TYPE=$(get_fs_env "/dev/block/$1") && host_fs_types["$(readlink -f "/dev/block/$1")"]="$ID_FS_TYPE"
1566 return 1
1567 fi
1568 if [[ -b $1 ]]; then
1569 ID_FS_TYPE=$(get_fs_env "$1") && host_fs_types["$(readlink -f "$1")"]="$ID_FS_TYPE"
1570 return 1
1571 fi
1572 if fstype=$(find_dev_fstype "$1"); then
1573 host_fs_types["$1"]="$fstype"
1574 return 1
1575 fi
1576 return 1
1577 }
1578
1579 for dev in "${host_devs[@]}"; do
1580 _get_fs_type "$dev"
1581 check_block_and_slaves_all _get_fs_type "$(get_maj_min "$dev")"
1582 done
1583
1584 for dev in "${!host_fs_types[@]}"; do
1585 [[ ${host_fs_types[$dev]} == "reiserfs" ]] || [[ ${host_fs_types[$dev]} == "xfs" ]] || continue
1586 rootopts=$(find_dev_fsopts "$dev")
1587 if [[ ${host_fs_types[$dev]} == "reiserfs" ]]; then
1588 journaldev=$(fs_get_option "$rootopts" "jdev")
1589 elif [[ ${host_fs_types[$dev]} == "xfs" ]]; then
1590 journaldev=$(fs_get_option "$rootopts" "logdev")
1591 fi
1592 if [[ $journaldev ]]; then
1593 dev="$(readlink -f "$dev")"
1594 push_host_devs "$dev"
1595 _get_fs_type "$dev"
1596 check_block_and_slaves_all _get_fs_type "$(get_maj_min "$dev")"
1597 fi
1598 done
1599
1600 [[ -d $dracutsysrootdir$dbus ]] \
1601 || dbus=$(pkg-config dbus --variable=dbus 2> /dev/null)
1602
1603 [[ -d $dracutsysrootdir$dbus ]] || dbus=/usr/share/dbus-1
1604
1605 [[ -d $dracutsysrootdir$dbusconfdir ]] \
1606 || dbusconfdir=$(pkg-config dbus --variable=dbusconfdir 2> /dev/null)
1607
1608 [[ -d $dracutsysrootdir$dbusconfdir ]] || dbusconfdir=/etc/dbus-1
1609
1610 [[ -d $dracutsysrootdir$dbusinterfaces ]] \
1611 || dbusinterfaces=$(pkg-config dbus --variable=dbusinterfaces 2> /dev/null)
1612
1613 [[ -d $dracutsysrootdir$dbusinterfaces ]] || dbusinterfaces=${dbus}/interfaces
1614
1615 [[ -d $dracutsysrootdir$dbusinterfacesconfdir ]] \
1616 || dbusinterfacesconfdir=$(pkg-config dbus --variable=dbusinterfacesconfdir 2> /dev/null)
1617
1618 [[ -d $dracutsysrootdir$dbusinterfacesconfdir ]] || dbusinterfacesconfdir=${dbusconfdir}/interfaces
1619
1620 [[ -d $dracutsysrootdir$dbusservices ]] \
1621 || dbusservices=$(pkg-config dbus --variable=dbusservices 2> /dev/null)
1622
1623 [[ -d $dracutsysrootdir$dbusservices ]] || dbusservices=${dbus}/services
1624
1625 [[ -d $dracutsysrootdir$dbusservicesconfdir ]] \
1626 || dbusservicesconfdir=$(pkg-config dbus --variable=dbusservicesconfdir 2> /dev/null)
1627
1628 [[ -d $dracutsysrootdir$dbusservicesconfdir ]] || dbusservicesconfdir=${dbusconfdir}/services
1629
1630 [[ -d $dracutsysrootdir$dbussession ]] \
1631 || dbussession=$(pkg-config dbus --variable=dbussession 2> /dev/null)
1632
1633 [[ -d $dracutsysrootdir$dbussession ]] || dbussession=${dbus}/session.d
1634
1635 [[ -d $dracutsysrootdir$dbussessionconfdir ]] \
1636 || dbussessionconfdir=$(pkg-config dbus --variable=dbussessionconfdir 2> /dev/null)
1637
1638 [[ -d $dracutsysrootdir$dbussessionconfdir ]] || dbussessionconfdir=${dbusconfdir}/session.d
1639
1640 [[ -d $dracutsysrootdir$dbussystem ]] \
1641 || dbussystem=$(pkg-config dbus --variable=dbussystem 2> /dev/null)
1642
1643 [[ -d $dracutsysrootdir$dbussystem ]] || dbussystem=${dbus}/system.d
1644
1645 [[ -d $dracutsysrootdir$dbussystemconfdir ]] \
1646 || dbussystemconfdir=$(pkg-config dbus --variable=dbussystemconfdir 2> /dev/null)
1647
1648 [[ -d $dracutsysrootdir$dbussystemconfdir ]] || dbussystemconfdir=${dbusconfdir}/system.d
1649
1650 [[ -d $dracutsysrootdir$dbussystemservices ]] \
1651 || dbussystemservices=$(pkg-config dbus --variable=dbussystemservices 2> /dev/null)
1652
1653 [[ -d $dracutsysrootdir$dbussystemservices ]] || dbussystemservices=${dbus}/system-services
1654
1655 [[ -d $dracutsysrootdir$dbussystemservicesconfdir ]] \
1656 || dbussystemservicesconfdir=$(pkg-config dbus --variable=dbussystemservicesconfdir 2> /dev/null)
1657
1658 [[ -d $dracutsysrootdir$dbussystemservicesconfdir ]] || dbussystemservicesconfdir=${dbusconfdir}/system-services
1659
1660 [[ -d $dracutsysrootdir$udevdir ]] \
1661 || udevdir="$(pkg-config udev --variable=udevdir 2> /dev/null)"
1662 if ! [[ -d $dracutsysrootdir$udevdir ]]; then
1663 [[ -e $dracutsysrootdir/lib/udev/ata_id ]] && udevdir=/lib/udev
1664 [[ -e $dracutsysrootdir/usr/lib/udev/ata_id ]] && udevdir=/usr/lib/udev
1665 fi
1666
1667 [[ -d $dracutsysrootdir$udevconfdir ]] \
1668 || udevconfdir=$(pkg-config udev --variable=udevconfdir 2> /dev/null)
1669
1670 [[ -d $dracutsysrootdir$udevconfdir ]] || udevconfdir=/etc/udev
1671
1672 [[ -d $dracutsysrootdir$udevrulesdir ]] \
1673 || udevrulesdir=$(pkg-config udev --variable=udevrulesdir 2> /dev/null)
1674
1675 [[ -d $dracutsysrootdir$udevrulesdir ]] || udevrulesdir=${udevdir}/rules.d
1676
1677 [[ -d $dracutsysrootdir$udevrulesconfdir ]] \
1678 || udevrulesconfdir=$(pkg-config udev --variable=udevrulesconfdir 2> /dev/null)
1679
1680 [[ -d $dracutsysrootdir$udevrulesconfdir ]] || udevrulesconfdir=${udevconfdir}/rules.d
1681
1682 [[ -d $dracutsysrootdir$sysctld ]] \
1683 || sysctld=$(pkg-config systemd --variable=sysctld 2> /dev/null)
1684
1685 [[ -d $dracutsysrootdir$sysctld ]] || sysctld=/usr/lib/sysctl.d
1686
1687 [[ -d $dracutsysrootdir$sysctlconfdir ]] \
1688 || sysctlconfdir=$(pkg-config systemd --variable=sysctlconfdir 2> /dev/null)
1689
1690 [[ -d $dracutsysrootdir$sysctlconfdir ]] || sysctlconfdir=/etc/sysctl.d
1691
1692 [[ -d $dracutsysrootdir$environment ]] \
1693 || environment=$(pkg-config systemd --variable=environment 2> /dev/null)
1694
1695 [[ -d $dracutsysrootdir$environment ]] || environment=/usr/lib/environment.d
1696
1697 [[ -d $dracutsysrootdir$environmentconfdir ]] \
1698 || environmentconfdir=$(pkg-config systemd --variable=environmentconfdir 2> /dev/null)
1699
1700 [[ -d $dracutsysrootdir$environmentconfdir ]] || environmentconfdir=/etc/environment.d
1701
1702 [[ -d $dracutsysrootdir$systemdcatalog ]] \
1703 || systemdcatalog=$(pkg-config systemd --variable=systemdcatalog 2> /dev/null)
1704
1705 [[ -d $dracutsysrootdir$systemdcatalog ]] || systemdcatalog=${systemdutildir}/catalog
1706
1707 [[ -d $dracutsysrootdir$modulesload ]] \
1708 || modulesload=$(pkg-config systemd --variable=modulesload 2> /dev/null)
1709
1710 [[ -d $dracutsysrootdir$modulesload ]] || modulesload=/usr/lib/modules-load.d
1711
1712 [[ -d $dracutsysrootdir$modulesloadconfdir ]] \
1713 || modulesloadconfdir=$(pkg-config systemd --variable=modulesloadconfdir 2> /dev/null)
1714
1715 [[ -d $dracutsysrootdir$modulesloadconfdir ]] || modulesloadconfdir=/etc/modules-load.d
1716
1717 [[ -d $dracutsysrootdir$systemdnetwork ]] \
1718 || systemdnetwork=$(pkg-config systemd --variable=systemdnetwork 2> /dev/null)
1719
1720 [[ -d $dracutsysrootdir$systemdnetwork ]] || systemdnetwork=${systemdutildir}/network
1721
1722 [[ -d $dracutsysrootdir$systemdnetworkconfdir ]] \
1723 || systemdnetworkconfdir=$(pkg-config systemd --variable=systemdnetworkconfdir 2> /dev/null)
1724
1725 [[ -d $dracutsysrootdir$systemdnetworkconfdir ]] || systemdnetworkconfdir=${systemdsystemconfdir}/network
1726
1727 [[ -d $dracutsysrootdir$systemdntpunits ]] \
1728 || systemdntpunits=$(pkg-config systemd --variable=systemdntpunits 2> /dev/null)
1729
1730 [[ -d $dracutsysrootdir$systemdntpunits ]] || systemdntpunits=${systemdutildir}/ntp-units.d
1731
1732 [[ -d $dracutsysrootdir$systemdntpunitsconfdir ]] \
1733 || systemdntpunitsconfdir=$(pkg-config systemd --variable=systemdntpunitsconfdir 2> /dev/null)
1734
1735 [[ -d $dracutsysrootdir$systemdntpunitsconfdir ]] || systemdntpunitsconfdir=${systemdsystemconfdir}/ntp-units.d
1736
1737 [[ -d $dracutsysrootdir$systemdportable ]] \
1738 || systemdportable=$(pkg-config systemd --variable=systemdportable 2> /dev/null)
1739
1740 [[ -d $dracutsysrootdir$systemdportable ]] || systemdportable=${systemdutildir}/portable
1741
1742 [[ -d $dracutsysrootdir$systemdportableconfdir ]] \
1743 || systemdportableconfdir=$(pkg-config systemd --variable=systemdportableconfdir 2> /dev/null)
1744
1745 [[ -d "$dracutsysrootdir$systemdportableconfdir" ]] || systemdportableconfdir=${systemdsystemconfdir}/portable
1746
1747 [[ -d $dracutsysrootdir$systemdsystemunitdir ]] \
1748 || systemdsystemunitdir=$(pkg-config systemd --variable=systemdsystemunitdir 2> /dev/null)
1749
1750 [[ -d "$dracutsysrootdir$systemdsystemunitdir" ]] || systemdsystemunitdir=${systemdutildir}/system
1751
1752 [[ -d $dracutsysrootdir$systemduser ]] \
1753 || systemduser=$(pkg-config systemd --variable=systemduser 2> /dev/null)
1754
1755 [[ -d $dracutsysrootdir$systemduser ]] || systemduser=${systemdutildir}/user
1756
1757 [[ -d $dracutsysrootdir$systemduserconfdir ]] \
1758 || systemduserconfdir=$(pkg-config systemd --variable=systemduserconfdir 2> /dev/null)
1759
1760 [[ -d $dracutsysrootdir$systemduserconfdir ]] || systemduserconfdir=${systemdsystemconfdir}/user
1761
1762 [[ -d $dracutsysrootdir$systemdsystemconfdir ]] \
1763 || systemdsystemconfdir=$(pkg-config systemd --variable=systemdsystemconfdir 2> /dev/null)
1764
1765 [[ -d $dracutsysrootdir$systemdsystemconfdir ]] || systemdsystemconfdir=/etc/systemd/system
1766
1767 [[ -d $dracutsysrootdir$sysusers ]] \
1768 || sysusers=$(pkg-config systemd --variable=sysusers 2> /dev/null)
1769
1770 [[ -d $dracutsysrootdir$sysusers ]] || sysusers=/usr/lib/sysusers.d
1771
1772 [[ -d $dracutsysrootdir$sysusersconfdir ]] \
1773 || sysusersconfdir=$(pkg-config systemd --variable=sysusersconfdir 2> /dev/null)
1774
1775 [[ -d $dracutsysrootdir$sysusersconfdir ]] || sysusersconfdir=/etc/sysusers.d
1776
1777 [[ -d $dracutsysrootdir$tmpfilesdir ]] \
1778 || tmpfilesdir=$(pkg-config systemd --variable=tmpfilesdir 2> /dev/null)
1779
1780 if ! [[ -d $dracutsysrootdir$tmpfilesdir ]]; then
1781 [[ -d $dracutsysrootdir/lib/tmpfiles.d ]] && tmpfilesdir=/lib/tmpfiles.d
1782 [[ -d $dracutsysrootdir/usr/lib/tmpfiles.d ]] && tmpfilesdir=/usr/lib/tmpfiles.d
1783 fi
1784
1785 [[ -d $dracutsysrootdir$tmpfilesconfdir ]] \
1786 || tmpfilesconfdir=$(pkg-config systemd --variable=tmpfilesconfdir 2> /dev/null)
1787
1788 [[ -d $dracutsysrootdir$tmpfilesconfdir ]] || tmpfilesconfdir=/etc/tmpfiles.d
1789
1790 [[ -d $dracutsysrootdir$depmodd ]] \
1791 || sysctld=$(pkg-config libkmod --variable=depmodd 2> /dev/null)
1792
1793 [[ -d $dracutsysrootdir$depmodd ]] || depmodd=/usr/lib/depmod.d
1794
1795 [[ -d $dracutsysrootdir$depmodconfdir ]] \
1796 || sysctlconfdir=$(pkg-config libkmod --variable=depmodconfdir 2> /dev/null)
1797
1798 [[ -d $dracutsysrootdir$depmodconfdir ]] || depmodconfdir=/etc/depmod.d
1799
1800 export initdir dracutbasedir \
1801 dracutmodules force_add_dracutmodules add_dracutmodules omit_dracutmodules \
1802 mods_to_load \
1803 fw_dir drivers_dir debug no_kernel kernel_only \
1804 omit_drivers mdadmconf lvmconf root_devs \
1805 use_fstab fstab_lines libdirs fscks nofscks ro_mnt \
1806 stdloglvl sysloglvl fileloglvl kmsgloglvl logfile \
1807 debug host_fs_types host_devs swap_devs sshkey add_fstab \
1808 DRACUT_VERSION udevdir udevconfdir udevrulesdir udevrulesconfdir \
1809 prefix filesystems drivers dbus dbusconfdir dbusinterfaces \
1810 dbusinterfacesconfdir dbusservices dbusservicesconfdir dbussession \
1811 dbussessionconfdir dbussystem dbussystemconfdir dbussystemservices \
1812 dbussystemservicesconfdir environment environmentconfdir modulesload \
1813 modulesloadconfdir sysctl sysctlconfdir sysusers sysusersconfdir \
1814 systemdutildir systemdutilconfdir systemdcatalog systemdntpunits \
1815 systemdntpunitsconfdir systemdsystemunitdir systemdsystemconfdir \
1816 hostonly_cmdline loginstall tmpfilesdir tmpfilesconfdir depmodd \
1817 depmodconfdir
1818
1819 mods_to_load=""
1820 # check all our modules to see if they should be sourced.
1821 # This builds a list of modules that we will install next.
1822 for_each_module_dir check_module
1823 for_each_module_dir check_mount
1824
1825 dracut_module_included "fips" && export DRACUT_FIPS_MODE=1
1826
1827 do_print_cmdline() {
1828 local -A _mods_to_print
1829 for i in $modules_loaded $mods_to_load; do
1830 _mods_to_print[$i]=1
1831 done
1832
1833 # source our modules.
1834 for moddir in "$dracutbasedir/modules.d"/[0-9][0-9]*; do
1835 _d_mod=${moddir##*/}
1836 _d_mod=${_d_mod#[0-9][0-9]}
1837 [[ ${_mods_to_print[$_d_mod]} ]] || continue
1838 module_cmdline "$_d_mod" "$moddir"
1839 done
1840 unset moddir
1841 }
1842
1843 if [[ $print_cmdline ]]; then
1844 do_print_cmdline
1845 printf "\n"
1846 exit 0
1847 fi
1848
1849 # Create some directory structure first
1850 # shellcheck disable=SC2174
1851 [[ $prefix ]] && mkdir -m 0755 -p "${initdir}${prefix}"
1852
1853 # shellcheck disable=SC2174
1854 [[ -L $dracutsysrootdir/lib ]] || mkdir -m 0755 -p "${initdir}${prefix}/lib"
1855 [[ $prefix ]] && ln -sfn "${prefix#/}/lib" "$initdir/lib"
1856
1857 if [[ $prefix ]]; then
1858 for d in bin etc lib sbin tmp usr var $libdirs; do
1859 d=${d#/}
1860 [[ $d == */* ]] && continue
1861 ln -sfn "${prefix#/}/${d#/}" "$initdir/$d"
1862 done
1863 fi
1864
1865 if [[ $kernel_only != yes ]]; then
1866 for d in usr usr/bin usr/sbin bin etc lib sbin tmp var var/tmp $libdirs; do
1867 d=${d#/}
1868 [[ -e "${initdir}${prefix}/$d" ]] && continue
1869 if [ -L "/$d" ]; then
1870 inst_symlink "/$d" "${prefix}/$d"
1871 else
1872 # shellcheck disable=SC2174
1873 mkdir -m 0755 -p "${initdir}${prefix}/$d"
1874 fi
1875 done
1876
1877 for d in dev proc sys sysroot root run; do
1878 if [ -L "/$d" ]; then
1879 inst_symlink "/$d"
1880 else
1881 # shellcheck disable=SC2174
1882 mkdir -m 0755 -p "$initdir/$d"
1883 fi
1884 done
1885
1886 ln -sfn ../run "$initdir/var/run"
1887 ln -sfn ../run/lock "$initdir/var/lock"
1888 else
1889 for d in lib "$libdirs"; do
1890 [[ -e "${initdir}${prefix}/$d" ]] && continue
1891 if [ -h "/$d" ]; then
1892 inst "/$d" "${prefix}/$d"
1893 else
1894 # shellcheck disable=SC2174
1895 mkdir -m 0755 -p "${initdir}${prefix}/$d"
1896 fi
1897 done
1898 fi
1899
1900 if [[ $kernel_only != yes ]]; then
1901 mkdir -p "${initdir}/etc/cmdline.d"
1902 # shellcheck disable=SC2174
1903 mkdir -m 0755 -p "${initdir}"/lib "${initdir}"/lib/dracut "${initdir}"/lib/dracut/hooks
1904 # shellcheck disable=SC2154
1905 for _d in $hookdirs; do
1906 # shellcheck disable=SC2174
1907 mkdir -m 0755 -p "${initdir}/lib/dracut/hooks/$_d"
1908 done
1909 if [[ $EUID == "0" ]] && ! [[ $DRACUT_NO_MKNOD ]]; then
1910 [[ -c ${initdir}/dev/null ]] || mknod "${initdir}"/dev/null c 1 3
1911 [[ -c ${initdir}/dev/kmsg ]] || mknod "${initdir}"/dev/kmsg c 1 11
1912 [[ -c ${initdir}/dev/console ]] || mknod "${initdir}"/dev/console c 5 1
1913 [[ -c ${initdir}/dev/random ]] || mknod "${initdir}"/dev/random c 1 8
1914 [[ -c ${initdir}/dev/urandom ]] || mknod "${initdir}"/dev/urandom c 1 9
1915 fi
1916 fi
1917
1918 _isize=0 #initramfs size
1919 modules_loaded=" "
1920 # source our modules.
1921 for moddir in "$dracutbasedir/modules.d"/[0-9][0-9]*; do
1922 _d_mod=${moddir##*/}
1923 _d_mod=${_d_mod#[0-9][0-9]}
1924 [[ $mods_to_load == *\ $_d_mod\ * ]] || continue
1925 if [[ $show_modules == yes ]]; then
1926 printf "%s\n" "$_d_mod"
1927 else
1928 dinfo "*** Including module: $_d_mod ***"
1929 fi
1930 if [[ $kernel_only == yes ]]; then
1931 module_installkernel "$_d_mod" "$moddir" || {
1932 dfatal "installkernel failed in module $_d_mod"
1933 exit 1
1934 }
1935 else
1936 module_install "$_d_mod" "$moddir"
1937 if [[ $no_kernel != yes ]]; then
1938 module_installkernel "$_d_mod" "$moddir" || {
1939 dfatal "installkernel failed in module $_d_mod"
1940 exit 1
1941 }
1942 fi
1943 fi
1944 mods_to_load=${mods_to_load// $_d_mod /}
1945 modules_loaded+="$_d_mod "
1946
1947 #print the module install size
1948 if [ -n "$printsize" ]; then
1949 _isize_new=$(du -sk "${initdir}" | {
1950 read -r a _
1951 echo -n "$a"
1952 })
1953 _isize_delta=$((_isize_new - _isize))
1954 printf "%s\n" "$_d_mod install size: ${_isize_delta}k"
1955 _isize=$_isize_new
1956 fi
1957 done
1958 unset moddir
1959
1960 for i in $modules_loaded; do
1961 mkdir -p "$initdir"/lib/dracut
1962 printf "%s\n" "$i" >> "$initdir"/lib/dracut/modules.txt
1963 done
1964
1965 dinfo "*** Including modules done ***"
1966
1967 ## final stuff that has to happen
1968 if [[ $no_kernel != yes ]]; then
1969 if [[ $hostonly_mode == "strict" ]]; then
1970 cp "$DRACUT_KERNEL_MODALIASES" "$initdir"/lib/dracut/hostonly-kernel-modules.txt
1971 fi
1972
1973 if [[ $drivers ]]; then
1974 # shellcheck disable=SC2086
1975 hostonly='' instmods $drivers
1976 fi
1977
1978 if [[ -n ${add_drivers// /} ]]; then
1979 # shellcheck disable=SC2086
1980 hostonly='' instmods -c $add_drivers
1981 fi
1982 if [[ $force_drivers ]]; then
1983 # shellcheck disable=SC2086
1984 hostonly='' instmods -c $force_drivers
1985 rm -f "$initdir"/etc/cmdline.d/20-force_driver.conf
1986 for mod in $force_drivers; do
1987 echo "rd.driver.pre=$mod" >> "$initdir"/etc/cmdline.d/20-force_drivers.conf
1988 done
1989 fi
1990 if [[ $filesystems ]]; then
1991 # shellcheck disable=SC2086
1992 hostonly='' instmods -c $filesystems
1993 fi
1994
1995 dinfo "*** Installing kernel module dependencies ***"
1996 dracut_kernel_post
1997 dinfo "*** Installing kernel module dependencies done ***"
1998
1999 if [[ $noimageifnotneeded == yes ]] && [[ $hostonly ]]; then
2000 if [[ ! -f "$initdir/lib/dracut/need-initqueue" ]] \
2001 && [[ -f ${initdir}/lib/modules/$kernel/modules.dep && ! -s ${initdir}/lib/modules/$kernel/modules.dep ]]; then
2002 for i in "${initdir}"/etc/cmdline.d/*.conf; do
2003 # We need no initramfs image and do not generate one.
2004 [[ $i == "${initdir}/etc/cmdline.d/*.conf" ]] && exit 0
2005 done
2006 fi
2007 fi
2008 fi
2009
2010 if [[ $kernel_only != yes ]]; then
2011 # FIXME: handle legacy item split
2012 # shellcheck disable=SC2068
2013 ((${#install_items[@]} > 0)) && inst_multiple ${install_items[@]}
2014 # shellcheck disable=SC2068
2015 ((${#install_optional_items[@]} > 0)) && inst_multiple -o ${install_optional_items[@]}
2016
2017 if [[ $kernel_cmdline ]] && [[ $uefi != yes ]]; then
2018 printf "%s\n" "$kernel_cmdline" >> "${initdir}/etc/cmdline.d/01-default.conf"
2019 fi
2020
2021 for line in "${fstab_lines[@]}"; do
2022 read -r -a fstab_field <<< "$line"
2023 if [ -z "${fstab_field[1]}" ]; then
2024 # Determine device and mount options from current system
2025 mountpoint -q "${fstab_field[0]}" || derror "${fstab_field[0]} is not a mount point!"
2026 read -r -a fstab_field < <(findmnt --raw -n --target "${fstab_field[0]}" --output=source,target,fstype,options)
2027 dinfo "Line for ${fstab_field[1]}: ${fstab_field[*]}"
2028 else
2029 # Use default options
2030 [ -z "${fstab_field[3]}" ] && fstab_field[3]="defaults"
2031 fi
2032
2033 # Default options for freq and passno
2034 [ -z "${fstab_field[4]}" ] && fstab_field[4]="0"
2035 [ -z "${fstab_field[5]}" ] && fstab_field[5]="2"
2036
2037 strstr "${fstab_field[2]}" "nfs" && fstab_field[5]="0"
2038 echo "${fstab_field[@]}" >> "${initdir}/etc/fstab"
2039 done
2040
2041 for f in $add_fstab; do
2042 cat "$f" >> "${initdir}/etc/fstab"
2043 done
2044
2045 if [[ $dracutsysrootdir$systemdutildir ]]; then
2046 if [[ -d ${initdir}/$systemdutildir ]]; then
2047 mkdir -p "${initdir}"/etc/conf.d
2048 {
2049 printf "%s\n" "systemdutildir=\"$systemdutildir\""
2050 printf "%s\n" "systemdsystemunitdir=\"$systemdsystemunitdir\""
2051 printf "%s\n" "systemdsystemconfdir=\"$systemdsystemconfdir\""
2052 } > "${initdir}"/etc/conf.d/systemd.conf
2053 fi
2054 fi
2055
2056 if [[ $DRACUT_RESOLVE_LAZY ]] && [[ $DRACUT_INSTALL ]]; then
2057 dinfo "*** Resolving executable dependencies ***"
2058 find "$initdir" -type f -perm /0111 -not -path '*.ko' -print0 \
2059 | xargs -r -0 "$DRACUT_INSTALL" ${initdir:+-D "$initdir"} ${dracutsysrootdir:+-r "$dracutsysrootdir"} -R ${DRACUT_FIPS_MODE:+-f} --
2060 dinfo "*** Resolving executable dependencies done ***"
2061 fi
2062
2063 # Now we are done with lazy resolving, always install dependencies
2064 unset DRACUT_RESOLVE_LAZY
2065 export DRACUT_RESOLVE_DEPS=1
2066 fi
2067
2068 for ((i = 0; i < ${#include_src[@]}; i++)); do
2069 src="${include_src[$i]}"
2070 target="${include_target[$i]}"
2071 if [[ $src && $target ]]; then
2072 if [[ -f $src ]]; then
2073 inst "$src" "$target"
2074 elif [[ -d $src ]]; then
2075 ddebug "Including directory: $src"
2076 destdir="${initdir}/${target}"
2077 mkdir -p "$destdir"
2078 # check for preexisting symlinks, so we can cope with the
2079 # symlinks to $prefix
2080 # Objectname is a file or a directory
2081 reset_dotglob="$(shopt -p dotglob)"
2082 shopt -q -s dotglob
2083 for objectname in "$src"/*; do
2084 [[ -e $objectname || -L $objectname ]] || continue
2085 if [[ -d $objectname ]] && [[ ! -L $objectname ]]; then
2086 # objectname is a directory, let's compute the final directory name
2087 object_destdir=${destdir}/${objectname#$src/}
2088 if ! [[ -e $object_destdir ]]; then
2089 # shellcheck disable=SC2174
2090 mkdir -m 0755 -p "$object_destdir"
2091 chmod --reference="$objectname" "$object_destdir"
2092 fi
2093 $DRACUT_CP -t "$object_destdir" "$dracutsysrootdir$objectname"/.
2094 else
2095 $DRACUT_CP -t "$destdir" "$dracutsysrootdir$objectname"
2096 fi
2097 done
2098 eval "$reset_dotglob"
2099 elif [[ -e $src ]]; then
2100 derror "$src is neither a directory nor a regular file"
2101 else
2102 derror "$src doesn't exist"
2103 fi
2104 fi
2105 done
2106
2107 if [[ $do_hardlink == yes ]] && command -v hardlink > /dev/null; then
2108 dinfo "*** Hardlinking files ***"
2109 hardlink "$initdir" 2>&1 | dinfo
2110 dinfo "*** Hardlinking files done ***"
2111 fi
2112
2113 # strip binaries
2114 if [[ $do_strip == yes ]]; then
2115 # Prefer strip from elfutils for package size
2116 declare strip_cmd
2117 strip_cmd=$(command -v eu-strip)
2118 [ -z "$strip_cmd" ] && strip_cmd="strip"
2119
2120 for p in $strip_cmd xargs find; do
2121 if ! type -P $p > /dev/null; then
2122 dinfo "Could not find '$p'. Not stripping the initramfs."
2123 do_strip=no
2124 fi
2125 done
2126
2127 if [[ $aggresive_strip ]]; then
2128 # `eu-strip` and `strip` both strips all unneeded parts by default
2129 strip_args=(-p)
2130 else
2131 strip_args=(-g -p)
2132 fi
2133 fi
2134
2135 # cleanup empty ldconfig_paths directories
2136 for d in $(ldconfig_paths); do
2137 rmdir -p --ignore-fail-on-non-empty "$initdir/$d" > /dev/null 2>&1
2138 done
2139
2140 if [[ $early_microcode == yes ]]; then
2141 dinfo "*** Generating early-microcode cpio image ***"
2142 ucode_dir=(amd-ucode intel-ucode)
2143 ucode_dest=(AuthenticAMD.bin GenuineIntel.bin)
2144 _dest_dir="$early_cpio_dir/d/kernel/x86/microcode"
2145 _dest_idx="0 1"
2146 mkdir -p "$_dest_dir"
2147 if [[ $hostonly ]]; then
2148 [[ $(get_cpu_vendor) == "AMD" ]] && _dest_idx="0"
2149 [[ $(get_cpu_vendor) == "Intel" ]] && _dest_idx="1"
2150 fi
2151 for idx in $_dest_idx; do
2152 _fw=${ucode_dir[$idx]}
2153 for _fwdir in $fw_dir; do
2154 if [[ -d $_fwdir && -d $_fwdir/$_fw ]]; then
2155 _src="*"
2156 dinfo "*** Constructing ${ucode_dest[$idx]} ***"
2157 if [[ $hostonly ]]; then
2158 _src=$(get_ucode_file)
2159 [[ $_src ]] || break
2160 [[ -r $_fwdir/$_fw/$_src ]] || _src="${_src}.early"
2161 [[ -r $_fwdir/$_fw/$_src ]] || break
2162 fi
2163
2164 for i in $_fwdir/$_fw/$_src; do
2165 [ -e "$i" ] && break
2166 break 2
2167 done
2168 for i in $_fwdir/$_fw/$_src; do
2169 [[ -e $i ]] || continue
2170 # skip gpg files
2171 str_ends "$i" ".asc" && continue
2172 cat "$i" >> "$_dest_dir/${ucode_dest[$idx]}"
2173 done
2174 create_early_cpio="yes"
2175 fi
2176 done
2177 if [[ ! -e "$_dest_dir/${ucode_dest[$idx]}" ]]; then
2178 if cd "$early_cpio_dir/d"; then
2179 for _ucodedir in "${early_microcode_image_dir[@]}"; do
2180 for _ucodename in "${early_microcode_image_name[@]}"; do
2181 [[ -e "$_ucodedir/$_ucodename" ]] \
2182 && cpio --extract --file "$_ucodedir/$_ucodename" --quiet \
2183 "kernel/x86/microcode/${ucode_dest[$idx]}"
2184 if [[ -e "$_dest_dir/${ucode_dest[$idx]}" ]]; then
2185 dinfo "*** Using microcode found in '$_ucodedir/$_ucodename' ***"
2186 create_early_cpio="yes"
2187 break 2
2188 fi
2189 done
2190 done
2191 fi
2192 fi
2193 done
2194 fi
2195
2196 if [[ $acpi_override == yes ]] && [[ -d $acpi_table_dir ]]; then
2197 dinfo "*** Packaging ACPI tables to override BIOS provided ones ***"
2198 _dest_dir="$early_cpio_dir/d/kernel/firmware/acpi"
2199 mkdir -p "$_dest_dir"
2200 for table in "$acpi_table_dir"/*.aml; do
2201 dinfo " Adding ACPI table: $table"
2202 $DRACUT_CP "$table" "$_dest_dir"
2203 create_early_cpio="yes"
2204 done
2205 fi
2206
2207 dinfo "*** Store current command line parameters ***"
2208 if ! (echo "$PARMS_TO_STORE" > "$initdir"/lib/dracut/build-parameter.txt); then
2209 dfatal "Could not store the current command line parameters"
2210 exit 1
2211 fi
2212
2213 if [[ $hostonly_cmdline == "yes" ]]; then
2214 unset _stored_cmdline
2215 if [[ -d $initdir/etc/cmdline.d ]]; then
2216 dinfo "Stored kernel commandline:"
2217 for conf in "$initdir"/etc/cmdline.d/*.conf; do
2218 [ -e "$conf" ] || continue
2219 dinfo "$(< "$conf")"
2220 _stored_cmdline=1
2221 done
2222 fi
2223 if ! [[ $_stored_cmdline ]]; then
2224 dinfo "No dracut internal kernel commandline stored in the initramfs"
2225 fi
2226 fi
2227
2228 if [[ $kernel_only != yes ]]; then
2229 # libpthread workaround: pthread_cancel wants to dlopen libgcc_s.so
2230 for _dir in $libdirs; do
2231 for _f in "$dracutsysrootdir$_dir/libpthread.so"*; do
2232 [[ -e $_f ]] || continue
2233 inst_libdir_file "libgcc_s.so*"
2234 break 2
2235 done
2236 done
2237
2238 # FIPS workaround for Fedora/RHEL: libcrypto needs libssl when FIPS is enabled
2239 if [[ $DRACUT_FIPS_MODE ]]; then
2240 for _dir in $libdirs; do
2241 for _f in "$dracutsysrootdir$_dir/libcrypto.so"*; do
2242 [[ -e $_f ]] || continue
2243 inst_libdir_file -o "libssl.so*"
2244 break 2
2245 done
2246 done
2247 fi
2248 fi
2249
2250 if [[ $kernel_only != yes ]]; then
2251 # make sure that library links are correct and up to date
2252 for f in "$dracutsysrootdir"/etc/ld.so.conf "$dracutsysrootdir"/etc/ld.so.conf.d/*; do
2253 [[ -f $f ]] && inst_simple "${f#$dracutsysrootdir}"
2254 done
2255 if ! $DRACUT_LDCONFIG -r "$initdir" -f /etc/ld.so.conf; then
2256 if [[ $EUID == 0 ]]; then
2257 derror "ldconfig exited ungracefully"
2258 else
2259 derror "ldconfig might need uid=0 (root) for chroot()"
2260 fi
2261 fi
2262 fi
2263
2264 if dracut_module_included "squash"; then
2265 readonly squash_dir="$initdir/squash/root"
2266 readonly squash_img="$initdir/squash-root.img"
2267 mkdir -p "$squash_dir"
2268 dinfo "*** Install squash loader ***"
2269 DRACUT_SQUASH_POST_INST=1 module_install "squash"
2270 fi
2271
2272 if [[ $do_strip == yes ]] && ! [[ $DRACUT_FIPS_MODE ]]; then
2273 # stripping files negates (dedup) benefits of using reflink
2274 [[ -n $enhanced_cpio ]] && ddebug "strip is enabled alongside cpio reflink"
2275 dinfo "*** Stripping files ***"
2276 find "$initdir" -type f \
2277 -executable -not -path '*/lib/modules/*.ko' -print0 \
2278 | xargs -r -0 $strip_cmd "${strip_args[@]}" 2> /dev/null
2279
2280 # strip kernel modules, but do not touch signed modules
2281 find "$initdir" -type f -path '*/lib/modules/*.ko' -print0 \
2282 | while read -r -d $'\0' f || [ -n "$f" ]; do
2283 SIG=$(tail -c 28 "$f" | tr -d '\000')
2284 [[ $SIG == '~Module signature appended~' ]] || { printf "%s\000" "$f"; }
2285 done | xargs -r -0 $strip_cmd "${strip_args[@]}"
2286 dinfo "*** Stripping files done ***"
2287 fi
2288
2289 if dracut_module_included "squash"; then
2290 dinfo "*** Squashing the files inside the initramfs ***"
2291 declare squash_compress_arg
2292 # shellcheck disable=SC2086
2293 if [[ $compress ]]; then
2294 if ! mksquashfs /dev/null "$DRACUT_TMPDIR"/.squash-test.img -no-progress -comp $compress &> /dev/null; then
2295 dwarn "mksquashfs doesn't support compressor '$compress', failing back to default compressor."
2296 else
2297 squash_compress_arg="$compress"
2298 fi
2299 fi
2300
2301 # shellcheck disable=SC2086
2302 if ! mksquashfs "$squash_dir" "$squash_img" \
2303 -no-xattrs -no-exports -noappend -no-recovery -always-use-fragments \
2304 -no-progress ${squash_compress_arg:+-comp $squash_compress_arg} 1> /dev/null; then
2305 dfatal "dracut: Failed making squash image"
2306 exit 1
2307 fi
2308
2309 rm -rf "$squash_dir"
2310 dinfo "*** Squashing the files inside the initramfs done ***"
2311
2312 # Skip initramfs compress
2313 compress="cat"
2314 fi
2315
2316 dinfo "*** Creating image file '$outfile' ***"
2317
2318 if [[ $uefi == yes ]]; then
2319 readonly uefi_outdir="$DRACUT_TMPDIR/uefi"
2320 mkdir -p "$uefi_outdir"
2321 fi
2322
2323 if [[ $DRACUT_REPRODUCIBLE ]]; then
2324 find "$initdir" -newer "$dracutbasedir/dracut-functions.sh" -print0 \
2325 | xargs -r -0 touch -h -m -c -r "$dracutbasedir/dracut-functions.sh"
2326
2327 if [[ "$(cpio --help)" == *--reproducible* ]]; then
2328 CPIO_REPRODUCIBLE=1
2329 else
2330 dinfo "cpio does not support '--reproducible'. Resulting image will not be reproducible."
2331 fi
2332 fi
2333
2334 [[ $EUID != 0 ]] && cpio_owner="0:0"
2335
2336 if [[ $create_early_cpio == yes ]]; then
2337 echo 1 > "$early_cpio_dir/d/early_cpio"
2338
2339 if [[ $DRACUT_REPRODUCIBLE ]]; then
2340 find "$early_cpio_dir/d" -newer "$dracutbasedir/dracut-functions.sh" -print0 \
2341 | xargs -r -0 touch -h -m -c -r "$dracutbasedir/dracut-functions.sh"
2342 fi
2343
2344 # The microcode blob is _before_ the initramfs blob, not after
2345 if [[ -n $enhanced_cpio ]]; then
2346 if ! (
2347 umask 077
2348 cd "$early_cpio_dir/d"
2349 find . -print0 | sort -z \
2350 | $enhanced_cpio --null ${cpio_owner:+--owner "$cpio_owner"} \
2351 --mtime 0 --data-align "$cpio_align" --truncate-existing \
2352 "${DRACUT_TMPDIR}/initramfs.img"
2353 ); then
2354 dfatal "dracut-cpio: creation of $outfile failed"
2355 exit 1
2356 fi
2357 else
2358 if ! (
2359 umask 077
2360 cd "$early_cpio_dir/d"
2361 find . -print0 | sort -z \
2362 | cpio ${CPIO_REPRODUCIBLE:+--reproducible} --null \
2363 ${cpio_owner:+-R "$cpio_owner"} -H newc -o --quiet > "${DRACUT_TMPDIR}/initramfs.img"
2364 ); then
2365 dfatal "dracut: creation of $outfile failed"
2366 exit 1
2367 fi
2368 fi
2369 fi
2370
2371 if check_kernel_config CONFIG_RD_ZSTD; then
2372 DRACUT_KERNEL_RD_ZSTD=yes
2373 else
2374 DRACUT_KERNEL_RD_ZSTD=
2375 fi
2376
2377 if [[ $compress == $DRACUT_COMPRESS_ZSTD* && ! $DRACUT_KERNEL_RD_ZSTD ]]; then
2378 dwarn "dracut: kernel has no zstd support compiled in."
2379 compress=
2380 fi
2381
2382 if [[ $compress && $compress != cat ]]; then
2383 if ! command -v "${compress%% *}" &> /dev/null; then
2384 derror "dracut: cannot execute compression command '$compress', falling back to default"
2385 compress=
2386 fi
2387 fi
2388
2389 if ! [[ $compress ]]; then
2390 # check all known compressors, if none specified
2391 for i in $DRACUT_COMPRESS_PIGZ $DRACUT_COMPRESS_GZIP $DRACUT_COMPRESS_LZ4 $DRACUT_COMPRESS_LZOP $DRACUT_COMPRESS_ZSTD $DRACUT_COMPRESS_LZMA $DRACUT_COMPRESS_XZ $DRACUT_COMPRESS_LBZIP2 $DRACUT_COMPRESS_BZIP2 $DRACUT_COMPRESS_CAT; do
2392 [[ $i != "$DRACUT_COMPRESS_ZSTD" || $DRACUT_KERNEL_RD_ZSTD ]] || continue
2393 command -v "$i" &> /dev/null || continue
2394 compress="$i"
2395 break
2396 done
2397 if [[ $compress == cat ]]; then
2398 dwarn "dracut: no compression tool available. Initramfs image is going to be big."
2399 else
2400 dinfo "dracut: using auto-determined compression method '$compress'"
2401 fi
2402 fi
2403
2404 # choose the right arguments for the compressor
2405 case $compress in
2406 bzip2 | lbzip2)
2407 if [[ $compress == lbzip2 ]] || command -v "$DRACUT_COMPRESS_LBZIP2" &> /dev/null; then
2408 compress="$DRACUT_COMPRESS_LBZIP2 -9"
2409 else
2410 compress="$DRACUT_COMPRESS_BZIP2 -9"
2411 fi
2412 ;;
2413 lzma)
2414 compress="$DRACUT_COMPRESS_LZMA -9 -T0"
2415 ;;
2416 xz)
2417 compress="$DRACUT_COMPRESS_XZ --check=crc32 --lzma2=dict=1MiB -T0"
2418 ;;
2419 gzip | pigz)
2420 if [[ $compress == pigz ]] || command -v "$DRACUT_COMPRESS_PIGZ" &> /dev/null; then
2421 compress="$DRACUT_COMPRESS_PIGZ -9 -n -T -R"
2422 elif command -v gzip &> /dev/null && $DRACUT_COMPRESS_GZIP --help 2>&1 | grep -q rsyncable; then
2423 compress="$DRACUT_COMPRESS_GZIP -n -9 --rsyncable"
2424 else
2425 compress="$DRACUT_COMPRESS_GZIP -n -9"
2426 fi
2427 ;;
2428 lzo | lzop)
2429 compress="$DRACUT_COMPRESS_LZOP -9"
2430 ;;
2431 lz4)
2432 compress="$DRACUT_COMPRESS_LZ4 -l -9"
2433 ;;
2434 zstd)
2435 compress="$DRACUT_COMPRESS_ZSTD -15 -q -T0"
2436 ;;
2437 esac
2438
2439 if [[ -n $enhanced_cpio ]]; then
2440 if [[ $compress == "cat" ]]; then
2441 # dracut-cpio appends by default, so any ucode remains
2442 cpio_outfile="${DRACUT_TMPDIR}/initramfs.img"
2443 else
2444 ddebug "$compress compression enabled alongside cpio reflink"
2445 # dracut-cpio doesn't output to stdout, so stage for compression
2446 cpio_outfile="${DRACUT_TMPDIR}/initramfs.img.uncompressed"
2447 fi
2448
2449 if ! (
2450 umask 077
2451 cd "$initdir"
2452 find . -print0 | sort -z \
2453 | $enhanced_cpio --null ${cpio_owner:+--owner "$cpio_owner"} \
2454 --mtime 0 --data-align "$cpio_align" "$cpio_outfile" || exit 1
2455 [[ $compress == "cat" ]] && exit 0
2456 $compress < "$cpio_outfile" >> "${DRACUT_TMPDIR}/initramfs.img" \
2457 && rm "$cpio_outfile"
2458 ); then
2459 dfatal "dracut-cpio: creation of $outfile failed"
2460 exit 1
2461 fi
2462 unset cpio_outfile
2463 else
2464 if ! (
2465 umask 077
2466 cd "$initdir"
2467 find . -print0 | sort -z \
2468 | cpio ${CPIO_REPRODUCIBLE:+--reproducible} --null ${cpio_owner:+-R "$cpio_owner"} -H newc -o --quiet \
2469 | $compress >> "${DRACUT_TMPDIR}/initramfs.img"
2470 ); then
2471 dfatal "dracut: creation of $outfile failed"
2472 exit 1
2473 fi
2474 fi
2475
2476 # shellcheck disable=SC2154
2477 if ((maxloglvl >= 5)) && ((verbosity_mod_l >= 0)); then
2478 if [[ $allowlocal ]]; then
2479 "$dracutbasedir/lsinitrd.sh" "${DRACUT_TMPDIR}/initramfs.img" | ddebug
2480 else
2481 lsinitrd "${DRACUT_TMPDIR}/initramfs.img" | ddebug
2482 fi
2483 fi
2484
2485 umask 077
2486
2487 if [[ $uefi == yes ]]; then
2488 if [[ $kernel_cmdline ]]; then
2489 echo -n "$kernel_cmdline" > "$uefi_outdir/cmdline.txt"
2490 elif [[ $hostonly_cmdline == yes ]] && [ -d "$initdir/etc/cmdline.d" ]; then
2491 for conf in "$initdir"/etc/cmdline.d/*.conf; do
2492 [ -e "$conf" ] || continue
2493 printf "%s " "$(< "$conf")" >> "$uefi_outdir/cmdline.txt"
2494 done
2495 fi
2496
2497 if [[ $kernel_cmdline ]] || [[ $hostonly_cmdline == yes && -d "$initdir/etc/cmdline.d" ]]; then
2498 echo -ne "\x00" >> "$uefi_outdir/cmdline.txt"
2499 dinfo "Using UEFI kernel cmdline:"
2500 dinfo "$(tr -d '\000' < "$uefi_outdir/cmdline.txt")"
2501 uefi_cmdline="${uefi_outdir}/cmdline.txt"
2502 else
2503 unset uefi_cmdline
2504 fi
2505
2506 [[ -s $dracutsysrootdir/usr/lib/os-release ]] && uefi_osrelease="$dracutsysrootdir/usr/lib/os-release"
2507 [[ -s $dracutsysrootdir/etc/os-release ]] && uefi_osrelease="$dracutsysrootdir/etc/os-release"
2508 if [[ -s ${dracutsysrootdir}${uefi_splash_image} ]]; then
2509 uefi_splash_image="${dracutsysrootdir}${uefi_splash_image}"
2510 else
2511 unset uefi_splash_image
2512 fi
2513
2514 if objcopy \
2515 ${uefi_osrelease:+--add-section .osrel="$uefi_osrelease" --change-section-vma .osrel=0x20000} \
2516 ${uefi_cmdline:+--add-section .cmdline="$uefi_cmdline" --change-section-vma .cmdline=0x30000} \
2517 ${uefi_splash_image:+--add-section .splash="$uefi_splash_image" --change-section-vma .splash=0x40000} \
2518 --add-section .linux="$kernel_image" --change-section-vma .linux=0x2000000 \
2519 --add-section .initrd="${DRACUT_TMPDIR}/initramfs.img" --change-section-vma .initrd=0x3000000 \
2520 "$uefi_stub" "${uefi_outdir}/linux.efi"; then
2521 if [[ -n ${uefi_secureboot_key} && -n ${uefi_secureboot_cert} ]]; then
2522 if sbsign \
2523 --key "${uefi_secureboot_key}" \
2524 --cert "${uefi_secureboot_cert}" \
2525 --output "$outfile" "${uefi_outdir}/linux.efi"; then
2526 dinfo "*** Creating signed UEFI image file '$outfile' done ***"
2527 else
2528 dfatal "*** Creating signed UEFI image file '$outfile' failed ***"
2529 exit 1
2530 fi
2531 else
2532 if cp --reflink=auto "${uefi_outdir}/linux.efi" "$outfile"; then
2533 dinfo "*** Creating UEFI image file '$outfile' done ***"
2534 fi
2535 fi
2536 else
2537 rm -f -- "$outfile"
2538 dfatal "*** Creating UEFI image file '$outfile' failed ***"
2539 exit 1
2540 fi
2541 else
2542 if cp --reflink=auto "${DRACUT_TMPDIR}/initramfs.img" "$outfile"; then
2543 dinfo "*** Creating initramfs image file '$outfile' done ***"
2544 else
2545 rm -f -- "$outfile"
2546 dfatal "dracut: creation of $outfile failed"
2547 exit 1
2548 fi
2549 fi
2550
2551 command -v restorecon &> /dev/null && restorecon -- "$outfile"
2552
2553 btrfs_uuid() {
2554 btrfs filesystem show "$1" | sed -n '1s/^.*uuid: //p'
2555 }
2556
2557 freeze_ok_for_btrfs() {
2558 local mnt uuid1 uuid2
2559 # If the output file is on btrfs, we need to make sure that it's
2560 # not on a subvolume of the same file system as the root FS.
2561 # Otherwise, fsfreeze() might freeze the entire system.
2562 # This is most conveniently checked by comparing the FS uuid.
2563
2564 [[ "$(stat -f -c %T -- "/")" == "btrfs" ]] || return 0
2565 mnt=$(stat -c %m -- "$1")
2566 uuid1=$(btrfs_uuid "$mnt")
2567 uuid2=$(btrfs_uuid "/")
2568 [[ $uuid1 && $uuid2 && $uuid1 != "$uuid2" ]]
2569 }
2570
2571 freeze_ok_for_fstype() {
2572 local outfile=$1
2573 local fstype
2574
2575 [[ "$(stat -c %m -- "$outfile")" == "/" ]] && return 1
2576 fstype=$(stat -f -c %T -- "$outfile")
2577 case $fstype in
2578 msdos)
2579 return 1
2580 ;;
2581 btrfs)
2582 freeze_ok_for_btrfs "$outfile"
2583 ;;
2584 *)
2585 return 0
2586 ;;
2587 esac
2588 }
2589
2590 # We sync/fsfreeze only if we're operating on a live booted system.
2591 # It's possible for e.g. `kernel` to be installed as an RPM BuildRequires or equivalent,
2592 # and there's no reason to sync, and *definitely* no reason to fsfreeze.
2593 # Another case where this happens is rpm-ostree, which performs its own sync/fsfreeze
2594 # globally. See e.g. https://github.com/ostreedev/ostree/commit/8642ef5ab3fec3ac8eb8f193054852f83a8bc4d0
2595 if [[ -d $dracutsysrootdir/run/systemd/system ]]; then
2596 if ! sync "$outfile" 2> /dev/null; then
2597 dinfo "dracut: sync operation on newly created initramfs $outfile failed"
2598 exit 1
2599 fi
2600
2601 # use fsfreeze only if we're not writing to /
2602 if [[ "$(stat -c %m -- "$outfile")" != "/" ]] && freeze_ok_for_fstype "$outfile"; then
2603 FSFROZEN="$(dirname "$outfile")"
2604 if ! (fsfreeze -f "${FSFROZEN}" 2> /dev/null && fsfreeze -u "${FSFROZEN}" 2> /dev/null); then
2605 dinfo "dracut: warning: could not fsfreeze $(dirname "$outfile")"
2606 fi
2607 unset FSFROZEN
2608 fi
2609 fi
2610
2611 exit 0