]> git.ipfire.org Git - thirdparty/bash.git/commitdiff
commit bash-20200424 snapshot
authorChet Ramey <chet.ramey@case.edu>
Mon, 27 Apr 2020 21:05:14 +0000 (17:05 -0400)
committerChet Ramey <chet.ramey@case.edu>
Mon, 27 Apr 2020 21:05:14 +0000 (17:05 -0400)
CWRU/CWRU.chlog
builtins/declare.def
parse.y
subst.c
tests/errors.right
tests/varenv.right
tests/varenv18.sub
variables.h

index 262763b6ea5c70d0169d264dcb6e68d6af6e3fdc..da7f24c60f3022571e087771e3140645d7615f31 100644 (file)
@@ -7579,7 +7579,7 @@ subst.c
          command with make_local_declare, meaning we have an array or assoc
          compound assignment. (Slighty unsatisfactory, but ok for now) Fix
          for bug report from Kevin Locke <kevin@kevinlocke.name>,
-          https://savannah.gnu.org/support/index.php?109669
+         https://savannah.gnu.org/support/index.php?109669
 
                                   3/18
                                   ----
@@ -8185,3 +8185,29 @@ jobs.c
          of a shell started to run a command or process substitution (after
          forking a child to run one command, but before forking another, for
          instance). Reported by Rob Landley <rob@landley.net>
+
+                                  4/27
+                                  ----
+parse.y
+       - function_def: break the productions starting with `function' without
+         `()' into two productions to avoid a shift-reduce conflict. Report
+         and patch from Dale R. Worley <worley@alum.mit.edu>
+
+variables.h
+       - localvar_inherit: add extern declaration here
+
+subst.c
+       - shell_expand_word_list: take out change from 3/17 to pass -I to
+         make_internal_declare; it generates errors the user will find
+         confusing if there is a variable with the same name but a different
+         type at a previous scope
+       - shell_expand_word_list: check for and note whether or not -I is
+         supplied to the declaration command, since it changes the default
+         behavior of a compound assignment without -a or -A
+       - shell_expand_word_list: if we have a compound assignment that is an
+         argument to a declaration command, but there are no options supplied
+         to the command that determine the type of the array, make sure we
+         call make_internal_declare with either -a (no localvar_inherit or -I)
+         or at least -- (if we are inheriting), because  we don't want the
+         declare to get skipped before we perform the word assignment. Fixes
+         bug reported by Ross Goldberg <ross.goldberg@gmail.com>
index 7af62c39ba1ddafc1200b427f8486acd99f40b74..4b26cb1fc43182c31d8a355f5d60ed14078d3e02 100644 (file)
@@ -1,7 +1,7 @@
 This file is declare.def, from which is created declare.c.
 It implements the builtins "declare" and "local" in Bash.
 
-Copyright (C) 1987-2016 Free Software Foundation, Inc.
+Copyright (C) 1987-2020 Free Software Foundation, Inc.
 
 This file is part of GNU Bash, the Bourne Again SHell.
 
@@ -22,7 +22,7 @@ $PRODUCES declare.c
 
 $BUILTIN declare
 $FUNCTION declare_builtin
-$SHORT_DOC declare [-aAfFgilnrtux] [-p] [name[=value] ...]
+$SHORT_DOC declare [-aAfFgiIlnrtux] [-p] [name[=value] ...]
 Set variable values and attributes.
 
 Declare variables and give them attributes.  If no NAMEs are given,
@@ -64,7 +64,7 @@ $END
 
 $BUILTIN typeset
 $FUNCTION declare_builtin
-$SHORT_DOC typeset [-aAfFgilnrtux] [-p] name[=value] ...
+$SHORT_DOC typeset [-aAfFgiIlnrtux] [-p] name[=value] ...
 Set variable values and attributes.
 
 A synonym for `declare'.  See `help declare'.
diff --git a/parse.y b/parse.y
index c5d9b93cd94b377b2f929ad2f32e1b4d83a9dec0..873bd596d8af2a72760a752204cfcbc8a83c44ab 100644 (file)
--- a/parse.y
+++ b/parse.y
@@ -926,12 +926,12 @@ case_command:     CASE WORD newline_list IN newline_list ESAC
 
 function_def:  WORD '(' ')' newline_list function_body
                        { $$ = make_function_def ($1, $5, function_dstart, function_bstart); }
-
        |       FUNCTION WORD '(' ')' newline_list function_body
                        { $$ = make_function_def ($2, $6, function_dstart, function_bstart); }
-
-       |       FUNCTION WORD newline_list function_body
-                       { $$ = make_function_def ($2, $4, function_dstart, function_bstart); }
+       |       FUNCTION WORD function_body
+                       { $$ = make_function_def ($2, $3, function_dstart, function_bstart); }
+       |       FUNCTION WORD '\n' newline_list function_body
+                       { $$ = make_function_def ($2, $5, function_dstart, function_bstart); }
        ;
 
 function_body: shell_command
diff --git a/subst.c b/subst.c
index 1d91dd5d0ee8e6f62da738bff9207eea79a35576..e5e05df22e70fd98d67b5175ba22c5a87862f93a 100644 (file)
--- a/subst.c
+++ b/subst.c
@@ -11472,8 +11472,10 @@ brace_expand_word_list (tlist, eflags)
 #endif
 
 #if defined (ARRAY_VARS)
-/* Take WORD, a compound associative array assignment, and internally run
-   'declare -A w', where W is the variable name portion of WORD. */
+/* Take WORD, a compound array assignment, and internally run (for example),
+   'declare -A w', where W is the variable name portion of WORD. OPTION is
+   the list of options to supply to `declare'. CMD is the declaration command
+   we are expanding right now; it's unused currently. */
 static int
 make_internal_declare (word, option, cmd)
      char *word;
@@ -11533,8 +11535,9 @@ shell_expand_word_list (tlist, eflags)
        {
          int t;
          char opts[16];
-         int opti, skip;
+         int opti, skip, inheriting, array;
 
+         inheriting = localvar_inherit;
          opti = 0;
          if (tlist->word->flags & (W_ASSIGNASSOC|W_ASSNGLOBAL|W_CHKLOCAL|W_ASSIGNARRAY))
            opts[opti++] = '-';
@@ -11547,7 +11550,10 @@ shell_expand_word_list (tlist, eflags)
          else if (tlist->word->flags & W_ASSIGNASSOC)
            {
              opts[opti++] = 'A';
-             opts[opti++] = 'I';
+             /* This doesn't work right if a variable with the same name but
+                a different type exists at a previous scope; it generates
+                errors that a user would find confusing. */
+/*           opts[opti++] = 'I'; */
            }
          else if ((tlist->word->flags & (W_ASSIGNARRAY|W_ASSNGLOBAL)) == (W_ASSIGNARRAY|W_ASSNGLOBAL))
            {
@@ -11557,7 +11563,7 @@ shell_expand_word_list (tlist, eflags)
          else if (tlist->word->flags & W_ASSIGNARRAY)
            {
              opts[opti++] = 'a';
-             opts[opti++] = 'I';
+/*           opts[opti++] = 'I'; */
            }
          else if (tlist->word->flags & W_ASSNGLOBAL)
            opts[opti++] = 'g';
@@ -11585,6 +11591,8 @@ shell_expand_word_list (tlist, eflags)
                  for (oind = 1; l->word->word[oind]; oind++)
                    switch (l->word->word[oind])
                      {
+                       case 'I':
+                         inheriting = 1;
                        case 'i':
                        case 'l':
                        case 'u':
@@ -11603,6 +11611,26 @@ shell_expand_word_list (tlist, eflags)
                  opts[opti++] = oind;
            }
 
+         /* If there are no -a/-A options, but we have a compound assignment,
+            we have a choice: we can set opts[0]='-', opt[1]='a', since the
+            default is to create an indexed array, and call
+            make_internal_declare, or we can just skip it and let
+            declare_builtin deal with it.  Once we're here, we're better set
+            up for the former. We don't do this if we're inheriting local
+            variables' attributes and values here, since that makes `-a' no
+            longer the default; we pass `--' instead if we don't have any
+            options at all, and just leave off the -a if we have some. */
+         if ((tlist->word->flags & (W_ASSIGNASSOC|W_ASSIGNARRAY)) == 0)
+           {
+             if (opti == 0)
+               {
+                 opts[opti++] = '-';
+                 opts[opti++] = inheriting ? '-' : 'a';
+               }
+             else if (inheriting == 0)
+               opts[opti++] = 'a';
+           }
+
          opts[opti] = '\0';
          skip = 0;
          if (opti > 0)
index 12eb047ce5f66c88547060bfbe1fd938b8bba4d7..25f036e69d1d92a32cdedaee557eea13b12390ca 100644 (file)
@@ -14,7 +14,7 @@ unset: usage: unset [-f] [-v] [-n] [name ...]
 ./errors.tests: line 62: unset: XPATH: cannot unset: readonly variable
 ./errors.tests: line 68: unset: cannot simultaneously unset a function and a variable
 ./errors.tests: line 71: declare: -z: invalid option
-declare: usage: declare [-aAfFgilnrtux] [-p] [name[=value] ...]
+declare: usage: declare [-aAfFgiIlnrtux] [-p] [name[=value] ...]
 ./errors.tests: line 73: declare: `-z': not a valid identifier
 ./errors.tests: line 74: declare: `/bin/sh': not a valid identifier
 ./errors.tests: line 78: declare: cannot use `-f' to make functions
index b16b4033fd169302ed54fc5994417a8ca055cba3..34a130f8f076c742a39127a1ebb1e28221c94806 100644 (file)
@@ -131,6 +131,7 @@ func: null or unset
 after func: x = outside
 ./varenv11.sub: line 17: local: qux: readonly variable
 ./varenv11.sub: line 18: qux: readonly variable
+./varenv11.sub: line 18: local: qux: readonly variable
 declare -A foo=([zero]="zero" [one]="one" )
 declare -a bar=([0]="zero" [1]="one")
 declare -A foo=([one]="one" [zero]="zero" )
@@ -172,16 +173,11 @@ declare -A var=([0]="X" )
 help
 ./varenv13.sub: line 34: `var[0]': not a valid identifier
 1
-./varenv14.sub: line 19: warning: var: cannot inherit value from incompatible type
-declare -a var=([0]="X")
-./varenv14.sub: line 22: warning: var: cannot inherit value from incompatible type
-declare -a var=([0]="Y")
-./varenv14.sub: line 23: warning: var: cannot inherit value from incompatible type
-declare -a var=([0]="Y")
-./varenv14.sub: line 24: warning: var: cannot inherit value from incompatible type
-declare -a var=()
-./varenv14.sub: line 25: warning: var: cannot inherit value from incompatible type
-declare -a var=()
+declare -A var=([0]="X" )
+declare -A var=([Y]="Y" )
+declare -A var=([Y]="Y" )
+declare -A var=()
+declare -A var=()
 ./varenv14.sub: line 31: f: var: cannot convert indexed to associative array
 ./varenv14.sub: line 31: declare: var: cannot convert indexed to associative array
 declare -a var=([0]="12")
@@ -250,9 +246,9 @@ declare -- var
 declare -- var="local"
 declare -- var="f1"
 declare -- var="local"
-declare -a arr=([0]="zero" [1]="one" [2]="two")
+declare -a arr=()
 declare -a arr=([0]="three" [1]="four" [2]="five")
-declare -a arr=([0]="zero" [1]="one" [2]="two")
+./varenv18.sub: line 39: !name: unbound variable
 a=z
 a=b
 a=z
index 4500c39e76a896313f2af246222a192d0ec43caa..e587a7c75a14f3f10541c880968fe25ed600992f 100644 (file)
@@ -12,8 +12,7 @@
 #   along with this program.  If not, see <http://www.gnu.org/licenses/>.
 #
 
-# this uses value inheritance internally so that the self-reference in the
-# local variable declaration works right
+# THIS DOESN'T WORK RIGHT YET
 
 arr=(zero one two)
 four=four
index 3865d21a0896a0e1cb317491c95b2648ea252213..c73eb4e52c04b5ccda7d4f3656ba2eda6343a3de 100644 (file)
@@ -253,6 +253,8 @@ extern WORD_LIST *rest_of_args;
 extern int posparam_count;
 extern pid_t dollar_dollar_pid;
 
+extern int localvar_inherit;           /* declared in variables.c */
+
 extern void initialize_shell_variables PARAMS((char **, int));
 
 extern int validate_inherited_value PARAMS((SHELL_VAR *, int));