bug-bash
[Top][All Lists]
Advanced

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

Re: Severe Bash Bug with Arrays


From: Ted Okuzumi
Subject: Re: Severe Bash Bug with Arrays
Date: Wed, 25 Apr 2012 14:17:48 -0700

Thank you for that detailed information.  I really appreciate the 2
workarounds you provided.

I can confirm by adding in this line to my script:

shopt -s lastpipe

fixes the problem, confirming that it was indeed a subshell issue.

Best regards,
Ted

On Wed, Apr 25, 2012 at 10:50 AM, DJ Mills <danielmills1@gmail.com> wrote:

> On Wed, Apr 25, 2012 at 1:36 PM, Ted Okuzumi <tedokuzumi@gmail.com> wrote:
> > Please note that if I use a different command in the while loop it works.
> >
> > So instead of
> > echo "$mydata" | while read -r line; do myarray+=( "$line" ); done
> >
> > if I say:
> > echo "$mydata" | while read -r line; do echo "$line" ; done
> >
> > Then it works.  To pipe output into a while statement works, normally,
> > however it fails when the array+=( )  is used.  It doesn't fail on other
> > commands that I've seen.
> >
> > This is why I am saying it is definitely a bug.  Do you not agree?
> >
> > Thanks,
> > Ted
>
>
>
> It is NOT a bug. POSIX specifies this behavior. The echo is still run
> in a subshell...
>
> The issue is that commands in a pipeline are run in a subshell. This
> means that assignments and changes in PWD do not persist afterwards.
> See http://mywiki.wooledge.org/BashFAQ/024.
>
> The lastpipe shopt will work, as discussed before. The other options
> are process substitution, or (POSIXly) a fifo.
>
> Examples:
>
> # Process substitution:
> while read -r line; do
>   array+=("$line")
> done < <(some_command)
>
>
> # FIFO:
> mkfifo myfifo || exit
> trap 'rm -f myfifo' EXIT
>
> some_command > myfifo &
> while read -r line; do
>   array+=("$line")
> done < myfifo
>
>
> # Or, since it's a string you're using in your example, you could use
> a here string or here document
> while read -r line; do array+=("$line"); done <<<"$mydata"
>
> while read -r line; do array+=("$line"); done <<EOF
> $mydata
> EOF
>
> mapfile, with bash4, is also an option for this particular case.
>


reply via email to

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