Path: csiph.com!au2pb.net!usenet.blueworldhosting.com!feeder01.blueworldhosting.com!news.glorb.com!usenet.stanford.edu!not-for-mail From: Oskar Maier Newsgroups: gnu.bash.bug Subject: Re: Possible bug in 4.3.11: Nameconflict when when passing an array to a function Date: Wed, 28 Oct 2015 15:42:08 +0100 Lines: 111 Approved: bug-bash@gnu.org Message-ID: References: <5630A4FE.4020608@imi.uni-luebeck.de> <20151028135335.GL27325@eeg.ccf.org> <20151028142215.GM27325@eeg.ccf.org> NNTP-Posting-Host: lists.gnu.org Mime-Version: 1.0 Content-Type: text/plain; charset=windows-1252; format=flowed Content-Transfer-Encoding: 8bit X-Trace: usenet.stanford.edu 1446043340 10130 208.118.235.17 (28 Oct 2015 14:42:20 GMT) X-Complaints-To: action@cs.stanford.edu Cc: bug-bash@gnu.org To: Greg Wooledge Envelope-to: bug-bash@gnu.org DKIM-Signature: v=1; a=rsa-sha256; c=simple/simple; d=uni-luebeck.de; s=uzl; h=subject:to:references:cc:from:message-id:date: mime-version:in-reply-to:content-transfer-encoding; bh=/l1KTrgsbWN2xuMdJsWusW8YC2LwYFnQ8e3YWKAhUdo=; b=Fu8MbN78tOvrYrCI6VsKqQ2xpBovmq1Bs3QU1ETxbggUQAkSXV0W/akW hFny6TK2bLVNA9oAh7PIo+i98voqOaUX0rfN52/0gErfeq8f5jHBjU3sh 3XTgODT2ZjEpPga89slpIiaMoWYnA0rcFugpxPZI7l2GsO6VU3CDjFfpD TNc1h4xLEhlq3xvbJPnV+mxb3NU+chpx/fdadHi8enGZh5CZNbkC361/S yD0H9LGNXR1vI6+cRmXPAxZpggvhBusmqho2IyLjpNiR+Hdm3BldL+e1Q GGD65HtUJgGjH39FGz22jS1xtfHpvDLPvtt4n6GDHIJdiE3OSy8adf1En A==; X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: A2A2AgCO3TBWjFRkU41bA4QKb8B1HYJEgzoCgTs8EAEBAQEBAQERAQEBJ0+ENgEBBDIBBREvARALDgoJFg8JAwIBAgFFBg0GAgEBiDDFYwEBAQcCASCLdYUAEAcShBwFjRuJIo59hD+CfQSPK4NwOII8FgcWgUFxAYV8AQEB X-IPAS-Result: A2A2AgCO3TBWjFRkU41bA4QKb8B1HYJEgzoCgTs8EAEBAQEBAQERAQEBJ0+ENgEBBDIBBREvARALDgoJFg8JAwIBAgFFBg0GAgEBiDDFYwEBAQcCASCLdYUAEAcShBwFjRuJIo59hD+CfQSPK4NwOII8FgcWgUFxAYV8AQEB User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:38.0) Gecko/20100101 Thunderbird/38.3.0 In-Reply-To: <20151028142215.GM27325@eeg.ccf.org> X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 141.83.100.71 X-BeenThere: bug-bash@gnu.org X-Mailman-Version: 2.1.14 Precedence: list List-Id: Bug reports for the GNU Bourne Again SHell List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Xref: csiph.com gnu.bash.bug:11791 Dear Greg, thank you for the extensive reply, I've already learned something new. The code I've posted was just intended as a minimal working example without giving it to much thought, therefore please excuse the unquoted "arr[@]". Furthermore, the original source is a small collection of bash function, purely for private use, hence I did not took too much pain to make it portable. The actual goal is hence not to print the array and I can solve the problem (while keeping the fragile hack) simply by removing the '-a' option of the 'local' statement. The reason I posted here is simply to know a) what changed, b) why it changed, c) why there is a difference in the behaviour of 'local -a NAME' to 'local NAME' and d) if it possible constitutes a bug. For the future, I will look out to avoid any hacks in my Bash-libraries. Lesson learned. Best and thanks again, Oskar On 28.10.2015 15:22, Greg Wooledge wrote: >> On Wed, Oct 28, 2015 at 11:35:42AM +0100, Oskar Maier wrote: > >> #!/bin/bash >> >> function printarray1 () { >> local -a arr=("${!1}") >> echo "${arr[@]}" # printing the complete array >> echo "${arr[9]}" # just to check if it is really recognized as an integer indexed array >> } > [...] >> printarray1 arr[@] > > > I have a few immediate comments: > > 1) Your unquoted arr[@] is subject to filename expansion (globbing) > and could be transformed to arr@ if you happen to have a file by > that name in the current directory. Quote it. > > 2) You're using that repulsive string="array[@]" ... ${!string} trick > that someone discovered once upon a time and which has spread like > a virus. This may give the illusion of being able to pass an array > to a function by name, but as you've learned, it falls apart when > the function's local variable name is the same as the caller's name. > Even bash 4.3's namerefs (declare -n) fall apart in this same > situation. There IS NO WAY to pass an array to a function by name > safely in bash. Everything you try is just a fragile hack that will > fail one day. > > You've made it even more repulsive by not hiding the [@] trickery > inside the function, but instead forcing the caller to be aware of it. > > 3) Using both "function" and "()" is redundant. > > > Now, as for the changes from bash 4.2 to 4.3, I don't know the whole > answer. Here are some of the changes from the CHANGES file: > > u. There are changes to the expansions peformed on compound array assignments, > in an effort to make foo=( [ind1]=bar [ind2]=baz ) identical to > foo[ind1]=bar foo[ind2]=baz. > > hhhh. Fixed a bug that caused `declare' and `test' to find variables that > had been given attributes but not assigned values. Such variables are > not set. > > Those might be related, or not. > > In any case, fragile hacks may stop working when you upgrade software. > That is the nature of fragile hacks, and it's why you should stick to > actual documented features. > > You're trying to make bash do things it simply cannot do. > > If the ACTUAL goal is to print the contents of an array (i.e. if the > actual goal is not "I'm trying to find a way to pass an array to a > function by name"), then do not call a function. Just use an inline > command, such as one of these: > > echo "${myarray[@]}" > declare -p myarray > printf "<%s> " "${myarray[@]}"; echo > > If you want to hide the details, you could make an alias, and turn on > the shopt that allows aliases in scripts. (I wouldn't do this; I'd just > leave the inline command as is.) > -- Oskar Maier, M.Sc. Wissenschaftlicher Mitarbeiter UNIVERSITÄT ZU LÜBECK INSTITUT FÜR MEDIZINISCHE INFORMATIK building 64, 2 floor, room 3 Ratzeburger Allee 160 23538 Lübeck Germany Tel +49 451 500 5645 Fax +49 451 500 5610 maier@imi.uni-luebeck.de www.imi.uni-luebeck.de