[lug] Losing what little Unix cred I once had

Hugh Brown hugh at math.byu.edu
Thu Dec 14 22:40:33 MST 2006


Daniel Webb wrote:
> $ a="$(echo -n -e '\0011')"
> $ echo -n "test two three" | grep "$a"
> <nothing>
> 
> $ a="$(echo -n -e '\0012')"
> $ echo -n "test two three" | grep "$a"
> test two three
> 
> $ a="$(echo -n -e '\0013')"
> $ echo -n "test two three" | grep "$a"
> <nothing>
> 
> Why?  \0012 is the echo escape for linefeed in octal.  So where is a linefeed
> getting in there?
> 


This is a curious one.  I'm assuming you are using bash from the $() 
syntax.  echo is being provided by bash and is not the system /bin/echo

I've been playing around with this and have put both sides of the pipe 
through strace.

If you do an
if [ -z "$a" ]; then echo "zero length"; fi
it will print "zero length" when a is \0012, but it won't print if a is 
\0011

As I was searching around for whether or not the bash builtin echo was 
using the same octal <-> character table as you were expecting, it 
occurred to me that you've told echo to enable the interpretation of 
octal escapes.  So when you do a="$(echo -n -e '\0012')" you've told it 
to take and run echo -n <return> and take the output and put it in a. 
It looks to "a" as if you've just told it $(echo -n ).

Then I stopped and thought about it more and wasn't sure why $() would 
treat echo -n <return> the same as echo -n.

It seemed so clear in my head :), somehow it was just like typing return 
  after entering a command and it got absorbed.

The reason  that the pipe to grep "$a" works for \0012 is the same 
reason that it would works for grep ""  Apparently, the empty string is 
found in every string ;)

Anyone have any insights into this?  I'm guessing it must have to do 
with the way bash uses $() to run a command and capture its output.

I don't think I had any Unix cred, so I had none to lose :)

Hugh



More information about the LUG mailing list