diff --git a/bash_completion b/bash_completion
index 9b8c2138fc0..4128da65351 100644
--- a/bash_completion
+++ b/bash_completion
@@ -791,6 +791,8 @@ _comp_compgen__call_generator()
local _comp_compgen__append=$_append
local _comp_compgen__var=$_var
local _comp_compgen__cur=$_cur cur=$_cur
+ local _comp_compgen__dir=$_dir
+ local _comp_compgen__prefix=$_prefix
if [[ $_prefix ]]; then
local -a tmp=()
local _comp_compgen__var=tmp
@@ -1286,11 +1288,11 @@ _comp_quote_compgen()
# Ignored with `-d`.
# OPTIONS
# -d Complete only on directories
+
# -f Perform `compopt -o filenames` modifications manually. This
-# suffixes a slash to a directory name. This can be combined with
-# the `-C dir` option to `_comp_compgen`, where the generated
-# filenames do not exist in the current working directory and Bash
-# fails to properly detect the filenames.
+# suffixes a slash to a directory name. When "-C
" or "-P
+# " is specified to the caller "_comp_compgen", this option
+# is automatically turned on.
# @return 0 if at least one completion is generated, or 1 otherwise.
#
# @since 2.12
@@ -1300,6 +1302,19 @@ _comp_compgen_filedir()
local -a toks
local _dir="" _filenames=""
+ if [[ ${_comp_compgen__dir-} || ${_comp_compgen__prefix-} ]]; then
+ # When "-C " or "-P " is specified, the working directory
+ # does not contain the generated candidates as filenames. In the case
+ # of "-C ", the generated filenames are located in the directory
+ # "" but not in the working directory. In the case of "-P
+ # ", candidates have the form "". In those
+ # cases, Bash fails to recognize the generated candidates to be
+ # filenames, and Bash does not adjust these as filenames. We
+ # automatically detect such cases and modify the generated filenames as
+ # if the option "-f" is passed.
+ _filenames=set
+ fi
+
local OPTIND=1 OPTARG="" OPTERR=0 _opt
while getopts ":df" _opt "$@"; do
case $_opt in
diff --git a/completions-core/curl.bash b/completions-core/curl.bash
index dc61bc4ccf6..72bf1a1bf01 100644
--- a/completions-core/curl.bash
+++ b/completions-core/curl.bash
@@ -55,10 +55,6 @@ _comp_cmd_curl()
if [[ $cur == \@* ]]; then
_comp_compgen -P @ filedir
_comp_compgen -aP @ -- -W '-'
- if [[ ${#COMPREPLY[@]} -eq 1 && -d ${COMPREPLY[0]#@} ]]; then
- COMPREPLY[0]+=/
- compopt -o nospace
- fi
fi
return
;;
diff --git a/completions-core/removepkg.bash b/completions-core/removepkg.bash
index 9bb1abe7e90..80c4800ebef 100644
--- a/completions-core/removepkg.bash
+++ b/completions-core/removepkg.bash
@@ -15,7 +15,7 @@ _comp_cmd_removepkg()
fi
local root=${ROOT:-/}
- _comp_compgen -C "$root/var/log/packages" filedir -f
+ _comp_compgen -C "$root/var/log/packages" filedir
} &&
complete -F _comp_cmd_removepkg removepkg
diff --git a/completions-core/sbopkg.bash b/completions-core/sbopkg.bash
index 975d19254a5..7fe8fc2e94c 100644
--- a/completions-core/sbopkg.bash
+++ b/completions-core/sbopkg.bash
@@ -64,7 +64,7 @@ _comp_cmd_sbopkg()
_comp_compgen_split -l -- "$(command sed -ne "s/^SLACKBUILD NAME: //p" \
"$file")"
if [[ -d ${QUEUEDIR-} ]]; then
- _comp_compgen -aC "$QUEUEDIR" filedir -f sqf
+ _comp_compgen -aC "$QUEUEDIR" filedir sqf
fi
} &&
complete -F _comp_cmd_sbopkg sbopkg
diff --git a/completions-core/slapt-get.bash b/completions-core/slapt-get.bash
index e961e5fbfa7..3950cce76c0 100644
--- a/completions-core/slapt-get.bash
+++ b/completions-core/slapt-get.bash
@@ -74,7 +74,7 @@ _comp_cmd_slapt_get()
return
;;
ins) # --remove|--filelist
- _comp_compgen -C /var/log/packages filedir -f
+ _comp_compgen -C /var/log/packages filedir
return
;;
set) # --install-set
diff --git a/completions-fallback/mount.linux.bash b/completions-fallback/mount.linux.bash
index 8e384bb936b..bd34ca8e4d2 100644
--- a/completions-fallback/mount.linux.bash
+++ b/completions-fallback/mount.linux.bash
@@ -32,11 +32,11 @@ _comp_cmd_mount()
return
;;
-L)
- _comp_compgen -C "/dev/disk/by-label/" filedir -f
+ _comp_compgen -C "/dev/disk/by-label/" filedir
return
;;
-U)
- _comp_compgen -C "/dev/disk/by-uuid/" filedir -f
+ _comp_compgen -C "/dev/disk/by-uuid/" filedir
return
;;
-O | --test-opts)
diff --git a/completions-fallback/slackpkg.bash b/completions-fallback/slackpkg.bash
index 830976eaf51..5923b1b2f9c 100644
--- a/completions-fallback/slackpkg.bash
+++ b/completions-fallback/slackpkg.bash
@@ -65,7 +65,7 @@ _comp_cmd_slackpkg()
;;
install-template | remove-template)
if [[ -e $confdir/templates ]]; then
- _comp_compgen -C "$confdir/templates" filedir -f template &&
+ _comp_compgen -C "$confdir/templates" filedir template &&
COMPREPLY=("${COMPREPLY[@]%.template}")
fi
return
@@ -74,7 +74,7 @@ _comp_cmd_slackpkg()
_comp_compgen_filedir
_comp_compgen -a -- -W 'a ap d e f k kde kdei l n t tcl x xap xfce
y'
- _comp_compgen -aC /var/log/packages filedir -f
+ _comp_compgen -aC /var/log/packages filedir
return
;;
install | reinstall | upgrade | blacklist | download)
diff --git a/test/t/unit/test_unit_compgen.py b/test/t/unit/test_unit_compgen.py
index 101d4bbe213..2b957a43878 100644
--- a/test/t/unit/test_unit_compgen.py
+++ b/test/t/unit/test_unit_compgen.py
@@ -127,7 +127,14 @@ def test_6_option_C_1(self, bash, functions):
want_output=True,
)
set1 = set(re.findall(r"<[^<>]*>", output.strip()))
- assert set1 == {"", "", "", "", "", ""}
+ assert set1 == {
+ "",
+ "",
+ "",
+ "",
+ " ",
+ "",
+ }
def test_6_option_C_2(self, bash, functions):
output = assert_bash_exec(
@@ -146,7 +153,7 @@ def test_6_option_C_3(self, bash, functions, funcname):
def test_6_option_C_4(self, functions, completion):
# Note: we are not in the original directory that "b" exists, so Bash
# will not suffix a slash to the directory name.
- assert completion == "b"
+ assert completion == "b/"
@pytest.mark.complete(r"fb nonexistent")
def test_6_option_C_5(self, bash, functions, completion):
diff --git a/test/t/unit/test_unit_compgen_filedir.py b/test/t/unit/test_unit_compgen_filedir.py
index 56f9fbe0532..7705061ee4d 100644
--- a/test/t/unit/test_unit_compgen_filedir.py
+++ b/test/t/unit/test_unit_compgen_filedir.py
@@ -34,7 +34,7 @@ def functions(self, request, bash):
)
assert_bash_exec(
bash,
- "_fcd() { local cur=$(_get_cword); unset -v COMPREPLY; _comp_compgen -C _filedir filedir -df; };"
+ "_fcd() { local cur=$(_get_cword); unset -v COMPREPLY; _comp_compgen -C _filedir filedir -d; };"
"complete -F _fcd fcd",
)