source: patches/bash-3.2-fixes-5.patch@ 91e274a

clfs-1.2 clfs-2.1 clfs-3.0.0-systemd clfs-3.0.0-sysvinit systemd sysvinit
Last change on this file since 91e274a was 24cc73c, checked in by Joe Ciccone <jciccone@…>, 17 years ago

Updated the bash fixes patch and the vim fixes patch.

  • Property mode set to 100644
File size: 32.0 KB
RevLine 
[24cc73c]1Submitted By: Joe Ciccone <jciccone@gmail.com>
2Date: 2007-07-23
3Initial Package Version: 3.2
4Origin: ftp://ftp.cwru.edu/pub/bash/bash-3.2-patches/
5Upstream Status: From Upstream
6Description: Contains patches 001-017 from upstream
7
8diff -Naur bash-3.2.orig/array.c bash-3.2/array.c
9--- bash-3.2.orig/array.c 2007-07-23 19:54:02.000000000 -0400
10+++ bash-3.2/array.c 2007-07-23 19:58:47.000000000 -0400
11@@ -120,7 +120,6 @@
12 return(a1);
13 }
14
15-#ifdef INCLUDE_UNUSED
16 /*
17 * Make and return a new array composed of the elements in array A from
18 * S to E, inclusive.
19@@ -141,13 +140,12 @@
20 for (p = s, i = 0; p != e; p = element_forw(p), i++) {
21 n = array_create_element (element_index(p), element_value(p));
22 ADD_BEFORE(a->head, n);
23- mi = element_index(ae);
24+ mi = element_index(n);
25 }
26 a->num_elements = i;
27 a->max_index = mi;
28 return a;
29 }
30-#endif
31
32 /*
33 * Walk the array, calling FUNC once for each element, with the array
34@@ -300,6 +298,23 @@
35 return array;
36 }
37
38+ARRAY *
39+array_quote_escapes(array)
40+ARRAY *array;
41+{
42+ ARRAY_ELEMENT *a;
43+ char *t;
44+
45+ if (array == 0 || array_head(array) == 0 || array_empty(array))
46+ return (ARRAY *)NULL;
47+ for (a = element_forw(array->head); a != array->head; a = element_forw(a)) {
48+ t = quote_escapes (a->value);
49+ FREE(a->value);
50+ a->value = t;
51+ }
52+ return array;
53+}
54+
55 /*
56 * Return a string whose elements are the members of array A beginning at
57 * index START and spanning NELEM members. Null elements are counted.
58@@ -311,9 +326,10 @@
59 arrayind_t start, nelem;
60 int starsub, quoted;
61 {
62+ ARRAY *a2;
63 ARRAY_ELEMENT *h, *p;
64 arrayind_t i;
65- char *ifs, sep[2];
66+ char *ifs, sep[2], *t;
67
68 p = a ? array_head (a) : 0;
69 if (p == 0 || array_empty (a) || start > array_max_index(a))
70@@ -336,6 +352,13 @@
71 for (i = 0, h = p; p != a->head && i < nelem; i++, p = element_forw(p))
72 ;
73
74+ a2 = array_slice(a, h, p);
75+
76+ if (quoted & (Q_DOUBLE_QUOTES|Q_HERE_DOCUMENT))
77+ array_quote(a2);
78+ else
79+ array_quote_escapes(a2);
80+
81 if (starsub && (quoted & (Q_DOUBLE_QUOTES|Q_HERE_DOCUMENT))) {
82 ifs = getifs();
83 sep[0] = ifs ? *ifs : '\0';
84@@ -343,7 +366,10 @@
85 sep[0] = ' ';
86 sep[1] = '\0';
87
88- return (array_to_string_internal (h, p, sep, quoted));
89+ t = array_to_string (a2, sep, 0);
90+ array_dispose(a2);
91+
92+ return t;
93 }
94
95 char *
96@@ -367,7 +393,9 @@
97 }
98
99 if (mflags & MATCH_QUOTED)
100- array_quote (a2);
101+ array_quote(a2);
102+ else
103+ array_quote_escapes(a2);
104 if (mflags & MATCH_STARSUB) {
105 ifs = getifs();
106 sifs[0] = ifs ? *ifs : '\0';
107diff -Naur bash-3.2.orig/array.h bash-3.2/array.h
108--- bash-3.2.orig/array.h 2007-07-23 19:54:02.000000000 -0400
109+++ bash-3.2/array.h 2007-07-23 19:58:47.000000000 -0400
110@@ -55,6 +55,7 @@
111 extern ARRAY_ELEMENT *array_unshift_element __P((ARRAY *));
112 extern int array_shift_element __P((ARRAY *, char *));
113 extern ARRAY *array_quote __P((ARRAY *));
114+extern ARRAY *array_quote_escapes __P((ARRAY *));
115
116 extern char *array_subrange __P((ARRAY *, arrayind_t, arrayind_t, int, int));
117 extern char *array_patsub __P((ARRAY *, char *, char *, int));
118diff -Naur bash-3.2.orig/builtins/common.c bash-3.2/builtins/common.c
119--- bash-3.2.orig/builtins/common.c 2007-07-23 19:54:02.000000000 -0400
120+++ bash-3.2/builtins/common.c 2007-07-23 19:58:47.000000000 -0400
121@@ -1,4 +1,4 @@
122-/* Copyright (C) 1987-2005 Free Software Foundation, Inc.
123+/* Copyright (C) 1987-2007 Free Software Foundation, Inc.
124
125 This file is part of GNU Bash, the Bourne Again SHell.
126
127@@ -475,7 +475,11 @@
128
129 if (the_current_working_directory == 0)
130 {
131+#if defined (GETCWD_BROKEN)
132+ the_current_working_directory = getcwd (0, PATH_MAX);
133+#else
134 the_current_working_directory = getcwd (0, 0);
135+#endif
136 if (the_current_working_directory == 0)
137 {
138 fprintf (stderr, _("%s: error retrieving current directory: %s: %s\n"),
139diff -Naur bash-3.2.orig/builtins/printf.def bash-3.2/builtins/printf.def
140--- bash-3.2.orig/builtins/printf.def 2007-07-23 19:54:02.000000000 -0400
141+++ bash-3.2/builtins/printf.def 2007-07-23 19:58:47.000000000 -0400
142@@ -1,7 +1,7 @@
143 This file is printf.def, from which is created printf.c.
144 It implements the builtin "printf" in Bash.
145
146-Copyright (C) 1997-2005 Free Software Foundation, Inc.
147+Copyright (C) 1997-2007 Free Software Foundation, Inc.
148
149 This file is part of GNU Bash, the Bourne Again SHell.
150
151@@ -49,6 +49,12 @@
152 # define INT_MIN (-2147483647-1)
153 #endif
154
155+#if defined (PREFER_STDARG)
156+# include <stdarg.h>
157+#else
158+# include <varargs.h>
159+#endif
160+
161 #include <stdio.h>
162 #include <chartypes.h>
163
164@@ -64,6 +70,10 @@
165 #include "bashgetopt.h"
166 #include "common.h"
167
168+#if defined (PRI_MACROS_BROKEN)
169+# undef PRIdMAX
170+#endif
171+
172 #if !defined (PRIdMAX)
173 # if HAVE_LONG_LONG
174 # define PRIdMAX "lld"
175@@ -151,6 +161,10 @@
176 #define SKIP1 "#'-+ 0"
177 #define LENMODS "hjlLtz"
178
179+#ifndef HAVE_ASPRINTF
180+extern int asprintf __P((char **, const char *, ...)) __attribute__((__format__ (printf, 2, 3)));
181+#endif
182+
183 static void printf_erange __P((char *));
184 static int printstr __P((char *, char *, int, int, int));
185 static int tescape __P((char *, char *, int *));
186diff -Naur bash-3.2.orig/config-bot.h bash-3.2/config-bot.h
187--- bash-3.2.orig/config-bot.h 2007-07-23 19:54:02.000000000 -0400
188+++ bash-3.2/config-bot.h 2007-07-23 19:58:47.000000000 -0400
189@@ -1,7 +1,7 @@
190 /* config-bot.h */
191 /* modify settings or make new ones based on what autoconf tells us. */
192
193-/* Copyright (C) 1989-2002 Free Software Foundation, Inc.
194+/* Copyright (C) 1989-2007 Free Software Foundation, Inc.
195
196 This file is part of GNU Bash, the Bourne Again SHell.
197
198@@ -70,9 +70,11 @@
199 # define TERMIOS_MISSING
200 #endif
201
202-/* If we have a getcwd(3), but it calls popen(), #undef HAVE_GETCWD so
203- the replacement in getcwd.c will be built. */
204-#if defined (HAVE_GETCWD) && defined (GETCWD_BROKEN)
205+/* If we have a getcwd(3), but one that does not dynamically allocate memory,
206+ #undef HAVE_GETCWD so the replacement in getcwd.c will be built. We do
207+ not do this on Solaris, because their implementation of loopback mounts
208+ breaks the traditional file system assumptions that getcwd uses. */
209+#if defined (HAVE_GETCWD) && defined (GETCWD_BROKEN) && !defined (SOLARIS)
210 # undef HAVE_GETCWD
211 #endif
212
213diff -Naur bash-3.2.orig/config.h.in bash-3.2/config.h.in
214--- bash-3.2.orig/config.h.in 2007-07-23 19:54:02.000000000 -0400
215+++ bash-3.2/config.h.in 2007-07-23 19:58:47.000000000 -0400
216@@ -1,6 +1,6 @@
217 /* config.h -- Configuration file for bash. */
218
219-/* Copyright (C) 1987-2006 Free Software Foundation, Inc.
220+/* Copyright (C) 1987-2007 Free Software Foundation, Inc.
221
222 This file is part of GNU Bash, the Bourne Again SHell.
223
224@@ -413,6 +413,8 @@
225
226 #undef HAVE_DECL_STRTOLD
227
228+#undef PRI_MACROS_BROKEN
229+
230 #undef STRTOLD_BROKEN
231
232 /* Define if WCONTINUED is defined in system headers, but rejected by waitpid */
233@@ -1006,6 +1008,9 @@
234 /* Define if you have the `dcgettext' function. */
235 #undef HAVE_DCGETTEXT
236
237+/* Define if you have the `localeconv' function. */
238+#undef HAVE_LOCALECONV
239+
240 /* Define if your system has a working `malloc' function. */
241 /* #undef HAVE_MALLOC */
242
243diff -Naur bash-3.2.orig/configure bash-3.2/configure
244--- bash-3.2.orig/configure 2007-07-23 19:54:02.000000000 -0400
245+++ bash-3.2/configure 2007-07-23 19:58:47.000000000 -0400
246@@ -27316,7 +27316,8 @@
247 sco3.2v4*) LOCAL_CFLAGS="-DMUST_UNBLOCK_CHLD -DPATH_MAX=1024" ;;
248 sco3.2*) LOCAL_CFLAGS=-DMUST_UNBLOCK_CHLD ;;
249 sunos4*) LOCAL_CFLAGS=-DSunOS4 ;;
250-solaris2.5*) LOCAL_CFLAGS=-DSunOS5 ;;
251+solaris2.5*) LOCAL_CFLAGS="-DSunOS5 -DSOLARIS" ;;
252+solaris2*) LOCAL_CFLAGS=-DSOLARIS ;;
253 lynxos*) LOCAL_CFLAGS=-DRECYCLES_PIDS ;;
254 linux*) LOCAL_LDFLAGS=-rdynamic # allow dynamic loading
255 case "`uname -r`" in
256diff -Naur bash-3.2.orig/configure.in bash-3.2/configure.in
257--- bash-3.2.orig/configure.in 2007-07-23 19:54:02.000000000 -0400
258+++ bash-3.2/configure.in 2007-07-23 19:58:47.000000000 -0400
259@@ -5,7 +5,7 @@
260 dnl
261 dnl Process this file with autoconf to produce a configure script.
262
263-# Copyright (C) 1987-2006 Free Software Foundation, Inc.
264+# Copyright (C) 1987-2007 Free Software Foundation, Inc.
265
266 # This program is free software; you can redistribute it and/or modify
267 # it under the terms of the GNU General Public License as published by
268@@ -991,7 +991,8 @@
269 sco3.2v4*) LOCAL_CFLAGS="-DMUST_UNBLOCK_CHLD -DPATH_MAX=1024" ;;
270 sco3.2*) LOCAL_CFLAGS=-DMUST_UNBLOCK_CHLD ;;
271 sunos4*) LOCAL_CFLAGS=-DSunOS4 ;;
272-solaris2.5*) LOCAL_CFLAGS=-DSunOS5 ;;
273+solaris2.5*) LOCAL_CFLAGS="-DSunOS5 -DSOLARIS" ;;
274+solaris2*) LOCAL_CFLAGS=-DSOLARIS ;;
275 lynxos*) LOCAL_CFLAGS=-DRECYCLES_PIDS ;;
276 linux*) LOCAL_LDFLAGS=-rdynamic # allow dynamic loading
277 case "`uname -r`" in
278diff -Naur bash-3.2.orig/execute_cmd.c bash-3.2/execute_cmd.c
279--- bash-3.2.orig/execute_cmd.c 2007-07-23 19:54:02.000000000 -0400
280+++ bash-3.2/execute_cmd.c 2007-07-23 19:58:47.000000000 -0400
281@@ -1,6 +1,6 @@
282 /* execute_cmd.c -- Execute a COMMAND structure. */
283
284-/* Copyright (C) 1987-2005 Free Software Foundation, Inc.
285+/* Copyright (C) 1987-2007 Free Software Foundation, Inc.
286
287 This file is part of GNU Bash, the Bourne Again SHell.
288
289@@ -2546,7 +2546,7 @@
290 arg1 = cond_expand_word (cond->left->op, 0);
291 if (arg1 == 0)
292 arg1 = nullstr;
293- arg2 = cond_expand_word (cond->right->op, patmatch||rmatch);
294+ arg2 = cond_expand_word (cond->right->op, rmatch ? 2 : (patmatch ? 1 : 0));
295 if (arg2 == 0)
296 arg2 = nullstr;
297
298@@ -3050,6 +3050,11 @@
299 if (command_line == 0)
300 command_line = savestring (the_printed_command_except_trap);
301
302+#if defined (PROCESS_SUBSTITUTION)
303+ if ((subshell_environment & SUBSHELL_COMSUB) && (simple_command->flags & CMD_NO_FORK) && fifos_pending() > 0)
304+ simple_command->flags &= ~CMD_NO_FORK;
305+#endif
306+
307 execute_disk_command (words, simple_command->redirects, command_line,
308 pipe_in, pipe_out, async, fds_to_close,
309 simple_command->flags);
310diff -Naur bash-3.2.orig/findcmd.c bash-3.2/findcmd.c
311--- bash-3.2.orig/findcmd.c 2007-07-23 19:54:02.000000000 -0400
312+++ bash-3.2/findcmd.c 2007-07-23 19:58:47.000000000 -0400
313@@ -308,7 +308,7 @@
314 if (hashed_file && (posixly_correct || check_hashed_filenames))
315 {
316 st = file_status (hashed_file);
317- if ((st ^ (FS_EXISTS | FS_EXECABLE)) != 0)
318+ if ((st & (FS_EXISTS|FS_EXECABLE)) != (FS_EXISTS|FS_EXECABLE))
319 {
320 phash_remove (pathname);
321 free (hashed_file);
322diff -Naur bash-3.2.orig/jobs.c bash-3.2/jobs.c
323--- bash-3.2.orig/jobs.c 2007-07-23 19:54:02.000000000 -0400
324+++ bash-3.2/jobs.c 2007-07-23 19:58:47.000000000 -0400
325@@ -984,8 +984,6 @@
326 temp = jobs[job_index];
327 if (temp == 0)
328 return;
329- if (job_index == js.j_current || job_index == js.j_previous)
330- reset_current ();
331
332 if ((dflags & DEL_NOBGPID) == 0)
333 {
334@@ -1028,6 +1026,9 @@
335 js.j_firstj = js.j_lastj = 0;
336 else if (jobs[js.j_firstj] == 0 || jobs[js.j_lastj] == 0)
337 reset_job_indices ();
338+
339+ if (job_index == js.j_current || job_index == js.j_previous)
340+ reset_current ();
341 }
342
343 /* Must be called with SIGCHLD blocked. */
344diff -Naur bash-3.2.orig/lib/readline/display.c bash-3.2/lib/readline/display.c
345--- bash-3.2.orig/lib/readline/display.c 2007-07-23 19:54:02.000000000 -0400
346+++ bash-3.2/lib/readline/display.c 2007-07-23 19:58:47.000000000 -0400
347@@ -561,6 +561,17 @@
348 wrap_offset = prompt_invis_chars_first_line = 0;
349 }
350
351+#if defined (HANDLE_MULTIBYTE)
352+#define CHECK_INV_LBREAKS() \
353+ do { \
354+ if (newlines >= (inv_lbsize - 2)) \
355+ { \
356+ inv_lbsize *= 2; \
357+ inv_lbreaks = (int *)xrealloc (inv_lbreaks, inv_lbsize * sizeof (int)); \
358+ _rl_wrapped_line = (int *)xrealloc (_rl_wrapped_line, inv_lbsize * sizeof (int)); \
359+ } \
360+ } while (0)
361+#else
362 #define CHECK_INV_LBREAKS() \
363 do { \
364 if (newlines >= (inv_lbsize - 2)) \
365@@ -569,6 +580,7 @@
366 inv_lbreaks = (int *)xrealloc (inv_lbreaks, inv_lbsize * sizeof (int)); \
367 } \
368 } while (0)
369+#endif /* HANDLE_MULTIBYTE */
370
371 #if defined (HANDLE_MULTIBYTE)
372 #define CHECK_LPOS() \
373@@ -1586,8 +1598,22 @@
374 temp = nls - nfd;
375 if (temp > 0)
376 {
377+ /* If nfd begins at the prompt, or before the invisible
378+ characters in the prompt, we need to adjust _rl_last_c_pos
379+ in a multibyte locale to account for the wrap offset and
380+ set cpos_adjusted accordingly. */
381 _rl_output_some_chars (nfd, temp);
382- _rl_last_c_pos += _rl_col_width (nfd, 0, temp);;
383+ if (MB_CUR_MAX > 1 && rl_byte_oriented == 0)
384+ {
385+ _rl_last_c_pos += _rl_col_width (nfd, 0, temp);
386+ if (current_line == 0 && wrap_offset && ((nfd - new) <= prompt_last_invisible))
387+ {
388+ _rl_last_c_pos -= wrap_offset;
389+ cpos_adjusted = 1;
390+ }
391+ }
392+ else
393+ _rl_last_c_pos += temp;
394 }
395 }
396 /* Otherwise, print over the existing material. */
397@@ -1595,8 +1621,20 @@
398 {
399 if (temp > 0)
400 {
401+ /* If nfd begins at the prompt, or before the invisible
402+ characters in the prompt, we need to adjust _rl_last_c_pos
403+ in a multibyte locale to account for the wrap offset and
404+ set cpos_adjusted accordingly. */
405 _rl_output_some_chars (nfd, temp);
406 _rl_last_c_pos += col_temp; /* XXX */
407+ if (MB_CUR_MAX > 1 && rl_byte_oriented == 0)
408+ {
409+ if (current_line == 0 && wrap_offset && ((nfd - new) <= prompt_last_invisible))
410+ {
411+ _rl_last_c_pos -= wrap_offset;
412+ cpos_adjusted = 1;
413+ }
414+ }
415 }
416 lendiff = (oe - old) - (ne - new);
417 if (MB_CUR_MAX > 1 && rl_byte_oriented == 0)
418@@ -1732,7 +1770,10 @@
419 if (MB_CUR_MAX > 1 && rl_byte_oriented == 0)
420 {
421 dpos = _rl_col_width (data, 0, new);
422- if (dpos > prompt_last_invisible) /* XXX - don't use woff here */
423+ /* Use NEW when comparing against the last invisible character in the
424+ prompt string, since they're both buffer indices and DPOS is a
425+ desired display position. */
426+ if (new > prompt_last_invisible) /* XXX - don't use woff here */
427 {
428 dpos -= woff;
429 /* Since this will be assigned to _rl_last_c_pos at the end (more
430@@ -2380,6 +2421,8 @@
431
432 if (end <= start)
433 return 0;
434+ if (MB_CUR_MAX == 1 || rl_byte_oriented)
435+ return (end - start);
436
437 memset (&ps, 0, sizeof (mbstate_t));
438
439diff -Naur bash-3.2.orig/lib/sh/snprintf.c bash-3.2/lib/sh/snprintf.c
440--- bash-3.2.orig/lib/sh/snprintf.c 2007-07-23 19:54:02.000000000 -0400
441+++ bash-3.2/lib/sh/snprintf.c 2007-07-23 19:58:47.000000000 -0400
442@@ -471,6 +471,8 @@
443 10^x ~= r
444 * log_10(200) = 2;
445 * log_10(250) = 2;
446+ *
447+ * NOTE: do not call this with r == 0 -- an infinite loop results.
448 */
449 static int
450 log_10(r)
451@@ -576,8 +578,11 @@
452 {
453 integral_part[0] = '0';
454 integral_part[1] = '\0';
455- fraction_part[0] = '0';
456- fraction_part[1] = '\0';
457+ /* The fractional part has to take the precision into account */
458+ for (ch = 0; ch < precision-1; ch++)
459+ fraction_part[ch] = '0';
460+ fraction_part[ch] = '0';
461+ fraction_part[ch+1] = '\0';
462 if (fract)
463 *fract = fraction_part;
464 return integral_part;
465@@ -663,7 +668,8 @@
466 p->flags &= ~PF_ZEROPAD;
467
468 sd = d; /* signed for ' ' padding in base 10 */
469- flags = (*p->pf == 'u' || *p->pf == 'U') ? FL_UNSIGNED : 0;
470+ flags = 0;
471+ flags = (*p->pf == 'x' || *p->pf == 'X' || *p->pf == 'o' || *p->pf == 'u' || *p->pf == 'U') ? FL_UNSIGNED : 0;
472 if (*p->pf == 'X')
473 flags |= FL_HEXUPPER;
474
475@@ -733,7 +739,7 @@
476 p->flags &= ~PF_ZEROPAD;
477
478 sd = d; /* signed for ' ' padding in base 10 */
479- flags = (*p->pf == 'u' || *p->pf == 'U') ? FL_UNSIGNED : 0;
480+ flags = (*p->pf == 'x' || *p->pf == 'X' || *p->pf == 'o' || *p->pf == 'u' || *p->pf == 'U') ? FL_UNSIGNED : 0;
481 if (*p->pf == 'X')
482 flags |= FL_HEXUPPER;
483
484@@ -805,6 +811,7 @@
485 PUT_CHAR(*tmp, p);
486 tmp++;
487 }
488+
489 PAD_LEFT(p);
490 }
491
492@@ -972,11 +979,21 @@
493 if ((p->flags & PF_THOUSANDS) && grouping && (t = groupnum (tmp)))
494 tmp = t;
495
496+ if ((*p->pf == 'g' || *p->pf == 'G') && (p->flags & PF_ALTFORM) == 0)
497+ {
498+ /* smash the trailing zeros unless altform */
499+ for (i = strlen(tmp2) - 1; i >= 0 && tmp2[i] == '0'; i--)
500+ tmp2[i] = '\0';
501+ if (tmp2[0] == '\0')
502+ p->precision = 0;
503+ }
504+
505 /* calculate the padding. 1 for the dot */
506 p->width = p->width -
507 ((d > 0. && p->justify == RIGHT) ? 1:0) -
508 ((p->flags & PF_SPACE) ? 1:0) -
509- strlen(tmp) - p->precision - 1;
510+ strlen(tmp) - p->precision -
511+ ((p->precision != 0 || (p->flags & PF_ALTFORM)) ? 1 : 0); /* radix char */
512 PAD_RIGHT(p);
513 PUT_PLUS(d, p, 0.);
514 PUT_SPACE(d, p, 0.);
515@@ -991,11 +1008,6 @@
516 if (p->precision != 0 || (p->flags & PF_ALTFORM))
517 PUT_CHAR(decpoint, p); /* put the '.' */
518
519- if ((*p->pf == 'g' || *p->pf == 'G') && (p->flags & PF_ALTFORM) == 0)
520- /* smash the trailing zeros unless altform */
521- for (i = strlen(tmp2) - 1; i >= 0 && tmp2[i] == '0'; i--)
522- tmp2[i] = '\0';
523-
524 for (; *tmp2; tmp2++)
525 PUT_CHAR(*tmp2, p); /* the fraction */
526
527@@ -1011,14 +1023,19 @@
528 char *tmp, *tmp2;
529 int j, i;
530
531- if (chkinfnan(p, d, 1) || chkinfnan(p, d, 2))
532+ if (d != 0 && (chkinfnan(p, d, 1) || chkinfnan(p, d, 2)))
533 return; /* already printed nan or inf */
534
535 GETLOCALEDATA(decpoint, thoussep, grouping);
536 DEF_PREC(p);
537- j = log_10(d);
538- d = d / pow_10(j); /* get the Mantissa */
539- d = ROUND(d, p);
540+ if (d == 0.)
541+ j = 0;
542+ else
543+ {
544+ j = log_10(d);
545+ d = d / pow_10(j); /* get the Mantissa */
546+ d = ROUND(d, p);
547+ }
548 tmp = dtoa(d, p->precision, &tmp2);
549
550 /* 1 for unit, 1 for the '.', 1 for 'e|E',
551@@ -1076,6 +1093,7 @@
552 PUT_CHAR(*tmp, p);
553 tmp++;
554 }
555+
556 PAD_LEFT(p);
557 }
558 #endif
559@@ -1358,7 +1376,7 @@
560 STAR_ARGS(data);
561 DEF_PREC(data);
562 d = GETDOUBLE(data);
563- i = log_10(d);
564+ i = (d != 0.) ? log_10(d) : -1;
565 /*
566 * for '%g|%G' ANSI: use f if exponent
567 * is in the range or [-4,p] exclusively
568diff -Naur bash-3.2.orig/parse.y bash-3.2/parse.y
569--- bash-3.2.orig/parse.y 2007-07-23 19:54:02.000000000 -0400
570+++ bash-3.2/parse.y 2007-07-23 19:58:47.000000000 -0400
571@@ -1029,6 +1029,7 @@
572 #define PST_CMDTOKEN 0x1000 /* command token OK - unused */
573 #define PST_COMPASSIGN 0x2000 /* parsing x=(...) compound assignment */
574 #define PST_ASSIGNOK 0x4000 /* assignment statement ok in this context */
575+#define PST_REGEXP 0x8000 /* parsing an ERE/BRE as a single word */
576
577 /* Initial size to allocate for tokens, and the
578 amount to grow them by. */
579@@ -2591,6 +2592,9 @@
580 return (character);
581 }
582
583+ if (parser_state & PST_REGEXP)
584+ goto tokword;
585+
586 /* Shell meta-characters. */
587 if MBTEST(shellmeta (character) && ((parser_state & PST_DBLPAREN) == 0))
588 {
589@@ -2698,6 +2702,7 @@
590 if MBTEST(character == '-' && (last_read_token == LESS_AND || last_read_token == GREATER_AND))
591 return (character);
592
593+tokword:
594 /* Okay, if we got this far, we have to read a word. Read one,
595 and then check it against the known ones. */
596 result = read_token_word (character);
597@@ -2735,7 +2740,7 @@
598 /* itrace("parse_matched_pair: open = %c close = %c", open, close); */
599 count = 1;
600 pass_next_character = backq_backslash = was_dollar = in_comment = 0;
601- check_comment = (flags & P_COMMAND) && qc != '\'' && qc != '"' && (flags & P_DQUOTE) == 0;
602+ check_comment = (flags & P_COMMAND) && qc != '`' && qc != '\'' && qc != '"' && (flags & P_DQUOTE) == 0;
603
604 /* RFLAGS is the set of flags we want to pass to recursive calls. */
605 rflags = (qc == '"') ? P_DQUOTE : (flags & P_DQUOTE);
606@@ -3202,8 +3207,11 @@
607 if (tok == WORD && test_binop (yylval.word->word))
608 op = yylval.word;
609 #if defined (COND_REGEXP)
610- else if (tok == WORD && STREQ (yylval.word->word,"=~"))
611- op = yylval.word;
612+ else if (tok == WORD && STREQ (yylval.word->word, "=~"))
613+ {
614+ op = yylval.word;
615+ parser_state |= PST_REGEXP;
616+ }
617 #endif
618 else if (tok == '<' || tok == '>')
619 op = make_word_from_token (tok); /* ( */
620@@ -3234,6 +3242,7 @@
621
622 /* rhs */
623 tok = read_token (READ);
624+ parser_state &= ~PST_REGEXP;
625 if (tok == WORD)
626 {
627 tright = make_cond_node (COND_TERM, yylval.word, (COND_COM *)NULL, (COND_COM *)NULL);
628@@ -3419,9 +3428,34 @@
629 goto next_character;
630 }
631
632+#ifdef COND_REGEXP
633+ /* When parsing a regexp as a single word inside a conditional command,
634+ we need to special-case characters special to both the shell and
635+ regular expressions. Right now, that is only '(' and '|'. */ /*)*/
636+ if MBTEST((parser_state & PST_REGEXP) && (character == '(' || character == '|')) /*)*/
637+ {
638+ if (character == '|')
639+ goto got_character;
640+
641+ push_delimiter (dstack, character);
642+ ttok = parse_matched_pair (cd, '(', ')', &ttoklen, 0);
643+ pop_delimiter (dstack);
644+ if (ttok == &matched_pair_error)
645+ return -1; /* Bail immediately. */
646+ RESIZE_MALLOCED_BUFFER (token, token_index, ttoklen + 2,
647+ token_buffer_size, TOKEN_DEFAULT_GROW_SIZE);
648+ token[token_index++] = character;
649+ strcpy (token + token_index, ttok);
650+ token_index += ttoklen;
651+ FREE (ttok);
652+ dollar_present = all_digit_token = 0;
653+ goto next_character;
654+ }
655+#endif /* COND_REGEXP */
656+
657 #ifdef EXTENDED_GLOB
658 /* Parse a ksh-style extended pattern matching specification. */
659- if (extended_glob && PATTERN_CHAR (character))
660+ if MBTEST(extended_glob && PATTERN_CHAR (character))
661 {
662 peek_char = shell_getc (1);
663 if MBTEST(peek_char == '(') /* ) */
664diff -Naur bash-3.2.orig/patchlevel.h bash-3.2/patchlevel.h
665--- bash-3.2.orig/patchlevel.h 2007-07-23 19:54:02.000000000 -0400
666+++ bash-3.2/patchlevel.h 2007-07-23 19:58:47.000000000 -0400
667@@ -25,6 +25,6 @@
668 regexp `^#define[ ]*PATCHLEVEL', since that's what support/mkversion.sh
669 looks for to find the patch level (for the sccs version string). */
670
671-#define PATCHLEVEL 0
672+#define PATCHLEVEL 17
673
674 #endif /* _PATCHLEVEL_H_ */
675diff -Naur bash-3.2.orig/pathexp.c bash-3.2/pathexp.c
676--- bash-3.2.orig/pathexp.c 2007-07-23 19:54:02.000000000 -0400
677+++ bash-3.2/pathexp.c 2007-07-23 19:58:47.000000000 -0400
678@@ -1,6 +1,6 @@
679 /* pathexp.c -- The shell interface to the globbing library. */
680
681-/* Copyright (C) 1995-2002 Free Software Foundation, Inc.
682+/* Copyright (C) 1995-2007 Free Software Foundation, Inc.
683
684 This file is part of GNU Bash, the Bourne Again SHell.
685
686@@ -110,6 +110,33 @@
687 return (0);
688 }
689
690+/* Return 1 if C is a character that is `special' in a POSIX ERE and needs to
691+ be quoted to match itself. */
692+static inline int
693+ere_char (c)
694+ int c;
695+{
696+ switch (c)
697+ {
698+ case '.':
699+ case '[':
700+ case '\\':
701+ case '(':
702+ case ')':
703+ case '*':
704+ case '+':
705+ case '?':
706+ case '{':
707+ case '|':
708+ case '^':
709+ case '$':
710+ return 1;
711+ default:
712+ return 0;
713+ }
714+ return (0);
715+}
716+
717 /* PATHNAME can contain characters prefixed by CTLESC; this indicates
718 that the character is to be quoted. We quote it here in the style
719 that the glob library recognizes. If flags includes QGLOB_CVTNULL,
720@@ -142,6 +169,8 @@
721 {
722 if ((qflags & QGLOB_FILENAME) && pathname[i+1] == '/')
723 continue;
724+ if ((qflags & QGLOB_REGEXP) && ere_char (pathname[i+1]) == 0)
725+ continue;
726 temp[j++] = '\\';
727 i++;
728 if (pathname[i] == '\0')
729diff -Naur bash-3.2.orig/pathexp.h bash-3.2/pathexp.h
730--- bash-3.2.orig/pathexp.h 2007-07-23 19:54:02.000000000 -0400
731+++ bash-3.2/pathexp.h 2007-07-23 19:58:47.000000000 -0400
732@@ -1,6 +1,6 @@
733 /* pathexp.h -- The shell interface to the globbing library. */
734
735-/* Copyright (C) 1987-2005 Free Software Foundation, Inc.
736+/* Copyright (C) 1987-2007 Free Software Foundation, Inc.
737
738 This file is part of GNU Bash, the Bourne Again SHell.
739
740@@ -32,6 +32,7 @@
741 /* Flag values for quote_string_for_globbing */
742 #define QGLOB_CVTNULL 0x01 /* convert QUOTED_NULL strings to '\0' */
743 #define QGLOB_FILENAME 0x02 /* do correct quoting for matching filenames */
744+#define QGLOB_REGEXP 0x04 /* quote an ERE for regcomp/regexec */
745
746 #if defined (EXTENDED_GLOB)
747 /* Flags to OR with other flag args to strmatch() to enabled the extended
748diff -Naur bash-3.2.orig/po/ru.po bash-3.2/po/ru.po
749--- bash-3.2.orig/po/ru.po 2007-07-23 19:54:02.000000000 -0400
750+++ bash-3.2/po/ru.po 2007-07-23 19:58:47.000000000 -0400
751@@ -12,7 +12,7 @@
752 "Last-Translator: Evgeniy Dushistov <dushistov@mail.ru>\n"
753 "Language-Team: Russian <ru@li.org>\n"
754 "MIME-Version: 1.0\n"
755-"Content-Type: text/plain; charset=UTF-8\n"
756+"Content-Type: text/plain; charset=KOI8-R\n"
757 "Content-Transfer-Encoding: 8bit\n"
758 "Plural-Forms: nplurals=3; plural=(n%10==1 && n%100!=11 ? 0 : n%10>=2 && n%10<=4 && (n%100<10 || n%100>=20) ? 1 : 2);\n"
759
760diff -Naur bash-3.2.orig/subst.c bash-3.2/subst.c
761--- bash-3.2.orig/subst.c 2007-07-23 19:54:02.000000000 -0400
762+++ bash-3.2/subst.c 2007-07-23 19:58:47.000000000 -0400
763@@ -4,7 +4,7 @@
764 /* ``Have a little faith, there's magic in the night. You ain't a
765 beauty, but, hey, you're alright.'' */
766
767-/* Copyright (C) 1987-2006 Free Software Foundation, Inc.
768+/* Copyright (C) 1987-2007 Free Software Foundation, Inc.
769
770 This file is part of GNU Bash, the Bourne Again SHell.
771
772@@ -1887,7 +1887,13 @@
773 sep[1] = '\0';
774 #endif
775
776+ /* XXX -- why call quote_list if ifs == 0? we can get away without doing
777+ it now that quote_escapes quotes spaces */
778+#if 0
779 tlist = ((quoted & (Q_HERE_DOCUMENT|Q_DOUBLE_QUOTES)) || (ifs && *ifs == 0))
780+#else
781+ tlist = (quoted & (Q_HERE_DOCUMENT|Q_DOUBLE_QUOTES))
782+#endif
783 ? quote_list (list)
784 : list_quote_escapes (list);
785
786@@ -2646,11 +2652,12 @@
787
788 /* This needs better error handling. */
789 /* Expand W for use as an argument to a unary or binary operator in a
790- [[...]] expression. If SPECIAL is nonzero, this is the rhs argument
791+ [[...]] expression. If SPECIAL is 1, this is the rhs argument
792 to the != or == operator, and should be treated as a pattern. In
793- this case, we quote the string specially for the globbing code. The
794- caller is responsible for removing the backslashes if the unquoted
795- words is needed later. */
796+ this case, we quote the string specially for the globbing code. If
797+ SPECIAL is 2, this is an rhs argument for the =~ operator, and should
798+ be quoted appropriately for regcomp/regexec. The caller is responsible
799+ for removing the backslashes if the unquoted word is needed later. */
800 char *
801 cond_expand_word (w, special)
802 WORD_DESC *w;
803@@ -2658,6 +2665,7 @@
804 {
805 char *r, *p;
806 WORD_LIST *l;
807+ int qflags;
808
809 if (w->word == 0 || w->word[0] == '\0')
810 return ((char *)NULL);
811@@ -2672,8 +2680,11 @@
812 }
813 else
814 {
815+ qflags = QGLOB_CVTNULL;
816+ if (special == 2)
817+ qflags |= QGLOB_REGEXP;
818 p = string_list (l);
819- r = quote_string_for_globbing (p, QGLOB_CVTNULL);
820+ r = quote_string_for_globbing (p, qflags);
821 free (p);
822 }
823 dispose_words (l);
824@@ -2916,7 +2927,12 @@
825
826 /* Quote escape characters in string s, but no other characters. This is
827 used to protect CTLESC and CTLNUL in variable values from the rest of
828- the word expansion process after the variable is expanded. */
829+ the word expansion process after the variable is expanded. If IFS is
830+ null, we quote spaces as well, just in case we split on spaces later
831+ (in the case of unquoted $@, we will eventually attempt to split the
832+ entire word on spaces). Corresponding code exists in dequote_escapes.
833+ Even if we don't end up splitting on spaces, quoting spaces is not a
834+ problem. */
835 char *
836 quote_escapes (string)
837 char *string;
838@@ -2924,17 +2940,19 @@
839 register char *s, *t;
840 size_t slen;
841 char *result, *send;
842+ int quote_spaces;
843 DECLARE_MBSTATE;
844
845 slen = strlen (string);
846 send = string + slen;
847
848+ quote_spaces = (ifs_value && *ifs_value == 0);
849 t = result = (char *)xmalloc ((slen * 2) + 1);
850 s = string;
851
852 while (*s)
853 {
854- if (*s == CTLESC || *s == CTLNUL)
855+ if (*s == CTLESC || *s == CTLNUL || (quote_spaces && *s == ' '))
856 *t++ = CTLESC;
857 COPY_CHAR_P (t, s, send);
858 }
859@@ -2976,6 +2994,7 @@
860 register char *s, *t;
861 size_t slen;
862 char *result, *send;
863+ int quote_spaces;
864 DECLARE_MBSTATE;
865
866 if (string == 0)
867@@ -2990,9 +3009,10 @@
868 if (strchr (string, CTLESC) == 0)
869 return (strcpy (result, s));
870
871+ quote_spaces = (ifs_value && *ifs_value == 0);
872 while (*s)
873 {
874- if (*s == CTLESC && (s[1] == CTLESC || s[1] == CTLNUL))
875+ if (*s == CTLESC && (s[1] == CTLESC || s[1] == CTLNUL || (quote_spaces && s[1] == ' ')))
876 {
877 s++;
878 if (*s == '\0')
879@@ -4123,6 +4143,12 @@
880 nfifo = 0;
881 }
882
883+int
884+fifos_pending ()
885+{
886+ return nfifo;
887+}
888+
889 static char *
890 make_named_pipe ()
891 {
892@@ -4172,6 +4198,12 @@
893 nfds++;
894 }
895
896+int
897+fifos_pending ()
898+{
899+ return 0; /* used for cleanup; not needed with /dev/fd */
900+}
901+
902 void
903 unlink_fifo_list ()
904 {
905@@ -4456,7 +4488,15 @@
906 /* Add the character to ISTRING, possibly after resizing it. */
907 RESIZE_MALLOCED_BUFFER (istring, istring_index, 2, istring_size, DEFAULT_ARRAY_SIZE);
908
909- if ((quoted & (Q_HERE_DOCUMENT|Q_DOUBLE_QUOTES)) || c == CTLESC || c == CTLNUL)
910+ /* This is essentially quote_string inline */
911+ if ((quoted & (Q_HERE_DOCUMENT|Q_DOUBLE_QUOTES)) /* || c == CTLESC || c == CTLNUL */)
912+ istring[istring_index++] = CTLESC;
913+ /* Escape CTLESC and CTLNUL in the output to protect those characters
914+ from the rest of the word expansions (word splitting and globbing.)
915+ This is essentially quote_escapes inline. */
916+ else if (c == CTLESC)
917+ istring[istring_index++] = CTLESC;
918+ else if (c == CTLNUL || (c == ' ' && (ifs_value && *ifs_value == 0)))
919 istring[istring_index++] = CTLESC;
920
921 istring[istring_index++] = c;
922@@ -4665,6 +4705,9 @@
923
924 last_command_exit_value = rc;
925 rc = run_exit_trap ();
926+#if defined (PROCESS_SUBSTITUTION)
927+ unlink_fifo_list ();
928+#endif
929 exit (rc);
930 }
931 else
932@@ -5546,12 +5589,16 @@
933 so verify_substring_values just returns the numbers specified and we
934 rely on array_subrange to understand how to deal with them). */
935 tt = array_subrange (array_cell (v), e1, e2, starsub, quoted);
936+#if 0
937+ /* array_subrange now calls array_quote_escapes as appropriate, so the
938+ caller no longer needs to. */
939 if ((quoted & (Q_DOUBLE_QUOTES|Q_HERE_DOCUMENT)) == 0)
940 {
941 temp = tt ? quote_escapes (tt) : (char *)NULL;
942 FREE (tt);
943 }
944 else
945+#endif
946 temp = tt;
947 break;
948 #endif
949@@ -5707,6 +5754,11 @@
950 vtype &= ~VT_STARSUB;
951
952 mflags = 0;
953+ if (patsub && *patsub == '/')
954+ {
955+ mflags |= MATCH_GLOBREP;
956+ patsub++;
957+ }
958
959 /* Malloc this because expand_string_if_necessary or one of the expansion
960 functions in its call chain may free it on a substitution error. */
961@@ -5741,13 +5793,12 @@
962 }
963
964 /* ksh93 doesn't allow the match specifier to be a part of the expanded
965- pattern. This is an extension. */
966+ pattern. This is an extension. Make sure we don't anchor the pattern
967+ at the beginning or end of the string if we're doing global replacement,
968+ though. */
969 p = pat;
970- if (pat && pat[0] == '/')
971- {
972- mflags |= MATCH_GLOBREP|MATCH_ANY;
973- p++;
974- }
975+ if (mflags & MATCH_GLOBREP)
976+ mflags |= MATCH_ANY;
977 else if (pat && pat[0] == '#')
978 {
979 mflags |= MATCH_BEG;
980@@ -5798,12 +5849,16 @@
981 #if defined (ARRAY_VARS)
982 case VT_ARRAYVAR:
983 temp = array_patsub (array_cell (v), p, rep, mflags);
984+#if 0
985+ /* Don't need to do this anymore; array_patsub calls array_quote_escapes
986+ as appropriate before adding the space separators. */
987 if (temp && (mflags & MATCH_QUOTED) == 0)
988 {
989 tt = quote_escapes (temp);
990 free (temp);
991 temp = tt;
992 }
993+#endif
994 break;
995 #endif
996 }
997diff -Naur bash-3.2.orig/subst.h bash-3.2/subst.h
998--- bash-3.2.orig/subst.h 2007-07-23 19:54:02.000000000 -0400
999+++ bash-3.2/subst.h 2007-07-23 19:58:47.000000000 -0400
1000@@ -222,6 +222,7 @@
1001 extern char *command_substitute __P((char *, int));
1002 extern char *pat_subst __P((char *, char *, char *, int));
1003
1004+extern int fifos_pending __P((void));
1005 extern void unlink_fifo_list __P((void));
1006
1007 extern WORD_LIST *list_string_with_quotes __P((char *));
1008diff -Naur bash-3.2.orig/tests/new-exp.right bash-3.2/tests/new-exp.right
1009--- bash-3.2.orig/tests/new-exp.right 2007-07-23 19:54:02.000000000 -0400
1010+++ bash-3.2/tests/new-exp.right 2007-07-23 19:58:47.000000000 -0400
1011@@ -430,7 +430,7 @@
1012 Case06---1---A B C::---
1013 Case07---3---A:B:C---
1014 Case08---3---A:B:C---
1015-./new-exp.tests: line 506: /${$(($#-1))}: bad substitution
1016+./new-exp.tests: line 506: ${$(($#-1))}: bad substitution
1017 argv[1] = <a>
1018 argv[2] = <b>
1019 argv[3] = <c>
Note: See TracBrowser for help on using the repository browser.