Subject: Re: bin/560: ls -i returns incorrect inodes on symlinks and root dirs
To: None <>
From: Charles M. Hannum <>
List: netbsd-bugs
Date: 11/08/1994 17:00:03
   Why is this?  ls(1) uses the directory structure to get inums,
   stat(2) goes out and actually LOOKS at the inode, completely
   ignoring the inode number in the directory.  They're doing two
   different things.

You seem to fail to realize that you're talking about the behavior of
a specific, historic, implementation.

To quote POSIX.2:

4.39 ls - List directory contents


4.39.3 Options


-i	For each file, write the file serial number of the file (see
	Section 5.6.2 of POSIX.1 {8}).'

... Standard Output


If the -i option is specified. the file serial number of the file (see
Section 5.6.1 of POSIX.1 {8}) shall be written in the following format
before any other output for the corresponding entry:


Section 5.6.1 of POSIX.1 talks about struct stat, and section 5.6.2
talks about the stat() function/syscall.  There is no direct wording
that the `file serial number' must be the same for ls(1) as for
stat(), but it is strongly implied.

Furthermore, section 5.6.1 states:

`NOTE: File serial number and device ID taken together uniquely
identify the file within the system.'

Therefore, st_ino and st_dev must either both be for the mounted-on
directory, or both for the mounted directory.

Now, there's really no chance that I'm going to modify stat(2) to
return the info for the mounted-on directory, so `you're screwed' in
that respect.  (Among other things, returning the st_dev for the
mounted-on directory would make `find -xdev' *rather* slow for NFS.)
However, it would make sense to optimize things so that ls(1) doesn't
need to stat(2) most of the time.

This actually gets much worse.  For things to be truly consistent,
either getdirentries(2) would need to be modified to check if an entry
points to a mounted-over directory and replace d_ino, or readdir(3)
would need to be modified to always stat(2) directories.

However, POSIX does not specify that readdir() returns a d_ino
element, so POSIX rules do not apply to it.