Here is the code,
x=
if [ -d $x ]; then
echo "it's a dir"
else
echo "not a dir"
fi
The above code gives me "it's a dir", why? $x is empty, isn't it?
x=
if [ -d $x ]; then
is equivalent to:
if [ -d ] ; then
A simpler way to demonstrate what's going on is:
test -d ; echo $?
which prints 0, indicating that the test succeeded ([ is actually a command, equivalent to test except that it takes a terminating ] argument.)
But this:
test -f ; echo $?
does the same thing. Does that mean that the missing argument is both a directory and a plain file?
No, it means that it's not doing those tests.
According to the POSIX specification for the test command, its behavior depends on the number of arguments it receives.
With 0 arguments, it exits with a status of 1, indicating failure.
With 1 argument, it exits with a status of 0 (success) if the argument is not empty, or 1 (success) if the argument is empty.
With 2 arguments, the result depends on the first argument, which can be either ! (which reverses the behavior for 1 arguments), or a "unary primary" like -f or -d, or something else; if it's something else, the results are unspecified.
(POSIX also specifies the behavior for more than 2 arguments, but that's not relevant to this question.)
So this:
x=
if [ -d $x ]; then echo yes ; else echo no ; fi
prints "yes", not because the missing argument is a directory, but because the single argument -d is not the empty string.
Incidentally, the GNU Coreutils manual doesn't mention this.
So don't do that. If you want to test whether $x is a directory, enclose it in double quotes:
if [ -d "$x" ] ; then ...
The stat system call, which your shell presumably uses to determine if is a directory, treats null as the current directory.
Try compiling this program and running it with no arguments:
#include <stdio.h>
#include <sys/stat.h>
int main(int argc, char* argv[]) {
struct stat s ;
stat(argv[1], &s) ;
if(s.st_mode & S_IFDIR != 0) {
printf("%s is a directory\n", argv[1]) ;
}
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With