#!/usr/bin/env bash
update_initramfs() {
local chroot_target=$1 target_dir
target_dir="$(find "${chroot_target}/lib/modules"/ -maxdepth 1 -type d -name "*${IMAGE_INSTALLED_KERNEL_VERSION}*")"
local initrd_kern_ver initrd_file initrd_cache_key initrd_cache_file_path initrd_hash
local initrd_cache_current_manifest_filepath initrd_cache_last_manifest_filepath initrd_files_to_hash
local initrd_debug="" update_initramfs_cmd
local logging_filter=""
if [[ "${SHOW_DEBUG}" == "yes" ]]; then
initrd_debug="v"
fi
if [[ "$target_dir" != "" ]]; then
initrd_kern_ver="$(basename "$target_dir")"
initrd_file="${chroot_target}/boot/initrd.img-${initrd_kern_ver}"
update_initramfs_cmd="TMPDIR=/tmp update-initramfs -u${initrd_debug} -k ${initrd_kern_ver}"
else
display_alert "Can't find kernel for version, here's what is in /lib/modules" "IMAGE_INSTALLED_KERNEL_VERSION: ${IMAGE_INSTALLED_KERNEL_VERSION}" "wrn"
SHOW_LOG=yes run_host_command_logged find "${chroot_target}/lib/modules"/ -maxdepth 1
exit_with_error "No kernel installed for the version" "${IMAGE_INSTALLED_KERNEL_VERSION}"
fi
display_alert "computing initrd cache hash" "${chroot_target}" "debug"
mkdir -p "${SRC}/cache/initrd"
initrd_cache_current_manifest_filepath="${WORKDIR}/initrd.img-${initrd_kern_ver}.${ARMBIAN_BUILD_UUID}.manifest"
initrd_cache_last_manifest_filepath="${SRC}/cache/initrd/initrd.manifest-${initrd_kern_ver}.last.manifest"
initrd_files_to_hash=("${chroot_target}/usr/bin/bash" "${chroot_target}/etc/initramfs")
initrd_files_to_hash+=("${chroot_target}/etc/initramfs-tools" "${chroot_target}/usr/share/initramfs-tools/")
initrd_files_to_hash+=("${chroot_target}/etc/modprobe.d")
if [[ $CRYPTROOT_ENABLE == yes ]]; then
if [[ $CRYPTROOT_SSH_UNLOCK == yes ]]; then
[[ -d "${chroot_target}/etc/dropbear-initramfs/" ]] && initrd_files_to_hash+=("${chroot_target}/etc/dropbear-initramfs/")
[[ -d "${chroot_target}/etc/dropbear/initramfs/" ]] && initrd_files_to_hash+=("${chroot_target}/etc/dropbear/initramfs/")
fi
initrd_files_to_hash+=("${chroot_target}/etc/crypttab")
fi
find "${target_dir}" "${initrd_files_to_hash[@]}" -type f | parallel -X md5sum |
awk '{print $2 " - " $1}' |
sed -e "s|^${chroot_target}||g" | LC_ALL=C sort > "${initrd_cache_current_manifest_filepath}"
initrd_hash="$(md5sum "${initrd_cache_current_manifest_filepath}" | cut -d ' ' -f 1)"
initrd_cache_key="initrd.img-${initrd_kern_ver}-${initrd_hash}"
initrd_cache_file_path="${SRC}/cache/initrd/${initrd_cache_key}"
display_alert "initrd cache hash" "${initrd_hash}" "debug"
display_alert "Mounting chroot for update-initramfs" "update-initramfs" "debug"
deploy_qemu_binary_to_chroot "${chroot_target}" "initrd"# is undeployed at the end of this function
mount_chroot "$chroot_target/"
if [[ -f "${initrd_cache_file_path}" ]]; then
display_alert "initrd cache hit" "${initrd_cache_key}" "cachehit"
run_host_command_logged cp -v "${initrd_cache_file_path}" "${initrd_file}"
touch "${initrd_cache_file_path}"
if [[ -f "${initrd_cache_last_manifest_filepath}" ]]; then
touch "${initrd_cache_last_manifest_filepath}"
fi
if [[ -d "${chroot_target}"/etc/initramfs/post-update.d/ ]]; then
chroot_custom "$chroot_target" /usr/bin/run-parts -a "${initrd_kern_ver}" -a "/boot/initrd.img-${initrd_kern_ver}" /etc/initramfs/post-update.d/
fi
else
display_alert "Cache miss for initrd cache" "${initrd_cache_key}" "debug"
if [[ -f "${initrd_cache_last_manifest_filepath}" ]]; then
if [[ "${SHOW_DEBUG}" == "yes" ]]; then
display_alert "Showing diff between last and current initrd cache manifests" "initrd" "debug"
run_host_command_logged diff -u --color=always "${initrd_cache_last_manifest_filepath}" "${initrd_cache_current_manifest_filepath}" "|| true"
fi
fi
display_alert "Updating initramfs..." "$update_initramfs_cmd" ""
chroot_custom_long_running "$chroot_target" "$update_initramfs_cmd" "${logging_filter}"
display_alert "Updated initramfs." "${update_initramfs_cmd}" "info"
display_alert "Storing initrd in cache" "${initrd_cache_key}" "debug"
run_host_command_logged cp -v "${initrd_file}" "${initrd_cache_file_path}"
run_host_command_logged cp -v "${initrd_cache_current_manifest_filepath}" "${initrd_cache_last_manifest_filepath}"
if [[ "${SHOW_DEBUG}" == "yes" ]]; then
display_alert "Showing which initrd caches would be removed/expired" "initrd" "debug"
find "${SRC}/cache/initrd" -type f -printf "%T@ %p\\n" | sort -n -r | sed "1,80d"
fi
find "${SRC}/cache/initrd" -type f -printf "%T@ %p\\n" | sort -n -r | sed "1,80d" | xargs rm -fv
fi
display_alert "Re-enabling" "initramfs-tools hook for kernel"
chroot_custom "$chroot_target" chmod -v +x /etc/kernel/postinst.d/initramfs-tools
display_alert "Unmounting chroot" "update-initramfs" "debug"
umount_chroot "${chroot_target}/"
undeploy_qemu_binary_from_chroot "${chroot_target}" "initrd"
return 0
}