diff options
-rw-r--r-- | HACKING | 2 | ||||
-rw-r--r-- | Makefile | 9 | ||||
-rw-r--r-- | PKGBUILD | 6 | ||||
-rw-r--r-- | README | 3 | ||||
-rw-r--r-- | libalpm/hooks/60-mkinitcpio-remove.hook | 16 | ||||
-rw-r--r-- | libalpm/hooks/90-mkinitcpio-install.hook | 12 | ||||
-rw-r--r-- | libalpm/scripts/mkinitcpio-install | 44 | ||||
-rw-r--r-- | libalpm/scripts/mkinitcpio-remove | 39 | ||||
-rw-r--r-- | man/lsinitcpio.1.txt | 2 | ||||
-rw-r--r-- | man/mkinitcpio.8.txt | 23 | ||||
-rw-r--r-- | man/mkinitcpio.conf.5.txt | 2 | ||||
-rwxr-xr-x | mkinitcpio | 54 | ||||
-rw-r--r-- | mkinitcpio.d/hook.preset | 14 | ||||
-rw-r--r-- | shell/bash-completion | 4 | ||||
-rw-r--r-- | shell/zsh-completion | 1 |
15 files changed, 199 insertions, 32 deletions
@@ -11,7 +11,7 @@ two are effectively identical. This means always using double braces over the inferior '[' and 'test'. -Variable usage and naming convetions +Variable usage and naming conventions ------------------------------------ There are three classifications of variables in mkinitcpio. @@ -18,7 +18,9 @@ DIRS = \ /usr/share/man/man1 \ /usr/share/mkinitcpio \ /usr/lib/systemd/system/shutdown.target.wants \ - /usr/lib/tmpfiles.d + /usr/lib/tmpfiles.d \ + /usr/share/libalpm/hooks \ + /usr/share/libalpm/scripts BASH_SCRIPTS = \ mkinitcpio \ @@ -70,6 +72,11 @@ install: all ln -s mkinitcpio $(DESTDIR)/usr/share/bash-completion/completions/lsinitcpio install -m644 shell/zsh-completion $(DESTDIR)/usr/share/zsh/site-functions/_mkinitcpio + install -m644 libalpm/hooks/90-mkinitcpio-install.hook $(DESTDIR)/usr/share/libalpm/hooks/90-mkinitcpio-install.hook + install -m755 libalpm/scripts/mkinitcpio-install $(DESTDIR)/usr/share/libalpm/scripts/mkinitcpio-install + install -m644 libalpm/hooks/60-mkinitcpio-remove.hook $(DESTDIR)/usr/share/libalpm/hooks/60-mkinitcpio-remove.hook + install -m755 libalpm/scripts/mkinitcpio-remove $(DESTDIR)/usr/share/libalpm/scripts/mkinitcpio-remove + doc: $(MANPAGES) man/%: man/%.txt Makefile a2x -d manpage \ @@ -7,7 +7,7 @@ url="https://git.archlinux.org/mkinitcpio.git/" license=('GPL') groups=('base') conflicts=('mkinitcpio') -provides=("mkinitcpio=$pkgver") +provides=("mkinitcpio=$pkgver" "initramfs") depends=('mkinitcpio-busybox>=1.19.4-2' 'kmod' 'util-linux>=2.23' 'libarchive' 'coreutils' 'awk' 'bash' 'findutils' 'grep' 'filesystem>=2011.10-1' 'systemd' 'gzip') makedepends=('asciidoc' 'git' 'sed') @@ -19,9 +19,9 @@ optdepends=('xz: Use lzma or xz compression for the initramfs image' backup=(etc/mkinitcpio.conf) build() { - make -C .. + make -C "$startdir" } package() { - make -C .. DESTDIR="$pkgdir" install + make -C "$startdir" DESTDIR="$pkgdir" install } @@ -1,7 +1,8 @@ The corresponding files are licensed under the GNU General Public License, version 2 as per the included LICENSE file. - Copyright (C) 2006-2013, Thomas Bächler <thomas@archlinux.org> + Copyright (C) 2006-2019, Thomas Bächler <thomas@archlinux.org> Aaron Griffin <aaronmgriffin@gmail.com> Tobias Powalowski <tpowa@archlinux.org> Dave Reisner <dreisner@archlinux.org> + Giancarlo Razzolini <grazzolini@archlinux.org> diff --git a/libalpm/hooks/60-mkinitcpio-remove.hook b/libalpm/hooks/60-mkinitcpio-remove.hook new file mode 100644 index 0000000..ab71ed6 --- /dev/null +++ b/libalpm/hooks/60-mkinitcpio-remove.hook @@ -0,0 +1,16 @@ +[Trigger] +Type = File +Operation = Remove +Target = usr/lib/modules/*/vmlinuz + +[Trigger] +Type = Package +Operation = Remove +Target = mkinitcpio +Target = mkinitcpio-git + +[Action] +Description = Removing linux initcpios... +When = PreTransaction +Exec = /usr/share/libalpm/scripts/mkinitcpio-remove +NeedsTargets diff --git a/libalpm/hooks/90-mkinitcpio-install.hook b/libalpm/hooks/90-mkinitcpio-install.hook new file mode 100644 index 0000000..48e6a1e --- /dev/null +++ b/libalpm/hooks/90-mkinitcpio-install.hook @@ -0,0 +1,12 @@ +[Trigger] +Type = File +Operation = Install +Operation = Upgrade +Target = usr/lib/modules/*/vmlinuz +Target = usr/lib/initcpio/* + +[Action] +Description = Updating linux initcpios... +When = PostTransaction +Exec = /usr/share/libalpm/scripts/mkinitcpio-install +NeedsTargets diff --git a/libalpm/scripts/mkinitcpio-install b/libalpm/scripts/mkinitcpio-install new file mode 100644 index 0000000..d2e5041 --- /dev/null +++ b/libalpm/scripts/mkinitcpio-install @@ -0,0 +1,44 @@ +#!/bin/bash -e + +args=() +all=0 + +while read -r line; do + if [[ $line != */vmlinuz ]]; then + # triggers when it's a change to usr/lib/initcpio/* + all=1 + continue + fi + + if ! read -r pkgbase > /dev/null 2>&1 < "${line%/vmlinuz}/pkgbase"; then + # if the kernel has no pkgbase, we skip it + continue + fi + + preset="/etc/mkinitcpio.d/${pkgbase}.preset" + if [[ ! -e $preset ]]; then + if [[ -e $preset.pacsave ]]; then + # move the pacsave to the template + mv "${preset}.pacsave" "$preset" + else + # create the preset from the template + sed "s|%PKGBASE%|${pkgbase}|g" /usr/share/mkinitcpio/hook.preset \ + | install -Dm644 /dev/stdin "$preset" + fi + fi + + # always install the kernel + install -Dm644 "${line}" "/boot/vmlinuz-${pkgbase}" + + # compound args for each kernel + args+=(-p "${pkgbase}") +done + +if (( all )) && compgen -G /etc/mkinitcpio.d/"*.preset" > /dev/null; then + # change to use all presets + args=(-P) +fi + +if (( ${#args[@]} )); then + mkinitcpio "${args[@]}" +fi diff --git a/libalpm/scripts/mkinitcpio-remove b/libalpm/scripts/mkinitcpio-remove new file mode 100644 index 0000000..86838e4 --- /dev/null +++ b/libalpm/scripts/mkinitcpio-remove @@ -0,0 +1,39 @@ +#!/bin/bash -e + +package=0 + +while read -r line; do + if [[ $line != */vmlinuz ]]; then + # triggers when it's a change to usr/lib/initcpio/* + package=1 + continue + fi + + if ! read -r pkgbase > /dev/null 2>&1 < "${line%/vmlinuz}/pkgbase"; then + # if the kernel has no pkgbase, we skip it + continue + fi + + # remove the actual kernel and images for the package being removed + kernel="/boot/vmlinuz-${pkgbase}" + preset="/etc/mkinitcpio.d/${pkgbase}.preset" + initramfs="/boot/initramfs-${pkgbase}.img" + fallback_initramfs="/boot/initramfs-${pkgbase}-fallback.img" + if [[ -e $kernel ]]; then + # remove the installed kernel + rm $kernel + fi + if [[ -e $preset ]]; then + # remove the preset + rm $preset + fi + if [[ -e $initramfs && -e $fallback_initramfs ]]; then + # remove the images + rm $initramfs $fallback_initramfs + fi +done + +if (( package )) && compgen -G /etc/mkinitcpio.d/"*.preset" > /dev/null; then + # remove all presets + rm /etc/mkinitcpio.d/*.preset +fi diff --git a/man/lsinitcpio.1.txt b/man/lsinitcpio.1.txt index 98bd756..4f25da0 100644 --- a/man/lsinitcpio.1.txt +++ b/man/lsinitcpio.1.txt @@ -65,4 +65,4 @@ lsinitcpio was created by Dave Reisner <dreisner@archlinux.org> Copyright --------- -Copyright (c) Arch Linux 2011-2012 +Copyright (c) Arch Linux 2011-2019 diff --git a/man/mkinitcpio.8.txt b/man/mkinitcpio.8.txt index 931a167..a69cf20 100644 --- a/man/mkinitcpio.8.txt +++ b/man/mkinitcpio.8.txt @@ -36,11 +36,14 @@ Options Set 'directory' as the location where the initramfs is built. This might be useful to generate a shutdown ramfs in '/run/initramfs'. +*-D, \--hookdir* 'directory':: + Set 'directory' as the location where hooks will be searched for when + generating the image. + *-g, \--generate* 'filename':: Generate a CPIO image as 'filename'. Default: no; this means nothing will be written to the filesystem unless this option is specified. - *-H, \--hookhelp* 'hookname':: Output help for hookname 'hookname'. @@ -301,6 +304,22 @@ These are only the variables that the core of mkinitcpio honor. Additional hooks may look for other environment variables and should be documented by the help output for the hook. +Reproducibility +--------------- +mkinitcpio aims to create reproducible initramfs images by default. + +This means that two subsequent runs of mkinitcpio should produce two files +that are identical at the binary level. + +Timestamps within the initramfs are set to the Unix epoch of 1970-01-01. + +Note that in order for the build to be fully reproducible, the compressor +specified (e.g. gzip, xz) must also produce reproducible archives. At the time +of writing, as an inexhaustive example, the lzop compressor is incapable of +producing reproducible archives due to the insertion of a runtime timestamp. + +More information can be found at https://reproducible-builds.org. + Files ----- '/etc/mkinitcpio.conf':: @@ -348,4 +367,4 @@ mkinitcpio is created and maintained by the Arch Linux Developer community. Copyright --------- -Copyright (c) Arch Linux 2006-2012 +Copyright (c) Arch Linux 2006-2019 diff --git a/man/mkinitcpio.conf.5.txt b/man/mkinitcpio.conf.5.txt index d272852..9c8d000 100644 --- a/man/mkinitcpio.conf.5.txt +++ b/man/mkinitcpio.conf.5.txt @@ -79,4 +79,4 @@ mkinitcpio is created and maintained by the Arch Linux Developer community. Copyright --------- -Copyright (c) Arch Linux 2006-2012 +Copyright (c) Arch Linux 2006-2019 @@ -14,6 +14,8 @@ _f_functions=functions _f_config=mkinitcpio.conf _d_hooks="$PWD/hooks:/usr/lib/initcpio/hooks:/lib/initcpio/hooks" _d_install="$PWD/install:/usr/lib/initcpio/install:/lib/initcpio/install" +_d_flag_hooks= +_d_flag_install= _d_firmware=({/usr,}/lib/firmware/updates {/usr,}/lib/firmware) _d_presets=mkinitcpio.d @@ -56,6 +58,7 @@ usage: ${0##*/} [options] -s, --save Save build directory. (default: no) -d, --generatedir <dir> Write generated image into <dir> -t, --builddir <dir> Use DIR as the temporary build directory + -D, --hookdir <dir> Specify where to look for hooks. -V, --version Display version information and exit -v, --verbose Verbose output (default: no) -z, --compress <program> Use an alternate compressor on the image @@ -192,8 +195,7 @@ compute_hookset() { } build_image() { - local out=$1 compress=$2 errmsg= - local -a pipesave cpio_opts + local out=$1 compress=$2 errmsg pipestatus case $compress in cat) @@ -211,27 +213,29 @@ build_image() { ;; esac - cpio_opts=('-0' '-o' '-H' 'newc') - (( _optquiet )) && cpio_opts+=('--quiet') - if (( EUID != 0 )); then - warning 'Not building as root, ownership cannot be preserved' - cpio_opts+=('-R' '0:0') - fi - pushd "$BUILDROOT" >/dev/null + + # Reproducibility: set all timestamps to 0 + find . -mindepth 1 -execdir touch -hcd "@0" "{}" + + + # If this pipeline changes, |pipeprogs| below needs to be updated as well. find . -mindepth 1 -printf '%P\0' | - LANG=C bsdcpio "${cpio_opts[@]}" | + sort -z | + LANG=C bsdtar --null -cnf - -T - | + LANG=C bsdtar --uid 0 --gid 0 --null -cf - --format=newc @- | $compress "${COMPRESSION_OPTIONS[@]}" > "$out" - pipesave=("${PIPESTATUS[@]}") # save immediately + + pipestatus=("${PIPESTATUS[@]}") + pipeprogs=('find' 'sort' 'bsdtar (step 1)' 'bsdtar (step 2)' "$compress") + popd >/dev/null - if (( pipesave[0] )); then - errmsg="find reported an error" - elif (( pipesave[1] )); then - errmsg="bsdcpio reported an error" - elif (( pipesave[2] )); then - errmsg="$compress reported an error" - fi + for (( i = 0; i < ${#pipestatus[*]}; ++i )); do + if (( pipestatus[i] )); then + errmsg="${pipeprogs[i]} reported an error" + break + fi + done if (( _builderrors )); then warning "errors were encountered during the build. The image may not be complete." @@ -313,8 +317,8 @@ process_preset() ( trap 'cleanup 130' INT trap 'cleanup 143' TERM -_opt_short='A:c:g:H:hk:nLMPp:r:S:sd:t:Vvz:' -_opt_long=('add:' 'addhooks:' 'config:' 'generate:' 'hookhelp:' 'help' +_opt_short='A:c:D:g:H:hk:nLMPp:r:S:sd:t:Vvz:' +_opt_long=('add:' 'addhooks:' 'config:' 'generate:' 'hookdir': 'hookhelp:' 'help' 'kernel:' 'listhooks' 'automods' 'moduleroot:' 'nocolor' 'allpresets' 'preset:' 'skiphooks:' 'save' 'generatedir:' 'builddir:' 'version' 'verbose' 'compress:') @@ -405,6 +409,11 @@ while :; do shift _optmoduleroot=$1 ;; + -D|--hookdir) + shift + _d_flag_hooks+="$1/hooks:" + _d_flag_install+="$1/install:" + ;; --) shift break 2 @@ -417,6 +426,11 @@ if [[ -t 1 ]] && (( _optcolor )); then try_enable_color fi +if [[ -n $_d_flag_hooks && -n $_d_flag_install ]]; then + _d_hooks=${_d_flag_hooks%:} + _d_install=${_d_flag_install%:} +fi + # insist that /proc and /dev be mounted (important for chroots) # NOTE: avoid using mountpoint for this -- look for the paths that we actually # use in mkinitcpio. Avoids issues like FS#26344. diff --git a/mkinitcpio.d/hook.preset b/mkinitcpio.d/hook.preset new file mode 100644 index 0000000..66709a8 --- /dev/null +++ b/mkinitcpio.d/hook.preset @@ -0,0 +1,14 @@ +# mkinitcpio preset file for the '%PKGBASE%' package + +ALL_config="/etc/mkinitcpio.conf" +ALL_kver="/boot/vmlinuz-%PKGBASE%" + +PRESETS=('default' 'fallback') + +#default_config="/etc/mkinitcpio.conf" +default_image="/boot/initramfs-%PKGBASE%.img" +#default_options="" + +#fallback_config="/etc/mkinitcpio.conf" +fallback_image="/boot/initramfs-%PKGBASE%-fallback.img" +fallback_options="-S autodetect" diff --git a/shell/bash-completion b/shell/bash-completion index a0f07dc..8f3663d 100644 --- a/shell/bash-completion +++ b/shell/bash-completion @@ -56,7 +56,7 @@ _files_from_dirs() { _mkinitcpio() { local action cur prev opts - opts=(-A --addhooks -c --config -g --generate -H --hookhelp -h --help -k --kernel + opts=(-A --addhooks -c --config -D --hookdir -g --generate -H --hookhelp -h --help -k --kernel -L --listhooks -M --automods -n --nocolor -P --allpresets -p --preset -r --moduleroot -S --skiphooks -s --save -t --builddir -V --version -v --verbose -z --compress) @@ -65,7 +65,7 @@ _mkinitcpio() { case $prev in -[cg]|--config|--generate) _filedir ;; - -r|--moduleroot|-t|--builddir) + -D|--hookdir|-r|--moduleroot|-t|--builddir) _filedir -d ;; -k|--kernel) _find_kernel_versions ;; diff --git a/shell/zsh-completion b/shell/zsh-completion index 4d1e435..587e3b2 100644 --- a/shell/zsh-completion +++ b/shell/zsh-completion @@ -39,6 +39,7 @@ case $service in _arguments : \ '(-A --addhooks)'{-A,--addhooks}'[Add specified hooks, comma separated, to image]::usr hooks:_path_files -W /usr/lib/initcpio/install::lib hooks:_path_files -W /lib/initcpio/install' \ '(-c --config)'{-c,--config}'[Use alternate config file. (default: /etc/mkinitcpio.conf)]:config files:_files' \ + '(-D --hookdir)'{-D,--hookdir}'[Specify where to look for hooks.]:directories:_files -/' \ '(-g --generate)'{-g,--generate}'[Generate cpio image and write to specified path]:config files:_files' \ '(-H --hookhelp)'{-H,--hookhelp}'[Display help for given hook and exit]::usr hooks:_path_files -W /usr/lib/initcpio/install::lib hooks:_path_files -W /lib/initcpio/install' \ '(-h --help)'{-h,--help}'[Display this message and exit]' \ |