This is one of those details that will bite you if you don’t know about it and you might struggle to find the answer for something that looks like a bug.
The characters * and ? have special meaning in the shell, as you know. * means zero or more characters while ? means any character. Favorably, these glob patterns are still the same for those of us who go back to the murky days of Ms DOS.
Glob patterns are very useful in the shell, but when used with programs that themselves accept glob patters the results may be surprising. For example:
$ ls file2.zip file.zip $ find -iname *.zip find: paths must precede expression Usage: find [-H] [-L] [-P] [path...] [expression] $ find . -iname *.zip find: paths must precede expression Usage: find [-H] [-L] [-P] [path...] [expression]
Download this code: glob1
Huh? To see what’s happening here, run the shell in echo mode:
$ bash -x $ find -iname *.zip + find -iname file2.zip file.zip find: paths must precede expression Usage: find [-H] [-L] [-P] [path...] [expression]
Download this code: glob2
So now we see what’s happening. *.zip was expanded because it matched two files in this directory. Those two files were then passed as arguments to find, not the *.zip pattern.
Bash will expand the glob pattern whether or not you use it with find, so you just have to tell it not to expand it:
$ find -iname '*.zip' + find -iname '*.zip' ./file2.zip ./file.zip
Download this code: glob3
This is confusing, because if *.zip doesn’t match any files, then it will be sent verbatim to the program. Therefore you should always quote your glob patterns if they are meant for a program, not the shell.

Thursday, July 24th, 2008