bug-bash
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: indirect variable behavior breakage


From: christopher barry
Subject: Re: indirect variable behavior breakage
Date: Fri, 9 Mar 2018 14:44:32 -0500

On Fri, 9 Mar 2018 11:29:35 -0500
Chet Ramey <chet.ramey@case.edu> wrote:

> On 3/7/18 3:20 PM, christopher barry wrote:
> > On Wed, 7 Mar 2018 11:45:13 -0500
> > christopher barry <cbarry@rajant.com> wrote:
> > 
> > ===8<---snip
> >   
> >>
> >> I am in fact using this method with associative arrays.
> >>
> >> I have a default hash that is full of default values for a
> >> particular generic type of thing. Variations of this thing use
> >> many of the defaults, but also set some values uniquely. I could
> >> simply duplicate this hash everywhere, and edit the differences,
> >> but then changing any defaults would require a change everywhere.
> >>
> >> As an alternative, I created a template hash that all non-default
> >> things start out with.
> >>
> >> this template hash has all of it's values pointing to
> >> "default_hash[somekey]"
> >>
> >> new things that need to change their specific values simply
> >> override that and put in their string.
> >>
> >> Now, changes to actual values in default_hash are seen everywhere
> >> they are not overridden locally by the specific thing using it.
> >>
> >> so reading a hash value may be an indirect pointer to the
> >> default_hash or an overridden value set by the specific thing
> >> using the hash.
> >>
> >> ivar solves this nicely.
> >>
> >>
> >> But to get back on point, the bug in bash was nasty, and it's
> >> fantastic that it's fixed now, but throwing an error now, rather
> >> than simply returning 1 with no data is a bit like throwing the
> >> baby out with the bathwater.
> >>
> >>
> >>  -C  
> > 
> > Chet,
> > 
> > Does modifying this current behavior sound like anything you would
> > be willing to entertain?  
> 
> I think that throwing an error when the value of a variable used for
> indirection would not be accepted as valid (and throw an error) when
> used directly is the right thing to do, and I will leave it as the
> default behavior.
> 
> I'm open to suggestions about how to allow alternate behavior: a shell
> option, something controlled by the shell compatibility level,
> something else? It seems like you're really interested in learning
> whether a particular string is a valid shell variable and doing
> something based on the result. You could check that directly -- the
> pattern to describe a shell variable isn't that hard to write -- but
> I get the sense that you'd rather not take the extra step.
> 
> Chet
> 

Hi Chet,

It's not that I don't want to take any required steps, it was that it
seemed logical to me to simply return 1 in that instance. When I
discovered that this method worked the way I was hoping, I was kinda
miffed at myself for never having noticed it earlier. Then I was shown
it was not working on new versions. I had never hit the core dump issue
before you pointed it out.

Could the fact that that bug caused a core dump be influencing why you
do not want to simply return 1 now? Maybe throwing an error now seems
better because it was such a bad bug before?

When assigning to a var, format checking absolutely should be done, and
an error should be thrown if invalid. But if only checking, e.g. just
reading a name, then returning 1 if it's an invalid name or does not
exist seems like the smallest, most applicable hammer for the job at
hand.

I did actually spend some time (longer than I would like to admit)
trying to craft a decent regex to make sure that every possible way of
asking was covered, but it turns out to be a bit more complex that one
may think at first blush.

^([#]*(_[[:digit:]]|[_[:alpha:]])[_[:alnum:]]*)(\[[_[:alnum:]*@]+\])$

testing against ${1}, ${BASH_REMATCH[0]} and ${BASH_REMATCH[1]} would
mostly show the valid forms, but this regex was still not quite right.

A colleague here at work came up with a beautiful 16oz ball-peen hammer
approach, no regex required, as can be seen here:

#-----------------------------------------------------------------------
function ivar()
# Description: cascading indirect -> regular var expander
{
    ( echo -n "${!1:-${1}}" ) 2>/dev/null || echo -n "${1}"
}
#---

it solves the problem, so that's what I'm using now, but it's obviously
not as clean and simple as it was, and it can still core dump the
sub-shell, which does suck, but it's non-fatal.

If you can't see my point about not needing to throw an error on just
a read, then I guess I'll just have to deal with it.

Thanks, and maybe you will come to see my position at some point, never
know :)

Regards,
-C








reply via email to

[Prev in Thread] Current Thread [Next in Thread]