Path: utzoo!attcan!utgpu!jarvis.csri.toronto.edu!rutgers!apple!motcsd!hpda!hpcuhb!hpcllla!hpclisp!hpcljws!jws From: jws@hpcljws.HP.COM (John Stafford) Newsgroups: comp.lang.c Subject: Re: What is wrong with this code ? Message-ID: <660067@hpcljws.HP.COM> Date: 14 Dec 89 03:18:04 GMT References: <1156@nsscb.UUCP> Organization: Hewlett-Packard Calif. Language Lab Lines: 44 Clarence Dold writes... . . . > Additionally, we don't want to mask permissions against S_IFMT. > For that matter, we don't need to mask type against S_IFMT. > > Don't we really want > if (nfile.st_mode & S_IFREG) > printf(...); > else if (nfile.st_mode & S_IFDIR) > printf(...); > > followed by several > if (nfile.st_mode & S_IWRITE) > printf(...); > if (nfile.st_mode & S_IREAD) > printf(...); I've seen this mistake in two fairly professionally written pieces of code, written by well meaning folks who simply aren't that familiar with Unix. The problem is that the various S_... items have, in some cases, more than one bit on. Guess what happens if one of the S_... items has a bit on that is also in one of the other items? For example on my system... #define S_IFMT 0170000 /* type of file */ #define S_IFDIR 0040000 /* directory */ #define S_IFCHR 0020000 /* character special */ #define S_IFBLK 0060000 /* block special */ #define S_IFREG 0100000 /* regular */ #define S_IFIFO 0010000 /* fifo */ #define S_IFNWK 0110000 /* network special */ #define S_IFLNK 0120000 /* symbolic link */ #define S_IFSOCK 0140000/* socket */ Hence (nfile.st_mode & S_IFDIR) will be true for directories, block special files, and sockets. This is likely to lead to incorrect program results. Please mask with S_IFMT and compare for equality with the S_... of your choice, it doesn't hurt that much. Thank you for your support.