[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
Re: Severe Bash Bug with Arrays
From: |
Linda Walsh |
Subject: |
Re: Severe Bash Bug with Arrays |
Date: |
Sat, 05 May 2012 04:17:38 -0700 |
User-agent: |
Mozilla/5.0 (Windows; U; Windows NT 6.0; en-US; rv:1.8.1.24) Gecko/20100228 Lightning/0.9 Thunderbird/2.0.0.24 Mnenhy/0.7.6.666 |
Maarten Billemont wrote:
This mail has gone slightly off-topic. Hit mark as read if you don't
care for that sort of thing.
I don't care if you like evil in your sexual play or in your vendettas.
When you write code, evil is nothing worth liking. In programming,
evil is defined as something that is stupid and not thought through. Doing
> evil has harmful side effects. It's not cool to be evil, it's short-sighted.
---
You have a very twisted view of evil.
code to yourself, just don't try to convince me with them.
---
There is no need to convince someone with your views of anything.
Maarten Billemont wrote:
On 26 Apr 2012, at 01:18, Linda Walsh wrote:
Ishtar:> echo "${b[*]}"
Please note that expanding array elements using [*] is usually NOT what anyone
wants.
I didn't say never to use "${b[*]}".
What I *did* say, is never to use ${b[*]}.
===
Uh, why do you bother to write about the horrors of such usage, when the
purpose of my test cases, was to progressively show effects.
When I echoed out the unquoted part, the intervening white space was removed...
To get the original text (with embedded line feeds, proving the file was
stored in the var), one must quote it.
Anyway, think about this: An array holds elements in a way that each is separated
from the other. To put these elements in an array is to want each element to be
distinct from the others. Therefore, the default way of expanding these elements
should preserve that distinction.
======
When I want to preserve that distinction, I usually try something like
printq save "$typeset -p arrayname)"..
then later
eval "$save" to recover the array.
That's not what the original author was asking about.
args="-dpi -xinerama -clipboard -unixkill -nowinkill -ac +bs -fp -multiwindow"
readarray -t dflts< <( a=( $args ); IFS=$'\n'; echo "${a[*]#?}"|sort -k1.2 )
printf " defaults=(%s)" "${dflts[*]}"
defaults=(-ac +bs -clipboard -dpi -fp -multiwindow -nowinkill -unixkill
-xinerama)
... What are you trying to prove? That with a very specific sent of input values you
can do some ugly and hacky mangling involving arrays and wordsplitting to sort
a word-list?
Why are you even USING arrays here at all? There's no point. Just to
replace spaces
with newlines?
---
The original args are in the format they were originally needed in to be passed
to a program. I wanted to sort them alphabetically regardless of +/-, then
pass them to the program. I took the existing input, sorted it, then restored
it to the order needed by the program.
The point is you know nothing about code other people deal with -- presuming
that your rules apply everywhere is insulting and invasive. Such
behaviors need to be dealt with like invasive weeds or they take over the
garden. Examples are rampant.
Also, you're doing a lot of really bad stuff here.
---
Then, from you, I know I am doing well.
Might I point out that you're stripping the leading - and + from your
arguments and not putting them back? I don't know where you got the output
you claim from, but the real output has lost the first character of each word.
---
Umm...no.. didn't you READ the output you idjit**! The output didn't
lose information. I sorted by -k1.2 (1st field second char), that doesn't
strip. (**-Inuyasa-ism).
% args="-dpi -xinerama -clipboard -unixkill -nowinkill -ac +bs -fp -multiwindow"
% readarray -t dflts< <( a=( $args ); IFS=$'\n'; echo "${a[*]#?}"|sort -k1.2 )
% printf " defaults=(%s)" "${dflts[*]}"
defaults=(-ac +bs -clipboard -dpi -fp -multiwindow -nowinkill -unixkill
-xinerama)
---
The output is staring you in the face... the "+" goes with "bs" --
hmmm... it's backing store, honest!
Want to create pathnames using bash's /path/{}/ feature and have the paths
in an array (for simple paths):
a=(lib tmp bin share)
(export IFS=,;eval "echo /usr/{${a[*]}}")
/usr/lib /usr/tmp /usr/bin /usr/share
Don't do this. You're injecting strings into bash code, and then evaluating that code.
---
Oh my gawd, you mean like DATA as OBJECTS?? The basis for object oriented
code? NOT THAT Mr. Wizard! Anything but that!
Ignoring the security aspect, this code will break for elements that contain commas
or braces or quotes or newlines. And you know what, yes, it's perfectly fine
for
filenames to contain those. It's not fine for your code to break on them.
----
I am a MAJOR user of those.. when my stuff doesn't work I eat the doodoo --
sometimes I go back to more primitive.
Grow up, use a loop. It really doesn't hurt that much.
---
If you don't know how to do things and know all of their pitfalls, how will you
grow up? If you prevent people from making their own mistakes, how will they
grow -- they don't. Doesn't mean you don't tell them, but to go off and preach
at them.... how patently absurd to think that will accomplish anything.
C'est la vi...
vie ;-)
Oui, I realized that just as I hit send... *busted*...;-)