Re: quoted compound array assignment deprecated
On 8/18/15 5:05 PM, Dan Douglas wrote: > Sorry I meant to reply to that thread but ran out of time. I think Stephane's > eventual proposal was pretty close to what I had in mind but expressed badly. > I'm not sure why it was eventually decided to deprecate the current system > entirely but I'm not opposed to the idea - especially if it provides no > functionality for which there aren't easy workarounds. Deprecated doesn't mean removed. In this case, the meaning is closer to discouraged or deemphasized. Bash understands `declare' as a Posix declaration utility, and does its best to treat arguments to declare and other declaration utilities identically to standalone assignment statements. The place where that breaks down is if a compound array assignment is treated as such by declare when it would have been treated as a scalar assignment had it appeared standalone. That's why the warning. It's not an error. > The only thing I'm actively abusing this for at the moment in scripts I > actually use is as a way of encoding 2D arrays. It's very much a read-only > datastructure too. > > ~ $ ( key1=foo key2=bar; declare -A a=([foo]='([bar]=baz)') "b=${a[$key1]}" > typeset -p a b; echo "${b[$key2]}" ) > declare -A a='([foo]="([bar]=baz)" )' > declare -A b='([bar]="baz" )' > baz > > Any change will likely break this property but I think wrapping it in eval > gives the same result. This will continue to work, but with a warning about a potentially dangerous construct. -- ``The lyf so short, the craft so long to lerne.'' - Chaucer ``Ars longa, vita brevis'' - Hippocrates Chet Ramey, ITS, CWRUc...@case.eduhttp://cnswww.cns.cwru.edu/~chet/
Re: quoted compound array assignment deprecated
-BEGIN PGP SIGNED MESSAGE- Hash: SHA1 On 8/18/15 11:41 PM, Mike Frysinger wrote: > just to double check, the warning from this code is expected ? > > $ bash-4.3 -c 'declare -a foo=(a b c); export foo; declare -p foo' > declare -ax foo='([0]="a" [1]="b" [2]="c")' > $ bash-4.4 -c "declare -a foo='(a b c)'" > bash-4.4: warning: foo=(a b c): quoted compound array assignment deprecat ed Yes. It may not last into the final bash-4.4 release. > we see this in Gentoo because we save/restore build envs via bash. so al l > builds done w/bash-4.3 and older use the quoted syntax, so updating with > bash-4.4 in the system triggers these warnings. we can adjust our toolin g > to handle it, but would be nice if older bash didn't do it either. maybe > send out a 4.3-p43 ? ;) I'd rather people experiment with it first. It changes a bunch of test output, so a patch would be pretty extensive. I've attached a patch for you to try with Gentoo. Chet - -- ``The lyf so short, the craft so long to lerne.'' - Chaucer ``Ars longa, vita brevis'' - Hippocrates Chet Ramey, ITS, CWRUc...@case.eduhttp://cnswww.cns.cwru.edu/~chet/ -BEGIN PGP SIGNATURE- Version: GnuPG v2 iEYEARECAAYFAlXUhGQACgkQu1hp8GTqdKsJhwCfTKaj3GXe7U2RVtWrNdfwGZd5 cHoAn0SBXhfrI1npA/e+0Los5Eh5fO7p =8f/u -END PGP SIGNATURE- *** ../bash-4.3.42/builtins/setattr.def 2014-01-09 11:34:35.0 -0500 --- builtins/setattr.def 2015-08-19 09:14:00.0 -0400 *** *** 427,433 #if defined (ARRAY_VARS) if (array_p (var)) ! print_array_assignment (var, 1); else if (assoc_p (var)) ! print_assoc_assignment (var, 1); else #endif --- 427,433 #if defined (ARRAY_VARS) if (array_p (var)) ! print_array_assignment (var, 0); else if (assoc_p (var)) ! print_assoc_assignment (var, 0); else #endif
Re: quoted compound array assignment deprecated
On 18 Aug 2015 10:51, Chet Ramey wrote: > On 8/17/15 4:19 AM, isabella parakiss wrote: > > Quoting is necessary in a few cases: > > > > $ var=foo; declare -A "arr$var=([x]=y)" > > bash: warning: arrfoo=([x]=y): quoted compound array assignment deprecated > > $ var=foo; declare -A arr$var=([x]=y) > > bash: syntax error near unexpected token `(' > > $ var=foo; declare -A "arr$var"=([x]=y) > > bash: syntax error near unexpected token `(' > > > > I don't think this should be the default behaiour... > > This is exactly the case for which the warning is intended. If you want > to construct variable names on the fly, use `eval' or don't mix > declarations of constructed variable names with compound assignment. > > You can read the extensive discussion starting at > http://lists.gnu.org/archive/html/bug-bash/2014-12/msg00028.html. > > http://lists.gnu.org/archive/html/bug-bash/2014-12/msg00115.html is the > newest proposal. just to double check, the warning from this code is expected ? $ bash-4.3 -c 'declare -a foo=(a b c); export foo; declare -p foo' declare -ax foo='([0]="a" [1]="b" [2]="c")' $ bash-4.4 -c "declare -a foo='(a b c)'" bash-4.4: warning: foo=(a b c): quoted compound array assignment deprecated we see this in Gentoo because we save/restore build envs via bash. so all builds done w/bash-4.3 and older use the quoted syntax, so updating with bash-4.4 in the system triggers these warnings. we can adjust our tooling to handle it, but would be nice if older bash didn't do it either. maybe send out a 4.3-p43 ? ;) -mike signature.asc Description: Digital signature
Re: quoted compound array assignment deprecated
Sorry I meant to reply to that thread but ran out of time. I think Stephane's eventual proposal was pretty close to what I had in mind but expressed badly. I'm not sure why it was eventually decided to deprecate the current system entirely but I'm not opposed to the idea - especially if it provides no functionality for which there aren't easy workarounds. The only thing I'm actively abusing this for at the moment in scripts I actually use is as a way of encoding 2D arrays. It's very much a read-only datastructure too. ~ $ ( key1=foo key2=bar; declare -A a=([foo]='([bar]=baz)') "b=${a[$key1]}" typeset -p a b; echo "${b[$key2]}" ) declare -A a='([foo]="([bar]=baz)" )' declare -A b='([bar]="baz" )' baz Any change will likely break this property but I think wrapping it in eval gives the same result. -- Dan Douglas
Re: quoted compound array assignment deprecated
2015-08-17 10:19:00 +0200, isabella parakiss: > Quoting is necessary in a few cases: > > $ var=foo; declare -A "arr$var=([x]=y)" > bash: warning: arrfoo=([x]=y): quoted compound array assignment deprecated > $ var=foo; declare -A arr$var=([x]=y) > bash: syntax error near unexpected token `(' > $ var=foo; declare -A "arr$var"=([x]=y) > bash: syntax error near unexpected token `(' > > I don't think this should be the default behaiour... [...] This typically requires two levels of evaluation. The syntax of "declare" is now more consistent with that of bare assignments and there are fewer cases where "declare" ends up evaluating code that it's not meant to. Here, I'd do: declare -A "arr$var" eval "arr$var"'=([x]=y)' By using "eval" (which has the reputation of being dangerous), you're making it clear that there is that second level of evaluation that one should be careful around (and which is there as well with declare but less obvious). The way you're expecting declare to work is just a disguised eval, it's not any safer than eval. To me, variable declaration should be separate from evaluating code. Ideally, I'd rather "declare" didn't do assignments either (note that it was ksh breaking "export" by allowing assignments and causing confusions between simple commands and assignments that was not there in the Bourne shell). -- Stephane
Re: quoted compound array assignment deprecated
On 8/18/15 1:52 PM, isabella parakiss wrote: > Sorry for being both pedantic and late for that discussion but what's the > point of this warning? From my understanding, the code is still valid, so > it doesn't stop a possible attacker and it only annoys regular users. It's meant as an indication that this form of assignment will not be treated as a compound array assignment in the future. The idea is that you give users plenty of warning and plenty of opportunity to change their scripts without impacting function or breaking existing scripts on a minor version upgrade. There are legitimate security concerns with having declare treat an expanded variable as specifying a compound array assignment. Stephane did a nice job of going through them, and the discussion is illuminating. > Using eval requires an extra level of escaping on everything else, I'd > rather use declare 2>/dev/null to suppress the warning than eval... Your choice, of course. > Idea: display the warnings in -n mode, like ksh. > This way bash wouldn't produce unexpected results on existing scripts, it > wouldn't even require a new compatibility level and shopt. > What do you think about it? Very few people run bash -n. It's a nice idea, but it wouldn't have the reach I'm looking for. Chet -- ``The lyf so short, the craft so long to lerne.'' - Chaucer ``Ars longa, vita brevis'' - Hippocrates Chet Ramey, ITS, CWRUc...@case.eduhttp://cnswww.cns.cwru.edu/~chet/
Re: quoted compound array assignment deprecated
On 8/18/15, Chet Ramey wrote: > On 8/17/15 4:19 AM, isabella parakiss wrote: >> Quoting is necessary in a few cases: >> >> $ var=foo; declare -A "arr$var=([x]=y)" >> bash: warning: arrfoo=([x]=y): quoted compound array assignment >> deprecated >> $ var=foo; declare -A arr$var=([x]=y) >> bash: syntax error near unexpected token `(' >> $ var=foo; declare -A "arr$var"=([x]=y) >> bash: syntax error near unexpected token `(' >> >> I don't think this should be the default behaiour... > > This is exactly the case for which the warning is intended. If you want > to construct variable names on the fly, use `eval' or don't mix > declarations of constructed variable names with compound assignment. > > You can read the extensive discussion starting at > http://lists.gnu.org/archive/html/bug-bash/2014-12/msg00028.html. > > http://lists.gnu.org/archive/html/bug-bash/2014-12/msg00115.html is the > newest proposal. > > Chet > -- > ``The lyf so short, the craft so long to lerne.'' - Chaucer >``Ars longa, vita brevis'' - Hippocrates > Chet Ramey, ITS, CWRUc...@case.eduhttp://cnswww.cns.cwru.edu/~chet/ > Sorry for being both pedantic and late for that discussion but what's the point of this warning? From my understanding, the code is still valid, so it doesn't stop a possible attacker and it only annoys regular users. Using eval requires an extra level of escaping on everything else, I'd rather use declare 2>/dev/null to suppress the warning than eval... Idea: display the warnings in -n mode, like ksh. This way bash wouldn't produce unexpected results on existing scripts, it wouldn't even require a new compatibility level and shopt. What do you think about it? --- xoxo iza
Re: quoted compound array assignment deprecated
On 8/17/15 4:19 AM, isabella parakiss wrote: > Quoting is necessary in a few cases: > > $ var=foo; declare -A "arr$var=([x]=y)" > bash: warning: arrfoo=([x]=y): quoted compound array assignment deprecated > $ var=foo; declare -A arr$var=([x]=y) > bash: syntax error near unexpected token `(' > $ var=foo; declare -A "arr$var"=([x]=y) > bash: syntax error near unexpected token `(' > > I don't think this should be the default behaiour... This is exactly the case for which the warning is intended. If you want to construct variable names on the fly, use `eval' or don't mix declarations of constructed variable names with compound assignment. You can read the extensive discussion starting at http://lists.gnu.org/archive/html/bug-bash/2014-12/msg00028.html. http://lists.gnu.org/archive/html/bug-bash/2014-12/msg00115.html is the newest proposal. Chet -- ``The lyf so short, the craft so long to lerne.'' - Chaucer ``Ars longa, vita brevis'' - Hippocrates Chet Ramey, ITS, CWRUc...@case.eduhttp://cnswww.cns.cwru.edu/~chet/