Re: heredoc and subshell

2016-02-24 Thread Oleg Bulatov
24.02.2016, 13:58, "Joerg Schilling" :
> BTW: If I replace $(..) by `..` and feed the code to the original SVr4 Bourne
> Shell, I get the same output as you got from bash. I would guess that the bash
> output you added above is correct.

The behavior of `..` with heredoc has also interesting corner cases:

$ cat x.sh 
cat 

Re: heredoc and subshell

2016-02-24 Thread Joerg Schilling
Eric Blake  wrote:

> > --- code
> > prefix() { sed -e "s/^/$1:/"; }
> > DASH_CODE() { :; }
> > 
> > prefix A < > echo line 1
> > XXX
> > echo line 2)" && prefix DASH_CODE < > echo line 3
> > XXX
> > echo line 4)"
> > echo line 5
> > DASH_CODE
> > 
> > --- bash 4.3.42 output:
> > A:echo line 3
> > B:echo line 1
> > line 2
> > DASH_CODE:echo line 4)"
> > DASH_CODE:echo line 5
>
> So, it looks like bash is interpreting this as "first newline that is
> not in the middle of another shell word), and parses the entire $(...)

I would like to get an explanation on what I should understand by:

"first newline that is not in the middle of another shell word)


BTW: If I replace $(..) by `..` and feed the code to the original SVr4 Bourne 
Shell, I get the same output as you got from bash. I would guess that the bash 
output you added above is correct.

Note that the command substitution is part of a " quoted string and even 
without that, it would need to be parsed first.

The POSIX version from ksh88 (seen on Solaris) behaves the same with $(..) and 
the `..` variant and the same as bash.

The fact that ksh93 behaves different with $(..) and the `..` variant makes it 
obvious that ksh93 has a bug.

Jörg

-- 
 EMail:jo...@schily.net(home) Jörg Schilling D-13353 Berlin
   joerg.schill...@fokus.fraunhofer.de (work) Blog: 
http://schily.blogspot.com/
 URL:  http://cdrecord.org/private/ 
http://sourceforge.net/projects/schilytools/files/'
--
To unsubscribe from this list: send the line "unsubscribe dash" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: heredoc and subshell

2016-02-23 Thread Eric Blake
[adding the Austin Group]

On 02/23/2016 03:07 PM, Oleg Bulatov wrote:
> Hello,
> 
> trying to minimize a shell code I found an unobvious moment with heredocs and 
> subshells.

Thanks for a cool testcase.

> 
> Is it specified by POSIX how next code should be parsed? dash output for this 
> code differs from bash and zsh.

XCU 2.3 says:

When an io_here token has been recognized by the grammar (see Shell
Grammar), one or more of the subsequent lines immediately following the
next NEWLINE token form the body of one or more here-documents and shall
be parsed according to the rules of Here-Document.

and 2.7.4 says:

The here-document shall be treated as a single word that begins after
the next  and continues until there is a line containing only
the delimiter and a , with no  characters in between.
Then the next here-document starts, if there is one.

but with no mention of what happens if you somehow manage to make the
next  be part of an incomplete shell word on the line
containing the here-doc operator.

> 
> --- code
> prefix() { sed -e "s/^/$1:/"; }
> DASH_CODE() { :; }
> 
> prefix A < echo line 1
> XXX
> echo line 2)" && prefix DASH_CODE < echo line 3
> XXX
> echo line 4)"
> echo line 5
> DASH_CODE
> 
> --- bash 4.3.42 output:
> A:echo line 3
> B:echo line 1
> line 2
> DASH_CODE:echo line 4)"
> DASH_CODE:echo line 5

So, it looks like bash is interpreting this as "first newline that is
not in the middle of another shell word), and parses the entire $(...)
construct through line 2 as if there were no newlines, then treats the
newline after DASH_CODE as starting the heredoc, for outputting A: while
visiting line 3 as the lone line in that heredoc.  Then it moves on to
the second command in the && sequence, by processing the command
substitution (a heredoc outputting line 1, then the output of line 2;
then moves on to the third component of the && sequence as a final
heredoc delimited by DASH_CODE, with both lines 4 and 5 output with the
DASH_CODE: prefix.

> 
> --- dash 0.5.8 output:
> A:echo line 1
> B:echo line 2)" && prefix DASH_CODE < B:echo line 3
> line 4
> line 5
> 

Meanwhile, dash is taking the literal first newline as the start of the
first heredoc, and outputting A: with line 1; then consuming the next
heredoc as lines 2 and 3 before finding the end of the command
substitution on line 4, then outputting line 5 on its own and doing
nothing else for the DASH_CODE function call.

ksh 93u+ 2012-08-01 behaves even differently:

B:echo line 1
line 2 && prefix DASH_CODE < after a here-doc operator occurs in
the middle of a shell word.

-- 
Eric Blake   eblake redhat com+1-919-301-3266
Libvirt virtualization library http://libvirt.org



signature.asc
Description: OpenPGP digital signature