Skip to content

Commit c4e7656

Browse files
committed
mkdumprd: basic support for btrfs subvol
The kdump scripts previously could not correctly handle cases where the dump target was located on a btrfs subvolume. The logic for finding the mount point did not account for the way subvolumes are represented, leading to failures in identifying the target device and checking for available space. This patch introduces support for btrfs subvolumes by: 1. Adding a new helper function `get_btrfs_subvol_from_mntopt` to extract the subvolume name from mount options. 2. Modifying `get_mntpoint_from_target` to accept a subvolume name. When a subvolume is provided, it correctly identifies the mount point by looking for the source entry that includes the subvolume name (e.g., `/dev/sda1[/subvol]`). 3. Updating various functions in `mkdumprd`, `kdump-lib.sh`, and the dracut module setup scripts to detect if the target is on a btrfs filesystem, parse the subvolume, and pass it to the relevant functions for mount point resolution and free space checks. This ensures that kdump can now be reliably configured with a dump target located on a btrfs subvolume. Signed-off-by: Lichen Liu <[email protected]>
1 parent d70f205 commit c4e7656

File tree

4 files changed

+46
-22
lines changed

4 files changed

+46
-22
lines changed

dracut/99kdumpbase/module-setup.sh

Lines changed: 8 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -683,16 +683,21 @@ kdump_install_pre_post_conf() {
683683
}
684684

685685
default_dump_target_install_conf() {
686-
local _target _fstype
686+
local _target _fstype _subvol _options
687687
local _mntpoint _save_path
688688

689689
is_user_configured_dump_target && return
690690

691691
_save_path=$(get_bind_mount_source "$(get_save_path)")
692692
_target=$(get_target_from_path "$_save_path")
693-
_mntpoint=$(get_mntpoint_from_target "$_target")
694-
693+
_options=$(get_mount_info OPTIONS target "$_save_path" -f)
695694
_fstype=$(get_fs_type_from_target "$_target")
695+
if [[ $_fstype == btrfs ]]; then
696+
_subvol=$(get_btrfs_subvol_from_mntopt "$_options")
697+
fi
698+
699+
_mntpoint=$(get_mntpoint_from_target "$_target" "$_subvol")
700+
696701
if is_fs_type_nfs "$_fstype"; then
697702
kdump_collect_netif_usage "$_target"
698703
_fstype="nfs"

kdump-lib-initramfs.sh

Lines changed: 16 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -109,15 +109,27 @@ get_fs_type_from_target()
109109

110110
get_mntpoint_from_target()
111111
{
112-
# get the first TARGET when SOURCE doesn't end with ].
113-
# In most cases, a SOURCE ends with ] when fsroot or subvol exists.
114-
_mntpoint=$(get_mount_info TARGET,SOURCE source "$1" | grep -v "\]$" | awk 'NR==1 { print $1 }')
115-
112+
_subvol="$2"
113+
if [ -z "$_subvol" ]; then
114+
# get the first TARGET when SOURCE doesn't end with ].
115+
# In most cases, a SOURCE ends with ] when fsroot or subvol exists.
116+
_mntpoint=$(get_mount_info TARGET,SOURCE source "$1" | grep -v "\]$" | awk 'NR==1 { print $1 }')
117+
else
118+
# btrfs with subvol
119+
_mntpoint=$(get_mount_info TARGET,SOURCE source "$1" | grep "\[$_subvol\]$" | awk 'NR==1 { print $1 }')
120+
fi
116121
# fallback to the old way when _mntpoint is empty.
117122
[ -n "$_mntpoint" ] || _mntpoint=$(get_mount_info TARGET source "$1" -f)
118123
echo "$_mntpoint"
119124
}
120125

126+
get_btrfs_subvol_from_mntopt()
127+
{
128+
_subvol=${1#*subvol=}
129+
_subvol=${_subvol%,*}
130+
echo "$_subvol"
131+
}
132+
121133
is_ssh_dump_target()
122134
{
123135
kdump_get_conf_val ssh | grep -q @

kdump-lib.sh

Lines changed: 6 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -188,7 +188,7 @@ get_kdump_targets()
188188
# part is the bind mounted directory which quotes by bracket "[]".
189189
get_bind_mount_source()
190190
{
191-
local _mnt _path _src _opt _fstype
191+
local _mnt _path _src _opt _fstype _subvol
192192
local _fsroot _src_nofsroot
193193

194194
_mnt=$(df "$1" | tail -1 | awk '{print $NF}')
@@ -211,15 +211,13 @@ get_bind_mount_source()
211211

212212
_fsroot=${_src#"${_src_nofsroot}"[}
213213
_fsroot=${_fsroot%]}
214-
_mnt=$(get_mntpoint_from_target "$_src_nofsroot")
215-
216214
# for btrfs, _fsroot will also contain the subvol value as well, strip it
217215
if [[ $_fstype == btrfs ]]; then
218-
local _subvol
219-
_subvol=${_opt#*subvol=}
220-
_subvol=${_subvol%,*}
216+
_subvol=$(get_btrfs_subvol_from_mntopt "$_opt")
221217
_fsroot=${_fsroot#"$_subvol"}
222218
fi
219+
_mnt=$(get_mntpoint_from_target "$_src_nofsroot" "$_subvol")
220+
223221
echo "$_mnt$_fsroot$_path"
224222
}
225223

@@ -230,11 +228,12 @@ get_mntopt_from_target()
230228

231229
# Get the path where the target will be mounted in kdump kernel
232230
# $1: kdump target device
231+
# $2: btrfs subvol
233232
get_kdump_mntpoint_from_target()
234233
{
235234
local _mntpoint
236235

237-
_mntpoint=$(get_mntpoint_from_target "$1")
236+
_mntpoint=$(get_mntpoint_from_target "$1" "$2")
238237
# mount under /sysroot if dump to root disk or mount under
239238
# mount under /kdumproot if dump target is not mounted in first kernel
240239
# mount under /kdumproot/$_mntpoint in other cases in 2nd kernel.

mkdumprd

Lines changed: 16 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -76,10 +76,13 @@ to_mount()
7676
{
7777
local _target=$1 _fstype=$2 _options=$3 _sed_cmd _new_mntpoint _pdev
7878

79-
_new_mntpoint=$(get_kdump_mntpoint_from_target "$_target")
8079
_fstype="${_fstype:-$(get_fs_type_from_target "$_target")}"
8180
_options="${_options:-$(get_mntopt_from_target "$_target")}"
8281
_options="${_options:-defaults}"
82+
if [[ $_fstype == btrfs ]]; then
83+
_subvol=$(get_btrfs_subvol_from_mntopt "$_options")
84+
fi
85+
_new_mntpoint=$(get_kdump_mntpoint_from_target "$_target" "$_subvol")
8386

8487
if [[ $_fstype == "nfs"* ]]; then
8588
_pdev=$_target
@@ -146,7 +149,7 @@ mkdir_save_path_ssh()
146149
#$1=dump target
147150
get_fs_size()
148151
{
149-
df --output=avail "$(get_mntpoint_from_target "$1")/$SAVE_PATH" | tail -1
152+
df --output=avail "$(get_mntpoint_from_target "$1" "$2")/$SAVE_PATH" | tail -1
150153
}
151154

152155
#Function: get_raw_size
@@ -159,6 +162,7 @@ get_raw_size()
159162
#Function: check_size
160163
#$1: dump type string ('raw', 'fs', 'ssh')
161164
#$2: dump target
165+
#$3: btrfs subvol
162166
check_size()
163167
{
164168
local avail memtotal
@@ -172,7 +176,7 @@ check_size()
172176
avail=$(get_ssh_size "$2")
173177
;;
174178
fs)
175-
avail=$(get_fs_size "$2")
179+
avail=$(get_fs_size "$2" "$3")
176180
;;
177181
*)
178182
return
@@ -302,20 +306,24 @@ add_mount()
302306
#handle the case user does not specify the dump target explicitly
303307
handle_default_dump_target()
304308
{
305-
local _target
306-
local _mntpoint
309+
local _target _mntpoint _fstype _subvol _options
307310

308311
is_user_configured_dump_target && return
309312

310313
check_save_path_fs "$SAVE_PATH"
311314

312315
_save_path=$(get_bind_mount_source "$SAVE_PATH")
316+
_options=$(get_mount_info OPTIONS target "$_save_path" -f)
313317
_target=$(get_target_from_path "$_save_path")
314-
_mntpoint=$(get_mntpoint_from_target "$_target")
318+
_fstype=$(get_fs_type_from_target "$_target")
319+
if [[ $_fstype == btrfs ]]; then
320+
_subvol=$(get_btrfs_subvol_from_mntopt "$_options")
321+
fi
315322

323+
_mntpoint=$(get_mntpoint_from_target "$_target" "$_subvol")
316324
SAVE_PATH=${_save_path##"$_mntpoint"}
317-
add_mount "$_target"
318-
check_size fs "$_target"
325+
add_mount "$_target" "$_fstype" "$_options"
326+
check_size fs "$_target" "$_subvol"
319327
}
320328

321329
# firstly get right SSH_KEY_LOCATION

0 commit comments

Comments
 (0)