Проблема: когда мы в ArchLinux и производных дистрибутивах обновляем ядро и если поменялась минорная цифра сменилась, то меняется и директория для модулей, а старая удаляется. В результате чего после обновления вы или сразу должны перезагрузиться с новым ядром или получать эпичные глюки: флешка там не примонтируется или ещё чего.
Очевидное решение: временно сохранить текущую диреторию для ядра. Почистить потом можно, на загрузке, к примеру.
Решение ниже - хуки для pacman, которое это делают.
Сами хуки, их два.
Первый, /etc/pacman/hooks/backup-current-kernel-modules-post.hook
:
[Trigger]
Type = Package
Operation = Upgrade
Target = linux[0-9]*
[Action]
Description = Kernel update detected. Restore current Kernel modules from backup
Depends = rsync
When = PostTransaction
Exec = /home/hatred/bin/pacman-backup-current-kernel-modules post
Второй, /etc/pacman/hooks/backup-current-kernel-modules-pre.hook
:
[Trigger]
Type = Package
Operation = Upgrade
Target = linux[0-9]*
[Action]
Description = Kernel update detected. Backup current Kernel modules
Depends = rsync
When = PreTransaction
Exec = /home/hatred/bin/pacman-backup-current-kernel-modules pre
Ну и сам скрипт, /home/hatred/bin/pacman-backup-current-kernel-modules
:
#!/usr/bin/env bash
# man pacman-hooks
# TBD: detect suffix automatically
suffix="-MANJARO"
mods="/lib/modules"
ver=$(uname -r)
orig="$mods/$ver"
backup="$mods/backup-$ver"
# Useful for clean-up on startup
flag=".htrd-backup-current-kernel-modules"
# YES/NO, case is a matter
#actual_clean="NO"
backup()
{
rsync -a $orig/ $backup
touch $backup/$flag
}
restore()
{
rsync -a $backup/ $orig
depmod -aA
}
clean()
{
local installed=($(pacman -Q | grep '^linux[0-9]\+ ' | awk '{print $2}'))
local old=$(ls /lib/modules/*/$flag | xargs -I{} dirname {} | xargs -I{} basename {})
for dir in $old
do
local ver_only=$(basename $dir $suffix)
if [[ ! " ${installed[*]} " =~ " ${ver_only} " ]]; then
echo "Directory flagged as backup and not found in installed, remove: $dir"
if [ "$actual_clean" = "YES" ]; then
true
#rm -rf "$mods/$dir"
fi
fi
done
}
case "$1" in
pre)
backup
;;
post)
restore
;;
clean)
clean
;;
esac
exit 0
С параметром clean
его вызвать можно на старте, например, из /etc/rc.local
(
rc-local).