[moving to the coreutils list, as coreutils has a bug here] On 09/05/2013 10:33 AM, Eric Blake wrote: > On 09/04/2013 11:06 PM, kneuf...@gmail.com wrote: >> According to the man page, [ -a ] and [ -e ] should have the same behaviour. > > Not a bug. -a behaves like -e only when it is unambiguously parsed as a > unary operator, because it is bash extension as a unary operator. > >> >> -a file >> True if file exists. >> ... >> -e file >> True if file exists. >> >> $ touch stuff.txt >> $ [ -a stuff.txt ]; echo $? >> 0 >> $ [ -e stuff.txt ]; echo $? >> 0 >> $ [ ! -e stuff.txt ]; echo $? >> 1 >> $ [ ! -a stuff.txt ]; echo $? >> 0 # what? > > But _this_ is an instance where -a is parsed as a binary operator (ie. > it was parsed as "\( ! \) -a \( stuff.txt \)", not "! \( -a stuff.txt > \)". -a as a binary operator is required by POSIX for XSI, therefore it > takes priority over -a as a unary operator as a bash extension. >
The POSIX wording states for 3-argument tests (http://pubs.opengroup.org/onlinepubs/9699919799/utilities/test.html): • If $2 is a binary primary, perform the binary test of $1 and $3. • If $1 is ’!’, negate the two-argument test of $2 and $3. • If $1 is ’(’ and $3 is ’)’, perform the unary test of $2. The first two bullets both apply to your situation, but it can be assumed that the ordering of the bullets is significant. Why? Because "test \( = \)" is a case of both the first and third bullet applying, and on that case, both bash and coreutils agree that it returns false (3-argument string comparison of different strings) rather than true (parenthesized 1-argument test of non-empty =). Coreutils therefore should fix its test to favor binary -a over unary -a, when there are three arguments and the first is !. -- Eric Blake eblake redhat com +1-919-301-3266 Libvirt virtualization library http://libvirt.org
signature.asc
Description: OpenPGP digital signature