source: patches/bash-4.2-branch_update-5.patch@ 7c48514

clfs-2.1 clfs-3.0.0-systemd clfs-3.0.0-sysvinit systemd sysvinit
Last change on this file since 7c48514 was bad4693, checked in by William Harrington <kb0iic@…>, 12 years ago

Add header info to bash-4.2-branch_update-5.patch and vim-7.3-branch_update-5.patch

  • Property mode set to 100644
File size: 52.6 KB
RevLine 
[bad4693]1Submitted By: William Harrington (kb0iic at gmail dot com)
2Date: 07-31-2012
3Initial Package Version: 4.2
4Origin: Upstream
5Upstream Status: Applied
6Description: Contains all upstream patches up to 4.2-037
7
[eb3c388]8diff -Naur bash-4.2.orig/assoc.c bash-4.2/assoc.c
9--- bash-4.2.orig/assoc.c 2009-08-06 00:19:40.000000000 +0000
[e80ea72]10+++ bash-4.2/assoc.c 2012-07-20 20:30:10.654261541 +0000
[eb3c388]11@@ -77,6 +77,11 @@
12 b = hash_search (key, hash, HASH_CREATE);
13 if (b == 0)
14 return -1;
15+ /* If we are overwriting an existing element's value, we're not going to
16+ use the key. Nothing in the array assignment code path frees the key
17+ string, so we can free it here to avoid a memory leak. */
18+ if (b->key != key)
19+ free (key);
20 FREE (b->data);
21 b->data = value ? savestring (value) : (char *)0;
22 return (0);
23diff -Naur bash-4.2.orig/bashline.c bash-4.2/bashline.c
24--- bash-4.2.orig/bashline.c 2011-01-16 20:32:47.000000000 +0000
[e80ea72]25+++ bash-4.2/bashline.c 2012-07-20 20:30:11.070928530 +0000
[eb3c388]26@@ -121,6 +121,9 @@
27 static int filename_completion_ignore __P((char **));
28 static int bash_push_line __P((void));
29
30+static rl_icppfunc_t *save_directory_hook __P((void));
31+static void reset_directory_hook __P((rl_icppfunc_t *));
32+
33 static void cleanup_expansion_error __P((void));
34 static void maybe_make_readline_line __P((char *));
35 static void set_up_new_line __P((char *));
36@@ -243,10 +246,17 @@
37 /* Perform spelling correction on directory names during word completion */
38 int dircomplete_spelling = 0;
39
40+/* Expand directory names during word/filename completion. */
41+int dircomplete_expand = 0;
42+int dircomplete_expand_relpath = 0;
43+
44 static char *bash_completer_word_break_characters = " \t\n\"'@><=;|&(:";
45 static char *bash_nohostname_word_break_characters = " \t\n\"'><=;|&(:";
46 /* )) */
47
48+static const char *default_filename_quote_characters = " \t\n\\\"'@<>=;|&()#$`?*[!:{~"; /*}*/
49+static char *custom_filename_quote_characters = 0;
50+
51 static rl_hook_func_t *old_rl_startup_hook = (rl_hook_func_t *)NULL;
52
53 static int dot_in_path = 0;
54@@ -501,7 +511,7 @@
55
56 /* Tell the completer that we might want to follow symbolic links or
57 do other expansion on directory names. */
58- rl_directory_rewrite_hook = bash_directory_completion_hook;
59+ set_directory_hook ();
60
61 rl_filename_rewrite_hook = bash_filename_rewrite_hook;
62
63@@ -529,7 +539,7 @@
64 enable_hostname_completion (perform_hostname_completion);
65
66 /* characters that need to be quoted when appearing in filenames. */
67- rl_filename_quote_characters = " \t\n\\\"'@<>=;|&()#$`?*[!:{~"; /*}*/
68+ rl_filename_quote_characters = default_filename_quote_characters;
69
70 rl_filename_quoting_function = bash_quote_filename;
71 rl_filename_dequoting_function = bash_dequote_filename;
72@@ -564,8 +574,10 @@
73 tilde_initialize ();
74 rl_attempted_completion_function = attempt_shell_completion;
75 rl_completion_entry_function = NULL;
76- rl_directory_rewrite_hook = bash_directory_completion_hook;
77 rl_ignore_some_completions_function = filename_completion_ignore;
78+ rl_filename_quote_characters = default_filename_quote_characters;
79+
80+ set_directory_hook ();
81 }
82
83 /* Contains the line to push into readline. */
84@@ -1279,6 +1291,9 @@
85 matches = (char **)NULL;
86 rl_ignore_some_completions_function = filename_completion_ignore;
87
88+ rl_filename_quote_characters = default_filename_quote_characters;
89+ set_directory_hook ();
90+
91 /* Determine if this could be a command word. It is if it appears at
92 the start of the line (ignoring preceding whitespace), or if it
93 appears after a character that separates commands. It cannot be a
94@@ -1591,6 +1606,12 @@
95 }
96 else
97 {
98+ if (dircomplete_expand && dot_or_dotdot (filename_hint))
99+ {
100+ dircomplete_expand = 0;
101+ set_directory_hook ();
102+ dircomplete_expand = 1;
103+ }
104 mapping_over = 4;
105 goto inner;
106 }
107@@ -1791,6 +1812,9 @@
108
109 inner:
110 val = rl_filename_completion_function (filename_hint, istate);
111+ if (mapping_over == 4 && dircomplete_expand)
112+ set_directory_hook ();
113+
114 istate = 1;
115
116 if (val == 0)
117@@ -2693,6 +2717,52 @@
118 return conv;
119 }
120
121+/* Functions to save and restore the appropriate directory hook */
122+/* This is not static so the shopt code can call it */
123+void
124+set_directory_hook ()
125+{
126+ if (dircomplete_expand)
127+ {
128+ rl_directory_completion_hook = bash_directory_completion_hook;
129+ rl_directory_rewrite_hook = (rl_icppfunc_t *)0;
130+ }
131+ else
132+ {
133+ rl_directory_rewrite_hook = bash_directory_completion_hook;
134+ rl_directory_completion_hook = (rl_icppfunc_t *)0;
135+ }
136+}
137+
138+static rl_icppfunc_t *
139+save_directory_hook ()
140+{
141+ rl_icppfunc_t *ret;
142+
143+ if (dircomplete_expand)
144+ {
145+ ret = rl_directory_completion_hook;
146+ rl_directory_completion_hook = (rl_icppfunc_t *)NULL;
147+ }
148+ else
149+ {
150+ ret = rl_directory_rewrite_hook;
151+ rl_directory_rewrite_hook = (rl_icppfunc_t *)NULL;
152+ }
153+
154+ return ret;
155+}
156+
157+static void
158+restore_directory_hook (hookf)
159+ rl_icppfunc_t *hookf;
160+{
161+ if (dircomplete_expand)
162+ rl_directory_completion_hook = hookf;
163+ else
164+ rl_directory_rewrite_hook = hookf;
165+}
166+
167 /* Handle symbolic link references and other directory name
168 expansions while hacking completion. This should return 1 if it modifies
169 the DIRNAME argument, 0 otherwise. It should make sure not to modify
170@@ -2702,20 +2772,31 @@
171 char **dirname;
172 {
173 char *local_dirname, *new_dirname, *t;
174- int return_value, should_expand_dirname;
175+ int return_value, should_expand_dirname, nextch, closer;
176 WORD_LIST *wl;
177 struct stat sb;
178
179- return_value = should_expand_dirname = 0;
180+ return_value = should_expand_dirname = nextch = closer = 0;
181 local_dirname = *dirname;
182
183- if (mbschr (local_dirname, '$'))
184- should_expand_dirname = 1;
185+ if (t = mbschr (local_dirname, '$'))
186+ {
187+ should_expand_dirname = '$';
188+ nextch = t[1];
189+ /* Deliberately does not handle the deprecated $[...] arithmetic
190+ expansion syntax */
191+ if (nextch == '(')
192+ closer = ')';
193+ else if (nextch == '{')
194+ closer = '}';
195+ else
196+ nextch = 0;
197+ }
198 else
199 {
200 t = mbschr (local_dirname, '`');
201 if (t && unclosed_pair (local_dirname, strlen (local_dirname), "`") == 0)
202- should_expand_dirname = 1;
203+ should_expand_dirname = '`';
204 }
205
206 #if defined (HAVE_LSTAT)
207@@ -2739,6 +2820,23 @@
208 free (new_dirname);
209 dispose_words (wl);
210 local_dirname = *dirname;
211+ /* XXX - change rl_filename_quote_characters here based on
212+ should_expand_dirname/nextch/closer. This is the only place
213+ custom_filename_quote_characters is modified. */
214+ if (rl_filename_quote_characters && *rl_filename_quote_characters)
215+ {
216+ int i, j, c;
217+ i = strlen (default_filename_quote_characters);
218+ custom_filename_quote_characters = xrealloc (custom_filename_quote_characters, i+1);
219+ for (i = j = 0; c = default_filename_quote_characters[i]; i++)
220+ {
221+ if (c == should_expand_dirname || c == nextch || c == closer)
222+ continue;
223+ custom_filename_quote_characters[j++] = c;
224+ }
225+ custom_filename_quote_characters[j] = '\0';
226+ rl_filename_quote_characters = custom_filename_quote_characters;
227+ }
228 }
229 else
230 {
231@@ -2758,11 +2856,31 @@
232 local_dirname = *dirname = new_dirname;
233 }
234
235+ /* no_symbolic_links == 0 -> use (default) logical view of the file system.
236+ local_dirname[0] == '.' && local_dirname[1] == '/' means files in the
237+ current directory (./).
238+ local_dirname[0] == '.' && local_dirname[1] == 0 means relative pathnames
239+ in the current directory (e.g., lib/sh).
240+ XXX - should we do spelling correction on these? */
241+
242+ /* This is test as it was in bash-4.2: skip relative pathnames in current
243+ directory. Change test to
244+ (local_dirname[0] != '.' || (local_dirname[1] && local_dirname[1] != '/'))
245+ if we want to skip paths beginning with ./ also. */
246 if (no_symbolic_links == 0 && (local_dirname[0] != '.' || local_dirname[1]))
247 {
248 char *temp1, *temp2;
249 int len1, len2;
250
251+ /* If we have a relative path
252+ (local_dirname[0] != '/' && local_dirname[0] != '.')
253+ that is canonical after appending it to the current directory, then
254+ temp1 = temp2+'/'
255+ That is,
256+ strcmp (temp1, temp2) == 0
257+ after adding a slash to temp2 below. It should be safe to not
258+ change those.
259+ */
260 t = get_working_directory ("symlink-hook");
261 temp1 = make_absolute (local_dirname, t);
262 free (t);
263@@ -2797,7 +2915,15 @@
264 temp2[len2 + 1] = '\0';
265 }
266 }
267- return_value |= STREQ (local_dirname, temp2) == 0;
268+
269+ /* dircomplete_expand_relpath == 0 means we want to leave relative
270+ pathnames that are unchanged by canonicalization alone.
271+ *local_dirname != '/' && *local_dirname != '.' == relative pathname
272+ (consistent with general.c:absolute_pathname())
273+ temp1 == temp2 (after appending a slash to temp2) means the pathname
274+ is not changed by canonicalization as described above. */
275+ if (dircomplete_expand_relpath || ((local_dirname[0] != '/' && local_dirname[0] != '.') && STREQ (temp1, temp2) == 0))
276+ return_value |= STREQ (local_dirname, temp2) == 0;
277 free (local_dirname);
278 *dirname = temp2;
279 free (temp1);
280@@ -3002,12 +3128,13 @@
281
282 orig_func = rl_completion_entry_function;
283 orig_attempt_func = rl_attempted_completion_function;
284- orig_dir_func = rl_directory_rewrite_hook;
285 orig_ignore_func = rl_ignore_some_completions_function;
286 orig_rl_completer_word_break_characters = rl_completer_word_break_characters;
287+
288+ orig_dir_func = save_directory_hook ();
289+
290 rl_completion_entry_function = rl_filename_completion_function;
291 rl_attempted_completion_function = (rl_completion_func_t *)NULL;
292- rl_directory_rewrite_hook = (rl_icppfunc_t *)NULL;
293 rl_ignore_some_completions_function = filename_completion_ignore;
294 rl_completer_word_break_characters = " \t\n\"\'";
295
296@@ -3015,10 +3142,11 @@
297
298 rl_completion_entry_function = orig_func;
299 rl_attempted_completion_function = orig_attempt_func;
300- rl_directory_rewrite_hook = orig_dir_func;
301 rl_ignore_some_completions_function = orig_ignore_func;
302 rl_completer_word_break_characters = orig_rl_completer_word_break_characters;
303
304+ restore_directory_hook (orig_dir_func);
305+
306 return r;
307 }
308
309diff -Naur bash-4.2.orig/bashline.h bash-4.2/bashline.h
310--- bash-4.2.orig/bashline.h 2009-01-04 19:32:22.000000000 +0000
[e80ea72]311+++ bash-4.2/bashline.h 2012-07-20 20:30:11.070928530 +0000
[eb3c388]312@@ -33,10 +33,15 @@
313 extern void bashline_reinitialize __P((void));
314 extern int bash_re_edit __P((char *));
315
316+extern void bashline_set_event_hook __P((void));
317+extern void bashline_reset_event_hook __P((void));
318+
319 extern int bind_keyseq_to_unix_command __P((char *));
320
321 extern char **bash_default_completion __P((const char *, int, int, int, int));
322
323+void set_directory_hook __P((void));
324+
325 /* Used by programmable completion code. */
326 extern char *command_word_completion_function __P((const char *, int));
327 extern char *bash_groupname_completion_function __P((const char *, int));
328diff -Naur bash-4.2.orig/builtins/declare.def bash-4.2/builtins/declare.def
329--- bash-4.2.orig/builtins/declare.def 2010-05-30 22:25:21.000000000 +0000
[e80ea72]330+++ bash-4.2/builtins/declare.def 2012-07-20 20:30:10.947595101 +0000
[eb3c388]331@@ -513,6 +513,11 @@
332 *subscript_start = '['; /* ] */
333 var = assign_array_element (name, value, 0); /* XXX - not aflags */
334 *subscript_start = '\0';
335+ if (var == 0) /* some kind of assignment error */
336+ {
337+ assign_error++;
338+ NEXT_VARIABLE ();
339+ }
340 }
341 else if (simple_array_assign)
342 {
343diff -Naur bash-4.2.orig/builtins/fc.def bash-4.2/builtins/fc.def
344--- bash-4.2.orig/builtins/fc.def 2010-05-30 22:25:38.000000000 +0000
[e80ea72]345+++ bash-4.2/builtins/fc.def 2012-07-20 20:30:10.624261519 +0000
[eb3c388]346@@ -304,7 +304,7 @@
347 last_hist = i - rh - hist_last_line_added;
348
349 /* XXX */
350- if (saved_command_line_count > 0 && i == last_hist && hlist[last_hist] == 0)
351+ if (i == last_hist && hlist[last_hist] == 0)
352 while (last_hist >= 0 && hlist[last_hist] == 0)
353 last_hist--;
354 if (last_hist < 0)
355@@ -475,7 +475,7 @@
356 HIST_ENTRY **hlist;
357 {
358 int sign, n, clen, rh;
359- register int i, j;
360+ register int i, j, last_hist;
361 register char *s;
362
363 sign = 1;
364@@ -495,7 +495,15 @@
365 has been enabled (interactive or not) should use it in the last_hist
366 calculation as if it were on. */
367 rh = remember_on_history || ((subshell_environment & SUBSHELL_COMSUB) && enable_history_list);
368- i -= rh + hist_last_line_added;
369+ last_hist = i - rh - hist_last_line_added;
370+
371+ if (i == last_hist && hlist[last_hist] == 0)
372+ while (last_hist >= 0 && hlist[last_hist] == 0)
373+ last_hist--;
374+ if (last_hist < 0)
375+ return (-1);
376+
377+ i = last_hist;
378
379 /* No specification defaults to most recent command. */
380 if (command == NULL)
[e80ea72]381diff -Naur bash-4.2.orig/builtins/mapfile.def bash-4.2/builtins/mapfile.def
382--- bash-4.2.orig/builtins/mapfile.def 2010-05-30 02:09:47.000000000 +0000
383+++ bash-4.2/builtins/mapfile.def 2012-07-20 20:30:11.190928623 +0000
384@@ -195,13 +195,9 @@
385 /* Reset the buffer for bash own stream */
386 interrupt_immediately++;
387 for (array_index = origin, line_count = 1;
388- zgetline (fd, &line, &line_length, unbuffered_read) != -1;
389- array_index++, line_count++)
390+ zgetline (fd, &line, &line_length, unbuffered_read) != -1;
391+ array_index++)
392 {
393- /* Have we exceeded # of lines to store? */
394- if (line_count_goal != 0 && line_count > line_count_goal)
395- break;
396-
397 /* Remove trailing newlines? */
398 if (flags & MAPF_CHOP)
399 do_chop (line);
400@@ -217,6 +213,11 @@
401 }
402
403 bind_array_element (entry, array_index, line, 0);
404+
405+ /* Have we exceeded # of lines to store? */
406+ line_count++;
407+ if (line_count_goal != 0 && line_count > line_count_goal)
408+ break;
409 }
410
411 xfree (line);
[eb3c388]412diff -Naur bash-4.2.orig/builtins/printf.def bash-4.2/builtins/printf.def
413--- bash-4.2.orig/builtins/printf.def 2010-11-23 15:02:55.000000000 +0000
[e80ea72]414+++ bash-4.2/builtins/printf.def 2012-07-20 20:30:10.980928461 +0000
[eb3c388]415@@ -255,6 +255,8 @@
416 #endif
417 {
418 vflag = 1;
419+ if (vbsize == 0)
420+ vbuf = xmalloc (vbsize = 16);
421 vblen = 0;
422 if (vbuf)
423 vbuf[0] = 0;
424@@ -465,6 +467,9 @@
425 secs = shell_start_time; /* roughly $SECONDS */
426 else
427 secs = arg;
428+#if defined (HAVE_TZSET)
429+ sv_tz ("TZ"); /* XXX -- just make sure */
430+#endif
431 tm = localtime (&secs);
432 n = strftime (timebuf, sizeof (timebuf), timefmt, tm);
433 free (timefmt);
434diff -Naur bash-4.2.orig/builtins/read.def bash-4.2/builtins/read.def
435--- bash-4.2.orig/builtins/read.def 2011-01-04 16:43:36.000000000 +0000
[e80ea72]436+++ bash-4.2/builtins/read.def 2012-07-20 20:30:10.957595109 +0000
[eb3c388]437@@ -642,6 +642,12 @@
438 xfree (input_string);
439 return EXECUTION_FAILURE; /* readonly or noassign */
440 }
441+ if (assoc_p (var))
442+ {
443+ builtin_error (_("%s: cannot convert associative to indexed array"), arrayname);
444+ xfree (input_string);
445+ return EXECUTION_FAILURE; /* existing associative array */
446+ }
447 array_flush (array_cell (var));
448
449 alist = list_string (input_string, ifs_chars, 0);
450@@ -731,7 +737,7 @@
451 xfree (t1);
452 }
453 else
454- var = bind_read_variable (varname, t);
455+ var = bind_read_variable (varname, t ? t : "");
456 }
457 else
458 {
459@@ -792,7 +798,7 @@
460 xfree (t);
461 }
462 else
463- var = bind_read_variable (list->word->word, input_string);
464+ var = bind_read_variable (list->word->word, input_string ? input_string : "");
465
466 if (var)
467 {
468diff -Naur bash-4.2.orig/builtins/shopt.def bash-4.2/builtins/shopt.def
469--- bash-4.2.orig/builtins/shopt.def 2010-07-03 02:42:44.000000000 +0000
[e80ea72]470+++ bash-4.2/builtins/shopt.def 2012-07-20 20:30:11.070928530 +0000
[eb3c388]471@@ -61,6 +61,10 @@
472 #include "common.h"
473 #include "bashgetopt.h"
474
475+#if defined (READLINE)
476+# include "../bashline.h"
477+#endif
478+
479 #if defined (HISTORY)
480 # include "../bashhist.h"
481 #endif
482@@ -94,7 +98,7 @@
483 extern int hist_verify, history_reediting, perform_hostname_completion;
484 extern int no_empty_command_completion;
485 extern int force_fignore;
486-extern int dircomplete_spelling;
487+extern int dircomplete_spelling, dircomplete_expand;
488
489 extern int enable_hostname_completion __P((int));
490 #endif
491@@ -121,6 +125,10 @@
492 static int set_restricted_shell __P((char *, int));
493 #endif
494
495+#if defined (READLINE)
496+static int shopt_set_complete_direxpand __P((char *, int));
497+#endif
498+
499 static int shopt_login_shell;
500 static int shopt_compat31;
501 static int shopt_compat32;
502@@ -150,6 +158,7 @@
503 { "compat40", &shopt_compat40, set_compatibility_level },
504 { "compat41", &shopt_compat41, set_compatibility_level },
505 #if defined (READLINE)
506+ { "direxpand", &dircomplete_expand, shopt_set_complete_direxpand },
507 { "dirspell", &dircomplete_spelling, (shopt_set_func_t *)NULL },
508 #endif
509 { "dotglob", &glob_dot_filenames, (shopt_set_func_t *)NULL },
510@@ -535,6 +544,17 @@
511 return 0;
512 }
513
514+#if defined (READLINE)
515+static int
516+shopt_set_complete_direxpand (option_name, mode)
517+ char *option_name;
518+ int mode;
519+{
520+ set_directory_hook ();
521+ return 0;
522+}
523+#endif
524+
525 #if defined (RESTRICTED_SHELL)
526 /* Don't allow the value of restricted_shell to be modified. */
527
528diff -Naur bash-4.2.orig/command.h bash-4.2/command.h
529--- bash-4.2.orig/command.h 2010-08-02 23:36:51.000000000 +0000
[e80ea72]530+++ bash-4.2/command.h 2012-07-20 20:30:11.004261811 +0000
[eb3c388]531@@ -97,6 +97,7 @@
532 #define W_HASCTLESC 0x200000 /* word contains literal CTLESC characters */
533 #define W_ASSIGNASSOC 0x400000 /* word looks like associative array assignment */
534 #define W_ARRAYIND 0x800000 /* word is an array index being expanded */
535+#define W_ASSNGLOBAL 0x1000000 /* word is a global assignment to declare (declare/typeset -g) */
536
537 /* Possible values for subshell_environment */
538 #define SUBSHELL_ASYNC 0x01 /* subshell caused by `command &' */
539diff -Naur bash-4.2.orig/doc/bash.1 bash-4.2/doc/bash.1
540--- bash-4.2.orig/doc/bash.1 2011-01-16 20:31:39.000000000 +0000
[e80ea72]541+++ bash-4.2/doc/bash.1 2012-07-20 20:30:11.077595201 +0000
[eb3c388]542@@ -8948,6 +8948,16 @@
543 quoted. This is the behavior of posix mode through version 4.1.
544 The default bash behavior remains as in previous versions.
545 .TP 8
546+.B direxpand
547+If set,
548+.B bash
549+replaces directory names with the results of word expansion when performing
550+filename completion. This changes the contents of the readline editing
551+buffer.
552+If not set,
553+.B bash
554+attempts to preserve what the user typed.
555+.TP 8
556 .B dirspell
557 If set,
558 .B bash
559diff -Naur bash-4.2.orig/doc/bashref.texi bash-4.2/doc/bashref.texi
560--- bash-4.2.orig/doc/bashref.texi 2011-01-16 20:31:57.000000000 +0000
[e80ea72]561+++ bash-4.2/doc/bashref.texi 2012-07-20 20:30:11.084261873 +0000
[eb3c388]562@@ -4535,6 +4535,13 @@
563 quoted. This is the behavior of @sc{posix} mode through version 4.1.
564 The default Bash behavior remains as in previous versions.
565
566+@item direxpand
567+If set, Bash
568+replaces directory names with the results of word expansion when performing
569+filename completion. This changes the contents of the readline editing
570+buffer.
571+If not set, Bash attempts to preserve what the user typed.
572+
573 @item dirspell
574 If set, Bash
575 attempts spelling correction on directory names during word completion
576diff -Naur bash-4.2.orig/error.c bash-4.2/error.c
577--- bash-4.2.orig/error.c 2009-08-22 02:31:31.000000000 +0000
[e80ea72]578+++ bash-4.2/error.c 2012-07-20 20:30:10.974261789 +0000
[eb3c388]579@@ -200,7 +200,11 @@
580
581 va_end (args);
582 if (exit_immediately_on_error)
583- exit_shell (1);
584+ {
585+ if (last_command_exit_value == 0)
586+ last_command_exit_value = 1;
587+ exit_shell (last_command_exit_value);
588+ }
589 }
590
591 void
592diff -Naur bash-4.2.orig/execute_cmd.c bash-4.2/execute_cmd.c
593--- bash-4.2.orig/execute_cmd.c 2011-02-09 22:32:25.000000000 +0000
[e80ea72]594+++ bash-4.2/execute_cmd.c 2012-07-20 20:30:11.024261827 +0000
[eb3c388]595@@ -2196,6 +2196,7 @@
596 if (ignore_return && cmd)
597 cmd->flags |= CMD_IGNORE_RETURN;
598
599+#if defined (JOB_CONTROL)
600 lastpipe_flag = 0;
601 begin_unwind_frame ("lastpipe-exec");
602 lstdin = -1;
603@@ -2204,7 +2205,7 @@
604 current shell environment. */
605 if (lastpipe_opt && job_control == 0 && asynchronous == 0 && pipe_out == NO_PIPE && prev > 0)
606 {
607- lstdin = move_to_high_fd (0, 0, 255);
608+ lstdin = move_to_high_fd (0, 1, -1);
609 if (lstdin > 0)
610 {
611 do_piping (prev, pipe_out);
612@@ -2215,15 +2216,19 @@
613 lastpipe_jid = stop_pipeline (0, (COMMAND *)NULL); /* XXX */
614 add_unwind_protect (lastpipe_cleanup, lastpipe_jid);
615 }
616- cmd->flags |= CMD_LASTPIPE;
617+ if (cmd)
618+ cmd->flags |= CMD_LASTPIPE;
619 }
620 if (prev >= 0)
621 add_unwind_protect (close, prev);
622+#endif
623
624 exec_result = execute_command_internal (cmd, asynchronous, prev, pipe_out, fds_to_close);
625
626+#if defined (JOB_CONTROL)
627 if (lstdin > 0)
628 restore_stdin (lstdin);
629+#endif
630
631 if (prev >= 0)
632 close (prev);
633@@ -2246,7 +2251,9 @@
634 unfreeze_jobs_list ();
635 }
636
637+#if defined (JOB_CONTROL)
638 discard_unwind_frame ("lastpipe-exec");
639+#endif
640
641 return (exec_result);
642 }
643@@ -3575,13 +3582,13 @@
644 {
645 WORD_LIST *w;
646 struct builtin *b;
647- int assoc;
648+ int assoc, global;
649
650 if (words == 0)
651 return;
652
653 b = 0;
654- assoc = 0;
655+ assoc = global = 0;
656
657 for (w = words; w; w = w->next)
658 if (w->word->flags & W_ASSIGNMENT)
659@@ -3598,12 +3605,17 @@
660 #if defined (ARRAY_VARS)
661 if (assoc)
662 w->word->flags |= W_ASSIGNASSOC;
663+ if (global)
664+ w->word->flags |= W_ASSNGLOBAL;
665 #endif
666 }
667 #if defined (ARRAY_VARS)
668 /* Note that we saw an associative array option to a builtin that takes
669 assignment statements. This is a bit of a kludge. */
670- else if (w->word->word[0] == '-' && strchr (w->word->word, 'A'))
671+ else if (w->word->word[0] == '-' && (strchr (w->word->word+1, 'A') || strchr (w->word->word+1, 'g')))
672+#else
673+ else if (w->word->word[0] == '-' && strchr (w->word->word+1, 'g'))
674+#endif
675 {
676 if (b == 0)
677 {
678@@ -3613,10 +3625,11 @@
679 else if (b && (b->flags & ASSIGNMENT_BUILTIN))
680 words->word->flags |= W_ASSNBLTIN;
681 }
682- if (words->word->flags & W_ASSNBLTIN)
683+ if ((words->word->flags & W_ASSNBLTIN) && strchr (w->word->word+1, 'A'))
684 assoc = 1;
685+ if ((words->word->flags & W_ASSNBLTIN) && strchr (w->word->word+1, 'g'))
686+ global = 1;
687 }
688-#endif
689 }
690
691 /* Return 1 if the file found by searching $PATH for PATHNAME, defaulting
692diff -Naur bash-4.2.orig/expr.c bash-4.2/expr.c
693--- bash-4.2.orig/expr.c 2010-12-21 16:12:13.000000000 +0000
[e80ea72]694+++ bash-4.2/expr.c 2012-07-20 20:30:10.907595071 +0000
[eb3c388]695@@ -476,19 +476,23 @@
696
697 if (special)
698 {
699+ if ((op == DIV || op == MOD) && value == 0)
700+ {
701+ if (noeval == 0)
702+ evalerror (_("division by 0"));
703+ else
704+ value = 1;
705+ }
706+
707 switch (op)
708 {
709 case MUL:
710 lvalue *= value;
711 break;
712 case DIV:
713- if (value == 0)
714- evalerror (_("division by 0"));
715 lvalue /= value;
716 break;
717 case MOD:
718- if (value == 0)
719- evalerror (_("division by 0"));
720 lvalue %= value;
721 break;
722 case PLUS:
723@@ -804,7 +808,12 @@
724 val2 = exppower ();
725
726 if (((op == DIV) || (op == MOD)) && (val2 == 0))
727- evalerror (_("division by 0"));
728+ {
729+ if (noeval == 0)
730+ evalerror (_("division by 0"));
731+ else
732+ val2 = 1;
733+ }
734
735 if (op == MUL)
736 val1 *= val2;
[e80ea72]737diff -Naur bash-4.2.orig/lib/glob/glob.c bash-4.2/lib/glob/glob.c
738--- bash-4.2.orig/lib/glob/glob.c 2009-11-14 23:39:30.000000000 +0000
739+++ bash-4.2/lib/glob/glob.c 2012-07-20 20:30:11.107595225 +0000
740@@ -200,8 +200,11 @@
741 wchar_t *pat_wc, *dn_wc;
742 size_t pat_n, dn_n;
743
744+ pat_wc = dn_wc = (wchar_t *)NULL;
745+
746 pat_n = xdupmbstowcs (&pat_wc, NULL, pat);
747- dn_n = xdupmbstowcs (&dn_wc, NULL, dname);
748+ if (pat_n != (size_t)-1)
749+ dn_n = xdupmbstowcs (&dn_wc, NULL, dname);
750
751 ret = 0;
752 if (pat_n != (size_t)-1 && dn_n !=(size_t)-1)
753@@ -221,6 +224,8 @@
754 (pat_wc[0] != L'\\' || pat_wc[1] != L'.'))
755 ret = 1;
756 }
757+ else
758+ ret = skipname (pat, dname, flags);
759
760 FREE (pat_wc);
761 FREE (dn_wc);
762@@ -266,8 +271,11 @@
763 /* Convert the strings into wide characters. */
764 n = xdupmbstowcs (&wpathname, NULL, pathname);
765 if (n == (size_t) -1)
766- /* Something wrong. */
767- return;
768+ {
769+ /* Something wrong. Fall back to single-byte */
770+ udequote_pathname (pathname);
771+ return;
772+ }
773 orig_wpathname = wpathname;
774
775 for (i = j = 0; wpathname && wpathname[i]; )
[eb3c388]776diff -Naur bash-4.2.orig/lib/glob/gmisc.c bash-4.2/lib/glob/gmisc.c
777--- bash-4.2.orig/lib/glob/gmisc.c 2011-02-05 21:11:17.000000000 +0000
[e80ea72]778+++ bash-4.2/lib/glob/gmisc.c 2012-07-20 20:30:10.557594801 +0000
[eb3c388]779@@ -77,8 +77,8 @@
780 wchar_t *wpat;
781 size_t wmax;
782 {
783- wchar_t wc, *wbrack;
784- int matlen, t, in_cclass, in_collsym, in_equiv;
785+ wchar_t wc;
786+ int matlen, bracklen, t, in_cclass, in_collsym, in_equiv;
787
788 if (*wpat == 0)
789 return (0);
790@@ -118,58 +118,80 @@
791 break;
792 case L'[':
793 /* scan for ending `]', skipping over embedded [:...:] */
794- wbrack = wpat;
795+ bracklen = 1;
796 wc = *wpat++;
797 do
798 {
799 if (wc == 0)
800 {
801- matlen += wpat - wbrack - 1; /* incremented below */
802- break;
803+ wpat--; /* back up to NUL */
804+ matlen += bracklen;
805+ goto bad_bracket;
806 }
807 else if (wc == L'\\')
808 {
809- wc = *wpat++;
810- if (*wpat == 0)
811- break;
812+ /* *wpat == backslash-escaped character */
813+ bracklen++;
814+ /* If the backslash or backslash-escape ends the string,
815+ bail. The ++wpat skips over the backslash escape */
816+ if (*wpat == 0 || *++wpat == 0)
817+ {
818+ matlen += bracklen;
819+ goto bad_bracket;
820+ }
821 }
822 else if (wc == L'[' && *wpat == L':') /* character class */
823 {
824 wpat++;
825+ bracklen++;
826 in_cclass = 1;
827 }
828 else if (in_cclass && wc == L':' && *wpat == L']')
829 {
830 wpat++;
831+ bracklen++;
832 in_cclass = 0;
833 }
834 else if (wc == L'[' && *wpat == L'.') /* collating symbol */
835 {
836 wpat++;
837+ bracklen++;
838 if (*wpat == L']') /* right bracket can appear as collating symbol */
839- wpat++;
840+ {
841+ wpat++;
842+ bracklen++;
843+ }
844 in_collsym = 1;
845 }
846 else if (in_collsym && wc == L'.' && *wpat == L']')
847 {
848 wpat++;
849+ bracklen++;
850 in_collsym = 0;
851 }
852 else if (wc == L'[' && *wpat == L'=') /* equivalence class */
853 {
854 wpat++;
855+ bracklen++;
856 if (*wpat == L']') /* right bracket can appear as equivalence class */
857- wpat++;
858+ {
859+ wpat++;
860+ bracklen++;
861+ }
862 in_equiv = 1;
863 }
864 else if (in_equiv && wc == L'=' && *wpat == L']')
865 {
866 wpat++;
867+ bracklen++;
868 in_equiv = 0;
869 }
870+ else
871+ bracklen++;
872 }
873 while ((wc = *wpat++) != L']');
874 matlen++; /* bracket expression can only match one char */
875+bad_bracket:
876 break;
877 }
878 }
879@@ -213,8 +235,8 @@
880 char *pat;
881 size_t max;
882 {
883- char c, *brack;
884- int matlen, t, in_cclass, in_collsym, in_equiv;
885+ char c;
886+ int matlen, bracklen, t, in_cclass, in_collsym, in_equiv;
887
888 if (*pat == 0)
889 return (0);
890@@ -254,58 +276,80 @@
891 break;
892 case '[':
893 /* scan for ending `]', skipping over embedded [:...:] */
894- brack = pat;
895+ bracklen = 1;
896 c = *pat++;
897 do
898 {
899 if (c == 0)
900 {
901- matlen += pat - brack - 1; /* incremented below */
902- break;
903+ pat--; /* back up to NUL */
904+ matlen += bracklen;
905+ goto bad_bracket;
906 }
907 else if (c == '\\')
908 {
909- c = *pat++;
910- if (*pat == 0)
911- break;
912+ /* *pat == backslash-escaped character */
913+ bracklen++;
914+ /* If the backslash or backslash-escape ends the string,
915+ bail. The ++pat skips over the backslash escape */
916+ if (*pat == 0 || *++pat == 0)
917+ {
918+ matlen += bracklen;
919+ goto bad_bracket;
920+ }
921 }
922 else if (c == '[' && *pat == ':') /* character class */
923 {
924 pat++;
925+ bracklen++;
926 in_cclass = 1;
927 }
928 else if (in_cclass && c == ':' && *pat == ']')
929 {
930 pat++;
931+ bracklen++;
932 in_cclass = 0;
933 }
934 else if (c == '[' && *pat == '.') /* collating symbol */
935 {
936 pat++;
937+ bracklen++;
938 if (*pat == ']') /* right bracket can appear as collating symbol */
939- pat++;
940+ {
941+ pat++;
942+ bracklen++;
943+ }
944 in_collsym = 1;
945 }
946 else if (in_collsym && c == '.' && *pat == ']')
947 {
948 pat++;
949+ bracklen++;
950 in_collsym = 0;
951 }
952 else if (c == '[' && *pat == '=') /* equivalence class */
953 {
954 pat++;
955+ bracklen++;
956 if (*pat == ']') /* right bracket can appear as equivalence class */
957- pat++;
958+ {
959+ pat++;
960+ bracklen++;
961+ }
962 in_equiv = 1;
963 }
964 else if (in_equiv && c == '=' && *pat == ']')
965 {
966 pat++;
967+ bracklen++;
968 in_equiv = 0;
969 }
970+ else
971+ bracklen++;
972 }
973 while ((c = *pat++) != ']');
974 matlen++; /* bracket expression can only match one char */
975+bad_bracket:
976 break;
977 }
978 }
[e80ea72]979diff -Naur bash-4.2.orig/lib/glob/xmbsrtowcs.c bash-4.2/lib/glob/xmbsrtowcs.c
980--- bash-4.2.orig/lib/glob/xmbsrtowcs.c 2010-05-30 22:36:27.000000000 +0000
981+++ bash-4.2/lib/glob/xmbsrtowcs.c 2012-07-20 20:30:11.107595225 +0000
982@@ -35,6 +35,8 @@
983
984 #if HANDLE_MULTIBYTE
985
986+#define WSBUF_INC 32
987+
988 #ifndef FREE
989 # define FREE(x) do { if (x) free (x); } while (0)
990 #endif
991@@ -148,7 +150,7 @@
992 size_t wsbuf_size; /* Size of WSBUF */
993 size_t wcnum; /* Number of wide characters in WSBUF */
994 mbstate_t state; /* Conversion State */
995- size_t wcslength; /* Number of wide characters produced by the conversion. */
996+ size_t n, wcslength; /* Number of wide characters produced by the conversion. */
997 const char *end_or_backslash;
998 size_t nms; /* Number of multibyte characters to convert at one time. */
999 mbstate_t tmp_state;
1000@@ -171,7 +173,18 @@
1001 /* Compute the number of produced wide-characters. */
1002 tmp_p = p;
1003 tmp_state = state;
1004- wcslength = mbsnrtowcs(NULL, &tmp_p, nms, 0, &tmp_state);
1005+
1006+ if (nms == 0 && *p == '\\') /* special initial case */
1007+ nms = wcslength = 1;
1008+ else
1009+ wcslength = mbsnrtowcs (NULL, &tmp_p, nms, 0, &tmp_state);
1010+
1011+ if (wcslength == 0)
1012+ {
1013+ tmp_p = p; /* will need below */
1014+ tmp_state = state;
1015+ wcslength = 1; /* take a single byte */
1016+ }
1017
1018 /* Conversion failed. */
1019 if (wcslength == (size_t)-1)
1020@@ -186,7 +199,8 @@
1021 {
1022 wchar_t *wstmp;
1023
1024- wsbuf_size = wcnum+wcslength+1; /* 1 for the L'\0' or the potential L'\\' */
1025+ while (wsbuf_size < wcnum+wcslength+1) /* 1 for the L'\0' or the potential L'\\' */
1026+ wsbuf_size += WSBUF_INC;
1027
1028 wstmp = (wchar_t *) realloc (wsbuf, wsbuf_size * sizeof (wchar_t));
1029 if (wstmp == NULL)
1030@@ -199,10 +213,18 @@
1031 }
1032
1033 /* Perform the conversion. This is assumed to return 'wcslength'.
1034- * It may set 'p' to NULL. */
1035- mbsnrtowcs(wsbuf+wcnum, &p, nms, wsbuf_size-wcnum, &state);
1036+ It may set 'p' to NULL. */
1037+ n = mbsnrtowcs(wsbuf+wcnum, &p, nms, wsbuf_size-wcnum, &state);
1038
1039- wcnum += wcslength;
1040+ /* Compensate for taking single byte on wcs conversion failure above. */
1041+ if (wcslength == 1 && (n == 0 || n == (size_t)-1))
1042+ {
1043+ state = tmp_state;
1044+ p = tmp_p;
1045+ wsbuf[wcnum++] = *p++;
1046+ }
1047+ else
1048+ wcnum += wcslength;
1049
1050 if (mbsinit (&state) && (p != NULL) && (*p == '\\'))
1051 {
1052@@ -230,8 +252,6 @@
1053 If conversion is failed, the return value is (size_t)-1 and the values
1054 of DESTP and INDICESP are NULL. */
1055
1056-#define WSBUF_INC 32
1057-
1058 size_t
1059 xdupmbstowcs (destp, indicesp, src)
1060 wchar_t **destp; /* Store the pointer to the wide character string */
[eb3c388]1061diff -Naur bash-4.2.orig/lib/readline/callback.c bash-4.2/lib/readline/callback.c
1062--- bash-4.2.orig/lib/readline/callback.c 2010-06-06 16:18:58.000000000 +0000
[e80ea72]1063+++ bash-4.2/lib/readline/callback.c 2012-07-20 20:30:10.547594793 +0000
[eb3c388]1064@@ -148,6 +148,9 @@
1065 eof = _rl_vi_domove_callback (_rl_vimvcxt);
1066 /* Should handle everything, including cleanup, numeric arguments,
1067 and turning off RL_STATE_VIMOTION */
1068+ if (RL_ISSTATE (RL_STATE_NUMERICARG) == 0)
1069+ _rl_internal_char_cleanup ();
1070+
1071 return;
1072 }
1073 #endif
[e80ea72]1074diff -Naur bash-4.2.orig/lib/readline/input.c bash-4.2/lib/readline/input.c
1075--- bash-4.2.orig/lib/readline/input.c 2010-05-30 22:33:01.000000000 +0000
1076+++ bash-4.2/lib/readline/input.c 2012-07-20 20:30:11.130928577 +0000
1077@@ -409,7 +409,7 @@
1078 int
1079 rl_read_key ()
1080 {
1081- int c;
1082+ int c, r;
1083
1084 rl_key_sequence_length++;
1085
1086@@ -429,14 +429,18 @@
1087 {
1088 while (rl_event_hook)
1089 {
1090- if (rl_gather_tyi () < 0) /* XXX - EIO */
1091+ if (rl_get_char (&c) != 0)
1092+ break;
1093+
1094+ if ((r = rl_gather_tyi ()) < 0) /* XXX - EIO */
1095 {
1096 rl_done = 1;
1097 return ('\n');
1098 }
1099+ else if (r == 1) /* read something */
1100+ continue;
1101+
1102 RL_CHECK_SIGNALS ();
1103- if (rl_get_char (&c) != 0)
1104- break;
1105 if (rl_done) /* XXX - experimental */
1106 return ('\n');
1107 (*rl_event_hook) ();
[eb3c388]1108diff -Naur bash-4.2.orig/lib/readline/vi_mode.c bash-4.2/lib/readline/vi_mode.c
1109--- bash-4.2.orig/lib/readline/vi_mode.c 2010-11-21 00:51:39.000000000 +0000
[e80ea72]1110+++ bash-4.2/lib/readline/vi_mode.c 2012-07-20 20:30:11.207595303 +0000
[eb3c388]1111@@ -1114,7 +1114,7 @@
1112 rl_beg_of_line (1, c);
1113 _rl_vi_last_motion = c;
1114 RL_UNSETSTATE (RL_STATE_VIMOTION);
1115- return (0);
1116+ return (vidomove_dispatch (m));
1117 }
1118 #if defined (READLINE_CALLBACKS)
1119 /* XXX - these need to handle rl_universal_argument bindings */
[e80ea72]1120@@ -1234,11 +1234,19 @@
1121 _rl_vimvcxt->motion = '$';
1122 r = rl_domove_motion_callback (_rl_vimvcxt);
1123 }
1124- else if (vi_redoing)
1125+ else if (vi_redoing && _rl_vi_last_motion != 'd') /* `dd' is special */
1126 {
1127 _rl_vimvcxt->motion = _rl_vi_last_motion;
1128 r = rl_domove_motion_callback (_rl_vimvcxt);
1129 }
1130+ else if (vi_redoing) /* handle redoing `dd' here */
1131+ {
1132+ _rl_vimvcxt->motion = _rl_vi_last_motion;
1133+ rl_mark = rl_end;
1134+ rl_beg_of_line (1, key);
1135+ RL_UNSETSTATE (RL_STATE_VIMOTION);
1136+ r = vidomove_dispatch (_rl_vimvcxt);
1137+ }
1138 #if defined (READLINE_CALLBACKS)
1139 else if (RL_ISSTATE (RL_STATE_CALLBACK))
1140 {
1141@@ -1316,11 +1324,19 @@
1142 _rl_vimvcxt->motion = '$';
1143 r = rl_domove_motion_callback (_rl_vimvcxt);
1144 }
1145- else if (vi_redoing)
1146+ else if (vi_redoing && _rl_vi_last_motion != 'c') /* `cc' is special */
1147 {
1148 _rl_vimvcxt->motion = _rl_vi_last_motion;
1149 r = rl_domove_motion_callback (_rl_vimvcxt);
1150 }
1151+ else if (vi_redoing) /* handle redoing `cc' here */
1152+ {
1153+ _rl_vimvcxt->motion = _rl_vi_last_motion;
1154+ rl_mark = rl_end;
1155+ rl_beg_of_line (1, key);
1156+ RL_UNSETSTATE (RL_STATE_VIMOTION);
1157+ r = vidomove_dispatch (_rl_vimvcxt);
1158+ }
1159 #if defined (READLINE_CALLBACKS)
1160 else if (RL_ISSTATE (RL_STATE_CALLBACK))
1161 {
1162@@ -1377,6 +1393,19 @@
1163 _rl_vimvcxt->motion = '$';
1164 r = rl_domove_motion_callback (_rl_vimvcxt);
1165 }
1166+ else if (vi_redoing && _rl_vi_last_motion != 'y') /* `yy' is special */
1167+ {
1168+ _rl_vimvcxt->motion = _rl_vi_last_motion;
1169+ r = rl_domove_motion_callback (_rl_vimvcxt);
1170+ }
1171+ else if (vi_redoing) /* handle redoing `yy' here */
1172+ {
1173+ _rl_vimvcxt->motion = _rl_vi_last_motion;
1174+ rl_mark = rl_end;
1175+ rl_beg_of_line (1, key);
1176+ RL_UNSETSTATE (RL_STATE_VIMOTION);
1177+ r = vidomove_dispatch (_rl_vimvcxt);
1178+ }
1179 #if defined (READLINE_CALLBACKS)
1180 else if (RL_ISSTATE (RL_STATE_CALLBACK))
1181 {
1182diff -Naur bash-4.2.orig/lib/sh/eaccess.c bash-4.2/lib/sh/eaccess.c
1183--- bash-4.2.orig/lib/sh/eaccess.c 2011-01-09 01:50:10.000000000 +0000
1184+++ bash-4.2/lib/sh/eaccess.c 2012-07-20 20:30:11.157595263 +0000
1185@@ -82,6 +82,8 @@
1186 const char *path;
1187 struct stat *finfo;
1188 {
1189+ static char *pbuf = 0;
1190+
1191 if (*path == '\0')
1192 {
1193 errno = ENOENT;
1194@@ -106,7 +108,7 @@
1195 trailing slash. Make sure /dev/fd/xx really uses DEV_FD_PREFIX/xx.
1196 On most systems, with the notable exception of linux, this is
1197 effectively a no-op. */
1198- char pbuf[32];
1199+ pbuf = xrealloc (pbuf, sizeof (DEV_FD_PREFIX) + strlen (path + 8));
1200 strcpy (pbuf, DEV_FD_PREFIX);
1201 strcat (pbuf, path + 8);
1202 return (stat (pbuf, finfo));
[eb3c388]1203diff -Naur bash-4.2.orig/lib/sh/zread.c bash-4.2/lib/sh/zread.c
1204--- bash-4.2.orig/lib/sh/zread.c 2009-03-02 13:54:45.000000000 +0000
[e80ea72]1205+++ bash-4.2/lib/sh/zread.c 2012-07-20 20:30:10.964261781 +0000
[eb3c388]1206@@ -160,14 +160,13 @@
1207 zsyncfd (fd)
1208 int fd;
1209 {
1210- off_t off;
1211- int r;
1212+ off_t off, r;
1213
1214 off = lused - lind;
1215 r = 0;
1216 if (off > 0)
1217 r = lseek (fd, -off, SEEK_CUR);
1218
1219- if (r >= 0)
1220+ if (r != -1)
1221 lused = lind = 0;
1222 }
1223diff -Naur bash-4.2.orig/parse.y bash-4.2/parse.y
1224--- bash-4.2.orig/parse.y 2011-01-02 20:48:11.000000000 +0000
[e80ea72]1225+++ bash-4.2/parse.y 2012-07-20 20:30:11.164261935 +0000
[eb3c388]1226@@ -2499,7 +2499,7 @@
1227 We do this only if it is time to do so. Notice that only here
1228 is the mail alarm reset; nothing takes place in check_mail ()
1229 except the checking of mail. Please don't change this. */
1230- if (prompt_is_ps1 && time_to_check_mail ())
1231+ if (prompt_is_ps1 && parse_and_execute_level == 0 && time_to_check_mail ())
1232 {
1233 check_mail ();
1234 reset_mail_timer ();
1235@@ -3842,6 +3842,7 @@
1236 int flags;
1237 {
1238 sh_parser_state_t ps;
1239+ sh_input_line_state_t ls;
1240 int orig_ind, nc, sflags;
1241 char *ret, *s, *ep, *ostring;
1242
1243@@ -3849,10 +3850,12 @@
1244 orig_ind = *indp;
1245 ostring = string;
1246
1247+/*itrace("xparse_dolparen: size = %d shell_input_line = `%s'", shell_input_line_size, shell_input_line);*/
1248 sflags = SEVAL_NONINT|SEVAL_NOHIST|SEVAL_NOFREE;
1249 if (flags & SX_NOLONGJMP)
1250 sflags |= SEVAL_NOLONGJMP;
1251 save_parser_state (&ps);
1252+ save_input_line_state (&ls);
1253
1254 /*(*/
1255 parser_state |= PST_CMDSUBST|PST_EOFTOKEN; /* allow instant ')' */ /*(*/
1256@@ -3861,6 +3864,8 @@
1257
1258 restore_parser_state (&ps);
1259 reset_parser ();
1260+ /* reset_parser clears shell_input_line and associated variables */
1261+ restore_input_line_state (&ls);
1262 if (interactive)
1263 token_to_read = 0;
1264
[e80ea72]1265@@ -4895,6 +4900,9 @@
1266 return (current_command_line_count == 2 ? "\n" : "");
1267 }
1268
1269+ if (parser_state & PST_COMPASSIGN)
1270+ return (" ");
1271+
1272 /* First, handle some special cases. */
1273 /*(*/
1274 /* If we just read `()', assume it's a function definition, and don't
1275@@ -5135,6 +5143,9 @@
[eb3c388]1276 case 'A':
1277 /* Make the current time/date into a string. */
1278 (void) time (&the_time);
1279+#if defined (HAVE_TZSET)
1280+ sv_tz ("TZ"); /* XXX -- just make sure */
1281+#endif
1282 tm = localtime (&the_time);
1283
1284 if (c == 'd')
[e80ea72]1285@@ -5905,6 +5916,12 @@
[eb3c388]1286 ps->expand_aliases = expand_aliases;
1287 ps->echo_input_at_read = echo_input_at_read;
1288
1289+ ps->token = token;
1290+ ps->token_buffer_size = token_buffer_size;
1291+ /* Force reallocation on next call to read_token_word */
1292+ token = 0;
1293+ token_buffer_size = 0;
1294+
1295 return (ps);
1296 }
1297
[e80ea72]1298@@ -5946,6 +5963,42 @@
[eb3c388]1299
1300 expand_aliases = ps->expand_aliases;
1301 echo_input_at_read = ps->echo_input_at_read;
1302+
1303+ FREE (token);
1304+ token = ps->token;
1305+ token_buffer_size = ps->token_buffer_size;
1306+}
1307+
1308+sh_input_line_state_t *
1309+save_input_line_state (ls)
1310+ sh_input_line_state_t *ls;
1311+{
1312+ if (ls == 0)
1313+ ls = (sh_input_line_state_t *)xmalloc (sizeof (sh_input_line_state_t));
1314+ if (ls == 0)
1315+ return ((sh_input_line_state_t *)NULL);
1316+
1317+ ls->input_line = shell_input_line;
1318+ ls->input_line_size = shell_input_line_size;
1319+ ls->input_line_len = shell_input_line_len;
1320+ ls->input_line_index = shell_input_line_index;
1321+
1322+ /* force reallocation */
1323+ shell_input_line = 0;
1324+ shell_input_line_size = shell_input_line_len = shell_input_line_index = 0;
1325+}
1326+
1327+void
1328+restore_input_line_state (ls)
1329+ sh_input_line_state_t *ls;
1330+{
1331+ FREE (shell_input_line);
1332+ shell_input_line = ls->input_line;
1333+ shell_input_line_size = ls->input_line_size;
1334+ shell_input_line_len = ls->input_line_len;
1335+ shell_input_line_index = ls->input_line_index;
1336+
1337+ set_line_mbstate ();
1338 }
1339
1340 /************************************************
1341diff -Naur bash-4.2.orig/patchlevel.h bash-4.2/patchlevel.h
1342--- bash-4.2.orig/patchlevel.h 2010-06-13 00:14:48.000000000 +0000
[e80ea72]1343+++ bash-4.2/patchlevel.h 2012-07-20 20:30:11.207595303 +0000
[eb3c388]1344@@ -25,6 +25,6 @@
1345 regexp `^#define[ ]*PATCHLEVEL', since that's what support/mkversion.sh
1346 looks for to find the patch level (for the sccs version string). */
1347
1348-#define PATCHLEVEL 0
[e80ea72]1349+#define PATCHLEVEL 37
[eb3c388]1350
1351 #endif /* _PATCHLEVEL_H_ */
1352diff -Naur bash-4.2.orig/pathexp.c bash-4.2/pathexp.c
1353--- bash-4.2.orig/pathexp.c 2010-08-14 03:21:57.000000000 +0000
[e80ea72]1354+++ bash-4.2/pathexp.c 2012-07-20 20:30:10.890928391 +0000
[eb3c388]1355@@ -196,7 +196,7 @@
1356 {
1357 if ((qflags & QGLOB_FILENAME) && pathname[i+1] == '/')
1358 continue;
1359- if ((qflags & QGLOB_REGEXP) && ere_char (pathname[i+1]) == 0)
1360+ if (pathname[i+1] != CTLESC && (qflags & QGLOB_REGEXP) && ere_char (pathname[i+1]) == 0)
1361 continue;
1362 temp[j++] = '\\';
1363 i++;
1364diff -Naur bash-4.2.orig/print_cmd.c bash-4.2/print_cmd.c
1365--- bash-4.2.orig/print_cmd.c 2010-05-30 22:34:08.000000000 +0000
[e80ea72]1366+++ bash-4.2/print_cmd.c 2012-07-20 20:30:10.627594855 +0000
[eb3c388]1367@@ -315,6 +315,7 @@
1368 cprintf ("( ");
1369 skip_this_indent++;
1370 make_command_string_internal (command->value.Subshell->command);
1371+ PRINT_DEFERRED_HEREDOCS ("");
1372 cprintf (" )");
1373 break;
1374
1375@@ -592,6 +593,7 @@
1376 newline ("do\n");
1377 indentation += indentation_amount;
1378 make_command_string_internal (arith_for_command->action);
1379+ PRINT_DEFERRED_HEREDOCS ("");
1380 semicolon ();
1381 indentation -= indentation_amount;
1382 newline ("done");
1383@@ -653,6 +655,7 @@
1384 }
1385
1386 make_command_string_internal (group_command->command);
1387+ PRINT_DEFERRED_HEREDOCS ("");
1388
1389 if (inside_function_def)
1390 {
1391diff -Naur bash-4.2.orig/shell.h bash-4.2/shell.h
1392--- bash-4.2.orig/shell.h 2011-01-07 03:16:55.000000000 +0000
[e80ea72]1393+++ bash-4.2/shell.h 2012-07-20 20:30:10.844261687 +0000
[eb3c388]1394@@ -136,6 +136,9 @@
1395 int parser_state;
1396 int *token_state;
1397
1398+ char *token;
1399+ int token_buffer_size;
1400+
1401 /* input line state -- line number saved elsewhere */
1402 int input_line_terminator;
1403 int eof_encountered;
1404@@ -166,6 +169,16 @@
1405
1406 } sh_parser_state_t;
1407
1408+typedef struct _sh_input_line_state_t {
1409+ char *input_line;
1410+ int input_line_index;
1411+ int input_line_size;
1412+ int input_line_len;
1413+} sh_input_line_state_t;
1414+
1415 /* Let's try declaring these here. */
1416 extern sh_parser_state_t *save_parser_state __P((sh_parser_state_t *));
1417 extern void restore_parser_state __P((sh_parser_state_t *));
1418+
1419+extern sh_input_line_state_t *save_input_line_state __P((sh_input_line_state_t *));
1420+extern void restore_input_line_state __P((sh_input_line_state_t *));
1421diff -Naur bash-4.2.orig/sig.c bash-4.2/sig.c
1422--- bash-4.2.orig/sig.c 2010-11-23 13:21:22.000000000 +0000
[e80ea72]1423+++ bash-4.2/sig.c 2012-07-20 20:30:10.620928183 +0000
[eb3c388]1424@@ -46,6 +46,7 @@
1425
1426 #if defined (READLINE)
1427 # include "bashline.h"
1428+# include <readline/readline.h>
1429 #endif
1430
1431 #if defined (HISTORY)
1432@@ -62,6 +63,7 @@
1433 #if defined (HISTORY)
1434 extern int history_lines_this_session;
1435 #endif
1436+extern int no_line_editing;
1437
1438 extern void initialize_siglist ();
1439
1440@@ -505,7 +507,10 @@
1441 {
1442 #if defined (HISTORY)
1443 /* XXX - will inhibit history file being written */
1444- history_lines_this_session = 0;
1445+# if defined (READLINE)
1446+ if (interactive_shell == 0 || interactive == 0 || (sig != SIGHUP && sig != SIGTERM) || no_line_editing || (RL_ISSTATE (RL_STATE_READCMD) == 0))
1447+# endif
1448+ history_lines_this_session = 0;
1449 #endif
1450 terminate_immediately = 0;
1451 termsig_handler (sig);
1452diff -Naur bash-4.2.orig/subst.c bash-4.2/subst.c
1453--- bash-4.2.orig/subst.c 2011-01-02 21:12:51.000000000 +0000
[e80ea72]1454+++ bash-4.2/subst.c 2012-07-20 20:30:11.200928631 +0000
[eb3c388]1455@@ -366,6 +366,11 @@
1456 f &= ~W_ASSNBLTIN;
1457 fprintf (stderr, "W_ASSNBLTIN%s", f ? "|" : "");
1458 }
1459+ if (f & W_ASSNGLOBAL)
1460+ {
1461+ f &= ~W_ASSNGLOBAL;
1462+ fprintf (stderr, "W_ASSNGLOBAL%s", f ? "|" : "");
1463+ }
1464 if (f & W_COMPASSIGN)
1465 {
1466 f &= ~W_COMPASSIGN;
1467@@ -1379,10 +1384,12 @@
1468 slen = strlen (string + *sindex) + *sindex;
1469
1470 /* The handling of dolbrace_state needs to agree with the code in parse.y:
1471- parse_matched_pair() */
1472- dolbrace_state = 0;
1473- if (quoted & (Q_HERE_DOCUMENT|Q_DOUBLE_QUOTES))
1474- dolbrace_state = (flags & SX_POSIXEXP) ? DOLBRACE_QUOTE : DOLBRACE_PARAM;
1475+ parse_matched_pair(). The different initial value is to handle the
1476+ case where this function is called to parse the word in
1477+ ${param op word} (SX_WORD). */
1478+ dolbrace_state = (flags & SX_WORD) ? DOLBRACE_WORD : DOLBRACE_PARAM;
1479+ if ((quoted & (Q_HERE_DOCUMENT|Q_DOUBLE_QUOTES)) && (flags & SX_POSIXEXP))
1480+ dolbrace_state = DOLBRACE_QUOTE;
1481
1482 i = *sindex;
1483 while (c = string[i])
1484@@ -2801,7 +2808,7 @@
1485 }
1486 else if (assign_list)
1487 {
1488- if (word->flags & W_ASSIGNARG)
1489+ if ((word->flags & W_ASSIGNARG) && (word->flags & W_ASSNGLOBAL) == 0)
1490 aflags |= ASS_MKLOCAL;
1491 if (word->flags & W_ASSIGNASSOC)
1492 aflags |= ASS_MKASSOC;
1493@@ -3371,7 +3378,7 @@
1494 if (string == 0 || *string == '\0')
1495 return (WORD_LIST *)NULL;
1496
1497- td.flags = 0;
1498+ td.flags = W_NOSPLIT2; /* no splitting, remove "" and '' */
1499 td.word = string;
1500 tresult = call_expand_word_internal (&td, quoted, 1, dollar_at_p, has_dollar_at);
1501 return (tresult);
1502@@ -3704,7 +3711,10 @@
1503 break;
1504 }
1505 else if (string[i] == CTLNUL)
1506- i++;
1507+ {
1508+ i++;
1509+ continue;
1510+ }
1511
1512 prev_i = i;
1513 ADVANCE_CHAR (string, slen, i);
1514@@ -4156,7 +4166,7 @@
1515 simple = (wpat[0] != L'\\' && wpat[0] != L'*' && wpat[0] != L'?' && wpat[0] != L'[');
1516 #if defined (EXTENDED_GLOB)
1517 if (extended_glob)
1518- simple |= (wpat[1] != L'(' || (wpat[0] != L'*' && wpat[0] != L'?' && wpat[0] != L'+' && wpat[0] != L'!' && wpat[0] != L'@')); /*)*/
1519+ simple &= (wpat[1] != L'(' || (wpat[0] != L'*' && wpat[0] != L'?' && wpat[0] != L'+' && wpat[0] != L'!' && wpat[0] != L'@')); /*)*/
1520 #endif
1521
1522 /* If the pattern doesn't match anywhere in the string, go ahead and
1523@@ -4607,6 +4617,7 @@
1524 if (ifs_firstc == 0)
1525 #endif
1526 word->flags |= W_NOSPLIT;
1527+ word->flags |= W_NOSPLIT2;
1528 result = call_expand_word_internal (word, quoted, 0, (int *)NULL, (int *)NULL);
1529 expand_no_split_dollar_star = 0;
1530
1531@@ -5798,6 +5809,16 @@
1532 is the only expansion that creates more than one word. */
1533 if (qdollaratp && ((hasdol && quoted) || l->next))
1534 *qdollaratp = 1;
1535+ /* If we have a quoted null result (QUOTED_NULL(temp)) and the word is
1536+ a quoted null (l->next == 0 && QUOTED_NULL(l->word->word)), the
1537+ flags indicate it (l->word->flags & W_HASQUOTEDNULL), and the
1538+ expansion is quoted (quoted & (Q_HERE_DOCUMENT|Q_DOUBLE_QUOTES))
1539+ (which is more paranoia than anything else), we need to return the
1540+ quoted null string and set the flags to indicate it. */
1541+ if (l->next == 0 && (quoted & (Q_HERE_DOCUMENT|Q_DOUBLE_QUOTES)) && QUOTED_NULL(temp) && QUOTED_NULL(l->word->word) && (l->word->flags & W_HASQUOTEDNULL))
1542+ {
1543+ w->flags |= W_HASQUOTEDNULL;
1544+ }
1545 dispose_words (l);
1546 }
1547 else if ((quoted & (Q_HERE_DOCUMENT|Q_DOUBLE_QUOTES)) && hasdol)
1548@@ -7176,7 +7197,7 @@
1549 {
1550 /* Extract the contents of the ${ ... } expansion
1551 according to the Posix.2 rules. */
1552- value = extract_dollar_brace_string (string, &sindex, quoted, (c == '%' || c == '#') ? SX_POSIXEXP : 0);
1553+ value = extract_dollar_brace_string (string, &sindex, quoted, (c == '%' || c == '#' || c =='/' || c == '^' || c == ',' || c ==':') ? SX_POSIXEXP|SX_WORD : SX_WORD);
1554 if (string[sindex] == RBRACE)
1555 sindex++;
1556 else
1557@@ -7268,6 +7289,7 @@
1558 default:
1559 case '\0':
1560 bad_substitution:
1561+ last_command_exit_value = EXECUTION_FAILURE;
1562 report_error (_("%s: bad substitution"), string ? string : "??");
1563 FREE (value);
1564 FREE (temp);
[e80ea72]1565@@ -7900,7 +7922,7 @@
1566
1567 /* State flags */
1568 int had_quoted_null;
1569- int has_dollar_at;
1570+ int has_dollar_at, temp_has_dollar_at;
1571 int tflag;
1572 int pflags; /* flags passed to param_expand */
1573
1574@@ -8105,13 +8127,14 @@
1575 if (expanded_something)
1576 *expanded_something = 1;
1577
1578- has_dollar_at = 0;
1579+ temp_has_dollar_at = 0;
1580 pflags = (word->flags & W_NOCOMSUB) ? PF_NOCOMSUB : 0;
1581 if (word->flags & W_NOSPLIT2)
1582 pflags |= PF_NOSPLIT2;
1583 tword = param_expand (string, &sindex, quoted, expanded_something,
1584- &has_dollar_at, &quoted_dollar_at,
1585+ &temp_has_dollar_at, &quoted_dollar_at,
1586 &had_quoted_null, pflags);
1587+ has_dollar_at += temp_has_dollar_at;
1588
1589 if (tword == &expand_wdesc_error || tword == &expand_wdesc_fatal)
1590 {
1591@@ -8129,6 +8152,14 @@
1592 temp = tword->word;
1593 dispose_word_desc (tword);
1594
1595+ /* Kill quoted nulls; we will add them back at the end of
1596+ expand_word_internal if nothing else in the string */
1597+ if (had_quoted_null && temp && QUOTED_NULL (temp))
1598+ {
1599+ FREE (temp);
1600+ temp = (char *)NULL;
1601+ }
1602+
1603 goto add_string;
1604 break;
1605
1606@@ -8244,9 +8275,10 @@
1607
1608 temp = (char *)NULL;
1609
1610- has_dollar_at = 0;
1611+ temp_has_dollar_at = 0; /* XXX */
1612 /* Need to get W_HASQUOTEDNULL flag through this function. */
1613- list = expand_word_internal (tword, Q_DOUBLE_QUOTES, 0, &has_dollar_at, (int *)NULL);
1614+ list = expand_word_internal (tword, Q_DOUBLE_QUOTES, 0, &temp_has_dollar_at, (int *)NULL);
1615+ has_dollar_at += temp_has_dollar_at;
1616
1617 if (list == &expand_word_error || list == &expand_word_fatal)
1618 {
1619@@ -8533,7 +8565,7 @@
1620 tword->flags |= W_NOEXPAND; /* XXX */
1621 if (quoted & (Q_HERE_DOCUMENT|Q_DOUBLE_QUOTES))
1622 tword->flags |= W_QUOTED;
1623- if (had_quoted_null)
1624+ if (had_quoted_null && QUOTED_NULL (istring))
1625 tword->flags |= W_HASQUOTEDNULL;
1626 list = make_word_list (tword, (WORD_LIST *)NULL);
1627 }
1628@@ -8564,7 +8596,7 @@
1629 tword->flags |= W_NOGLOB;
1630 if (word->flags & W_NOEXPAND)
1631 tword->flags |= W_NOEXPAND;
1632- if (had_quoted_null)
1633+ if (had_quoted_null && QUOTED_NULL (istring))
1634 tword->flags |= W_HASQUOTEDNULL; /* XXX */
1635 list = make_word_list (tword, (WORD_LIST *)NULL);
1636 }
[eb3c388]1637diff -Naur bash-4.2.orig/subst.h bash-4.2/subst.h
1638--- bash-4.2.orig/subst.h 2010-12-03 01:21:29.000000000 +0000
[e80ea72]1639+++ bash-4.2/subst.h 2012-07-20 20:30:10.527594777 +0000
[eb3c388]1640@@ -56,6 +56,7 @@
1641 #define SX_NOLONGJMP 0x0040 /* don't longjmp on fatal error */
1642 #define SX_ARITHSUB 0x0080 /* extracting $(( ... )) (currently unused) */
1643 #define SX_POSIXEXP 0x0100 /* extracting new Posix pattern removal expansions in extract_dollar_brace_string */
1644+#define SX_WORD 0x0200 /* extracting word in ${param op word} */
1645
1646 /* Remove backslashes which are quoting backquotes from STRING. Modifies
1647 STRING, and returns a pointer to it. */
1648diff -Naur bash-4.2.orig/support/shobj-conf bash-4.2/support/shobj-conf
1649--- bash-4.2.orig/support/shobj-conf 2009-10-28 13:20:21.000000000 +0000
[e80ea72]1650+++ bash-4.2/support/shobj-conf 2012-07-20 20:30:10.954261773 +0000
[eb3c388]1651@@ -157,7 +157,7 @@
1652 ;;
1653
1654 # Darwin/MacOS X
1655-darwin[89]*|darwin10*)
1656+darwin[89]*|darwin1[012]*)
1657 SHOBJ_STATUS=supported
1658 SHLIB_STATUS=supported
1659
1660@@ -186,7 +186,7 @@
1661 SHLIB_LIBSUFF='dylib'
1662
1663 case "${host_os}" in
1664- darwin[789]*|darwin10*) SHOBJ_LDFLAGS=''
1665+ darwin[789]*|darwin1[012]*) SHOBJ_LDFLAGS=''
1666 SHLIB_XLDFLAGS='-dynamiclib -arch_only `/usr/bin/arch` -install_name $(libdir)/$@ -current_version $(SHLIB_MAJOR)$(SHLIB_MINOR) -compatibility_version $(SHLIB_MAJOR) -v'
1667 ;;
1668 *) SHOBJ_LDFLAGS='-dynamic'
1669diff -Naur bash-4.2.orig/tests/shopt.right bash-4.2/tests/shopt.right
1670--- bash-4.2.orig/tests/shopt.right 2010-07-03 03:36:30.000000000 +0000
[e80ea72]1671+++ bash-4.2/tests/shopt.right 2012-07-20 20:30:11.087595209 +0000
[eb3c388]1672@@ -12,6 +12,7 @@
1673 shopt -u compat32
1674 shopt -u compat40
1675 shopt -u compat41
1676+shopt -u direxpand
1677 shopt -u dirspell
1678 shopt -u dotglob
1679 shopt -u execfail
1680@@ -68,6 +69,7 @@
1681 shopt -u compat32
1682 shopt -u compat40
1683 shopt -u compat41
1684+shopt -u direxpand
1685 shopt -u dirspell
1686 shopt -u dotglob
1687 shopt -u execfail
1688@@ -101,6 +103,7 @@
1689 compat32 off
1690 compat40 off
1691 compat41 off
1692+direxpand off
1693 dirspell off
1694 dotglob off
1695 execfail off
1696diff -Naur bash-4.2.orig/variables.c bash-4.2/variables.c
1697--- bash-4.2.orig/variables.c 2011-01-25 01:07:48.000000000 +0000
[e80ea72]1698+++ bash-4.2/variables.c 2012-07-20 20:30:10.610928175 +0000
[eb3c388]1699@@ -3653,6 +3653,22 @@
1700 return n;
1701 }
1702
1703+int
1704+chkexport (name)
1705+ char *name;
1706+{
1707+ SHELL_VAR *v;
1708+
1709+ v = find_variable (name);
1710+ if (v && exported_p (v))
1711+ {
1712+ array_needs_making = 1;
1713+ maybe_make_export_env ();
1714+ return 1;
1715+ }
1716+ return 0;
1717+}
1718+
1719 void
1720 maybe_make_export_env ()
1721 {
1722@@ -4214,7 +4230,7 @@
1723 { "TEXTDOMAIN", sv_locale },
1724 { "TEXTDOMAINDIR", sv_locale },
1725
1726-#if defined (HAVE_TZSET) && defined (PROMPT_STRING_DECODE)
1727+#if defined (HAVE_TZSET)
1728 { "TZ", sv_tz },
1729 #endif
1730
1731@@ -4558,12 +4574,13 @@
1732 }
1733 #endif /* HISTORY */
1734
1735-#if defined (HAVE_TZSET) && defined (PROMPT_STRING_DECODE)
1736+#if defined (HAVE_TZSET)
1737 void
1738 sv_tz (name)
1739 char *name;
1740 {
1741- tzset ();
1742+ if (chkexport (name))
1743+ tzset ();
1744 }
1745 #endif
1746
1747diff -Naur bash-4.2.orig/variables.h bash-4.2/variables.h
1748--- bash-4.2.orig/variables.h 2010-12-03 01:22:01.000000000 +0000
[e80ea72]1749+++ bash-4.2/variables.h 2012-07-20 20:30:10.590928159 +0000
[eb3c388]1750@@ -313,6 +313,7 @@
1751
1752 extern void sort_variables __P((SHELL_VAR **));
1753
1754+extern int chkexport __P((char *));
1755 extern void maybe_make_export_env __P((void));
1756 extern void update_export_env_inplace __P((char *, int, char *));
1757 extern void put_command_name_into_env __P((char *));
Note: See TracBrowser for help on using the repository browser.