From 38cad9c5bb48ebca7fa171b1e18f06bfdf6fd472 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Vin=C3=ADcius=20Ferr=C3=A3o?= <2031761+viniciusferrao@users.noreply.github.com> Date: Mon, 17 Aug 2026 14:34:37 -0300 Subject: [PATCH 1/7] fix(enablekdump): stage the NFS dump setup under a per-node directory For the RHEL 7/8 NFS path, enablekdump created var/crash and a dummy proc file at the root of the shared dump export, from every node, at deploy. It also mounted the export over a general-purpose directory such as /mnt. kdump checks that the dump path exists on the target when it builds the initrd, so the path has to exist at deploy time. Create only this node's own subdirectory, $NODE/var/crash, and point kdump.conf at path /$NODE/var/crash. Each node now writes only under its own subdir, so nodes no longer share or collide at the export root, and the dump lands in the node's directory. The setup mounts a dedicated /mnt/kdumpsetup rather than a general-purpose directory. The dummy proc file only ever mattered to the RHEL 7 dracut check, which wants root= to look like a real filesystem. Keep it for RHEL 7, per node, and point root= at $KDIP:$KDPATH/$NODE. RHEL 8 no longer writes it. This design was identified by a lenovobuild change and validated on a running node: a real kernel panic saved the vmcore under the node's own directory, and nothing was written to the export root. --- xCAT/postscripts/enablekdump | 33 ++++++++++++++++----------------- 1 file changed, 16 insertions(+), 17 deletions(-) diff --git a/xCAT/postscripts/enablekdump b/xCAT/postscripts/enablekdump index 55ca75d7d..5e9127372 100755 --- a/xCAT/postscripts/enablekdump +++ b/xCAT/postscripts/enablekdump @@ -92,16 +92,13 @@ if [ ! -z "$DUMP" ]; then KDIP=${XCAT%:*} fi - # workaround for RHEL6 + # xCAT sets NODE in the postscript environment; fall back to the short + # hostname so a per-node dump path is still used if run by hand. + [ -z "$NODE" ] && NODE=$(hostname -s) + # the $KDIP:$KDPATH directory will be used to generate the initrd for kdump service - MOUNTPATH="" - if (pmatch $OSVER "*6\.*"); then - MOUNTPATH="/tmp" - elif (pmatch $OSVER "*[78]\.*"); then - MOUNTPATH="/mnt" - else - MOUNTPATH="/var/tmp" - fi + MOUNTPATH="/mnt/kdumpsetup" + mkdir -p $MOUNTPATH if [ "$KDPROTO" = "nfs" ]; then if (pmatch $OSVER "sle*") || (pmatch $OSVER "suse*") || [ -f /etc/SuSE-release ] || [ -f /etc/SUSE-brand ]; then @@ -238,16 +235,14 @@ EOF else /bin/echo "nfs server is not available" fi - [ -d $MOUNTPATH/var/crash ] || mkdir -p $MOUNTPATH/var/crash - - #The initramfs used in kdump does not need "root", however, the initramfs refused to continue - #if no valid "root" provided in redhat7.1 kdump; As a workaround,we provide a fake "root=nfs:$KDIP:$KDPATH" - #with a dummy "proc" inside, which will fake "root=nfs:$KDIP:$KDPATH" as a valid root directory - [ -e $MOUNTPATH/proc ] || echo "Dummy file: fake the /proc to pass the checking of 'root=' inside dracut-cmdline " > $MOUNTPATH/proc + # Create only this node's own subdirectory on the dump target. + # kdump checks the dump path exists when it builds the initrd, so + # it must exist now, at deploy time. + mkdir -p $MOUNTPATH/$NODE/var/crash echo "nfs $KDIP:$KDPATH" > /etc/kdump.conf echo "default shell" >> /etc/kdump.conf - echo "path /var/crash" >> /etc/kdump.conf + echo "path /$NODE/var/crash" >> /etc/kdump.conf echo "core_collector makedumpfile -c --message-level 1 -d 31" >> /etc/kdump.conf #strip "xcat" out of the initramfs for kdump echo "dracut_args --omit \"xcat\"" >> /etc/kdump.conf @@ -264,7 +259,11 @@ EOF done sed -i "s#^[\t ]*KDUMP_COMMANDLINE=\"#KDUMP_COMMANDLINE=\"$kdumpcmdline#" /etc/sysconfig/kdump if (pmatch $OSVER "rhel7*") || (pmatch $OSVER "rhels7*"); then - sed -i "s#^[\t ]*KDUMP_COMMANDLINE_APPEND=\"#KDUMP_COMMANDLINE_APPEND=\"root=nfs:$KDIP:$KDPATH #" /etc/sysconfig/kdump + # The RHEL7 kdump initramfs refuses to continue unless root= + # names a valid filesystem, checked by dracut-cmdline at crash + # time, so give this node's subdir a dummy /proc for it. + [ -e $MOUNTPATH/$NODE/proc ] || echo "xCAT: dummy /proc so RHEL7 dracut-cmdline accepts root=" > $MOUNTPATH/$NODE/proc + sed -i "s#^[\t ]*KDUMP_COMMANDLINE_APPEND=\"#KDUMP_COMMANDLINE_APPEND=\"root=nfs:$KDIP:$KDPATH/$NODE #" /etc/sysconfig/kdump fi [ -f /etc/dracut.conf ] && mv /etc/dracut.conf /tmp/dracut.conf restartservice kdump From a2cf00295982ebbf9453934667e2091e1bc91dfc Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Vin=C3=ADcius=20Ferr=C3=A3o?= <2031761+viniciusferrao@users.noreply.github.com> Date: Mon, 17 Aug 2026 14:34:37 -0300 Subject: [PATCH 2/7] test(enablekdump): cover the per-node NFS dump staging Runs the RHEL NFS path of the postscript against a scratch tree that stands in for the mounted dump export. Checks that kdump.conf points at the node's own subdirectory, that only that subdirectory is created on the target, and that nothing lands at the export root. RHEL 7 keeps the dracut workaround but under the node subdirectory. Five of the eight assertions fail against the previous behavior. --- xCAT-test/unit/enablekdump_per_node.t | 105 ++++++++++++++++++++++++++ 1 file changed, 105 insertions(+) create mode 100644 xCAT-test/unit/enablekdump_per_node.t diff --git a/xCAT-test/unit/enablekdump_per_node.t b/xCAT-test/unit/enablekdump_per_node.t new file mode 100644 index 000000000..e17730e28 --- /dev/null +++ b/xCAT-test/unit/enablekdump_per_node.t @@ -0,0 +1,105 @@ +#!/usr/bin/env perl +use strict; +use warnings; + +use File::Path qw(make_path); +use File::Temp qw(tempdir); +use FindBin; +use Test::More; + +my $script = "$FindBin::Bin/../../xCAT/postscripts/enablekdump"; +plan skip_all => 'enablekdump not found' unless -r $script; +# The postscript uses GNU sed -i, which behaves differently on BSD. +plan skip_all => 'postscript targets Linux nodes' unless $^O eq 'linux'; + +my $source = read_file($script); + +# Run the RHEL NFS path of enablekdump against a scratch tree. The dump target +# is a local directory standing in for the mounted NFS export, so we can check +# what the postscript writes to it and to /etc/kdump.conf. +sub run_enablekdump { + my (%opt) = @_; + my $osver = $opt{osver}; + my $node = $opt{node} || 'n01'; + + my $root = tempdir(CLEANUP => 1); + make_path("$root/etc/sysconfig", "$root/target", "$root/bin"); + + # /etc/sysconfig/kdump must exist for the in-place seds to land. + write_file("$root/etc/sysconfig/kdump", + "KDUMP_COMMANDLINE=\"\"\nKDUMP_COMMANDLINE_APPEND=\"\"\n"); + # xcatlib.sh is sourced; only restartservice is needed and is a no-op here. + write_file("$root/xcatlib.sh", "restartservice(){ :; }\n"); + write_file("$root/bin/logger", "#!/bin/sh\nexit 0\n"); + chmod 0755, "$root/bin/logger"; + + my $src = $source; + # Redirect everything the postscript touches into the scratch tree. + $src =~ s{/etc/kdump\.conf}{$root/etc/kdump.conf}g; + $src =~ s{/etc/sysconfig/kdump}{$root/etc/sysconfig/kdump}g; + $src =~ s{/etc/dracut\.conf}{$root/etc/dracut.conf}g; + $src =~ s{/tmp/dracut\.conf}{$root/tmp/dracut.conf}g; + # No real NFS server: make the version probe empty so the mount is skipped; + # the per-node mkdir and kdump.conf rendering still run against the target. + $src =~ s{/usr/sbin/rpcinfo}{/bin/false}g; + $src =~ s{/bin/mount}{true}g; + $src =~ s{/bin/umount}{true}g; + # Point the staging mount point at the scratch target that stands in for the + # mounted NFS export. + $src =~ s{/mnt/kdumpsetup}{$root/target}g; + + write_file("$root/enablekdump", $src); + chmod 0755, "$root/enablekdump"; + + my $dump = "nfs://10.0.0.1/dumparea"; + system(qq{cd '$root' && DUMP='$dump' XCAT='10.0.0.1:eth0' OSVER='$osver' } + . qq{ARCH='x86_64' NODE='$node' PATH="$root/bin:\$PATH" ./enablekdump >/dev/null 2>&1}); + + return { + root => $root, + target => "$root/target", + kdump_conf => read_file("$root/etc/kdump.conf"), + sysconfig => read_file("$root/etc/sysconfig/kdump"), + }; +} + +sub read_file { + my ($p) = @_; + return '' unless -e $p; + open my $fh, '<', $p or die "open $p: $!"; + local $/; + return <$fh>; +} + +sub write_file { + my ($p, $c) = @_; + open my $fh, '>', $p or die "open $p: $!"; + print {$fh} $c; + close $fh; + return; +} + +# --- RHEL 8: per-node, no shared-root writes ------------------------------- +{ + my $r = run_enablekdump(osver => 'rhels8.0', node => 'n01'); + + like($r->{kdump_conf}, qr{^path\s+/n01/var/crash$}m, + 'kdump.conf points the dump path at the node subdirectory'); + unlike($r->{kdump_conf}, qr{^path\s+/var/crash$}m, + 'kdump.conf does not use the shared /var/crash path'); + ok(-d "$r->{target}/n01/var/crash", 'the node subdirectory is created on the target'); + ok(!-e "$r->{target}/var/crash", 'nothing is created at the shared export root'); + ok(!-e "$r->{target}/proc", 'no dummy proc file is written on RHEL 8'); +} + +# --- RHEL 7: keeps the dracut workaround, but per-node ---------------------- +{ + my $r = run_enablekdump(osver => 'rhels7.9', node => 'n07'); + + like($r->{sysconfig}, qr{root=nfs:10\.0\.0\.1:/dumparea/n07}, + 'the RHEL 7 root= workaround points at the node subdirectory'); + ok(-e "$r->{target}/n07/proc", 'the RHEL 7 dummy proc is written under the node subdirectory'); + ok(!-e "$r->{target}/proc", 'the RHEL 7 dummy proc is not written at the shared root'); +} + +done_testing(); From eec50e14a2cd453f7da98f1cca3c218647517834 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Vin=C3=ADcius=20Ferr=C3=A3o?= <2031761+viniciusferrao@users.noreply.github.com> Date: Mon, 17 Aug 2026 14:34:38 -0300 Subject: [PATCH 3/7] docs(kdump): document the per-node dump path for RHEL 7 and 8 The RHEL 7/8 crash dump now lands under the node's own subdirectory on the NFS export, matching the layout SLES already uses. --- .../manage_clusters/common/deployment/enable_kdump.rst | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/docs/source/guides/admin-guides/manage_clusters/common/deployment/enable_kdump.rst b/docs/source/guides/admin-guides/manage_clusters/common/deployment/enable_kdump.rst index f6e9c3fbd..016fafde0 100644 --- a/docs/source/guides/admin-guides/manage_clusters/common/deployment/enable_kdump.rst +++ b/docs/source/guides/admin-guides/manage_clusters/common/deployment/enable_kdump.rst @@ -132,7 +132,11 @@ Check your Operating System specific documentation for the path where the kernel * **[RHELS6]** :: /var/crash/-