Compare commits

...

No commits in common. "c8" and "c9-beta" have entirely different histories.
c8 ... c9-beta

40 changed files with 4465 additions and 3301 deletions

6
.gitignore vendored
View File

@ -1,3 +1,3 @@
SOURCES/1.7.2.tar.gz SOURCES/eppic-e8844d3.tar.gz
SOURCES/eppic_050615.tar.gz SOURCES/kexec-tools-2.0.27.tar.xz
SOURCES/kexec-tools-2.0.26.tar.xz SOURCES/makedumpfile-1.7.4.tar.gz

View File

@ -1,3 +1,3 @@
24bce02cd42cdbb960ada4d9e733355582e35784 SOURCES/1.7.2.tar.gz 80ac3f5e77d3c79883edadf14428734db4720009 SOURCES/eppic-e8844d3.tar.gz
a096c8e0892b559f40b01916aae240652f75b68a SOURCES/eppic_050615.tar.gz ed15f191adee22ab0721ba62af1cae67eb981670 SOURCES/kexec-tools-2.0.27.tar.xz
27cea5d032ec1e93506b8110222420abf754df2d SOURCES/kexec-tools-2.0.26.tar.xz 98cae2b1062871905795918c32b6d46ccd115074 SOURCES/makedumpfile-1.7.4.tar.gz

31
SOURCES/60-fadump.install Executable file
View File

@ -0,0 +1,31 @@
#!/usr/bin/bash
COMMAND="$1"
KERNEL_VERSION="$2"
if ! [[ ${KERNEL_INSTALL_MACHINE_ID-x} ]]; then
exit 0
fi
# Currently, fadump is supported only in environments with
# writable /boot directory.
if [[ ! -w "/boot" ]]; then
exit 0
fi
FADUMP_INITRD="/boot/.initramfs-${KERNEL_VERSION}.img.default"
FADUMP_INITRD_CHECKSUM="$FADUMP_INITRD.checksum"
ret=0
case "$COMMAND" in
add)
# Do nothing, fadump initramfs is strictly host only
# and managed by kdump service
;;
remove)
rm -f -- "$FADUMP_INITRD"
rm -f -- "$FADUMP_INITRD_CHECKSUM"
ret=$?
;;
esac
exit $ret

13
SOURCES/92-crashkernel.install Executable file
View File

@ -0,0 +1,13 @@
#!/usr/bin/bash
COMMAND="$1"
KERNEL_VERSION="$2"
KDUMP_INITRD_DIR_ABS="$3"
KERNEL_IMAGE="$4"
case "$COMMAND" in
add)
kdumpctl _reset-crashkernel-for-installed_kernel "$KERNEL_VERSION"
exit 0
;;
esac

View File

@ -17,6 +17,6 @@ GOTO="kdump_reload_end"
LABEL="kdump_reload_cpu" LABEL="kdump_reload_cpu"
RUN+="/bin/sh -c '/usr/bin/systemctl is-active kdump.service || exit 0; ! test -f /sys/kernel/fadump_enabled || cat /sys/kernel/fadump_enabled | grep 0 || exit 0; /usr/bin/systemd-run --quiet --no-block /usr/lib/udev/kdump-udev-throttler'" RUN+="/bin/sh -c '/usr/bin/systemctl is-active kdump.service || exit 0; ! test -f /sys/kernel/fadump/enabled || cat /sys/kernel/fadump/enabled | grep 0 || exit 0; /usr/bin/systemd-run --quiet --no-block /usr/lib/udev/kdump-udev-throttler'"
LABEL="kdump_reload_end" LABEL="kdump_reload_end"

View File

@ -0,0 +1,120 @@
Introduction
============
This document describes features the kexec-tools package provides for setting
and estimating the crashkernel value.
Kdump lives in a pre-reserved chunk of memory, and the size of the reserved
memory is specified by the `crashkernel=` kernel parameter. It's hard to
estimate an accurate `crashkernel=` value, so it's always recommended to test
kdump after you updated the `crashkernel=` value or changed the dump target.
Default crashkernel value
=========================
Latest kexec-tools provides "kdumpctl get-default-crashkernel" to retrieve
the default crashkernel value,
$ echo $(kdumpctl get-default-crashkernel)
1G-4G:192M,4G-64G:256M,64G-:512M
It will be taken as the default value of 'crashkernel=', you can use
this value as a reference for setting crashkernel value manually.
New installed system
====================
Anaconda is the OS installer which sets all the kernel boot cmdline on a newly
installed system. If kdump is enabled during Anaconda installation, Anaconda
will use the default crashkernel value as the default `crashkernel=` value on
the newly installed system.
Users can override the value during Anaconda installation manually.
Auto update of crashkernel boot parameter
=========================================
A new release of kexec-tools could update the default crashkernel value. By
default, kexec-tools would reset crashkernel to the new default value if it
detects the old default crashkernel value is used by installed kernels. If you
don't want kexec-tools to update the old default crashkernel to the new default
crashkernel, you can change auto_reset_crashkernel to no in kdump.conf.
Supported Bootloaders
---------------------
This auto update only works with GRUB2 and ZIPL, as kexec-tools heavily depends
on `grubby`. If other boot loaders are used, the user will have to update the
`crashkernel=` value manually.
Reset crashkernel to default value
==================================
kexec-tools only perform the auto update of crashkernel value when it can
confirm the boot kernel's crashkernel value is using its corresponding default
value and auto_reset_crashkernel=yes in kdump.conf. In other cases, the user
can reset the crashkernel value by themselves.
Reset using kdumpctl
--------------------
To make it easier to reset the `crashkernel=` kernel cmdline to this default
value properly, `kdumpctl` also provides a sub-command:
`kdumpctl reset-crashkernel [--kernel=path_to_kernel] [--reboot]`
This command will reset the bootloader's kernel cmdline to the default value.
It will also update bootloader config if the bootloader has a standalone config
file. User will have to reboot the machine after this command to make it take
effect if --reboot is not specified. For more details, please refer to the
reset-crashkernel command in `man kdumpctl`.
Reset manually
--------------
To reset the crashkernel value manually, it's recommended to use utils like
`grubby`. A one liner script for resetting `crashkernel=` value of all installed
kernels to the default value is:
grubby --update-kernel ALL --args "crashkernel=$(kdumpctl get-default-crashkernel)"
NOTE: On s390x you also need to run zipl for the change to take effect.
Estimate crashkernel
====================
The best way to estimate a usable crashkernel value is by testing kdump
manually. And you can set crashkernel to a large value, then adjust the
crashkernel value to an acceptable value gradually.
`kdumpctl` also provides a sub-command for doing rough estimating without
triggering kdump:
`kdumpctl estimate`
The output will be like this:
```
Encrypted kdump target requires extra memory, assuming using the keyslot with minimum memory requirement
Reserved crashkernel: 256M
Recommended crashkernel: 655M
Kernel image size: 47M
Kernel modules size: 12M
Initramfs size: 19M
Runtime reservation: 64M
LUKS required size: 512M
Large modules:
xfs: 1892352
nouveau: 2318336
WARNING: Current crashkernel size is lower than recommended size 655M.
```
It will generate a summary report about the estimated memory consumption
of each component of kdump. The value may not be accurate enough, but
would be a good start for finding a suitable crashkernel value.

View File

@ -6,9 +6,8 @@ KDUMP_KERNEL=""
KDUMP_INITRD="" KDUMP_INITRD=""
check() { check() {
if [ ! -f /etc/sysconfig/kdump ] || [ ! -f /lib/kdump/kdump-lib.sh ]\ if [[ ! -f /etc/sysconfig/kdump ]] || [[ ! -f /lib/kdump/kdump-lib.sh ]] \
|| [ -n "${IN_KDUMP}" ] || [[ -n ${IN_KDUMP} ]]; then
then
return 1 return 1
fi fi
return 255 return 255
@ -25,7 +24,7 @@ prepare_kernel_initrd() {
prepare_kdump_bootinfo prepare_kdump_bootinfo
# $kernel is a variable from dracut # $kernel is a variable from dracut
if [ "$KDUMP_KERNELVER" != $kernel ]; then if [[ $KDUMP_KERNELVER != "$kernel" ]]; then
dwarn "Using kernel version '$KDUMP_KERNELVER' for early kdump," \ dwarn "Using kernel version '$KDUMP_KERNELVER' for early kdump," \
"but the initramfs is generated for kernel version '$kernel'" "but the initramfs is generated for kernel version '$kernel'"
fi fi
@ -33,12 +32,12 @@ prepare_kernel_initrd() {
install() { install() {
prepare_kernel_initrd prepare_kernel_initrd
if [ ! -f "$KDUMP_KERNEL" ]; then if [[ ! -f $KDUMP_KERNEL ]]; then
derror "Could not find required kernel for earlykdump," \ derror "Could not find required kernel for earlykdump," \
"earlykdump will not work!" "earlykdump will not work!"
return 1 return 1
fi fi
if [ ! -f "$KDUMP_INITRD" ]; then if [[ ! -f $KDUMP_INITRD ]]; then
derror "Could not find required kdump initramfs for earlykdump," \ derror "Could not find required kdump initramfs for earlykdump," \
"please ensure kdump initramfs is generated first," \ "please ensure kdump initramfs is generated first," \
"earlykdump will not work!" "earlykdump will not work!"
@ -51,7 +50,9 @@ install() {
inst_binary "/usr/bin/gawk" "/usr/bin/awk" inst_binary "/usr/bin/gawk" "/usr/bin/awk"
inst_binary "/usr/bin/logger" "/usr/bin/logger" inst_binary "/usr/bin/logger" "/usr/bin/logger"
inst_binary "/usr/bin/printf" "/usr/bin/printf" inst_binary "/usr/bin/printf" "/usr/bin/printf"
inst_binary "/usr/bin/xargs" "/usr/bin/xargs"
inst_script "/lib/kdump/kdump-lib.sh" "/lib/kdump-lib.sh" inst_script "/lib/kdump/kdump-lib.sh" "/lib/kdump-lib.sh"
inst_script "/lib/kdump/kdump-lib-initramfs.sh" "/lib/kdump/kdump-lib-initramfs.sh"
inst_script "/lib/kdump/kdump-logger.sh" "/lib/kdump-logger.sh" inst_script "/lib/kdump/kdump-logger.sh" "/lib/kdump-logger.sh"
inst_hook cmdline 00 "$moddir/early-kdump.sh" inst_hook cmdline 00 "$moddir/early-kdump.sh"
inst_binary "$KDUMP_KERNEL" inst_binary "$KDUMP_KERNEL"

View File

@ -14,9 +14,8 @@ EARLY_KEXEC_ARGS=""
. /lib/kdump-lib.sh . /lib/kdump-lib.sh
. /lib/kdump-logger.sh . /lib/kdump-logger.sh
#initiate the kdump logger # initiate the kdump logger
dlog_init if ! dlog_init; then
if [ $? -ne 0 ]; then
echo "failed to initiate the kdump logger." echo "failed to initiate the kdump logger."
exit 1 exit 1
fi fi
@ -30,8 +29,7 @@ prepare_parameters()
early_kdump_load() early_kdump_load()
{ {
check_kdump_feasibility if ! check_kdump_feasibility; then
if [ $? -ne 0 ]; then
return 1 return 1
fi fi
@ -40,8 +38,7 @@ early_kdump_load()
return 1 return 1
fi fi
check_current_kdump_status if is_kernel_loaded "kdump"; then
if [ $? == 0 ]; then
return 1 return 1
fi fi
@ -56,10 +53,9 @@ early_kdump_load()
--command-line=$EARLY_KDUMP_CMDLINE --initrd=$EARLY_KDUMP_INITRD \ --command-line=$EARLY_KDUMP_CMDLINE --initrd=$EARLY_KDUMP_INITRD \
$EARLY_KDUMP_KERNEL" $EARLY_KDUMP_KERNEL"
$KEXEC ${EARLY_KEXEC_ARGS} $standard_kexec_args \ if $KEXEC $EARLY_KEXEC_ARGS $standard_kexec_args \
--command-line="$EARLY_KDUMP_CMDLINE" \ --command-line="$EARLY_KDUMP_CMDLINE" \
--initrd=$EARLY_KDUMP_INITRD $EARLY_KDUMP_KERNEL --initrd=$EARLY_KDUMP_INITRD $EARLY_KDUMP_KERNEL; then
if [ $? == 0 ]; then
dinfo "kexec: loaded early-kdump kernel" dinfo "kexec: loaded early-kdump kernel"
return 0 return 0
else else

View File

@ -1,27 +1,26 @@
# This file is part of systemd. # This service will run the real kdump error handler code. Executing the
# # failure action configured in kdump.conf
# systemd is free software; you can redistribute it and/or modify it
# under the terms of the GNU Lesser General Public License as published by
# the Free Software Foundation; either version 2.1 of the License, or
# (at your option) any later version.
# This service will be placed in kdump initramfs and replace both the systemd
# emergency service and dracut emergency shell. IOW, any emergency will be
# kick this service and in turn isolating to kdump error handler.
[Unit] [Unit]
Description=Kdump Emergency Description=Kdump Error Handler
DefaultDependencies=no DefaultDependencies=no
IgnoreOnIsolate=yes After=systemd-vconsole-setup.service
Wants=systemd-vconsole-setup.service
[Service] [Service]
ExecStart=/usr/bin/systemctl --no-block isolate kdump-error-handler.service Environment=HOME=/
Environment=DRACUT_SYSTEMD=1
Environment=NEWROOT=/sysroot
WorkingDirectory=/
ExecStart=/bin/kdump.sh --error-handler
ExecStopPost=-/bin/rm -f -- /.console_lock
Type=oneshot Type=oneshot
StandardInput=tty-force StandardInput=tty-force
StandardOutput=inherit StandardOutput=inherit
StandardError=inherit StandardError=inherit
KillMode=process KillMode=process
IgnoreSIGPIPE=no IgnoreSIGPIPE=no
TasksMax=infinity
# Bash ignores SIGTERM, so we send SIGHUP instead, to ensure that bash # Bash ignores SIGTERM, so we send SIGHUP instead, to ensure that bash
# terminates cleanly. # terminates cleanly.

View File

@ -1,33 +0,0 @@
# This file is part of systemd.
#
# systemd is free software; you can redistribute it and/or modify it
# under the terms of the GNU Lesser General Public License as published by
# the Free Software Foundation; either version 2.1 of the License, or
# (at your option) any later version.
# This service will run the real kdump error handler code. Executing the
# failure action configured in kdump.conf
[Unit]
Description=Kdump Error Handler
DefaultDependencies=no
After=systemd-vconsole-setup.service
Wants=systemd-vconsole-setup.service
AllowIsolate=yes
[Service]
Environment=HOME=/
Environment=DRACUT_SYSTEMD=1
Environment=NEWROOT=/sysroot
WorkingDirectory=/
ExecStart=/bin/kdump-error-handler.sh
Type=oneshot
StandardInput=tty-force
StandardOutput=inherit
StandardError=inherit
KillMode=process
IgnoreSIGPIPE=no
# Bash ignores SIGTERM, so we send SIGHUP instead, to ensure that bash
# terminates cleanly.
KillSignal=SIGHUP

View File

@ -1,10 +0,0 @@
#!/bin/sh
. /lib/kdump-lib-initramfs.sh
set -o pipefail
export PATH=$PATH:$KDUMP_SCRIPT_DIR
get_kdump_confs
do_failure_action
do_final_action

View File

@ -1,22 +1,311 @@
#!/bin/sh #!/bin/sh
#
# continue here only if we have to save dump. # The main kdump routine in capture kernel, bash may not be the
if [ -f /etc/fadump.initramfs ] && [ ! -f /proc/device-tree/rtas/ibm,kernel-dump ] && [ ! -f /proc/device-tree/ibm,opal/dump/mpipl-boot ]; then # default shell. Any code added must be POSIX compliant.
exit 0
fi
. /lib/dracut-lib.sh . /lib/dracut-lib.sh
. /lib/kdump-logger.sh
. /lib/kdump-lib-initramfs.sh . /lib/kdump-lib-initramfs.sh
set -o pipefail #initiate the kdump logger
if ! dlog_init; then
echo "failed to initiate the kdump logger."
exit 1
fi
KDUMP_PATH="/var/crash"
KDUMP_LOG_FILE="/run/initramfs/kexec-dmesg.log"
CORE_COLLECTOR=""
DEFAULT_CORE_COLLECTOR="makedumpfile -l --message-level 7 -d 31"
DMESG_COLLECTOR="/sbin/vmcore-dmesg"
FAILURE_ACTION="systemctl reboot -f"
DATEDIR=$(date +%Y-%m-%d-%T)
HOST_IP='127.0.0.1'
DUMP_INSTRUCTION=""
SSH_KEY_LOCATION="/root/.ssh/kdump_id_rsa"
DD_BLKSIZE=512
FINAL_ACTION="systemctl reboot -f"
KDUMP_PRE=""
KDUMP_POST=""
NEWROOT="/sysroot"
OPALCORE="/sys/firmware/opal/mpipl/core"
KDUMP_CONF_PARSED="/tmp/kdump.conf.$$"
# POSIX doesn't have pipefail, only apply when using bash
# shellcheck disable=SC3040
[ -n "$BASH" ] && set -o pipefail
DUMP_RETVAL=0 DUMP_RETVAL=0
export PATH=$PATH:$KDUMP_SCRIPT_DIR kdump_read_conf > $KDUMP_CONF_PARSED
get_kdump_confs()
{
while read -r config_opt config_val; do
# remove inline comments after the end of a directive.
case "$config_opt" in
path)
KDUMP_PATH="$config_val"
;;
core_collector)
[ -n "$config_val" ] && CORE_COLLECTOR="$config_val"
;;
sshkey)
if [ -f "$config_val" ]; then
SSH_KEY_LOCATION=$config_val
fi
;;
kdump_pre)
KDUMP_PRE="$config_val"
;;
kdump_post)
KDUMP_POST="$config_val"
;;
fence_kdump_args)
FENCE_KDUMP_ARGS="$config_val"
;;
fence_kdump_nodes)
FENCE_KDUMP_NODES="$config_val"
;;
failure_action | default)
case $config_val in
shell)
FAILURE_ACTION="kdump_emergency_shell"
;;
reboot)
FAILURE_ACTION="systemctl reboot -f && exit"
;;
halt)
FAILURE_ACTION="halt && exit"
;;
poweroff)
FAILURE_ACTION="systemctl poweroff -f && exit"
;;
dump_to_rootfs)
FAILURE_ACTION="dump_to_rootfs"
;;
esac
;;
final_action)
case $config_val in
reboot)
FINAL_ACTION="systemctl reboot -f"
;;
halt)
FINAL_ACTION="halt"
;;
poweroff)
FINAL_ACTION="systemctl poweroff -f"
;;
esac
;;
esac
done < "$KDUMP_CONF_PARSED"
if [ -z "$CORE_COLLECTOR" ]; then
CORE_COLLECTOR="$DEFAULT_CORE_COLLECTOR"
if is_ssh_dump_target || is_raw_dump_target; then
CORE_COLLECTOR="$CORE_COLLECTOR -F"
fi
fi
}
# store the kexec kernel log to a file.
save_log()
{
dmesg -T > $KDUMP_LOG_FILE
if command -v journalctl > /dev/null; then
journalctl -ab >> $KDUMP_LOG_FILE
fi
chmod 600 $KDUMP_LOG_FILE
}
# $1: dump path, must be a mount point
dump_fs()
{
ddebug "dump_fs _mp=$1"
if ! is_mounted "$1"; then
dinfo "dump path '$1' is not mounted, trying to mount..."
if ! mount --target "$1"; then
derror "failed to dump to '$1', it's not a mount point!"
return 1
fi
fi
# Remove -F in makedumpfile case. We don't want a flat format dump here.
case $CORE_COLLECTOR in
*makedumpfile*)
CORE_COLLECTOR=$(echo "$CORE_COLLECTOR" | sed -e "s/-F//g")
;;
esac
_dump_fs_path=$(echo "$1/$KDUMP_PATH/$HOST_IP-$DATEDIR/" | tr -s /)
dinfo "saving to $_dump_fs_path"
# Only remount to read-write mode if the dump target is mounted read-only.
_dump_mnt_op=$(get_mount_info OPTIONS target "$1" -f)
case $_dump_mnt_op in
ro*)
dinfo "Remounting the dump target in rw mode."
mount -o remount,rw "$1" || return 1
;;
esac
mkdir -p "$_dump_fs_path" || return 1
save_vmcore_dmesg_fs ${DMESG_COLLECTOR} "$_dump_fs_path"
save_opalcore_fs "$_dump_fs_path"
dinfo "saving vmcore"
$CORE_COLLECTOR /proc/vmcore "$_dump_fs_path/vmcore-incomplete"
_dump_exitcode=$?
if [ $_dump_exitcode -eq 0 ]; then
sync -f "$_dump_fs_path/vmcore-incomplete"
_sync_exitcode=$?
if [ $_sync_exitcode -eq 0 ]; then
mv "$_dump_fs_path/vmcore-incomplete" "$_dump_fs_path/vmcore"
dinfo "saving vmcore complete"
else
derror "sync vmcore failed, exitcode:$_sync_exitcode"
return 1
fi
else
derror "saving vmcore failed, exitcode:$_dump_exitcode"
fi
dinfo "saving the $KDUMP_LOG_FILE to $_dump_fs_path/"
save_log
mv "$KDUMP_LOG_FILE" "$_dump_fs_path/"
if [ $_dump_exitcode -ne 0 ]; then
return 1
fi
# improper kernel cmdline can cause the failure of echo, we can ignore this kind of failure
return 0
}
# $1: dmesg collector
# $2: dump path
save_vmcore_dmesg_fs()
{
dinfo "saving vmcore-dmesg.txt to $2"
if $1 /proc/vmcore > "$2/vmcore-dmesg-incomplete.txt"; then
mv "$2/vmcore-dmesg-incomplete.txt" "$2/vmcore-dmesg.txt"
chmod 600 "$2/vmcore-dmesg.txt"
# Make sure file is on disk. There have been instances where later
# saving vmcore failed and system rebooted without sync and there
# was no vmcore-dmesg.txt available.
sync
dinfo "saving vmcore-dmesg.txt complete"
else
if [ -f "$2/vmcore-dmesg-incomplete.txt" ]; then
chmod 600 "$2/vmcore-dmesg-incomplete.txt"
fi
derror "saving vmcore-dmesg.txt failed"
fi
}
# $1: dump path
save_opalcore_fs()
{
if [ ! -f $OPALCORE ]; then
# Check if we are on an old kernel that uses a different path
if [ -f /sys/firmware/opal/core ]; then
OPALCORE="/sys/firmware/opal/core"
else
return 0
fi
fi
dinfo "saving opalcore:$OPALCORE to $1/opalcore"
if ! cp $OPALCORE "$1/opalcore"; then
derror "saving opalcore failed"
return 1
fi
sync
dinfo "saving opalcore complete"
return 0
}
dump_to_rootfs()
{
if [ "$(systemctl status dracut-initqueue | sed -n "s/^\s*Active: \(\S*\)\s.*$/\1/p")" = "inactive" ]; then
dinfo "Trying to bring up initqueue for rootfs mount"
systemctl start dracut-initqueue
fi
dinfo "Clean up dead systemd services"
systemctl cancel
dinfo "Waiting for rootfs mount, will timeout after 90 seconds"
systemctl start --no-block sysroot.mount
_loop=0
while [ $_loop -lt 90 ] && ! is_mounted /sysroot; do
sleep 1
_loop=$((_loop + 1))
done
if ! is_mounted /sysroot; then
derror "Failed to mount rootfs"
return
fi
ddebug "NEWROOT=$NEWROOT"
dump_fs $NEWROOT
}
kdump_emergency_shell()
{
ddebug "Switching to kdump emergency shell..."
[ -f /etc/profile ] && . /etc/profile
export PS1='kdump:${PWD}# '
. /lib/dracut-lib.sh
if [ -f /dracut-state.sh ]; then
. /dracut-state.sh 2> /dev/null
fi
source_conf /etc/conf.d
type plymouth > /dev/null 2>&1 && plymouth quit
source_hook "emergency"
while read -r _tty rest; do
(
echo
echo
echo 'Entering kdump emergency mode.'
echo 'Type "journalctl" to view system logs.'
echo 'Type "rdsosreport" to generate a sosreport, you can then'
echo 'save it elsewhere and attach it to a bug report.'
echo
echo
) > "/dev/$_tty"
done < /proc/consoles
sh -i -l
/bin/rm -f -- /.console_lock
}
do_failure_action()
{
dinfo "Executing failure action $FAILURE_ACTION"
eval $FAILURE_ACTION
}
do_final_action()
{
dinfo "Executing final action $FINAL_ACTION"
eval $FINAL_ACTION
}
do_dump() do_dump()
{ {
local _ret
eval $DUMP_INSTRUCTION eval $DUMP_INSTRUCTION
_ret=$? _ret=$?
@ -29,8 +318,6 @@ do_dump()
do_kdump_pre() do_kdump_pre()
{ {
local _ret
if [ -n "$KDUMP_PRE" ]; then if [ -n "$KDUMP_PRE" ]; then
"$KDUMP_PRE" "$KDUMP_PRE"
_ret=$? _ret=$?
@ -55,8 +342,6 @@ do_kdump_pre()
do_kdump_post() do_kdump_post()
{ {
local _ret
if [ -d /etc/kdump/post.d ]; then if [ -d /etc/kdump/post.d ]; then
for file in /etc/kdump/post.d/*; do for file in /etc/kdump/post.d/*; do
"$file" "$1" "$file" "$1"
@ -76,110 +361,87 @@ do_kdump_post()
fi fi
} }
add_dump_code() # $1: block target, eg. /dev/sda
{
DUMP_INSTRUCTION=$1
}
dump_raw() dump_raw()
{ {
local _raw=$1 [ -b "$1" ] || return 1
[ -b "$_raw" ] || return 1 dinfo "saving to raw disk $1"
dinfo "saving to raw disk $_raw" if ! echo "$CORE_COLLECTOR" | grep -q makedumpfile; then
_src_size=$(stat --format %s /proc/vmcore)
if ! $(echo -n $CORE_COLLECTOR|grep -q makedumpfile); then _src_size_mb=$((_src_size / 1048576))
_src_size=`ls -l /proc/vmcore | cut -d' ' -f5` /kdumpscripts/monitor_dd_progress $_src_size_mb &
_src_size_mb=$(($_src_size / 1048576))
monitor_dd_progress $_src_size_mb &
fi fi
dinfo "saving vmcore" dinfo "saving vmcore"
$CORE_COLLECTOR /proc/vmcore | dd of=$_raw bs=$DD_BLKSIZE >> /tmp/dd_progress_file 2>&1 || return 1 $CORE_COLLECTOR /proc/vmcore | dd of="$1" bs=$DD_BLKSIZE >> /tmp/dd_progress_file 2>&1 || return 1
sync sync
dinfo "saving vmcore complete" dinfo "saving vmcore complete"
return 0 return 0
} }
# $1: ssh key file
# $2: ssh address in <user>@<host> format
dump_ssh() dump_ssh()
{ {
local _ret=0 _ret=0
local _exitcode=0 _exitcode2=0 _ssh_opt="-i $1 -o BatchMode=yes -o StrictHostKeyChecking=yes"
local _opt="-i $1 -o BatchMode=yes -o StrictHostKeyChecking=yes" _ssh_dir="$KDUMP_PATH/$HOST_IP-$DATEDIR"
local _dir="$KDUMP_PATH/$HOST_IP-$DATEDIR" if is_ipv6_address "$2"; then
local _host=$2 _scp_address=${2%@*}@"[${2#*@}]"
local _vmcore="vmcore" else
local _ipv6_addr="" _username="" _scp_address=$2
fi
dinfo "saving to $_host:$_dir" dinfo "saving to $2:$_ssh_dir"
cat /var/lib/random-seed > /dev/urandom cat /var/lib/random-seed > /dev/urandom
ssh -q $_opt $_host mkdir -p $_dir || return 1 ssh -q $_ssh_opt "$2" mkdir -p "$_ssh_dir" || return 1
save_vmcore_dmesg_ssh ${DMESG_COLLECTOR} ${_dir} "${_opt}" $_host
save_opalcore_ssh ${_dir} "${_opt}" $_host
save_vmcore_dmesg_ssh "$DMESG_COLLECTOR" "$_ssh_dir" "$_ssh_opt" "$2"
dinfo "saving vmcore" dinfo "saving vmcore"
if is_ipv6_address "$_host"; then save_opalcore_ssh "$_ssh_dir" "$_ssh_opt" "$2" "$_scp_address"
_username=${_host%@*}
_ipv6_addr="[${_host#*@}]"
fi
if [ "${CORE_COLLECTOR%%[[:blank:]]*}" = "scp" ]; then if [ "${CORE_COLLECTOR%%[[:blank:]]*}" = "scp" ]; then
if [ -n "$_username" ] && [ -n "$_ipv6_addr" ]; then scp -q $_ssh_opt /proc/vmcore "$_scp_address:$_ssh_dir/vmcore-incomplete"
scp -q $_opt /proc/vmcore "$_username@$_ipv6_addr:$_dir/vmcore-incomplete" _ret=$?
_vmcore="vmcore"
else else
scp -q $_opt /proc/vmcore "$_host:$_dir/vmcore-incomplete" $CORE_COLLECTOR /proc/vmcore | ssh $_ssh_opt "$2" "umask 0077 && dd bs=512 of='$_ssh_dir/vmcore-incomplete'"
fi _ret=$?
_exitcode=$?
else
$CORE_COLLECTOR /proc/vmcore | ssh $_opt $_host "umask 0077 && dd bs=512 of=$_dir/vmcore-incomplete"
_exitcode=$?
_vmcore="vmcore.flat" _vmcore="vmcore.flat"
fi fi
if [ $_exitcode -eq 0 ]; then if [ $_ret -eq 0 ]; then
ssh $_opt $_host "mv $_dir/vmcore-incomplete $_dir/$_vmcore" ssh $_ssh_opt "$2" "mv '$_ssh_dir/vmcore-incomplete' '$_ssh_dir/$_vmcore'"
_exitcode2=$? _ret=$?
if [ $_exitcode2 -ne 0 ]; then if [ $_ret -ne 0 ]; then
derror "moving vmcore failed, _exitcode:$_exitcode2" derror "moving vmcore failed, exitcode:$_ret"
else else
dinfo "saving vmcore complete" dinfo "saving vmcore complete"
fi fi
else else
derror "saving vmcore failed, _exitcode:$_exitcode" derror "saving vmcore failed, exitcode:$_ret"
fi fi
dinfo "saving the $KDUMP_LOG_FILE to $_host:$_dir/" dinfo "saving the $KDUMP_LOG_FILE to $2:$_ssh_dir/"
save_log save_log
if [ -n "$_username" ] && [ -n "$_ipv6_addr" ]; then if ! scp -q $_ssh_opt $KDUMP_LOG_FILE "$_scp_address:$_ssh_dir/"; then
scp -q $_opt $KDUMP_LOG_FILE "$_username@$_ipv6_addr:$_dir/"
else
scp -q $_opt $KDUMP_LOG_FILE "$_host:$_dir/"
fi
_ret=$?
if [ $_ret -ne 0 ]; then
derror "saving log file failed, _exitcode:$_ret" derror "saving log file failed, _exitcode:$_ret"
fi fi
if [ $_exitcode -ne 0 ] || [ $_exitcode2 -ne 0 ];then return $_ret
return 1
fi
return 0
} }
save_opalcore_ssh() { # $1: dump path
local _path=$1 # $2: ssh opts
local _opts="$2" # $3: ssh address in <user>@<host> format
local _location=$3 # $4: scp address, similar with ssh address but IPv6 addresses are quoted
local _user_name="" _ipv6addr="" save_opalcore_ssh()
{
ddebug "_path=$_path _opts=$_opts _location=$_location"
if [ ! -f $OPALCORE ]; then if [ ! -f $OPALCORE ]; then
# Check if we are on an old kernel that uses a different path # Check if we are on an old kernel that uses a different path
if [ -f /sys/firmware/opal/core ]; then if [ -f /sys/firmware/opal/core ]; then
@ -189,120 +451,153 @@ save_opalcore_ssh() {
fi fi
fi fi
if is_ipv6_address "$_host"; then dinfo "saving opalcore:$OPALCORE to $3:$1"
_user_name=${_location%@*}
_ipv6addr="[${_location#*@}]"
fi
dinfo "saving opalcore:$OPALCORE to $_location:$_path" if ! scp $2 $OPALCORE "$4:$1/opalcore-incomplete"; then
if [ -n "$_user_name" ] && [ -n "$_ipv6addr" ]; then
scp $_opts $OPALCORE $_user_name@$_ipv6addr:$_path/opalcore-incomplete
else
scp $_opts $OPALCORE $_location:$_path/opalcore-incomplete
fi
if [ $? -ne 0 ]; then
derror "saving opalcore failed" derror "saving opalcore failed"
return 1 return 1
fi fi
ssh $_opts $_location mv $_path/opalcore-incomplete $_path/opalcore ssh $2 "$3" mv "$1/opalcore-incomplete" "$1/opalcore"
dinfo "saving opalcore complete" dinfo "saving opalcore complete"
return 0 return 0
} }
save_vmcore_dmesg_ssh() { # $1: dmesg collector
local _dmesg_collector=$1 # $2: dump path
local _path=$2 # $3: ssh opts
local _opts="$3" # $4: ssh address in <user>@<host> format
local _location=$4 save_vmcore_dmesg_ssh()
{
dinfo "saving vmcore-dmesg.txt to $_location:$_path" dinfo "saving vmcore-dmesg.txt to $4:$2"
$_dmesg_collector /proc/vmcore | ssh $_opts $_location "umask 0077 && dd of=$_path/vmcore-dmesg-incomplete.txt" if $1 /proc/vmcore | ssh $3 "$4" "umask 0077 && dd of='$2/vmcore-dmesg-incomplete.txt'"; then
_exitcode=$? ssh -q $3 "$4" mv "$2/vmcore-dmesg-incomplete.txt" "$2/vmcore-dmesg.txt"
if [ $_exitcode -eq 0 ]; then
ssh -q $_opts $_location mv $_path/vmcore-dmesg-incomplete.txt $_path/vmcore-dmesg.txt
dinfo "saving vmcore-dmesg.txt complete" dinfo "saving vmcore-dmesg.txt complete"
else else
derror "saving vmcore-dmesg.txt failed" derror "saving vmcore-dmesg.txt failed"
fi fi
} }
get_host_ip() wait_online_network()
{ {
local _host # In some cases, network may still not be ready because nm-online is called
if is_nfs_dump_target || is_ssh_dump_target # with "-s" which means to wait for NetworkManager startup to complete, rather
then # than waiting for network connectivity specifically. Wait 10mins more for the
kdumpnic=$(getarg kdumpnic=) # network to be truely ready in these cases.
[ -z "$kdumpnic" ] && derror "failed to get kdumpnic!" && return 1 _loop=0
_host=`ip addr show dev $kdumpnic|grep '[ ]*inet'` while [ $_loop -lt 600 ]; do
[ $? -ne 0 ] && derror "wrong kdumpnic: $kdumpnic" && return 1 sleep 1
_host=`echo $_host | head -n 1 | cut -d' ' -f2` _loop=$((_loop + 1))
_host="${_host%%/*}" if _route=$(kdump_get_ip_route "$1" 2> /dev/null); then
[ -z "$_host" ] && derror "wrong kdumpnic: $kdumpnic" && return 1 printf "%s" "$_route"
HOST_IP=$_host return
else
dwarn "Waiting for network to be ready (${_loop}s / 10min)"
fi fi
return 0 done
derror "Oops. The network still isn't ready after waiting 10mins."
exit 1
} }
read_kdump_conf() get_host_ip()
{ {
if [ ! -f "$KDUMP_CONF" ]; then
derror "$KDUMP_CONF not found" if ! is_nfs_dump_target && ! is_ssh_dump_target; then
return 0
fi
_kdump_remote_ip=$(getarg kdump_remote_ip=)
if [ -z "$_kdump_remote_ip" ]; then
derror "failed to get remote IP address!"
return 1
fi
if ! _route=$(wait_online_network "$_kdump_remote_ip"); then
return 1
fi
_netdev=$(kdump_get_ip_route_field "$_route" "dev")
if ! _kdumpip=$(ip addr show dev "$_netdev" | grep '[ ]*inet'); then
derror "Failed to get IP of $_netdev"
return 1
fi
_kdumpip=$(echo "$_kdumpip" | head -n 1 | awk '{print $2}')
_kdumpip="${_kdumpip%%/*}"
HOST_IP=$_kdumpip
}
read_kdump_confs()
{
if [ ! -f "$KDUMP_CONFIG_FILE" ]; then
derror "$KDUMP_CONFIG_FILE not found"
return return
fi fi
get_kdump_confs get_kdump_confs
# rescan for add code for dump target # rescan for add code for dump target
while read config_opt config_val; while read -r config_opt config_val; do
do
# remove inline comments after the end of a directive. # remove inline comments after the end of a directive.
case "$config_opt" in case "$config_opt" in
dracut_args) dracut_args)
config_val=$(get_dracut_args_target "$config_val") config_val=$(get_dracut_args_target "$config_val")
if [ -n "$config_val" ]; then if [ -n "$config_val" ]; then
config_val=$(get_mntpoint_from_target "$config_val") config_val=$(get_mntpoint_from_target "$config_val")
add_dump_code "dump_fs $config_val" DUMP_INSTRUCTION="dump_fs $config_val"
fi fi
;; ;;
ext[234]|xfs|btrfs|minix|nfs) ext[234] | xfs | btrfs | minix | nfs | virtiofs)
config_val=$(get_mntpoint_from_target "$config_val") config_val=$(get_mntpoint_from_target "$config_val")
add_dump_code "dump_fs $config_val" DUMP_INSTRUCTION="dump_fs $config_val"
;; ;;
raw) raw)
add_dump_code "dump_raw $config_val" DUMP_INSTRUCTION="dump_raw $config_val"
;; ;;
ssh) ssh)
add_dump_code "dump_ssh $SSH_KEY_LOCATION $config_val" DUMP_INSTRUCTION="dump_ssh $SSH_KEY_LOCATION $config_val"
;; ;;
esac esac
done <<< "$(read_strip_comments $KDUMP_CONF)" done < "$KDUMP_CONF_PARSED"
} }
fence_kdump_notify() fence_kdump_notify()
{ {
if [ -n "$FENCE_KDUMP_NODES" ]; then if [ -n "$FENCE_KDUMP_NODES" ]; then
# shellcheck disable=SC2086
$FENCE_KDUMP_SEND $FENCE_KDUMP_ARGS $FENCE_KDUMP_NODES & $FENCE_KDUMP_SEND $FENCE_KDUMP_ARGS $FENCE_KDUMP_NODES &
fi fi
} }
read_kdump_conf if [ "$1" = "--error-handler" ]; then
get_kdump_confs
do_failure_action
do_final_action
exit $?
fi
# continue here only if we have to save dump.
if [ -f /etc/fadump.initramfs ] && [ ! -f /proc/device-tree/rtas/ibm,kernel-dump ] && [ ! -f /proc/device-tree/ibm,opal/dump/mpipl-boot ]; then
exit 0
fi
read_kdump_confs
fence_kdump_notify fence_kdump_notify
get_host_ip if ! get_host_ip; then
if [ $? -ne 0 ]; then
derror "get_host_ip exited with non-zero status!" derror "get_host_ip exited with non-zero status!"
exit 1 exit 1
fi fi
if [ -z "$DUMP_INSTRUCTION" ]; then if [ -z "$DUMP_INSTRUCTION" ]; then
add_dump_code "dump_fs $NEWROOT" DUMP_INSTRUCTION="dump_fs $NEWROOT"
fi fi
do_kdump_pre if ! do_kdump_pre; then
if [ $? -ne 0 ]; then
derror "kdump_pre script exited with non-zero status!" derror "kdump_pre script exited with non-zero status!"
do_final_action do_final_action
# During systemd service to reboot the machine, stop this shell script running # During systemd service to reboot the machine, stop this shell script running
@ -312,8 +607,7 @@ make_trace_mem "kdump saving vmcore" '1:shortmem' '2+:mem' '3+:slab'
do_dump do_dump
DUMP_RETVAL=$? DUMP_RETVAL=$?
do_kdump_post $DUMP_RETVAL if ! do_kdump_post $DUMP_RETVAL; then
if [ $? -ne 0 ]; then
derror "kdump_post script exited with non-zero status!" derror "kdump_post script exited with non-zero status!"
fi fi

File diff suppressed because it is too large Load Diff

View File

@ -39,7 +39,7 @@ kernel are one and the same on ppc64.
If you're reading this document, you should already have kexec-tools If you're reading this document, you should already have kexec-tools
installed. If not, you install it via the following command: installed. If not, you install it via the following command:
# yum install kexec-tools # dnf install kexec-tools
Fadump Operational Flow: Fadump Operational Flow:
@ -82,7 +82,7 @@ How to configure fadump:
Again, we assume if you're reading this document, you should already have Again, we assume if you're reading this document, you should already have
kexec-tools installed. If not, you install it via the following command: kexec-tools installed. If not, you install it via the following command:
# yum install kexec-tools # dnf install kexec-tools
Make the kernel to be configured with FADump as the default boot entry, if Make the kernel to be configured with FADump as the default boot entry, if
it isn't already: it isn't already:
@ -94,20 +94,24 @@ anything interesting in the way of debug analysis, you'll also need to install
the kernel-debuginfo package, of the same arch as your running kernel, and the the kernel-debuginfo package, of the same arch as your running kernel, and the
crash utility: crash utility:
# yum --enablerepo=\*debuginfo install kernel-debuginfo.$(uname -m) crash # dnf --enablerepo=\*debuginfo install kernel-debuginfo.$(uname -m) crash
Next up, we need to modify some boot parameters to enable firmware assisted Next up, we can enable firmware assisted dump and reserve the memory for boot
dump. With the help of grubby, it's very easy to append "fadump=on" to the end memory preservation as specified in in the table of 'FADump Memory Requirements'
of your kernel boot parameters. To reserve the appropriate amount of memory section:
for boot memory preservation, pass 'crashkernel=X' kernel cmdline parameter.
For the recommended value of X, see 'FADump Memory Requirements' section. # kdumpctl reset-crashkernel --fadump=on
Alternatively, you can use grubby to reserve custom amount of memory:
# grubby --args="fadump=on crashkernel=6G" --update-kernel=/boot/vmlinuz-`uname -r` # grubby --args="fadump=on crashkernel=6G" --update-kernel=/boot/vmlinuz-`uname -r`
By default, FADump reserved memory will be initialized as CMA area to make the By default, FADump reserved memory will be initialized as CMA area to make the
memory available through CMA allocator on the production kernel. We can opt out memory available through CMA allocator on the production kernel. We can opt out
of this, making reserved memory unavailable to production kernel, by booting the of this, making reserved memory unavailable to production kernel, by booting the
linux kernel with 'fadump=nocma' instead of 'fadump=on'. linux kernel with 'fadump=nocma' instead of 'fadump=on':
# kdumpctl reset-crashkernel --fadump=nocma
The term 'boot memory' means size of the low memory chunk that is required for The term 'boot memory' means size of the low memory chunk that is required for
a kernel to boot successfully when booted with restricted memory. By default, a kernel to boot successfully when booted with restricted memory. By default,
@ -133,7 +137,7 @@ Then, start up kdump as well:
# systemctl start kdump.service # systemctl start kdump.service
This should turn on the firmware assisted functionality in kernel by This should turn on the firmware assisted functionality in kernel by
echo'ing 1 to /sys/kernel/fadump_registered, leaving the system ready echo'ing 1 to /sys/kernel/fadump/registered, leaving the system ready
to capture a vmcore upon crashing. For journaling filesystems like XFS an to capture a vmcore upon crashing. For journaling filesystems like XFS an
additional step is required to ensure bootloader does not pick the additional step is required to ensure bootloader does not pick the
older initrd (without vmcore capture scripts): older initrd (without vmcore capture scripts):
@ -344,9 +348,12 @@ or
OR OR
# grubby --update-kernel=/boot/vmlinuz-`uname -r` --args="fadump=off" # grubby --update-kernel=/boot/vmlinuz-`uname -r` --args="fadump=off"
If KDump is to be used as the dump capturing mechanism, update the crashkernel Remove "crashkernel=" from kernel cmdline parameters:
parameter (Else, remove "crashkernel=" parameter too, using grubby):
# grubby --update-kernel=/boot/vmlinuz-$kver --args="crashkernl=auto" # grubby --update-kernel=/boot/vmlinuz-`uname -r` --remove-args="crashkernel"
If KDump is to be used as the dump capturing mechanism, reset the crashkernel parameter:
# kdumpctl reset-crashkernel --fadump=off
Reboot the system for the settings to take effect. Reboot the system for the settings to take effect.

View File

@ -1,7 +1,6 @@
#!/bin/bash #!/bin/bash
# $1: target arch # $1: target arch
SED_EXP="" SED_EXP=""
generate() generate()
@ -20,6 +19,12 @@ generate()
# #
# Supported options: # Supported options:
# #
# auto_reset_crashkernel <yes|no>
# - whether to reset kernel crashkernel to new default value
# or not when kexec-tools updates the default crashkernel value and
# existing kernels using the old default kernel crashkernel value.
# The default value is yes.
#
# raw <partition> # raw <partition>
# - Will dd /proc/vmcore into <partition>. # - Will dd /proc/vmcore into <partition>.
# Use persistent device names for partition devices, # Use persistent device names for partition devices,
@ -41,11 +46,12 @@ generate()
# #
# <fs type> <partition> # <fs type> <partition>
# - Will mount -t <fs type> <partition> <mnt>, and copy # - Will mount -t <fs type> <partition> <mnt>, and copy
# /proc/vmcore to <mnt>/<path>/%DATE/. # /proc/vmcore to <mnt>/<path>/%HOST_IP-%DATE/.
# NOTE: <partition> can be a device node, label or uuid. # NOTE: <partition> can be a device node, label or uuid.
# It's recommended to use persistent device names # It's recommended to use persistent device names
# such as /dev/vg/<devname>. # such as /dev/vg/<devname>.
# Otherwise it's suggested to use label or uuid. # Otherwise it's suggested to use label or uuid.
# Supported fs types: ext[234], xfs, btrfs, minix, virtiofs
# #
# path <path> # path <path>
# - "path" represents the file system path in which vmcore # - "path" represents the file system path in which vmcore
@ -174,11 +180,13 @@ generate()
#ext4 /dev/vg/lv_kdump #ext4 /dev/vg/lv_kdump
#ext4 LABEL=/boot #ext4 LABEL=/boot
#ext4 UUID=03138356-5e61-4ab3-b58e-27507ac41937 #ext4 UUID=03138356-5e61-4ab3-b58e-27507ac41937
#virtiofs myfs
#nfs my.server.com:/export/tmp #nfs my.server.com:/export/tmp
#nfs [2001:db8::1:2:3:4]:/export/tmp #nfs [2001:db8::1:2:3:4]:/export/tmp
#ssh user@my.server.com #ssh user@my.server.com
#ssh user@2001:db8::1:2:3:4 #ssh user@2001:db8::1:2:3:4
#sshkey /root/.ssh/kdump_id_rsa #sshkey /root/.ssh/kdump_id_rsa
auto_reset_crashkernel yes
path /var/crash path /var/crash
core_collector makedumpfile -l --message-level 7 -d 31 core_collector makedumpfile -l --message-level 7 -d 31
#core_collector scp #core_collector scp
@ -201,20 +209,20 @@ update_param()
} }
case "$1" in case "$1" in
aarch64) aarch64) ;;
;;
i386) i386) ;;
;;
ppc64) ppc64) ;;
;;
ppc64le) ppc64le) ;;
;;
s390x) s390x)
update_param core_collector \ update_param core_collector \
"makedumpfile -c --message-level 7 -d 31" "makedumpfile -c --message-level 7 -d 31"
;; ;;
x86_64) x86_64) ;;
;;
*) *)
echo "Warning: Unknown architecture '$1', using default kdump.conf template." echo "Warning: Unknown architecture '$1', using default kdump.conf template."
;; ;;

View File

@ -1,248 +1,184 @@
# These variables and functions are useful in 2nd kernel #!/bin/sh
#
# The code in this file will be used in initramfs environment, bash may
# not be the default shell. Any code added must be POSIX compliant.
. /lib/kdump-lib.sh DEFAULT_PATH="/var/crash/"
. /lib/kdump-logger.sh KDUMP_CONFIG_FILE="/etc/kdump.conf"
FENCE_KDUMP_CONFIG_FILE="/etc/sysconfig/fence_kdump"
FENCE_KDUMP_SEND="/usr/libexec/fence_kdump_send"
LVM_CONF="/etc/lvm/lvm.conf"
KDUMP_PATH="/var/crash" # Read kdump config in well formated style
KDUMP_LOG_FILE="/run/initramfs/kexec-dmesg.log" kdump_read_conf()
CORE_COLLECTOR="" {
DEFAULT_CORE_COLLECTOR="makedumpfile -l --message-level 7 -d 31" # Following steps are applied in order: strip trailing comment, strip trailing space,
DMESG_COLLECTOR="/sbin/vmcore-dmesg" # strip heading space, match non-empty line, remove duplicated spaces between conf name and value
FAILURE_ACTION="systemctl reboot -f" [ -f "$KDUMP_CONFIG_FILE" ] && sed -n -e "s/#.*//;s/\s*$//;s/^\s*//;s/\(\S\+\)\s*\(.*\)/\1 \2/p" $KDUMP_CONFIG_FILE
DATEDIR=`date +%Y-%m-%d-%T` }
HOST_IP='127.0.0.1'
DUMP_INSTRUCTION=""
SSH_KEY_LOCATION="/root/.ssh/kdump_id_rsa"
KDUMP_SCRIPT_DIR="/kdumpscripts"
DD_BLKSIZE=512
FINAL_ACTION="systemctl reboot -f"
KDUMP_CONF="/etc/kdump.conf"
KDUMP_PRE=""
KDUMP_POST=""
NEWROOT="/sysroot"
OPALCORE="/sys/firmware/opal/mpipl/core"
#initiate the kdump logger # Retrieves config value defined in kdump.conf
dlog_init # $1: config name, sed regexp compatible
if [ $? -ne 0 ]; then kdump_get_conf_val()
echo "failed to initiate the kdump logger." {
# For lines matching "^\s*$1\s+", remove matched part (config name including space),
# remove tailing comment, space, then store in hold space. Print out the hold buffer on last line.
[ -f "$KDUMP_CONFIG_FILE" ] &&
sed -n -e "/^\s*\($1\)\s\+/{s/^\s*\($1\)\s\+//;s/#.*//;s/\s*$//;h};\${x;p}" $KDUMP_CONFIG_FILE
}
is_mounted()
{
findmnt -k -n "$1" > /dev/null 2>&1
}
# $1: info type
# $2: mount source type
# $3: mount source
# $4: extra args
get_mount_info()
{
__kdump_mnt=$(findmnt -k -n -r -o "$1" "--$2" "$3" $4)
[ -z "$__kdump_mnt" ] && [ -e "/etc/fstab" ] && __kdump_mnt=$(findmnt -s -n -r -o "$1" "--$2" "$3" $4)
echo "$__kdump_mnt"
}
is_ipv6_address()
{
echo "$1" | grep -q ":"
}
is_fs_type_nfs()
{
[ "$1" = "nfs" ] || [ "$1" = "nfs4" ]
}
is_fs_type_virtiofs()
{
[ "$1" = "virtiofs" ]
}
# If $1 contains dracut_args "--mount", return <filesystem type>
get_dracut_args_fstype()
{
echo $1 | grep "\-\-mount" | sed "s/.*--mount .\(.*\)/\1/" | cut -d' ' -f3
}
# If $1 contains dracut_args "--mount", return <device>
get_dracut_args_target()
{
echo $1 | grep "\-\-mount" | sed "s/.*--mount .\(.*\)/\1/" | cut -d' ' -f1
}
get_save_path()
{
__kdump_path=$(kdump_get_conf_val path)
[ -z "$__kdump_path" ] && __kdump_path=$DEFAULT_PATH
# strip the duplicated "/"
echo "$__kdump_path" | tr -s /
}
get_root_fs_device()
{
findmnt -k -f -n -o SOURCE /
}
# Return the current underlying device of a path, ignore bind mounts
get_target_from_path()
{
__kdump_target=$(df "$1" 2> /dev/null | tail -1 | awk '{print $1}')
[ "$__kdump_target" = "/dev/root" ] && [ ! -e /dev/root ] && __kdump_target=$(get_root_fs_device)
echo "$__kdump_target"
}
get_fs_type_from_target()
{
get_mount_info FSTYPE source "$1" -f
}
get_mntpoint_from_target()
{
local SOURCE TARGET
findmnt -k --pairs -o SOURCE,TARGET "$1" | while read line; do
eval "$line"
# omit sources that are bind mounts i.e. they contain a [/path/to/subpath].
if [[ ! "$SOURCE" =~ \[ ]]; then
echo $TARGET
break
fi
done
}
is_ssh_dump_target()
{
kdump_get_conf_val ssh | grep -q @
}
is_raw_dump_target()
{
[ -n "$(kdump_get_conf_val raw)" ]
}
is_virtiofs_dump_target()
{
if [ -n "$(kdump_get_conf_val virtiofs)" ]; then
return 0
fi
if is_fs_type_virtiofs "$(get_dracut_args_fstype "$(kdump_get_conf_val dracut_args)")"; then
return 0
fi
if is_fs_type_virtiofs "$(get_fs_type_from_target "$(get_target_from_path "$(get_save_path)")")"; then
return 0
fi
return 1
}
is_nfs_dump_target()
{
if [ -n "$(kdump_get_conf_val nfs)" ]; then
return 0
fi
if is_fs_type_nfs "$(get_dracut_args_fstype "$(kdump_get_conf_val dracut_args)")"; then
return 0
fi
if is_fs_type_nfs "$(get_fs_type_from_target "$(get_target_from_path "$(get_save_path)")")"; then
return 0
fi
return 1
}
is_fs_dump_target()
{
[ -n "$(kdump_get_conf_val "ext[234]\|xfs\|btrfs\|minix\|virtiofs")" ]
}
is_lvm2_thinp_device()
{
_device_path=$1
_lvm2_thin_device=$(lvm lvs -S 'lv_layout=sparse && lv_layout=thin' \
--nosuffix --noheadings -o vg_name,lv_name "$_device_path" 2> /dev/null)
[ -n "$_lvm2_thin_device" ]
}
kdump_get_ip_route()
{
if ! _route=$(/sbin/ip -o route get to "$1" 2>&1); then
exit 1 exit 1
fi fi
echo "$_route"
}
get_kdump_confs() kdump_get_ip_route_field()
{ {
local config_opt config_val echo "$1" | sed -n -e "s/^.*\<$2\>\s\+\(\S\+\).*$/\1/p"
while read config_opt config_val;
do
# remove inline comments after the end of a directive.
case "$config_opt" in
path)
KDUMP_PATH="$config_val"
;;
core_collector)
[ -n "$config_val" ] && CORE_COLLECTOR="$config_val"
;;
sshkey)
if [ -f "$config_val" ]; then
SSH_KEY_LOCATION=$config_val
fi
;;
kdump_pre)
KDUMP_PRE="$config_val"
;;
kdump_post)
KDUMP_POST="$config_val"
;;
fence_kdump_args)
FENCE_KDUMP_ARGS="$config_val"
;;
fence_kdump_nodes)
FENCE_KDUMP_NODES="$config_val"
;;
failure_action|default)
case $config_val in
shell)
FAILURE_ACTION="kdump_emergency_shell"
;;
reboot)
FAILURE_ACTION="systemctl reboot -f && exit"
;;
halt)
FAILURE_ACTION="halt && exit"
;;
poweroff)
FAILURE_ACTION="systemctl poweroff -f && exit"
;;
dump_to_rootfs)
FAILURE_ACTION="dump_to_rootfs"
;;
esac
;;
final_action)
case $config_val in
reboot)
FINAL_ACTION="systemctl reboot -f"
;;
halt)
FINAL_ACTION="halt"
;;
poweroff)
FINAL_ACTION="systemctl poweroff -f"
;;
esac
;;
esac
done <<< "$(read_strip_comments $KDUMP_CONF)"
if [ -z "$CORE_COLLECTOR" ]; then
CORE_COLLECTOR="$DEFAULT_CORE_COLLECTOR"
if is_ssh_dump_target || is_raw_dump_target; then
CORE_COLLECTOR="$CORE_COLLECTOR -F"
fi
fi
}
# store the kexec kernel log to a file.
save_log()
{
dmesg -T > $KDUMP_LOG_FILE
if command -v journalctl > /dev/null; then
journalctl -ab >> $KDUMP_LOG_FILE
fi
chmod 600 $KDUMP_LOG_FILE
}
# dump_fs <mount point>
dump_fs()
{
local _exitcode
local _mp=$1
ddebug "dump_fs _mp=$_mp"
if ! is_mounted "$_mp"; then
dinfo "dump path \"$_mp\" is not mounted, trying to mount..."
mount --target $_mp
if [ $? -ne 0 ]; then
derror "failed to dump to \"$_mp\", it's not a mount point!"
return 1
fi
fi
# Remove -F in makedumpfile case. We don't want a flat format dump here.
[[ $CORE_COLLECTOR = *makedumpfile* ]] && CORE_COLLECTOR=`echo $CORE_COLLECTOR | sed -e "s/-F//g"`
dinfo "saving to $_mp/$KDUMP_PATH/$HOST_IP-$DATEDIR/"
mount -o remount,rw $_mp || return 1
mkdir -p $_mp/$KDUMP_PATH/$HOST_IP-$DATEDIR || return 1
save_vmcore_dmesg_fs ${DMESG_COLLECTOR} "$_mp/$KDUMP_PATH/$HOST_IP-$DATEDIR/"
save_opalcore_fs "$_mp/$KDUMP_PATH/$HOST_IP-$DATEDIR/"
dinfo "saving vmcore"
$CORE_COLLECTOR /proc/vmcore $_mp/$KDUMP_PATH/$HOST_IP-$DATEDIR/vmcore-incomplete
_exitcode=$?
if [ $_exitcode -eq 0 ]; then
sync -f "$_mp/$KDUMP_PATH/$HOST_IP-$DATEDIR/vmcore-incomplete"
_sync_exitcode=$?
if [ $_sync_exitcode -eq 0 ]; then
mv "$_mp/$KDUMP_PATH/$HOST_IP-$DATEDIR/vmcore-incomplete" "$_mp/$KDUMP_PATH/$HOST_IP-$DATEDIR/vmcore"
dinfo "saving vmcore complete"
else
derror "sync vmcore failed, _exitcode:$_sync_exitcode"
return 1
fi
else
derror "saving vmcore failed, _exitcode:$_exitcode"
fi
dinfo "saving the $KDUMP_LOG_FILE to $_mp/$KDUMP_PATH/$HOST_IP-$DATEDIR/"
save_log
mv $KDUMP_LOG_FILE $_mp/$KDUMP_PATH/$HOST_IP-$DATEDIR/
if [ $_exitcode -ne 0 ]; then
return 1
fi
# improper kernel cmdline can cause the failure of echo, we can ignore this kind of failure
return 0
}
save_vmcore_dmesg_fs() {
local _dmesg_collector=$1
local _path=$2
dinfo "saving vmcore-dmesg.txt to ${_path}"
$_dmesg_collector /proc/vmcore > ${_path}/vmcore-dmesg-incomplete.txt
_exitcode=$?
if [ $_exitcode -eq 0 ]; then
mv ${_path}/vmcore-dmesg-incomplete.txt ${_path}/vmcore-dmesg.txt
chmod 600 ${_path}/vmcore-dmesg.txt
# Make sure file is on disk. There have been instances where later
# saving vmcore failed and system rebooted without sync and there
# was no vmcore-dmesg.txt available.
sync
dinfo "saving vmcore-dmesg.txt complete"
else
derror "saving vmcore-dmesg.txt failed"
fi
}
save_opalcore_fs() {
local _path=$1
if [ ! -f $OPALCORE ]; then
# Check if we are on an old kernel that uses a different path
if [ -f /sys/firmware/opal/core ]; then
OPALCORE="/sys/firmware/opal/core"
else
return 0
fi
fi
dinfo "saving opalcore:$OPALCORE to ${_path}/opalcore"
cp $OPALCORE ${_path}/opalcore
if [ $? -ne 0 ]; then
derror "saving opalcore failed"
return 1
fi
sync
dinfo "saving opalcore complete"
return 0
}
dump_to_rootfs()
{
dinfo "Trying to bring up rootfs device"
systemctl start dracut-initqueue
dinfo "Waiting for rootfs mount, will timeout after 90 seconds"
systemctl start sysroot.mount
ddebug "NEWROOT=$NEWROOT"
dump_fs $NEWROOT
}
kdump_emergency_shell()
{
echo "PS1=\"kdump:\\\${PWD}# \"" >/etc/profile
ddebug "Switching to dracut emergency..."
/bin/dracut-emergency
rm -f /etc/profile
}
do_failure_action()
{
dinfo "Executing failure action $FAILURE_ACTION"
eval $FAILURE_ACTION
}
do_final_action()
{
dinfo "Executing final action $FINAL_ACTION"
eval $FINAL_ACTION
} }

File diff suppressed because it is too large Load Diff

View File

@ -1,4 +1,4 @@
#!/bin/bash #!/bin/sh
# #
# This comes from the dracut-logger.sh # This comes from the dracut-logger.sh
# #
@ -34,6 +34,8 @@
# First of all you have to start with dlog_init() function which initializes # First of all you have to start with dlog_init() function which initializes
# required variables. Don't call any other logging function before that one! # required variables. Don't call any other logging function before that one!
# #
# The code in this file might be run in an environment without bash.
# Any code added must be POSIX compliant.
# Define vairables for the log levels in this module. # Define vairables for the log levels in this module.
kdump_stdloglvl="" kdump_stdloglvl=""
@ -53,11 +55,12 @@ fi
# #
get_kdump_loglvl() get_kdump_loglvl()
{ {
(type -p getarg) && kdump_sysloglvl=$(getarg rd.kdumploglvl) [ -f /lib/dracut-lib.sh ] && kdump_sysloglvl=$(getarg rd.kdumploglvl)
[ -z "$kdump_sysloglvl" ] && return 1; [ -z "$kdump_sysloglvl" ] && return 1;
(type -p isdigit) && isdigit $kdump_sysloglvl if [ -f /lib/dracut-lib.sh ] && ! isdigit "$kdump_sysloglvl"; then
[ $? -ne 0 ] && return 1; return 1
fi
return 0 return 0
} }
@ -83,11 +86,10 @@ check_loglvl()
# @retval 0 on success. # @retval 0 on success.
# #
dlog_init() { dlog_init() {
local ret=0; local errmsg ret=0
if [ -s /proc/vmcore ];then if [ -s /proc/vmcore ];then
get_kdump_loglvl if ! get_kdump_loglvl; then
if [ $? -ne 0 ];then
logger -t "kdump[$$]" -p warn -- "Kdump is using the default log level(3)." logger -t "kdump[$$]" -p warn -- "Kdump is using the default log level(3)."
kdump_sysloglvl=3 kdump_sysloglvl=3
fi fi
@ -104,8 +106,7 @@ dlog_init() {
[ -z "$kdump_kmsgloglvl" ] && kdump_kmsgloglvl=0 [ -z "$kdump_kmsgloglvl" ] && kdump_kmsgloglvl=0
for loglvl in "$kdump_stdloglvl" "$kdump_kmsgloglvl" "$kdump_sysloglvl"; do for loglvl in "$kdump_stdloglvl" "$kdump_kmsgloglvl" "$kdump_sysloglvl"; do
check_loglvl "$loglvl" if ! check_loglvl "$loglvl"; then
if [ $? -ne 0 ]; then
echo "Illegal log level: $kdump_stdloglvl $kdump_kmsgloglvl $kdump_sysloglvl" echo "Illegal log level: $kdump_stdloglvl $kdump_kmsgloglvl $kdump_sysloglvl"
return 1 return 1
fi fi
@ -114,21 +115,21 @@ dlog_init() {
# Skip initialization if it's already done. # Skip initialization if it's already done.
[ -n "$kdump_maxloglvl" ] && return 0 [ -n "$kdump_maxloglvl" ] && return 0
if [[ $UID -ne 0 ]]; then if [ "$UID" -ne 0 ]; then
kdump_kmsgloglvl=0 kdump_kmsgloglvl=0
kdump_sysloglvl=0 kdump_sysloglvl=0
fi fi
if [[ $kdump_sysloglvl -gt 0 ]]; then if [ "$kdump_sysloglvl" -gt 0 ]; then
if [[ -d /run/systemd/journal ]] \ if [ -d /run/systemd/journal ] \
&& type -P systemd-cat &>/dev/null \ && systemd-cat --version 1>/dev/null 2>&1 \
&& systemctl --quiet is-active systemd-journald.socket &>/dev/null; then && systemctl --quiet is-active systemd-journald.socket 1>/dev/null 2>&1; then
readonly _systemdcatfile="/var/tmp/systemd-cat" readonly _systemdcatfile="/var/tmp/systemd-cat"
mkfifo "$_systemdcatfile" &>/dev/null mkfifo "$_systemdcatfile" 1>/dev/null 2>&1
readonly _dlogfd=15 readonly _dlogfd=15
systemd-cat -t 'kdump' --level-prefix=true <"$_systemdcatfile" & systemd-cat -t 'kdump' --level-prefix=true <"$_systemdcatfile" &
exec 15>"$_systemdcatfile" exec 15>"$_systemdcatfile"
elif ! [ -S /dev/log -a -w /dev/log ] || ! command -v logger >/dev/null; then elif ! [ -S /dev/log ] && [ -w /dev/log ] || ! command -v logger >/dev/null; then
# We cannot log to syslog, so turn this facility off. # We cannot log to syslog, so turn this facility off.
kdump_kmsgloglvl=$kdump_sysloglvl kdump_kmsgloglvl=$kdump_sysloglvl
kdump_sysloglvl=0 kdump_sysloglvl=0
@ -137,31 +138,31 @@ dlog_init() {
fi fi
fi fi
local lvl; local maxloglvl_l=0 kdump_maxloglvl=0
for lvl in $kdump_stdloglvl $kdump_sysloglvl $kdump_kmsgloglvl; do for _dlog_lvl in $kdump_stdloglvl $kdump_sysloglvl $kdump_kmsgloglvl; do
[[ $lvl -gt $maxloglvl_l ]] && maxloglvl_l=$lvl [ $_dlog_lvl -gt $kdump_maxloglvl ] && kdump_maxloglvl=$_dlog_lvl
done done
readonly kdump_maxloglvl=$maxloglvl_l readonly kdump_maxloglvl
export kdump_maxloglvl export kdump_maxloglvl
if [[ $kdump_stdloglvl -lt 4 ]] && [[ $kdump_kmsgloglvl -lt 4 ]] && [[ $kdump_sysloglvl -lt 4 ]]; then if [ $kdump_stdloglvl -lt 4 ] && [ $kdump_kmsgloglvl -lt 4 ] && [ $kdump_sysloglvl -lt 4 ]; then
unset ddebug unset ddebug
ddebug() { :; }; ddebug() { :; };
fi fi
if [[ $kdump_stdloglvl -lt 3 ]] && [[ $kdump_kmsgloglvl -lt 3 ]] && [[ $kdump_sysloglvl -lt 3 ]]; then if [ $kdump_stdloglvl -lt 3 ] && [ $kdump_kmsgloglvl -lt 3 ] && [ $kdump_sysloglvl -lt 3 ]; then
unset dinfo unset dinfo
dinfo() { :; }; dinfo() { :; };
fi fi
if [[ $kdump_stdloglvl -lt 2 ]] && [[ $kdump_kmsgloglvl -lt 2 ]] && [[ $kdump_sysloglvl -lt 2 ]]; then if [ $kdump_stdloglvl -lt 2 ] && [ $kdump_kmsgloglvl -lt 2 ] && [ $kdump_sysloglvl -lt 2 ]; then
unset dwarn unset dwarn
dwarn() { :; }; dwarn() { :; };
unset dwarning unset dwarning
dwarning() { :; }; dwarning() { :; };
fi fi
if [[ $kdump_stdloglvl -lt 1 ]] && [[ $kdump_kmsgloglvl -lt 1 ]] && [[ $kdump_sysloglvl -lt 1 ]]; then if [ $kdump_stdloglvl -lt 1 ] && [ $kdump_kmsgloglvl -lt 1 ] && [ $kdump_sysloglvl -lt 1 ]; then
unset derror unset derror
derror() { :; }; derror() { :; };
fi fi
@ -173,7 +174,7 @@ dlog_init() {
## @brief Converts numeric level to logger priority defined by POSIX.2. ## @brief Converts numeric level to logger priority defined by POSIX.2.
# #
# @param lvl Numeric logging level in range from 1 to 4. # @param $1: Numeric logging level in range from 1 to 4.
# @retval 1 if @a lvl is out of range. # @retval 1 if @a lvl is out of range.
# @retval 0 if @a lvl is correct. # @retval 0 if @a lvl is correct.
# @result Echoes logger priority. # @result Echoes logger priority.
@ -189,7 +190,7 @@ _lvl2syspri() {
## @brief Converts logger numeric level to syslog log level ## @brief Converts logger numeric level to syslog log level
# #
# @param lvl Numeric logging level in range from 1 to 4. # @param $1: Numeric logging level in range from 1 to 4.
# @retval 1 if @a lvl is out of range. # @retval 1 if @a lvl is out of range.
# @retval 0 if @a lvl is correct. # @retval 0 if @a lvl is correct.
# @result Echoes kernel console numeric log level # @result Echoes kernel console numeric log level
@ -209,27 +210,25 @@ _lvl2syspri() {
# #
# @see /usr/include/sys/syslog.h # @see /usr/include/sys/syslog.h
_dlvl2syslvl() { _dlvl2syslvl() {
local lvl
case "$1" in case "$1" in
1) lvl=3;; 1) set -- 3;;
2) lvl=4;; 2) set -- 4;;
3) lvl=6;; 3) set -- 6;;
4) lvl=7;; 4) set -- 7;;
*) return 1;; *) return 1;;
esac esac
# The number is constructed by multiplying the facility by 8 and then # The number is constructed by multiplying the facility by 8 and then
# adding the level. # adding the level.
# About The Syslog Protocol, please refer to the RFC5424 for more details. # About The Syslog Protocol, please refer to the RFC5424 for more details.
echo $((24+$lvl)) echo $((24 + $1))
} }
## @brief Prints to stderr, to syslog and/or /dev/kmsg given message with ## @brief Prints to stderr, to syslog and/or /dev/kmsg given message with
# given level (priority). # given level (priority).
# #
# @param lvl Numeric logging level. # @param $1: Numeric logging level.
# @param msg Message. # @param $2: Message.
# @retval 0 It's always returned, even if logging failed. # @retval 0 It's always returned, even if logging failed.
# #
# @note This function is not supposed to be called manually. Please use # @note This function is not supposed to be called manually. Please use
@ -251,27 +250,24 @@ _dlvl2syslvl() {
# - @c INFO to @c info # - @c INFO to @c info
# - @c DEBUG to @c debug # - @c DEBUG to @c debug
_do_dlog() { _do_dlog() {
local lvl="$1"; shift [ "$1" -le $kdump_stdloglvl ] && printf -- 'kdump: %s\n' "$2" >&2
local msg="$*"
[[ $lvl -le $kdump_stdloglvl ]] && printf -- 'kdump: %s\n' "$msg" >&2 if [ "$1" -le $kdump_sysloglvl ]; then
if [ "$_dlogfd" ]; then
if [[ $lvl -le $kdump_sysloglvl ]]; then printf -- "<%s>%s\n" "$(($(_dlvl2syslvl "$1") & 7))" "$2" 1>&$_dlogfd
if [[ "$_dlogfd" ]]; then
printf -- "<%s>%s\n" "$(($(_dlvl2syslvl $lvl) & 7))" "$msg" >&$_dlogfd
else else
logger -t "kdump[$$]" -p $(_lvl2syspri $lvl) -- "$msg" logger -t "kdump[$$]" -p "$(_lvl2syspri "$1")" -- "$2"
fi fi
fi fi
[[ $lvl -le $kdump_kmsgloglvl ]] && \ [ "$1" -le $kdump_kmsgloglvl ] && \
echo "<$(_dlvl2syslvl $lvl)>kdump[$$] $msg" >/dev/kmsg echo "<$(_dlvl2syslvl "$1")>kdump[$$] $2" >/dev/kmsg
} }
## @brief Internal helper function for _do_dlog() ## @brief Internal helper function for _do_dlog()
# #
# @param lvl Numeric logging level. # @param $1: Numeric logging level.
# @param msg Message. # @param $2 [...]: Message.
# @retval 0 It's always returned, even if logging failed. # @retval 0 It's always returned, even if logging failed.
# #
# @note This function is not supposed to be called manually. Please use # @note This function is not supposed to be called manually. Please use
@ -286,12 +282,13 @@ _do_dlog() {
# echo "This is a warning" | dwarn # echo "This is a warning" | dwarn
dlog() { dlog() {
[ -z "$kdump_maxloglvl" ] && return 0 [ -z "$kdump_maxloglvl" ] && return 0
[[ $1 -le $kdump_maxloglvl ]] || return 0 [ "$1" -le "$kdump_maxloglvl" ] || return 0
if [[ $# -gt 1 ]]; then if [ $# -gt 1 ]; then
_do_dlog "$@" _dlog_lvl=$1; shift
_do_dlog "$_dlog_lvl" "$*"
else else
while read line || [ -n "$line" ]; do while read -r line || [ -n "$line" ]; do
_do_dlog "$1" "$line" _do_dlog "$1" "$line"
done done
fi fi
@ -304,7 +301,9 @@ dlog() {
ddebug() { ddebug() {
set +x set +x
dlog 4 "$@" dlog 4 "$@"
[ -n "$debug" ] && set -x || : if [ -n "$debug" ]; then
set -x
fi
} }
## @brief Logs message at INFO level (3) ## @brief Logs message at INFO level (3)
@ -314,7 +313,9 @@ ddebug() {
dinfo() { dinfo() {
set +x set +x
dlog 3 "$@" dlog 3 "$@"
[ -n "$debug" ] && set -x || : if [ -n "$debug" ]; then
set -x
fi
} }
## @brief Logs message at WARN level (2) ## @brief Logs message at WARN level (2)
@ -324,7 +325,9 @@ dinfo() {
dwarn() { dwarn() {
set +x set +x
dlog 2 "$@" dlog 2 "$@"
[ -n "$debug" ] && set -x || : if [ -n "$debug" ]; then
set -x
fi
} }
## @brief It's an alias to dwarn() function. ## @brief It's an alias to dwarn() function.
@ -334,7 +337,9 @@ dwarn() {
dwarning() { dwarning() {
set +x set +x
dwarn "$@" dwarn "$@"
[ -n "$debug" ] && set -x || : if [ -n "$debug" ]; then
set -x
fi
} }
## @brief Logs message at ERROR level (1) ## @brief Logs message at ERROR level (1)
@ -344,5 +349,7 @@ dwarning() {
derror() { derror() {
set +x set +x
dlog 1 "$@" dlog 1 "$@"
[ -n "$debug" ] && set -x || : if [ -n "$debug" ]; then
set -x
fi
} }

View File

@ -26,6 +26,24 @@ understand how this configuration file affects the behavior of kdump.
.SH OPTIONS .SH OPTIONS
.B auto_reset_crashkernel <yes|no>
.RS
determine whether to reset kernel crashkernel parameter to the default value
or not when kexec-tools is updated or a new kernel is installed. The default
crashkernel values are different for different architectures and also take the
following factors into consideration,
- AMD Secure Memory Encryption (SME) and Secure Encrypted Virtualization (SEV)
- Mellanox 5th generation network driver
- aarch64 64k kernel
- Firmware-assisted dump (FADump)
Since the kernel crasherkernel parameter will be only reset when kexec-tools is
updated or a new kernel is installed, you need to call "kdumpctl
reset-crashkernel [--kernel=path_to_kernel]" if you want to use the default
value set after having enabled features like SME/SEV for a specific kernel. And
you should also reboot the system for the new crashkernel value to take effect.
Also see kdumpctl(8).
.B raw <partition> .B raw <partition>
.RS .RS
Will dd /proc/vmcore into <partition>. Use persistent device names for Will dd /proc/vmcore into <partition>. Use persistent device names for
@ -41,7 +59,7 @@ mount point.
.B ssh <user@server> .B ssh <user@server>
.RS .RS
Will scp /proc/vmcore to <user@server>:<path>/%HOST-%DATE/, Will save /proc/vmcore through ssh pipe to <user@server>:<path>/%HOST-%DATE/,
supports DNS. NOTE: make sure user has necessary write permissions on supports DNS. NOTE: make sure user has necessary write permissions on
server and that a fqdn is used as the server name. server and that a fqdn is used as the server name.
.RE .RE
@ -55,7 +73,7 @@ The default value is /root/.ssh/kdump_id_rsa.
.B <fs type> <partition> .B <fs type> <partition>
.RS .RS
Will mount -t <fs type> <partition> <mnt>, and copy /proc/vmcore to Will mount -t <fs type> <partition> <mnt>, and copy /proc/vmcore to
<mnt>/<path>/%DATE/. NOTE: <partition> can be a device node, label <mnt>/<path>/%HOST_IP-%DATE/. NOTE: <partition> can be a device node, label
or uuid. It's recommended to use persistent device names such as or uuid. It's recommended to use persistent device names such as
/dev/vg/<devname>. Otherwise it's suggested to use label or uuid. /dev/vg/<devname>. Otherwise it's suggested to use label or uuid.
.RE .RE
@ -121,7 +139,7 @@ specified kdump_post parameter is executed.
Note that scripts written for use with this directive must use the /bin/bash Note that scripts written for use with this directive must use the /bin/bash
interpreter. And since these scripts run in kdump enviroment, the reference to interpreter. And since these scripts run in kdump enviroment, the reference to
the storage or network device in the scripts should adhere to the section the storage or network device in the scripts should adhere to the section
\'Supported dump target types and requirements\' in kexec-kdump-howto.txt. 'Supported dump target types and requirements' in kexec-kdump-howto.txt.
.RE .RE
@ -145,7 +163,7 @@ returns non 0 exit status, the processing is continued.
Note that scripts written for use with this directive must use the /bin/bash Note that scripts written for use with this directive must use the /bin/bash
interpreter. And since these scripts run in kdump enviroment, the reference to interpreter. And since these scripts run in kdump enviroment, the reference to
the storage or network device in the scripts should adhere to the section the storage or network device in the scripts should adhere to the section
\'Supported dump target types and requirements\' in kexec-kdump-howto.txt. 'Supported dump target types and requirements' in kexec-kdump-howto.txt.
.RE .RE
@ -296,7 +314,7 @@ retaining blacklist option creates more confusing behavior. It has been
deprecated. deprecated.
.PP .PP
Instead, use rd.driver.blacklist option on second kernel to blacklist Instead, use rd.driver.blacklist option on second kernel to blacklist
a certain module. One can edit /etc/sysconfig/kdump and edit a certain module. One can edit /etc/sysconfig/kdump.conf and edit
KDUMP_COMMANDLINE_APPEND to pass kernel command line options. Refer KDUMP_COMMANDLINE_APPEND to pass kernel command line options. Refer
to dracut.cmdline man page for more details on module blacklist option. to dracut.cmdline man page for more details on module blacklist option.
.RE .RE

View File

@ -11,6 +11,7 @@ ExecStop=/usr/bin/kdumpctl stop
ExecReload=/usr/bin/kdumpctl reload ExecReload=/usr/bin/kdumpctl reload
RemainAfterExit=yes RemainAfterExit=yes
StartLimitInterval=0 StartLimitInterval=0
PrivateTmp=yes
[Install] [Install]
WantedBy=multi-user.target WantedBy=multi-user.target

View File

@ -17,11 +17,11 @@ KDUMP_COMMANDLINE=""
# This variable lets us remove arguments from the current kdump commandline # This variable lets us remove arguments from the current kdump commandline
# as taken from either KDUMP_COMMANDLINE above, or from /proc/cmdline # as taken from either KDUMP_COMMANDLINE above, or from /proc/cmdline
# NOTE: some arguments such as crashkernel will always be removed # NOTE: some arguments such as crashkernel will always be removed
KDUMP_COMMANDLINE_REMOVE="hugepages hugepagesz slub_debug quiet log_buf_len ignition.firstboot" KDUMP_COMMANDLINE_REMOVE="hugepages hugepagesz slub_debug quiet log_buf_len swiotlb cma hugetlb_cma ignition.firstboot"
# This variable lets us append arguments to the current kdump commandline # This variable lets us append arguments to the current kdump commandline
# after processed by KDUMP_COMMANDLINE_REMOVE # after processed by KDUMP_COMMANDLINE_REMOVE
KDUMP_COMMANDLINE_APPEND="irqpoll maxcpus=1 reset_devices novmcoredd" KDUMP_COMMANDLINE_APPEND="irqpoll nr_cpus=1 reset_devices novmcoredd cma=0 hugetlb_cma=0"
# Any additional kexec arguments required. In most situations, this should # Any additional kexec arguments required. In most situations, this should
# be left empty # be left empty

View File

@ -17,11 +17,11 @@ KDUMP_COMMANDLINE=""
# This variable lets us remove arguments from the current kdump commandline # This variable lets us remove arguments from the current kdump commandline
# as taken from either KDUMP_COMMANDLINE above, or from /proc/cmdline # as taken from either KDUMP_COMMANDLINE above, or from /proc/cmdline
# NOTE: some arguments such as crashkernel will always be removed # NOTE: some arguments such as crashkernel will always be removed
KDUMP_COMMANDLINE_REMOVE="hugepages hugepagesz slub_debug quiet log_buf_len swiotlb ignition.firstboot" KDUMP_COMMANDLINE_REMOVE="hugepages hugepagesz slub_debug quiet log_buf_len swiotlb cma hugetlb_cma ignition.firstboot"
# This variable lets us append arguments to the current kdump commandline # This variable lets us append arguments to the current kdump commandline
# after processed by KDUMP_COMMANDLINE_REMOVE # after processed by KDUMP_COMMANDLINE_REMOVE
KDUMP_COMMANDLINE_APPEND="irqpoll nr_cpus=1 reset_devices cgroup_disable=memory udev.children-max=2 panic=10 swiotlb=noforce novmcoredd" KDUMP_COMMANDLINE_APPEND="irqpoll nr_cpus=1 reset_devices cgroup_disable=memory udev.children-max=2 panic=10 swiotlb=noforce novmcoredd cma=0 hugetlb_cma=0"
# Any additional kexec arguments required. In most situations, this should # Any additional kexec arguments required. In most situations, this should
# be left empty # be left empty

View File

@ -17,11 +17,11 @@ KDUMP_COMMANDLINE=""
# This variable lets us remove arguments from the current kdump commandline # This variable lets us remove arguments from the current kdump commandline
# as taken from either KDUMP_COMMANDLINE above, or from /proc/cmdline # as taken from either KDUMP_COMMANDLINE above, or from /proc/cmdline
# NOTE: some arguments such as crashkernel will always be removed # NOTE: some arguments such as crashkernel will always be removed
KDUMP_COMMANDLINE_REMOVE="hugepages hugepagesz slub_debug quiet log_buf_len swiotlb ignition.firstboot" KDUMP_COMMANDLINE_REMOVE="hugepages hugepagesz slub_debug quiet log_buf_len swiotlb cma hugetlb_cma ignition.firstboot"
# This variable lets us append arguments to the current kdump commandline # This variable lets us append arguments to the current kdump commandline
# after processed by KDUMP_COMMANDLINE_REMOVE # after processed by KDUMP_COMMANDLINE_REMOVE
KDUMP_COMMANDLINE_APPEND="irqpoll nr_cpus=1 reset_devices numa=off udev.children-max=2 panic=10 rootflags=nofail transparent_hugepage=never novmcoredd" KDUMP_COMMANDLINE_APPEND="irqpoll nr_cpus=1 reset_devices numa=off udev.children-max=2 panic=10 transparent_hugepage=never novmcoredd cma=0 hugetlb_cma=0"
# Any additional kexec arguments required. In most situations, this should # Any additional kexec arguments required. In most situations, this should
# be left empty # be left empty

View File

@ -17,11 +17,11 @@ KDUMP_COMMANDLINE=""
# This variable lets us remove arguments from the current kdump commandline # This variable lets us remove arguments from the current kdump commandline
# as taken from either KDUMP_COMMANDLINE above, or from /proc/cmdline # as taken from either KDUMP_COMMANDLINE above, or from /proc/cmdline
# NOTE: some arguments such as crashkernel will always be removed # NOTE: some arguments such as crashkernel will always be removed
KDUMP_COMMANDLINE_REMOVE="hugepages hugepagesz slub_debug quiet log_buf_len swiotlb ignition.firstboot" KDUMP_COMMANDLINE_REMOVE="hugepages hugepagesz slub_debug quiet log_buf_len swiotlb hugetlb_cma ignition.firstboot"
# This variable lets us append arguments to the current kdump commandline # This variable lets us append arguments to the current kdump commandline
# after processed by KDUMP_COMMANDLINE_REMOVE # after processed by KDUMP_COMMANDLINE_REMOVE
KDUMP_COMMANDLINE_APPEND="irqpoll maxcpus=1 noirqdistrib reset_devices cgroup_disable=memory numa=off udev.children-max=2 ehea.use_mcs=0 panic=10 rootflags=nofail kvm_cma_resv_ratio=0 transparent_hugepage=never novmcoredd" KDUMP_COMMANDLINE_APPEND="irqpoll nr_cpus=1 noirqdistrib reset_devices cgroup_disable=memory numa=off udev.children-max=2 ehea.use_mcs=0 panic=10 kvm_cma_resv_ratio=0 transparent_hugepage=never novmcoredd hugetlb_cma=0"
# Any additional kexec arguments required. In most situations, this should # Any additional kexec arguments required. In most situations, this should
# be left empty # be left empty

View File

@ -17,18 +17,18 @@ KDUMP_COMMANDLINE=""
# This variable lets us remove arguments from the current kdump commandline # This variable lets us remove arguments from the current kdump commandline
# as taken from either KDUMP_COMMANDLINE above, or from /proc/cmdline # as taken from either KDUMP_COMMANDLINE above, or from /proc/cmdline
# NOTE: some arguments such as crashkernel will always be removed # NOTE: some arguments such as crashkernel will always be removed
KDUMP_COMMANDLINE_REMOVE="hugepages hugepagesz slub_debug quiet log_buf_len swiotlb ignition.firstboot" KDUMP_COMMANDLINE_REMOVE="hugepages hugepagesz slub_debug quiet log_buf_len swiotlb hugetlb_cma ignition.firstboot"
# This variable lets us append arguments to the current kdump commandline # This variable lets us append arguments to the current kdump commandline
# after processed by KDUMP_COMMANDLINE_REMOVE # after processed by KDUMP_COMMANDLINE_REMOVE
KDUMP_COMMANDLINE_APPEND="irqpoll maxcpus=1 noirqdistrib reset_devices cgroup_disable=memory numa=off udev.children-max=2 ehea.use_mcs=0 panic=10 rootflags=nofail kvm_cma_resv_ratio=0 transparent_hugepage=never novmcoredd" KDUMP_COMMANDLINE_APPEND="irqpoll nr_cpus=1 noirqdistrib reset_devices cgroup_disable=memory numa=off udev.children-max=2 ehea.use_mcs=0 panic=10 kvm_cma_resv_ratio=0 transparent_hugepage=never novmcoredd hugetlb_cma=0"
# Any additional kexec arguments required. In most situations, this should # Any additional kexec arguments required. In most situations, this should
# be left empty # be left empty
# #
# Example: # Example:
# KEXEC_ARGS="--elf32-core-headers" # KEXEC_ARGS="--elf32-core-headers"
KEXEC_ARGS="--dt-no-old-root" KEXEC_ARGS="--dt-no-old-root -s"
#Where to find the boot image #Where to find the boot image
#KDUMP_BOOTDIR="/boot" #KDUMP_BOOTDIR="/boot"

View File

@ -17,11 +17,11 @@ KDUMP_COMMANDLINE=""
# This variable lets us remove arguments from the current kdump commandline # This variable lets us remove arguments from the current kdump commandline
# as taken from either KDUMP_COMMANDLINE above, or from /proc/cmdline # as taken from either KDUMP_COMMANDLINE above, or from /proc/cmdline
# NOTE: some arguments such as crashkernel will always be removed # NOTE: some arguments such as crashkernel will always be removed
KDUMP_COMMANDLINE_REMOVE="hugepages hugepagesz slub_debug quiet log_buf_len swiotlb prot_virt ignition.firstboot zfcp.allow_lun_scan" KDUMP_COMMANDLINE_REMOVE="hugepages hugepagesz slub_debug quiet log_buf_len swiotlb vmcp_cma cma hugetlb_cma prot_virt ignition.firstboot zfcp.allow_lun_scan"
# This variable lets us append arguments to the current kdump commandline # This variable lets us append arguments to the current kdump commandline
# after processed by KDUMP_COMMANDLINE_REMOVE # after processed by KDUMP_COMMANDLINE_REMOVE
KDUMP_COMMANDLINE_APPEND="nr_cpus=1 cgroup_disable=memory numa=off udev.children-max=2 panic=10 rootflags=nofail transparent_hugepage=never novmcoredd" KDUMP_COMMANDLINE_APPEND="nr_cpus=1 cgroup_disable=memory numa=off udev.children-max=2 panic=10 transparent_hugepage=never novmcoredd vmcp_cma=0 cma=0 hugetlb_cma=0"
# Any additional /sbin/mkdumprd arguments required. # Any additional /sbin/mkdumprd arguments required.
MKDUMPRD_ARGS="" MKDUMPRD_ARGS=""

View File

@ -17,11 +17,11 @@ KDUMP_COMMANDLINE=""
# This variable lets us remove arguments from the current kdump commandline # This variable lets us remove arguments from the current kdump commandline
# as taken from either KDUMP_COMMANDLINE above, or from /proc/cmdline # as taken from either KDUMP_COMMANDLINE above, or from /proc/cmdline
# NOTE: some arguments such as crashkernel will always be removed # NOTE: some arguments such as crashkernel will always be removed
KDUMP_COMMANDLINE_REMOVE="hugepages hugepagesz slub_debug quiet log_buf_len swiotlb ignition.firstboot" KDUMP_COMMANDLINE_REMOVE="hugepages hugepagesz slub_debug quiet log_buf_len swiotlb cma hugetlb_cma ignition.firstboot"
# This variable lets us append arguments to the current kdump commandline # This variable lets us append arguments to the current kdump commandline
# after processed by KDUMP_COMMANDLINE_REMOVE # after processed by KDUMP_COMMANDLINE_REMOVE
KDUMP_COMMANDLINE_APPEND="irqpoll nr_cpus=1 reset_devices cgroup_disable=memory mce=off numa=off udev.children-max=2 panic=10 rootflags=nofail acpi_no_memhotplug transparent_hugepage=never nokaslr novmcoredd hest_disable" KDUMP_COMMANDLINE_APPEND="irqpoll nr_cpus=1 reset_devices cgroup_disable=memory mce=off numa=off udev.children-max=2 panic=10 acpi_no_memhotplug transparent_hugepage=never nokaslr hest_disable novmcoredd cma=0 hugetlb_cma=0 pcie_ports=compat"
# Any additional kexec arguments required. In most situations, this should # Any additional kexec arguments required. In most situations, this should
# be left empty # be left empty

File diff suppressed because it is too large Load Diff

View File

@ -14,7 +14,7 @@ In most cases, you should use
.B systemctl .B systemctl
to start / stop / enable kdump service instead. However, to start / stop / enable kdump service instead. However,
.B kdumpctl .B kdumpctl
provides more details for debug and a helper to setup ssh key authentication. provides more details for debugging and a helper to set up ssh key authentication.
.SH COMMANDS .SH COMMANDS
.TP .TP
@ -26,14 +26,14 @@ Stop the service.
.TP .TP
.I status .I status
Prints the current status of kdump service. Prints the current status of kdump service.
It returns non-zero value if kdump is not operational. It returns a non-zero value if kdump is not operational.
.TP .TP
.I restart .I restart
Is equal to Is equal to
.I start; stop .I start; stop
.TP .TP
.I reload .I reload
reload crash kernel image and initramfs without triggering a rebuild. reload the crash kernel image and initramfs without triggering a rebuild.
.TP .TP
.I rebuild .I rebuild
rebuild the crash kernel initramfs. rebuild the crash kernel initramfs.
@ -43,12 +43,33 @@ Helps to setup key authentication for ssh storage since it's
impossible to use password authentication during kdump. impossible to use password authentication during kdump.
.TP .TP
.I showmem .I showmem
Prints the size of reserved memory for crash kernel in megabytes. Prints the size of reserved memory for the crash kernel in megabytes.
.TP .TP
.I estimate .I estimate
Estimate a suitable crashkernel value for current machine. This is a Estimate a suitable crashkernel value for the current machine. This is a
best-effort estimate. It will print a recommanded crashkernel value best-effort estimate. It will print a recommended crashkernel value
based on current kdump setup, and list some details of memory usage. based on the current kdump setup, and list some details of memory usage.
.TP
.I get-default-crashkernel
Return the default crashkernel value provided by kexec-tools.
.TP
.I reset-crashkernel [--kernel=path_to_kernel] [--reboot]
Reset crashkernel to default value recommended by kexec-tools. If no kernel
is specified, will reset KDUMP_KERNELVER if it's defined in /etc/sysconfig/kdump
or the current running kernel's crashkernel value if KDUMP_KERNELVER is empty. You can
also specify --kernel=ALL and --kernel=DEFAULT which have the same meaning as
grubby's kernel-path=ALL and kernel-path=DEFAULT. ppc64le supports FADump and
supports an additional [--fadump=[on|off|nocma]] parameter to toggle FADump
on/off.
If the optional parameter [--reboot] is provided the system will automatically
reboot for changes to take effect. If no changes were made to the kernel
command line the reboot is omitted.
Note: The memory requirements for kdump varies heavily depending on the
used hardware and system configuration. Thus the recommended
crashkernel might not work for your specific setup. Please test if
kdump works after resetting the crashkernel value.
.SH "SEE ALSO" .SH "SEE ALSO"
.BR kdump.conf (5), .BR kdump.conf (5),

View File

@ -44,7 +44,7 @@ ia64 and ppc64.
If you're reading this document, you should already have kexec-tools If you're reading this document, you should already have kexec-tools
installed. If not, you install it via the following command: installed. If not, you install it via the following command:
# yum install kexec-tools # dnf install kexec-tools
Now load a kernel with kexec: Now load a kernel with kexec:
@ -66,23 +66,31 @@ How to configure kdump
Again, we assume if you're reading this document, you should already have Again, we assume if you're reading this document, you should already have
kexec-tools installed. If not, you install it via the following command: kexec-tools installed. If not, you install it via the following command:
# yum install kexec-tools # dnf install kexec-tools
To be able to do much of anything interesting in the way of debug analysis, To be able to do much of anything interesting in the way of debug analysis,
you'll also need to install the kernel-debuginfo package, of the same arch you'll also need to install the kernel-debuginfo package, of the same arch
as your running kernel, and the crash utility: as your running kernel, and the crash utility:
# yum --enablerepo=\*debuginfo install kernel-debuginfo.$(uname -m) crash # dnf --enablerepo=\*debuginfo install kernel-debuginfo.$(uname -m) crash
Next up, we need to modify some boot parameters to reserve a chunk of memory for Next up, we need to reserve a chunk of memory for the capture kernel. To use
the capture kernel. With the help of grubby, it's very easy to append the default crashkernel value, you can kdumpctl:
"crashkernel=128M" to the end of your kernel boot parameters. Note that the X
values are such that X = the amount of memory to reserve for the capture kernel.
And based on arch and system configuration, one might require more than 128M to
be reserved for kdump. One need to experiment and test kdump, if 128M is not
sufficient, try reserving more memory.
# grubby --args="crashkernel=128M" --update-kernel=/boot/vmlinuz-`uname -r` # kdumpctl reset-crashkernel --kernel=/boot/vmlinuz-`uname -r`
If the default value does not work for your setup you can use
# grubby --args="crashkernel=256M" --update-kernel=/boot/vmlinuz-`uname -r`
to specify a larger value, in this case 256M. You need to experiment to
find the best value that works for your setup. To begin with
# kdumpctl estimate
gives you an estimation for the crashkernel value based on the currently
running kernel. For more details, please refer to the "Estimate crashkernel"
section in /usr/share/doc/kexec-tools/crashkernel-howto.txt.
Note that there is an alternative form in which to specify a crashkernel Note that there is an alternative form in which to specify a crashkernel
memory reservation, in the event that more control is needed over the size and memory reservation, in the event that more control is needed over the size and
@ -135,7 +143,7 @@ in /var/crash/<YYYY-MM-DD-HH:MM>/vmcore), then the system rebooted back into
your normal kernel. your normal kernel.
Once back to your normal kernel, you can use the previously installed crash Once back to your normal kernel, you can use the previously installed crash
kernel in conjunction with the previously installed kernel-debuginfo to utility in conjunction with the previously installed kernel-debuginfo to
perform postmortem analysis: perform postmortem analysis:
# crash /usr/lib/debug/lib/modules/2.6.17-1.2621.el5/vmlinux # crash /usr/lib/debug/lib/modules/2.6.17-1.2621.el5/vmlinux
@ -187,7 +195,7 @@ on your system, with the scripts enabled as described in the section above.
Kdump can be triggered with the combination of the 'Alt','SysRq' and 'C' Kdump can be triggered with the combination of the 'Alt','SysRq' and 'C'
keyboard keys. Please refer to the following link for more details: keyboard keys. Please refer to the following link for more details:
https://access.redhat.com/solutions/2023 http://kbase.redhat.com/faq/FAQ_43_5559.shtm
In addition, on PowerPC boxes, Kdump can also be triggered via Hardware In addition, on PowerPC boxes, Kdump can also be triggered via Hardware
Management Console(HMC) using 'Ctrl', 'O' and 'C' keyboard keys. Management Console(HMC) using 'Ctrl', 'O' and 'C' keyboard keys.
@ -199,7 +207,7 @@ respond to keyboard interrupts. As a result 'Alt-SysRq' keys will not help
trigger a dump. In such scenarios Nmi Watchdog feature can prove to be useful. trigger a dump. In such scenarios Nmi Watchdog feature can prove to be useful.
The following link has more details on configuring Nmi watchdog option. The following link has more details on configuring Nmi watchdog option.
https://access.redhat.com/solutions/125103 http://kbase.redhat.com/faq/FAQ_85_9129.shtm
Once this feature has been enabled in the kernel, any lockups will result in an Once this feature has been enabled in the kernel, any lockups will result in an
OOPs message to be generated, followed by Kdump being triggered. OOPs message to be generated, followed by Kdump being triggered.
@ -1008,12 +1016,7 @@ Debugging Tips
and the second kernel. and the second kernel.
In the first kernel, you can find the historical logs with the journalctl In the first kernel, you can find the historical logs with the journalctl
command and check kdump service debugging information. In addition, the command and check kdump service debugging information.
'kexec -d' debugging messages are also saved to /var/log/kdump.log in the
first kernel. For example:
[root@ibm-z-109 ~]# ls -al /var/log/kdump.log
-rw-r--r--. 1 root root 63238 Oct 28 06:40 /var/log/kdump.log
If you want to get the debugging information of building kdump initramfs, you If you want to get the debugging information of building kdump initramfs, you
can enable the '--debug' option for the dracut_args in the /etc/kdump.conf, and can enable the '--debug' option for the dracut_args in the /etc/kdump.conf, and

View File

@ -1,72 +0,0 @@
From 58553ad03187f0cf208d6c4a0dc026c6338e5edd Mon Sep 17 00:00:00 2001
From: "Daisuke Hatayama (Fujitsu)" <d.hatayama@fujitsu.com>
Date: Wed, 29 Mar 2023 12:44:10 +0000
Subject: [PATCH] [PATCH] sadump: fix failure of reading memory when 5-level
paging is enabled
makedumpfile fails as follows for memory dumps collected by sadump
when 5-level paging is enabled on the corresponding systems:
# makedumpfile -l -d 31 -x ./vmlinux ./dump.sadump dump.sadump-ld31
__vtop4_x86_64: Can't get a valid pgd.
...snip...
__vtop4_x86_64: Can't get a valid pgd.
calc_kaslr_offset: failed to calculate kaslr_offset and phys_base; default to 0
__vtop4_x86_64: Can't get a valid pgd.
readmem: Can't convert a virtual address(ffffffff82fce960) to physical address.
readmem: type_addr: 0, addr:ffffffff82fce960, size:1024
cpu_online_mask_init: Can't read cpu_online_mask memory.
makedumpfile Failed.
This is because 5-level paging support has not been done yet for
sadump; the work of the 5-level paging support was done by the commit
30a3214a7193e94c551c0cebda5918a72a35c589 (PATCH 4/4 arch/x86_64: Add
5-level paging support) but that was focused on the core part only.
Having said that, most of things has already been finished in the
commit. What needs to be newly added for sadump is just how to check
if 5-level paging is enabled for a given memory dump.
For that purpose, let's refer to CR4.LA57, bit 12 of CR4, representing
whether 5-level paging is enabled or not. We can do this because
memory dumps collected by sadump have SMRAM as note information and
they include CR4 together with the other control registers.
Signed-off-by: HATAYAMA Daisuke <d.hatayama@fujitsu.com>
---
sadump_info.c | 4 ++++
1 file changed, 4 insertions(+)
diff --git a/makedumpfile-1.7.2/sadump_info.c b/makedumpfile-1.7.2/sadump_info.c
index adfa8dc..2c44068 100644
--- a/makedumpfile-1.7.2/sadump_info.c
+++ b/makedumpfile-1.7.2/sadump_info.c
@@ -1362,6 +1362,7 @@ static int linux_banner_sanity_check(ulong cr3)
#define PTI_USER_PGTABLE_BIT (info->page_shift)
#define PTI_USER_PGTABLE_MASK (1 << PTI_USER_PGTABLE_BIT)
#define CR3_PCID_MASK 0xFFFull
+#define CR4_LA57 (1 << 12)
int
calc_kaslr_offset(void)
{
@@ -1397,6 +1398,8 @@ calc_kaslr_offset(void)
else
cr3 = smram.Cr3 & ~CR3_PCID_MASK;
+ NUMBER(pgtable_l5_enabled) = !!(smram.Cr4 & CR4_LA57);
+
/* Convert virtual address of IDT table to physical address */
idtr_paddr = vtop4_x86_64_pagetable(idtr, cr3);
if (idtr_paddr == NOT_PADDR) {
@@ -1417,6 +1420,7 @@ calc_kaslr_offset(void)
DEBUG_MSG("sadump: idtr=%" PRIx64 "\n", idtr);
DEBUG_MSG("sadump: cr3=%" PRIx64 "\n", cr3);
+ DEBUG_MSG("sadump: cr4=%" PRIx32 "\n", smram.Cr4);
DEBUG_MSG("sadump: idtr(phys)=%" PRIx64 "\n", idtr_paddr);
DEBUG_MSG("sadump: devide_error(vmlinux)=%lx\n",
divide_error_vmlinux);
--
2.31.1

View File

@ -0,0 +1,39 @@
From bd0200c47c45dd420244b39ddabcecdab1fb9a8e Mon Sep 17 00:00:00 2001
From: Hari Bathini <hbathini@linux.ibm.com>
Date: Wed, 20 Sep 2023 17:29:27 +0530
Subject: [PATCH] kexec: update manpage with explicit mention of clean kexec
While the manpage does mention about kexec boot with a clean shutdown,
it is not explicit about it. Make it explicit.
Signed-off-by: Hari Bathini <hbathini@linux.ibm.com>
Signed-off-by: Simon Horman <horms@kernel.org>
---
kexec/kexec.8 | 11 +++++++++--
1 file changed, 9 insertions(+), 2 deletions(-)
diff --git a/kexec/kexec.8 b/kexec/kexec.8
index 3a344c5..179dcf2 100644
--- a/kexec/kexec.8
+++ b/kexec/kexec.8
@@ -95,8 +95,15 @@ then you would use the following command to load the kernel:
.RB "\-\-append=" "root=/dev/hda1" "\ \-\-initrd=" /boot/initrd
.RE
.PP
-After this kernel is loaded, it can be booted to at any time using the
-command:
+After this kernel is loaded, assuming the user-space supports kexec-based
+rebooting, it can be booted to, with a clean shutdown, using the command:
+
+.RS
+.BR reboot
+.RE
+.PP
+Alternatively, it can also be booted to, without calling shutdown(8), with
+the command:
.RS
.BR kexec \ \-e
--
2.41.0

View File

@ -0,0 +1,44 @@
From 9d9cf8de8b2ad8273861a30476a46f34cd34871a Mon Sep 17 00:00:00 2001
From: Baoquan He <bhe@redhat.com>
Date: Tue, 14 Nov 2023 23:20:30 +0800
Subject: [PATCH] kexec_file: add kexec_file flag to support debug printing
Content-type: text/plain
This add KEXEC_FILE_DEBUG to kexec_file_flags so that it can be passed
to kernel when '-d' is added with kexec_file_load interface. With that
flag enabled, kernel can enable the debugging message printing.
Signed-off-by: Baoquan He <bhe@redhat.com>
Signed-off-by: Simon Horman <horms@kernel.org>
---
kexec/kexec-syscall.h | 1 +
kexec/kexec.c | 1 +
2 files changed, 2 insertions(+)
diff --git a/kexec/kexec-syscall.h b/kexec/kexec-syscall.h
index 2559bffb93da..73e52543e1b0 100644
--- a/kexec/kexec-syscall.h
+++ b/kexec/kexec-syscall.h
@@ -119,6 +119,7 @@ static inline long kexec_file_load(int kernel_fd, int initrd_fd,
#define KEXEC_FILE_UNLOAD 0x00000001
#define KEXEC_FILE_ON_CRASH 0x00000002
#define KEXEC_FILE_NO_INITRAMFS 0x00000004
+#define KEXEC_FILE_DEBUG 0x00000008
/* These values match the ELF architecture values.
* Unless there is a good reason that should continue to be the case.
diff --git a/kexec/kexec.c b/kexec/kexec.c
index 9d0ec46e5657..222f79e3112e 100644
--- a/kexec/kexec.c
+++ b/kexec/kexec.c
@@ -1477,6 +1477,7 @@ int main(int argc, char *argv[])
return 0;
case OPT_DEBUG:
kexec_debug = 1;
+ kexec_file_flags |= KEXEC_FILE_DEBUG;
break;
case OPT_NOIFDOWN:
skip_ifdown = 1;
--
2.41.0

View File

@ -6,7 +6,7 @@
# Written by Cong Wang <amwang@redhat.com> # Written by Cong Wang <amwang@redhat.com>
# #
if [ -f /etc/sysconfig/kdump ]; then if [[ -f /etc/sysconfig/kdump ]]; then
. /etc/sysconfig/kdump . /etc/sysconfig/kdump
fi fi
@ -17,23 +17,21 @@ fi
export IN_KDUMP=1 export IN_KDUMP=1
#initiate the kdump logger #initiate the kdump logger
dlog_init if ! dlog_init; then
if [ $? -ne 0 ]; then
echo "failed to initiate the kdump logger." echo "failed to initiate the kdump logger."
exit 1 exit 1
fi fi
conf_file="/etc/kdump.conf"
SSH_KEY_LOCATION="/root/.ssh/kdump_id_rsa" SSH_KEY_LOCATION="/root/.ssh/kdump_id_rsa"
SAVE_PATH=$(get_save_path) SAVE_PATH=$(get_save_path)
OVERRIDE_RESETTABLE=0 OVERRIDE_RESETTABLE=0
extra_modules="" extra_modules=""
dracut_args="--add kdumpbase --quiet --hostonly --hostonly-cmdline --hostonly-i18n --hostonly-mode strict --hostonly-nics '' -o \"plymouth dash resume ifcfg earlykdump\" --compress=xz" dracut_args=(--add kdumpbase --quiet --hostonly --hostonly-cmdline --hostonly-i18n --hostonly-mode strict --hostonly-nics '' -o "plymouth resume ifcfg earlykdump")
readonly MKDUMPRD_TMPDIR="$(mktemp -d -t mkdumprd.XXXXXX)" MKDUMPRD_TMPDIR="$(mktemp -d -t mkdumprd.XXXXXX)"
[ -d "$MKDUMPRD_TMPDIR" ] || perror_exit "dracut: mktemp -p -d -t dracut.XXXXXX failed." [ -d "$MKDUMPRD_TMPDIR" ] || perror_exit "dracut: mktemp -p -d -t dracut.XXXXXX failed."
readonly MKDUMPRD_TMPMNT="$MKDUMPRD_TMPDIR/target" MKDUMPRD_TMPMNT="$MKDUMPRD_TMPDIR/target"
trap ' trap '
ret=$?; ret=$?;
@ -45,48 +43,54 @@ trap '
# clean up after ourselves no matter how we die. # clean up after ourselves no matter how we die.
trap 'exit 1;' SIGINT trap 'exit 1;' SIGINT
add_dracut_arg() { add_dracut_arg()
dracut_args="$dracut_args $@" {
dracut_args+=("$@")
} }
add_dracut_mount() { add_dracut_mount()
add_dracut_arg "--mount" "\"$1\"" {
add_dracut_arg "--mount" "$1"
} }
add_dracut_sshkey() { add_dracut_sshkey()
add_dracut_arg "--sshkey" "\"$1\"" {
add_dracut_arg "--sshkey" "$1"
} }
# caller should ensure $1 is valid and mounted in 1st kernel # caller should ensure $1 is valid and mounted in 1st kernel
to_mount() { to_mount()
local _target=$1 _fstype=$2 _options=$3 _new_mntpoint _pdev {
local _target=$1 _fstype=$2 _options=$3 _sed_cmd _new_mntpoint _pdev
_new_mntpoint=$(get_kdump_mntpoint_from_target $_target) _new_mntpoint=$(get_kdump_mntpoint_from_target "$_target")
_fstype="${_fstype:-$(get_fs_type_from_target $_target)}" _fstype="${_fstype:-$(get_fs_type_from_target "$_target")}"
_options="${_options:-$(get_mntopt_from_target $_target)}" _options="${_options:-$(get_mntopt_from_target "$_target")}"
_options="${_options:-defaults}" _options="${_options:-defaults}"
if [[ "$_fstype" == "nfs"* ]]; then if [[ $_fstype == "nfs"* ]]; then
_pdev=$_target _pdev=$_target
_options=$(echo $_options | sed 's/,\(mount\)\?addr=[^,]*//g') _sed_cmd+='s/,\(mount\)\?addr=[^,]*//g;'
_options=$(echo $_options | sed 's/,\(mount\)\?proto=[^,]*//g') _sed_cmd+='s/,\(mount\)\?proto=[^,]*//g;'
_options=$(echo $_options | sed 's/,clientaddr=[^,]*//') _sed_cmd+='s/,clientaddr=[^,]*//;'
else else
# for non-nfs _target converting to use udev persistent name # for non-nfs _target converting to use udev persistent name
_pdev="$(kdump_get_persistent_dev $_target)" _pdev="$(kdump_get_persistent_dev "$_target")"
if [ -z "$_pdev" ]; then if [[ -z $_pdev ]]; then
return 1 return 1
fi fi
fi fi
#mount fs target as rw in 2nd kernel # mount fs target as rw in 2nd kernel
_options=$(echo $_options | sed 's/\(^\|,\)ro\($\|,\)/\1rw\2/g') _sed_cmd+='s/\(^\|,\)ro\($\|,\)/\1rw\2/g;'
# with 'noauto' in fstab nfs and non-root disk mount will fail in 2nd # with 'noauto' in fstab nfs and non-root disk mount will fail in 2nd
# kernel, filter it out here. # kernel, filter it out here.
_options=$(echo $_options | sed 's/\(^\|,\)noauto\($\|,\)/\1/g') _sed_cmd+='s/\(^\|,\)noauto\($\|,\)/\1/g;'
# use both nofail and x-systemd.before to ensure systemd will try best to # drop nofail or nobootwait
# mount it before kdump starts, this is an attempt to improve robustness _sed_cmd+='s/\(^\|,\)nofail\($\|,\)/\1/g;'
_options="$_options,nofail,x-systemd.before=initrd-fs.target" _sed_cmd+='s/\(^\|,\)nobootwait\($\|,\)/\1/g;'
_options=$(echo "$_options" | sed "$_sed_cmd")
echo "$_pdev $_new_mntpoint $_fstype $_options" echo "$_pdev $_new_mntpoint $_fstype $_options"
} }
@ -94,17 +98,16 @@ to_mount() {
#Function: get_ssh_size #Function: get_ssh_size
#$1=dump target #$1=dump target
#called from while loop and shouldn't read from stdin, so we're using "ssh -n" #called from while loop and shouldn't read from stdin, so we're using "ssh -n"
get_ssh_size() { get_ssh_size()
local _opt _out _size {
_opt="-i $SSH_KEY_LOCATION -o BatchMode=yes -o StrictHostKeyChecking=yes" local _out
_out=$(ssh -q -n $_opt $1 "df -P $SAVE_PATH") local _opt=("-i" "$SSH_KEY_LOCATION" "-o" "BatchMode=yes" "-o" "StrictHostKeyChecking=yes")
[ $? -ne 0 ] && {
perror_exit "checking remote ssh server available size failed."
}
#ssh output removed the line break, so print field NF-2 if ! _out=$(ssh -q -n "${_opt[@]}" "$1" "df" "--output=avail" "$SAVE_PATH"); then
_size=$(echo -n $_out| awk '{avail=NF-2; print $avail}') perror_exit "checking remote ssh server available size failed."
echo -n $_size fi
echo -n "$_out" | tail -1
} }
#mkdir if save path does not exist on ssh dump target #mkdir if save path does not exist on ssh dump target
@ -114,41 +117,37 @@ get_ssh_size() {
mkdir_save_path_ssh() mkdir_save_path_ssh()
{ {
local _opt _dir local _opt _dir
_opt="-i $SSH_KEY_LOCATION -o BatchMode=yes -o StrictHostKeyChecking=yes" _opt=(-i "$SSH_KEY_LOCATION" -o BatchMode=yes -o StrictHostKeyChecking=yes)
ssh -qn $_opt $1 mkdir -p $SAVE_PATH 2>&1 > /dev/null ssh -qn "${_opt[@]}" "$1" mkdir -p "$SAVE_PATH" &> /dev/null ||
_ret=$?
if [ $_ret -ne 0 ]; then
perror_exit "mkdir failed on $1:$SAVE_PATH" perror_exit "mkdir failed on $1:$SAVE_PATH"
fi
#check whether user has write permission on $1:$SAVE_PATH # check whether user has write permission on $1:$SAVE_PATH
_dir=$(ssh -qn $_opt $1 mktemp -dqp $SAVE_PATH 2>/dev/null) _dir=$(ssh -qn "${_opt[@]}" "$1" mktemp -dqp "$SAVE_PATH" 2> /dev/null) ||
_ret=$?
if [ $_ret -ne 0 ]; then
perror_exit "Could not create temporary directory on $1:$SAVE_PATH. Make sure user has write permission on destination" perror_exit "Could not create temporary directory on $1:$SAVE_PATH. Make sure user has write permission on destination"
fi ssh -qn "${_opt[@]}" "$1" rmdir "$_dir"
ssh -qn $_opt $1 rmdir $_dir
return 0 return 0
} }
#Function: get_fs_size #Function: get_fs_size
#$1=dump target #$1=dump target
get_fs_size() { get_fs_size()
local _mnt=$(get_mntpoint_from_target $1) {
echo -n $(df -P "${_mnt}/$SAVE_PATH"|tail -1|awk '{print $4}') df --output=avail "$(get_mntpoint_from_target "$1")/$SAVE_PATH" | tail -1
} }
#Function: get_raw_size #Function: get_raw_size
#$1=dump target #$1=dump target
get_raw_size() { get_raw_size()
echo -n $(fdisk -s "$1") {
fdisk -s "$1"
} }
#Function: check_size #Function: check_size
#$1: dump type string ('raw', 'fs', 'ssh') #$1: dump type string ('raw', 'fs', 'ssh')
#$2: dump target #$2: dump target
check_size() { check_size()
{
local avail memtotal local avail memtotal
memtotal=$(awk '/MemTotal/{print $2}' /proc/meminfo) memtotal=$(awk '/MemTotal/{print $2}' /proc/meminfo)
@ -164,13 +163,10 @@ check_size() {
;; ;;
*) *)
return return
esac ;;
esac || perror_exit "Check dump target size failed"
if [ $? -ne 0 ]; then if [[ $avail -lt $memtotal ]]; then
perror_exit "Check dump target size failed"
fi
if [ $avail -lt $memtotal ]; then
dwarn "Warning: There might not be enough space to save a vmcore." dwarn "Warning: There might not be enough space to save a vmcore."
dwarn " The size of $2 should be greater than $memtotal kilo bytes." dwarn " The size of $2 should be greater than $memtotal kilo bytes."
fi fi
@ -180,23 +176,45 @@ check_save_path_fs()
{ {
local _path=$1 local _path=$1
if [ ! -d $_path ]; then if [[ ! -d $_path ]]; then
perror_exit "Dump path $_path does not exist." perror_exit "Dump path $_path does not exist."
fi fi
} }
mount_failure()
{
local _target=$1
local _mnt=$2
local _fstype=$3
local msg="Failed to mount $_target"
if [[ -n $_mnt ]]; then
msg="$msg on $_mnt"
fi
msg="$msg for kdump preflight check."
if [[ $_fstype == "nfs" ]]; then
msg="$msg Please make sure nfs-utils has been installed."
fi
perror_exit "$msg"
}
check_user_configured_target() check_user_configured_target()
{ {
local _target=$1 _cfg_fs_type=$2 _mounted local _target=$1 _cfg_fs_type=$2 _mounted
local _mnt=$(get_mntpoint_from_target $_target) local _mnt _opt _fstype
local _opt=$(get_mntopt_from_target $_target)
local _fstype=$(get_fs_type_from_target $_target)
if [ -n "$_fstype" ]; then _mnt=$(get_mntpoint_from_target "$_target")
_opt=$(get_mntopt_from_target "$_target")
_fstype=$(get_fs_type_from_target "$_target")
if [[ -n $_fstype ]]; then
# In case of nfs4, nfs should be used instead, nfs* options is deprecated in kdump.conf # In case of nfs4, nfs should be used instead, nfs* options is deprecated in kdump.conf
[[ $_fstype = "nfs"* ]] && _fstype=nfs [[ $_fstype == "nfs"* ]] && _fstype=nfs
if [ -n "$_cfg_fs_type" ] && [ "$_fstype" != "$_cfg_fs_type" ]; then if [[ -n $_cfg_fs_type ]] && [[ $_fstype != "$_cfg_fs_type" ]]; then
perror_exit "\"$_target\" have a wrong type config \"$_cfg_fs_type\", expected \"$_fstype\"" perror_exit "\"$_target\" have a wrong type config \"$_cfg_fs_type\", expected \"$_fstype\""
fi fi
else else
@ -206,11 +224,10 @@ check_user_configured_target()
# For noauto mount, mount it inplace with default value. # For noauto mount, mount it inplace with default value.
# Else use the temporary target directory # Else use the temporary target directory
if [ -n "$_mnt" ]; then if [[ -n $_mnt ]]; then
if ! is_mounted "$_mnt"; then if ! is_mounted "$_mnt"; then
if [[ $_opt = *",noauto"* ]]; then if [[ $_opt == *",noauto"* ]]; then
mount $_mnt mount "$_mnt" || mount_failure "$_target" "$_mnt" "$_fstype"
[ $? -ne 0 ] && perror_exit "Failed to mount $_target on $_mnt for kdump preflight check."
_mounted=$_mnt _mounted=$_mnt
else else
perror_exit "Dump target \"$_target\" is neither mounted nor configured as \"noauto\"" perror_exit "Dump target \"$_target\" is neither mounted nor configured as \"noauto\""
@ -218,31 +235,31 @@ check_user_configured_target()
fi fi
else else
_mnt=$MKDUMPRD_TMPMNT _mnt=$MKDUMPRD_TMPMNT
mkdir -p $_mnt mkdir -p "$_mnt"
mount $_target $_mnt -t $_fstype -o defaults mount "$_target" "$_mnt" -t "$_fstype" -o defaults || mount_failure "$_target" "" "$_fstype"
[ $? -ne 0 ] && perror_exit "Failed to mount $_target for kdump preflight check."
_mounted=$_mnt _mounted=$_mnt
fi fi
# For user configured target, use $SAVE_PATH as the dump path within the target # For user configured target, use $SAVE_PATH as the dump path within the target
if [ ! -d "$_mnt/$SAVE_PATH" ]; then if [[ ! -d "$_mnt/$SAVE_PATH" ]]; then
perror_exit "Dump path \"$SAVE_PATH\" does not exist in dump target \"$_target\"" perror_exit "Dump path \"$SAVE_PATH\" does not exist in dump target \"$_target\""
fi fi
check_size fs "$_target" check_size fs "$_target"
# Unmount it early, if function is interrupted and didn't reach here, the shell trap will clear it up anyway # Unmount it early, if function is interrupted and didn't reach here, the shell trap will clear it up anyway
if [ -n "$_mounted" ]; then if [[ -n $_mounted ]]; then
umount -f -- $_mounted umount -f -- "$_mounted"
fi fi
} }
# $1: core_collector config value # $1: core_collector config value
verify_core_collector() { verify_core_collector()
{
local _cmd="${1%% *}" local _cmd="${1%% *}"
local _params="${1#${_cmd}}" local _params="${1#${_cmd}}"
if [ "$_cmd" != "makedumpfile" ]; then if [[ $_cmd != "makedumpfile" ]]; then
if is_raw_dump_target; then if is_raw_dump_target; then
dwarn "Warning: specifying a non-makedumpfile core collector, you will have to recover the vmcore manually." dwarn "Warning: specifying a non-makedumpfile core collector, you will have to recover the vmcore manually."
fi fi
@ -251,24 +268,24 @@ verify_core_collector() {
if is_ssh_dump_target || is_raw_dump_target; then if is_ssh_dump_target || is_raw_dump_target; then
if ! strstr "$_params" "-F"; then if ! strstr "$_params" "-F"; then
perror_exit "The specified dump target needs makedumpfile \"-F\" option." perror_exit 'The specified dump target needs makedumpfile "-F" option.'
fi fi
_params="$_params vmcore" _params="$_params vmcore"
else else
_params="$_params vmcore dumpfile" _params="$_params vmcore dumpfile"
fi fi
# shellcheck disable=SC2086
if ! $_cmd --check-params $_params; then if ! $_cmd --check-params $_params; then
perror_exit "makedumpfile parameter check failed." perror_exit "makedumpfile parameter check failed."
fi fi
} }
add_mount() { add_mount()
local _mnt=$(to_mount $@) {
local _mnt
if [ $? -ne 0 ]; then _mnt=$(to_mount "$@") || exit 1
exit 1
fi
add_dracut_mount "$_mnt" add_dracut_mount "$_mnt"
} }
@ -281,28 +298,15 @@ handle_default_dump_target()
is_user_configured_dump_target && return is_user_configured_dump_target && return
check_save_path_fs $SAVE_PATH check_save_path_fs "$SAVE_PATH"
_save_path=$(get_bind_mount_source $SAVE_PATH) _save_path=$(get_bind_mount_source "$SAVE_PATH")
_target=$(get_target_from_path $_save_path) _target=$(get_target_from_path "$_save_path")
_mntpoint=$(get_mntpoint_from_target $_target) _mntpoint=$(get_mntpoint_from_target "$_target")
SAVE_PATH=${_save_path##"$_mntpoint"} SAVE_PATH=${_save_path##"$_mntpoint"}
add_mount "$_target" add_mount "$_target"
check_size fs $_target check_size fs "$_target"
}
get_override_resettable()
{
local override_resettable
override_resettable=$(grep "^override_resettable" $conf_file)
if [ -n "$override_resettable" ]; then
OVERRIDE_RESETTABLE=$(echo $override_resettable | cut -d' ' -f2)
if [ "$OVERRIDE_RESETTABLE" != "0" ] && [ "$OVERRIDE_RESETTABLE" != "1" ];then
perror_exit "override_resettable value $OVERRIDE_RESETTABLE is invalid"
fi
fi
} }
# $1: function name # $1: function name
@ -311,9 +315,9 @@ for_each_block_target()
local dev majmin local dev majmin
for dev in $(get_kdump_targets); do for dev in $(get_kdump_targets); do
[ -b "$dev" ] || continue [[ -b $dev ]] || continue
majmin=$(get_maj_min $dev) majmin=$(get_maj_min "$dev")
check_block_and_slaves $1 $majmin && return 1 check_block_and_slaves "$1" "$majmin" && return 1
done done
return 0 return 0
@ -323,14 +327,13 @@ for_each_block_target()
#return false if unresettable. #return false if unresettable.
is_unresettable() is_unresettable()
{ {
local path="/sys/$(udevadm info --query=all --path=/sys/dev/block/$1 | awk '/^P:/ {print $2}' | sed -e 's/\(cciss[0-9]\+\/\).*/\1/g' -e 's/\/block\/.*$//')/resettable" local path device resettable=1
local resettable=1
if [ -f "$path" ] path="/sys/$(udevadm info --query=all --path="/sys/dev/block/$1" | awk '/^P:/ {print $2}' | sed -e 's/\(cciss[0-9]\+\/\).*/\1/g' -e 's/\/block\/.*$//')/resettable"
then if [[ -f $path ]]; then
resettable="$(cat $path)" resettable="$(< "$path")"
[ $resettable -eq 0 -a "$OVERRIDE_RESETTABLE" -eq 0 ] && { [[ $resettable -eq 0 ]] && [[ $OVERRIDE_RESETTABLE -eq 0 ]] && {
local device=$(udevadm info --query=all --path=/sys/dev/block/$1 | awk -F= '/DEVNAME/{print $2}') device=$(udevadm info --query=all --path="/sys/dev/block/$1" | awk -F= '/DEVNAME/{print $2}')
derror "Error: Can not save vmcore because device $device is unresettable" derror "Error: Can not save vmcore because device $device is unresettable"
return 0 return 0
} }
@ -343,14 +346,15 @@ is_unresettable()
#return true if resettable #return true if resettable
check_resettable() check_resettable()
{ {
local _ret _target local _target _override_resettable
get_override_resettable _override_resettable=$(kdump_get_conf_val override_resettable)
OVERRIDE_RESETTABLE=${_override_resettable:-$OVERRIDE_RESETTABLE}
if [ "$OVERRIDE_RESETTABLE" != "0" ] && [ "$OVERRIDE_RESETTABLE" != "1" ]; then
perror_exit "override_resettable value '$OVERRIDE_RESETTABLE' is invalid"
fi
for_each_block_target is_unresettable for_each_block_target is_unresettable && return
_ret=$?
[ $_ret -eq 0 ] && return
return 1 return 1
} }
@ -371,44 +375,42 @@ if ! check_resettable; then
fi fi
if ! check_crypt; then if ! check_crypt; then
dwarn "Warning: Encrypted device is in dump path. User will prompted for password during second kernel boot." dwarn "Warning: Encrypted device is in dump path, which is not recommended, see kexec-kdump-howto.txt for more details."
fi fi
# firstly get right SSH_KEY_LOCATION # firstly get right SSH_KEY_LOCATION
keyfile=$(awk '/^sshkey/ {print $2}' $conf_file) keyfile=$(kdump_get_conf_val sshkey)
if [ -f "$keyfile" ]; then if [[ -f $keyfile ]]; then
# canonicalize the path # canonicalize the path
SSH_KEY_LOCATION=$(/usr/bin/readlink -m $keyfile) SSH_KEY_LOCATION=$(/usr/bin/readlink -m "$keyfile")
fi fi
while read config_opt config_val; while read -r config_opt config_val; do
do
# remove inline comments after the end of a directive. # remove inline comments after the end of a directive.
case "$config_opt" in case "$config_opt" in
extra_modules) extra_modules)
extra_modules="$extra_modules $config_val" extra_modules="$extra_modules $config_val"
;; ;;
ext[234]|xfs|btrfs|minix|nfs) ext[234] | xfs | btrfs | minix | nfs | virtiofs)
check_user_configured_target "$config_val" "$config_opt" check_user_configured_target "$config_val" "$config_opt"
add_mount "$config_val" "$config_opt" add_mount "$config_val" "$config_opt"
;; ;;
raw) raw)
# checking raw disk writable # checking raw disk writable
dd if=$config_val count=1 of=/dev/null > /dev/null 2>&1 || { dd if="$config_val" count=1 of=/dev/null > /dev/null 2>&1 || {
perror_exit "Bad raw disk $config_val" perror_exit "Bad raw disk $config_val"
} }
_praw=$(persistent_policy="by-id" kdump_get_persistent_dev $config_val) _praw=$(persistent_policy="by-id" kdump_get_persistent_dev "$config_val")
if [ -z "$_praw" ]; then if [[ -z $_praw ]]; then
exit 1 exit 1
fi fi
add_dracut_arg "--device" "$_praw" add_dracut_arg "--device" "$_praw"
check_size raw $config_val check_size raw "$config_val"
;; ;;
ssh) ssh)
if strstr "$config_val" "@"; if strstr "$config_val" "@"; then
then mkdir_save_path_ssh "$config_val"
mkdir_save_path_ssh $config_val check_size ssh "$config_val"
check_size ssh $config_val
add_dracut_sshkey "$SSH_KEY_LOCATION" add_dracut_sshkey "$SSH_KEY_LOCATION"
else else
perror_exit "Bad ssh dump target $config_val" perror_exit "Bad ssh dump target $config_val"
@ -418,18 +420,36 @@ do
verify_core_collector "$config_val" verify_core_collector "$config_val"
;; ;;
dracut_args) dracut_args)
add_dracut_arg $config_val
;; # When users specify nfs dumping via dracut_args, kexec-tools won't
*) # mount nfs fs beforehand thus nfsv4-related drivers won't be installed
# because we call dracut with --hostonly-mode strict. So manually install
# nfsv4-related drivers.
if [[ $(get_dracut_args_fstype "$config_val") == nfs* ]]; then
add_dracut_arg "--add-drivers" nfs_layout_nfsv41_files
fi
while read -r dracut_arg; do
add_dracut_arg "$dracut_arg"
done <<< "$(echo "$config_val" | xargs -n 1 echo)"
;; ;;
*) ;;
esac esac
done <<< "$(read_strip_comments $conf_file)" done <<< "$(kdump_read_conf)"
handle_default_dump_target handle_default_dump_target
if [ -n "$extra_modules" ] if ! have_compression_in_dracut_args; then
then if is_squash_available && dracut_have_option "--squash-compressor"; then
add_dracut_arg "--add-drivers" \"$extra_modules\" add_dracut_arg "--squash-compressor" "zstd"
elif is_zstd_command_available; then
add_dracut_arg "--compress" "zstd"
fi
fi
if [[ -n $extra_modules ]]; then
add_dracut_arg "--add-drivers" "$extra_modules"
fi fi
# TODO: The below check is not needed anymore with the introduction of # TODO: The below check is not needed anymore with the introduction of
@ -440,7 +460,7 @@ fi
if ! is_fadump_capable; then if ! is_fadump_capable; then
# The 2nd rootfs mount stays behind the normal dump target mount, # The 2nd rootfs mount stays behind the normal dump target mount,
# so it doesn't affect the logic of check_dump_fs_modified(). # so it doesn't affect the logic of check_dump_fs_modified().
is_dump_to_rootfs && add_mount "$(to_dev_name $(get_root_fs_device))" is_dump_to_rootfs && add_mount "$(to_dev_name "$(get_root_fs_device)")"
add_dracut_arg "--no-hostonly-default-device" add_dracut_arg "--no-hostonly-default-device"
@ -449,4 +469,13 @@ if ! is_fadump_capable; then
fi fi
fi fi
echo "$dracut_args $@" | xargs dracut # This is RHEL-only to work around nvme problem, then real fix should go to dracut
if [[ -d /sys/module/nvme ]]; then
add_dracut_arg "--add-drivers" "nvme"
fi
dracut "${dracut_args[@]}" "$@"
_rc=$?
sync
exit $_rc

View File

@ -2,7 +2,7 @@
# Generate an initramfs image that isolates dump capture capability within # Generate an initramfs image that isolates dump capture capability within
# the default initramfs using zz-fadumpinit dracut module. # the default initramfs using zz-fadumpinit dracut module.
if [ -f /etc/sysconfig/kdump ]; then if [[ -f /etc/sysconfig/kdump ]]; then
. /etc/sysconfig/kdump . /etc/sysconfig/kdump
fi fi
@ -17,7 +17,7 @@ if ! dlog_init; then
exit 1 exit 1
fi fi
readonly MKFADUMPRD_TMPDIR="$(mktemp -d -t mkfadumprd.XXXXXX)" MKFADUMPRD_TMPDIR="$(mktemp -d -t mkfadumprd.XXXXXX)"
[ -d "$MKFADUMPRD_TMPDIR" ] || perror_exit "mkfadumprd: mktemp -d -t mkfadumprd.XXXXXX failed." [ -d "$MKFADUMPRD_TMPDIR" ] || perror_exit "mkfadumprd: mktemp -d -t mkfadumprd.XXXXXX failed."
trap ' trap '
ret=$?; ret=$?;
@ -38,27 +38,37 @@ FADUMP_INITRD="$MKFADUMPRD_TMPDIR/fadump.img"
# this file tells the initrd is fadump enabled # this file tells the initrd is fadump enabled
touch "$MKFADUMPRD_TMPDIR/fadump.initramfs" touch "$MKFADUMPRD_TMPDIR/fadump.initramfs"
ddebug "rebuild fadump initrd: $FADUMP_INITRD $DEFAULT_INITRD $KDUMP_KERNELVER" ddebug "rebuild fadump initrd: $FADUMP_INITRD $DEFAULT_INITRD $KDUMP_KERNELVER"
if ! $MKDUMPRD "$FADUMP_INITRD" -i "$MKFADUMPRD_TMPDIR/fadump.initramfs" /etc/fadump.initramfs; then # Don't use squash for capture image or default image as it negatively impacts
# compression ratio and increases the size of the initramfs image.
# Don't compress the capture image as uncompressed image is needed immediately.
# Also, early microcode would not be needed here.
if ! $MKDUMPRD "$FADUMP_INITRD" -i "$MKFADUMPRD_TMPDIR/fadump.initramfs" /etc/fadump.initramfs --omit squash --no-compress --no-early-microcode; then
perror_exit "mkfadumprd: failed to build image with dump capture support" perror_exit "mkfadumprd: failed to build image with dump capture support"
fi fi
### Unpack the initramfs having dump capture capability ### Unpack the initramfs having dump capture capability retaining previous file modification time.
# This helps in saving space by hardlinking identical files.
mkdir -p "$MKFADUMPRD_TMPDIR/fadumproot" mkdir -p "$MKFADUMPRD_TMPDIR/fadumproot"
if ! (pushd "$MKFADUMPRD_TMPDIR/fadumproot" > /dev/null && lsinitrd --unpack "$FADUMP_INITRD" && \ if ! cpio -id --preserve-modification-time --quiet -D "$MKFADUMPRD_TMPDIR/fadumproot" < "$FADUMP_INITRD"; then
popd > /dev/null); then
derror "mkfadumprd: failed to unpack '$MKFADUMPRD_TMPDIR'" derror "mkfadumprd: failed to unpack '$MKFADUMPRD_TMPDIR'"
exit 1 exit 1
fi fi
### Pack it into the normal boot initramfs with zz-fadumpinit module ### Pack it into the normal boot initramfs with zz-fadumpinit module
_dracut_isolate_args="--rebuild $REBUILD_INITRD --add zz-fadumpinit \ _dracut_isolate_args=(
-i $MKFADUMPRD_TMPDIR/fadumproot /fadumproot \ --rebuild "$REBUILD_INITRD" --add zz-fadumpinit
-i $MKFADUMPRD_TMPDIR/fadumproot/usr/lib/dracut/loaded-kernel-modules.txt -i "$MKFADUMPRD_TMPDIR/fadumproot" /fadumproot
/usr/lib/dracut/fadump-kernel-modules.txt" -i "$MKFADUMPRD_TMPDIR/fadumproot/usr/lib/dracut/hostonly-kernel-modules.txt"
/usr/lib/dracut/fadump-kernel-modules.txt
)
if is_squash_available; then # Use zstd compression method, if available
_dracut_isolate_args="$_dracut_isolate_args --add squash" if ! have_compression_in_dracut_args; then
if is_zstd_command_available; then
_dracut_isolate_args+=(--compress zstd)
fi
fi fi
if ! dracut --force --quiet $_dracut_isolate_args $@ "$TARGET_INITRD"; then
if ! dracut --force --quiet "${_dracut_isolate_args[@]}" "$@" "$TARGET_INITRD"; then
perror_exit "mkfadumprd: failed to setup '$TARGET_INITRD' with dump capture capability" perror_exit "mkfadumprd: failed to setup '$TARGET_INITRD' with dump capture capability"
fi fi

View File

@ -1,13 +0,0 @@
diff --git a/purgatory/Makefile b/purgatory/Makefile
index 49ce80a..97b7a03 100644
--- a/purgatory/Makefile
+++ b/purgatory/Makefile
@@ -67,7 +67,7 @@ $(PURGATORY): $(PURGATORY_OBJS)
$(MKDIR) -p $(@D)
$(CC) $(CFLAGS) $(LDFLAGS) -o $@.sym $^
# $(LD) $(LDFLAGS) $(EXTRA_LDFLAGS) --no-undefined -e purgatory_start -r -o $@ $(PURGATORY_OBJS) $(UTIL_LIB)
- $(STRIP) --strip-debug -o $@ $@.sym
+ $(STRIP) --strip-debug --no-merge-notes -o $@ $@.sym
echo::
@echo "PURGATORY_SRCS $(PURGATORY_SRCS)"

View File

@ -1,51 +0,0 @@
From ce720608d5933e62f77f2c2f216859cf4f06adf8 Mon Sep 17 00:00:00 2001
From: Kairui Song <kasong@redhat.com>
Date: Wed, 13 Feb 2019 00:03:51 +0800
Subject: [PATCH] Fix eppic issue with hardening flags
This is stash of two commits:
commit f98cf5fe07f390554696755f0a5843f6bb9c4716
Author: ryncsn <ryncsn@gmail.com>
Date: Tue Mar 19 13:39:25 2019 +0800
Tell gcc not to omit frame pointer
After commit 0209874, it's now possible to enable optimization above O0.
But eppic might call __builtin_return_address(1). With O1,
-fomit-frame-pointer is enabled gcc may omit frame pointer.
__builtin_return_address(1) relies on callee preserves RBP as the stack
base, which is untrue if optimization is usded. In this case it may return
wrong value or crash.
In case of any potential failure, use -fno-omit-frame-pointer globally.
Signed-off-by: Kairui Song <ryncsn@gmail.com>
commit 0209874f4b46b8af5a2d42662ba6775cf5a1dc44
Author: Kairui Song <kasong@redhat.com>
Date: Wed Feb 13 00:03:51 2019 +0800
Drop O0 CFLAGS override in Makefile
Signed-off-by: Kairui Song <kasong@redhat.com>
---
libeppic/Makefile | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/libeppic/Makefile b/libeppic/Makefile
index bcf2edf..8b97c87 100644
--- a/eppic/libeppic/Makefile
+++ b/eppic/libeppic/Makefile
@@ -24,7 +24,7 @@ LDIRT = lex.eppic.c lex.eppicpp.c eppic.tab.c eppic.tab.h eppicpp.tab.c \
LIBDIR = /usr/lib
TARGETS = libeppic.a
-CFLAGS += -O0 -g -fPIC
+CFLAGS += -g -fno-omit-frame-pointer -fPIC
ifeq ($(TARGET), PPC64)
CFLAGS += -m64
endif
--
2.20.1

View File

@ -1,88 +0,0 @@
From 0f632fa180e5a44219ab6bbe0879c3583f8c65cf Mon Sep 17 00:00:00 2001
From: Pingfan Liu <piliu@redhat.com>
Date: Tue, 9 Nov 2021 11:24:22 +0800
Subject: [PATCH] RHEL-only
Cope with RHEL8 kernel
Signed-off-by: Pingfan Liu <piliu@redhat.com>
---
arch/arm64.c | 14 +++++++++++++-
makedumpfile.c | 2 ++
makedumpfile.h | 1 +
3 files changed, 16 insertions(+), 1 deletion(-)
diff --git a/makedumpfile-1.7.2/arch/arm64.c b/makedumpfile-1.7.2/arch/arm64.c
index 1072178..95beae6 100644
--- a/makedumpfile-1.7.2/arch/arm64.c
+++ b/makedumpfile-1.7.2/arch/arm64.c
@@ -50,6 +50,7 @@ static int va_bits;
static int vabits_actual;
static int flipped_va;
static unsigned long kimage_voffset;
+static int max_user_va_bits;
#define SZ_4K 4096
#define SZ_16K 16384
@@ -108,7 +109,7 @@ typedef unsigned long pgdval_t;
#define PGDIR_SHIFT ARM64_HW_PGTABLE_LEVEL_SHIFT(4 - (pgtable_level))
#define PGDIR_SIZE (_AC(1, UL) << PGDIR_SHIFT)
#define PGDIR_MASK (~(PGDIR_SIZE-1))
-#define PTRS_PER_PGD (1 << ((va_bits) - PGDIR_SHIFT))
+#define PTRS_PER_PGD (1 << ((max_user_va_bits) - PGDIR_SHIFT))
/*
* Section address mask and size definitions.
@@ -449,6 +450,17 @@ get_machdep_info_arm64(void)
ERRMSG("Can't determine platform config values\n");
return FALSE;
}
+ if (NUMBER(MAX_USER_VA_BITS) != NOT_FOUND_NUMBER) {
+ max_user_va_bits = NUMBER(MAX_USER_VA_BITS);
+ DEBUG_MSG("max_user_va_bits : %d (vmcoreinfo)\n",
+ max_user_va_bits);
+ }
+ if (!max_user_va_bits) {
+ max_user_va_bits = va_bits;
+ DEBUG_MSG("max_user_va_bits : %d (default = va_bits)\n",
+ max_user_va_bits);
+ }
+
kimage_voffset = NUMBER(kimage_voffset);
info->section_size_bits = SECTIONS_SIZE_BITS;
diff --git a/makedumpfile-1.7.2/makedumpfile.c b/makedumpfile-1.7.2/makedumpfile.c
index 3ad4443..018ea4c 100644
--- a/makedumpfile-1.7.2/makedumpfile.c
+++ b/makedumpfile-1.7.2/makedumpfile.c
@@ -2417,6 +2417,7 @@ write_vmcoreinfo_data(void)
WRITE_NUMBER("HUGETLB_PAGE_DTOR", HUGETLB_PAGE_DTOR);
#ifdef __aarch64__
+ WRITE_NUMBER("MAX_USER_VA_BITS", MAX_USER_VA_BITS);
WRITE_NUMBER("VA_BITS", VA_BITS);
/* WRITE_NUMBER("TCR_EL1_T1SZ", TCR_EL1_T1SZ); should not exists */
WRITE_NUMBER_UNSIGNED("PHYS_OFFSET", PHYS_OFFSET);
@@ -2863,6 +2864,7 @@ read_vmcoreinfo(void)
READ_NUMBER("phys_base", phys_base);
READ_NUMBER("KERNEL_IMAGE_SIZE", KERNEL_IMAGE_SIZE);
#ifdef __aarch64__
+ READ_NUMBER("MAX_USER_VA_BITS", MAX_USER_VA_BITS);
READ_NUMBER("VA_BITS", VA_BITS);
READ_NUMBER("TCR_EL1_T1SZ", TCR_EL1_T1SZ);
READ_NUMBER_UNSIGNED("PHYS_OFFSET", PHYS_OFFSET);
diff --git a/makedumpfile-1.7.2/makedumpfile.h b/makedumpfile-1.7.2/makedumpfile.h
index e59239d..b6236dd 100644
--- a/makedumpfile-1.7.2/makedumpfile.h
+++ b/makedumpfile-1.7.2/makedumpfile.h
@@ -2064,6 +2064,7 @@ struct number_table {
long phys_base;
long KERNEL_IMAGE_SIZE;
#ifdef __aarch64__
+ long MAX_USER_VA_BITS;
long VA_BITS;
long TCR_EL1_T1SZ;
unsigned long PHYS_OFFSET;
--
2.31.1

View File

@ -40,24 +40,24 @@ storage:
FC disks (qla2xxx, lpfc, bnx2fc, bfa) FC disks (qla2xxx, lpfc, bnx2fc, bfa)
software initiator based iSCSI software initiator based iSCSI
software RAID (mdraid) software RAID (mdraid)
hardware RAID (cciss, hpsa, megaraid_sas, mpt2sas, aacraid) hardware RAID (smartpqi, hpsa, megaraid, mpt3sas, aacraid, mpi3mr)
SCSI/SATA disks SCSI/SATA disks
iSCSI HBA (all offload) iSCSI HBA (all offload)
hardware FCoE (qla2xxx, lpfc) hardware FCoE (qla2xxx, lpfc)
software FCoE (bnx2fc) (Extra configuration required, software FCoE (bnx2fc) (Extra configuration required,
please read "Note on FCoE" section below) please read "Note on FCoE" section below)
NVMe-FC (qla2xxx, lpfc)
network: network:
Hardware using kernel modules: (tg3, igb, ixgbe, sfc, e1000e, bna, Hardware using kernel modules: (igb, ixgbe, ice, i40e, e1000e, igc,
cnic, netxen_nic, qlge, bnx2x, bnx, qlcnic, be2net, enic, tg3, bnx2x, bnxt_en, qede, cxgb4, be2net, enic, sfc, mlx4_en,
virtio-net, ixgbevf, igbvf) mlx5_core, r8169, atlantic, nfp, ionic; nicvf (aarch64 only))
protocol: ipv4 protocol: ipv4
bonding bonding
vlan vlan
bridge bridge
team
vlan tagged bonding vlan tagged bonding
bridge over bond/team/vlan bridge over bond/vlan
hypervisor: hypervisor:
kvm kvm
@ -67,14 +67,17 @@ filesystem:
ext[234] ext[234]
xfs xfs
nfs nfs
virtiofs
firmware: firmware:
BIOS BIOS
UEFI UEFI
hypervisor: hypervisor:
VMWare ESXi 4.1 and 5.1 VMWare ESXi 4.x 5.x would not be tested/supported any more.
Hyper-V 2012 R2 (RHEL Gen1 UP Guest only) only support ESXi 6.6, 6.7, 7.0
Hyper-V 2012 R2 (RHEL Gen1 UP Guest only), later version will
also be tested/supported
Unsupported Dump targets Unsupported Dump targets
------------------------ ------------------------
@ -114,15 +117,5 @@ issue, because some software FCoE requires more memory to work. In such case,
you may need to increase the kdump reserved memory size in "crashkernel=" you may need to increase the kdump reserved memory size in "crashkernel="
kernel parameter. kernel parameter.
By default, RHEL systems have "crashkernel=auto" in kernel boot arguments.
The auto reserved memory size is designed to balance the coverage of use cases
and an acceptable memory overhead, so not every use case could fit in, software
FCoE is one of the case.
For hardware FCoE, kdump should work naturally as firmware will do the For hardware FCoE, kdump should work naturally as firmware will do the
initialization job. The capture kernel and kdump tools will run just fine. initialization job. The capture kernel and kdump tools will run just fine.
Useful Links
============
[1] RHEL6: Enabling kdump for full-virt (HVM) Xen DomU
(https://access.redhat.com/knowledge/solutions/92943)

File diff suppressed because it is too large Load Diff