The function is pretty broken right now. To start with the -o/--omit
option allows a quoted, space separated list of modules. But using 'set'
breaks quotation and thus only considers the first element in the list.
Furthermore dracut uses getopt internally. This means that it is also
possible to pass the list via --omit=.
Fix the function by making use of getopt for parsing the dracut_args.
While at it also add a test cases to cover the functions.
Signed-off-by: Philipp Rudo <prudo(a)redhat.com>
---
kdumpctl | 52 ++++++++++++++++++++++++++++-------
kexec-tools.spec | 1 +
spec/kdumpctl_general_spec.sh | 48 ++++++++++++++++++++++++++++++++
3 files changed, 91 insertions(+), 10 deletions(-)
diff --git a/kdumpctl b/kdumpctl
index ee711ac..8c2c422 100755
--- a/kdumpctl
+++ b/kdumpctl
@@ -45,23 +45,55 @@ if ! dlog_init; then
exit 1
fi
-# returns 0 when omission of a module is desired in dracut_args
-# returns 1 otherwise
-is_dracut_mod_omitted()
+_get_dracut_arg()
{
- local dracut_args dracut_mod=$1
+ local shortopt longopt n tmp
+ local -a _opt _ret
+
+ shortopt=$1; shift
+ longopt=$1; shift
+ n=0
- set -- $(kdump_get_conf_val dracut_args)
- while [ $# -gt 0 ]; do
+ if [[ -n $shortopt ]]; then
+ _opt+=(-o "${shortopt#-}:")
+ else
+ # getopt requires the -o/--option to be set.
+ _opt+=(-o "")
+ fi
+ [[ -n $longopt ]] && _opt+=(--long "${longopt#--}:")
+
+ # make sure bash didn't break quoting
+ eval set -- "$*"
+ tmp=$(
+ unset POSIXLY_CORRECT
+ getopt -q "${_opt[@]}" -- "$@"
+ )
+ eval set -- "$tmp"
+ while :; do
case $1 in
- -o | --omit)
- [[ " ${2//[^[:alnum:]]/ } " == *" $dracut_mod "* ]] &&
return 0
- ;;
+ "$shortopt"|"$longopt")
+ _ret+=("$2"); shift
+ n=$((n+1))
+ ;;
+ --|*)
+ break
+ ;;
esac
shift
done
- return 1
+ echo "${_ret[@]}"
+ return $n
+}
+
+is_dracut_mod_omitted()
+{
+ local mod omitted
+
+ mod=$1
+ omitted=$(_get_dracut_arg -o --omit "${OPT[dracut_args]}")
+
+ [[ " $omitted " == *" $mod "* ]]
}
single_instance_lock()
diff --git a/kexec-tools.spec b/kexec-tools.spec
index 5c42af6..0156767 100644
--- a/kexec-tools.spec
+++ b/kexec-tools.spec
@@ -65,6 +65,7 @@ Requires: dracut >= 050
Requires: dracut-network >= 050
Requires: dracut-squash >= 050
Requires: ethtool
+Requires: util-linx
Recommends: grubby
Recommends: hostname
BuildRequires: make
diff --git a/spec/kdumpctl_general_spec.sh b/spec/kdumpctl_general_spec.sh
index 41fbc29..bb5755c 100644
--- a/spec/kdumpctl_general_spec.sh
+++ b/spec/kdumpctl_general_spec.sh
@@ -107,6 +107,54 @@ Describe 'kdumpctl'
End
End
+ Describe "_get_dracut_arg"
+ dracut_args='-o "foo bar baz" -t 1 --test="a b c" --omit
bla'
+ Parameters
+ -o --omit 2 "foo bar baz bla"
+ -e --empty 0 ""
+ -t "" 1 "1"
+ "" --test 1 "a b c"
+ "" "" 0 ""
+ End
+ It "should parse the dracut_args correctly"
+ When call _get_dracut_arg "$1" "$2" "$dracut_args"
+ The status should equal $3
+ The output should equal "$4"
+ End
+ End
+
+ Describe "is_dracut_mod_omitted()"
+ KDUMP_CONFIG_FILE=$(mktemp -t kdump_conf.XXXXXXXXXX)
+ cleanup() {
+ rm -f "$kdump_conf"
+ }
+ AfterAll 'cleanup'
+
+ Parameters:dynamic
+ for opt in '-o ' '--omit ' '--omit='; do
+ for val in \
+ 'foo' \
+ '"foo"' \
+ '"foo bar baz"' \
+ '"bar foo baz"' \
+ '"bar baz foo"'; do
+ %data success foo "$opt$val"
+ %data success foo "-a x $opt$val -i y"
+ %data failure xyz "$opt$val"
+ %data failure xyz "-a x $opt$val -i y"
+ done
+ done
+ %data success foo "-o xxx -o foo"
+ %data failure foo "-a x -i y"
+ End
+ It "shall return $1 for module $2 and dracut_args '$3'"
+ echo "dracut_args $3" > $KDUMP_CONFIG_FILE
+ parse_config
+ When call is_dracut_mod_omitted $2
+ The status should be $1
+ End
+ End
+
Describe '_update_kernel_arg_in_grub_etc_default()'
GRUB_ETC_DEFAULT=/tmp/default_grub
--
2.39.2