summaryrefslogtreecommitdiffstats
path: root/debian/patches/bash50-003.diff
diff options
context:
space:
mode:
Diffstat (limited to '')
-rw-r--r--debian/patches/bash50-003.diff188
1 files changed, 188 insertions, 0 deletions
diff --git a/debian/patches/bash50-003.diff b/debian/patches/bash50-003.diff
new file mode 100644
index 0000000..58b0aae
--- /dev/null
+++ b/debian/patches/bash50-003.diff
@@ -0,0 +1,188 @@
+ BASH PATCH REPORT
+ =================
+
+Bash-Release: 5.0
+Patch-ID: bash50-003
+
+Bug-Reported-by: Andrew Church <achurch+bash@achurch.org>
+Bug-Reference-ID: <5c534aa2.04371@msgid.achurch.org>
+Bug-Reference-URL: http://lists.gnu.org/archive/html/bug-bash/2019-01/msg00276.html
+
+Bug-Description:
+
+There are several incompatibilities in how bash-5.0 processes pathname
+expansion (globbing) of filename arguments that have backslashes in the
+directory portion.
+
+--- a/bashline.c
++++ b/bashline.c
+@@ -3752,7 +3752,7 @@ completion_glob_pattern (string)
+ continue;
+
+ case '\\':
+- if (*string == 0)
++ if (*string++ == 0)
+ return (0);
+ }
+
+--- a/lib/glob/glob.c
++++ b/lib/glob/glob.c
+@@ -1061,7 +1061,7 @@ glob_filename (pathname, flags)
+ char *directory_name, *filename, *dname, *fn;
+ unsigned int directory_len;
+ int free_dirname; /* flag */
+- int dflags;
++ int dflags, hasglob;
+
+ result = (char **) malloc (sizeof (char *));
+ result_size = 1;
+@@ -1110,9 +1110,12 @@ glob_filename (pathname, flags)
+ free_dirname = 1;
+ }
+
++ hasglob = 0;
+ /* If directory_name contains globbing characters, then we
+- have to expand the previous levels. Just recurse. */
+- if (directory_len > 0 && glob_pattern_p (directory_name))
++ have to expand the previous levels. Just recurse.
++ If glob_pattern_p returns != [0,1] we have a pattern that has backslash
++ quotes but no unquoted glob pattern characters. We dequote it below. */
++ if (directory_len > 0 && (hasglob = glob_pattern_p (directory_name)) == 1)
+ {
+ char **directories, *d, *p;
+ register unsigned int i;
+@@ -1175,7 +1178,7 @@ glob_filename (pathname, flags)
+ if (d[directory_len - 1] == '/')
+ d[directory_len - 1] = '\0';
+
+- directories = glob_filename (d, dflags);
++ directories = glob_filename (d, dflags|GX_RECURSE);
+
+ if (free_dirname)
+ {
+@@ -1332,6 +1335,20 @@ only_filename:
+ free (directory_name);
+ return (NULL);
+ }
++ /* If we have a directory name with quoted characters, and we are
++ being called recursively to glob the directory portion of a pathname,
++ we need to dequote the directory name before returning it so the
++ caller can read the directory */
++ if (directory_len > 0 && hasglob == 2 && (flags & GX_RECURSE) != 0)
++ {
++ dequote_pathname (directory_name);
++ directory_len = strlen (directory_name);
++ }
++
++ /* We could check whether or not the dequoted directory_name is a
++ directory and return it here, returning the original directory_name
++ if not, but we don't do that yet. I'm not sure it matters. */
++
+ /* Handle GX_MARKDIRS here. */
+ result[0] = (char *) malloc (directory_len + 1);
+ if (result[0] == NULL)
+--- a/lib/glob/glob.h
++++ b/lib/glob/glob.h
+@@ -30,6 +30,7 @@
+ #define GX_NULLDIR 0x100 /* internal -- no directory preceding pattern */
+ #define GX_ADDCURDIR 0x200 /* internal -- add passed directory name */
+ #define GX_GLOBSTAR 0x400 /* turn on special handling of ** */
++#define GX_RECURSE 0x800 /* internal -- glob_filename called recursively */
+
+ extern int glob_pattern_p __P((const char *));
+ extern char **glob_vector __P((char *, char *, int));
+--- a/lib/glob/glob_loop.c
++++ b/lib/glob/glob_loop.c
+@@ -26,10 +26,10 @@ INTERNAL_GLOB_PATTERN_P (pattern)
+ {
+ register const GCHAR *p;
+ register GCHAR c;
+- int bopen;
++ int bopen, bsquote;
+
+ p = pattern;
+- bopen = 0;
++ bopen = bsquote = 0;
+
+ while ((c = *p++) != L('\0'))
+ switch (c)
+@@ -55,13 +55,22 @@ INTERNAL_GLOB_PATTERN_P (pattern)
+
+ case L('\\'):
+ /* Don't let the pattern end in a backslash (GMATCH returns no match
+- if the pattern ends in a backslash anyway), but otherwise return 1,
+- since the matching engine uses backslash as an escape character
+- and it can be removed. */
+- return (*p != L('\0'));
++ if the pattern ends in a backslash anyway), but otherwise note that
++ we have seen this, since the matching engine uses backslash as an
++ escape character and it can be removed. We return 2 later if we
++ have seen only backslash-escaped characters, so interested callers
++ know they can shortcut and just dequote the pathname. */
++ if (*p != L('\0'))
++ {
++ p++;
++ bsquote = 1;
++ continue;
++ }
++ else /* (*p == L('\0')) */
++ return 0;
+ }
+
+- return 0;
++ return bsquote ? 2 : 0;
+ }
+
+ #undef INTERNAL_GLOB_PATTERN_P
+--- a/patchlevel.h
++++ b/patchlevel.h
+@@ -25,6 +25,6 @@
+ regexp `^#define[ ]*PATCHLEVEL', since that's what support/mkversion.sh
+ looks for to find the patch level (for the sccs version string). */
+
+-#define PATCHLEVEL 2
++#define PATCHLEVEL 3
+
+ #endif /* _PATCHLEVEL_H_ */
+--- a/pathexp.c
++++ b/pathexp.c
+@@ -65,11 +65,11 @@ unquoted_glob_pattern_p (string)
+ {
+ register int c;
+ char *send;
+- int open;
++ int open, bsquote;
+
+ DECLARE_MBSTATE;
+
+- open = 0;
++ open = bsquote = 0;
+ send = string + strlen (string);
+
+ while (c = *string++)
+@@ -100,7 +100,14 @@ unquoted_glob_pattern_p (string)
+ can be removed by the matching engine, so we have to run it through
+ globbing. */
+ case '\\':
+- return (*string != 0);
++ if (*string != '\0' && *string != '/')
++ {
++ bsquote = 1;
++ string++;
++ continue;
++ }
++ else if (*string == 0)
++ return (0);
+
+ case CTLESC:
+ if (*string++ == '\0')
+@@ -117,7 +124,8 @@ unquoted_glob_pattern_p (string)
+ ADVANCE_CHAR_P (string, send - string);
+ #endif
+ }
+- return (0);
++
++ return (bsquote ? 2 : 0);
+ }
+
+ /* Return 1 if C is a character that is `special' in a POSIX ERE and needs to