summaryrefslogtreecommitdiff
path: root/source/a/bash/bash-4.3-patches/bash43-016
blob: 882d5939b0b96b990fe30eb2dd06bc2e0bd3395d (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
			     BASH PATCH REPORT
			     =================

Bash-Release:	4.3
Patch-ID:	bash43-016

Bug-Reported-by:	Pierre Gaston <pierre.gaston@gmail.com>
Bug-Reference-ID:	<CAPSX3sTCD61k1VQLJ5r-LWzEt+e7Xc-fxXmwn2u8EA5gJJej8Q@mail.gmail.com>
Bug-Reference-URL:	http://lists.gnu.org/archive/html/bug-bash/2014-04/msg00100.html

Bug-Description:

An extended glob pattern containing a slash (`/') causes the globbing code
to misinterpret it as a directory separator.

Patch (apply with `patch -p0'):
*** ../bash-4.3-patched/lib/glob/glob.c	2014-03-28 10:54:23.000000000 -0400
--- lib/glob/glob.c	2014-05-02 10:24:28.000000000 -0400
***************
*** 124,127 ****
--- 124,129 ----
  extern wchar_t *glob_patscan_wc __P((wchar_t *, wchar_t *, int));
  
+ extern char *glob_dirscan __P((char *, int));
+ 
  /* Compile `glob_loop.c' for single-byte characters. */
  #define CHAR	unsigned char
***************
*** 188,191 ****
--- 190,196 ----
    pe = glob_patscan (pp, se, 0);	/* end of extglob pattern (( */
    /* we should check for invalid extglob pattern here */
+   if (pe == 0)
+     return 0;
+ 
    /* if pe != se we have more of the pattern at the end of the extglob
       pattern. Check the easy case first ( */
***************
*** 1016,1020 ****
    char **result;
    unsigned int result_size;
!   char *directory_name, *filename, *dname;
    unsigned int directory_len;
    int free_dirname;			/* flag */
--- 1021,1025 ----
    char **result;
    unsigned int result_size;
!   char *directory_name, *filename, *dname, *fn;
    unsigned int directory_len;
    int free_dirname;			/* flag */
***************
*** 1032,1035 ****
--- 1037,1052 ----
    /* Find the filename.  */
    filename = strrchr (pathname, '/');
+ #if defined (EXTENDED_GLOB)
+   if (filename && extended_glob)
+     {
+       fn = glob_dirscan (pathname, '/');
+ #if DEBUG_MATCHING
+       if (fn != filename)
+ 	fprintf (stderr, "glob_filename: glob_dirscan: fn (%s) != filename (%s)\n", fn ? fn : "(null)", filename);
+ #endif
+       filename = fn;
+     }
+ #endif
+ 
    if (filename == NULL)
      {
*** ../bash-4.3-patched/lib/glob/gmisc.c	2014-03-28 10:54:23.000000000 -0400
--- lib/glob/gmisc.c	2014-05-02 09:35:57.000000000 -0400
***************
*** 43,46 ****
--- 43,48 ----
  #define WRPAREN         L')'
  
+ extern char *glob_patscan __P((char *, char *, int));
+ 
  /* Return 1 of the first character of WSTRING could match the first
     character of pattern WPAT.  Wide character version. */
***************
*** 376,377 ****
--- 378,410 ----
    return matlen;
  }
+ 
+ /* Skip characters in PAT and return the final occurrence of DIRSEP.  This
+    is only called when extended_glob is set, so we have to skip over extglob
+    patterns x(...) */
+ char *
+ glob_dirscan (pat, dirsep)
+      char *pat;
+      int dirsep;
+ {
+   char *p, *d, *pe, *se;
+ 
+   d = pe = se = 0;
+   for (p = pat; p && *p; p++)
+     {
+       if (extglob_pattern_p (p))
+ 	{
+ 	  if (se == 0)
+ 	    se = p + strlen (p) - 1;
+ 	  pe = glob_patscan (p + 2, se, 0);
+ 	  if (pe == 0)
+ 	    continue;
+ 	  else if (*pe == 0)
+ 	    break;
+ 	  p = pe - 1;	/* will do increment above */
+ 	  continue;
+ 	}
+       if (*p ==  dirsep)
+ 	d = p;
+     }
+   return d;
+ }

*** ../bash-4.3/patchlevel.h	2012-12-29 10:47:57.000000000 -0500
--- patchlevel.h	2014-03-20 20:01:28.000000000 -0400
***************
*** 26,30 ****
     looks for to find the patch level (for the sccs version string). */
  
! #define PATCHLEVEL 15
  
  #endif /* _PATCHLEVEL_H_ */
--- 26,30 ----
     looks for to find the patch level (for the sccs version string). */
  
! #define PATCHLEVEL 16
  
  #endif /* _PATCHLEVEL_H_ */