4.23. Device Special FilesThe two fields st_dev and st_rdev are often confused. We'll need to use these fields in Section 18.9 when we write the ttyname function. The rules are simple.
ExampleThe program in Figure 4.25 prints the device number for each command-line argument. Additionally, if the argument refers to a character special file or a block special file, the st_rdev value for the special file is also printed. Running this program gives us the following output: $ ./a.out / /home/sar /dev/tty[01] /: dev = 3/3 /home/sar: dev = 3/4 /dev/tty0: dev = 0/7 (character) rdev = 4/0 /dev/tty1: dev = 0/7 (character) rdev = 4/1 $ mount which directories are mounted on which devices? /dev/hda3 on / type ext2 (rw,noatime) /dev/hda4 on /home type ext2 (rw,noatime) $ ls -lL /dev/tty[01] /dev/hda[34] brw------- 1 root 3, 3 Dec 31 1969 /dev/hda3 brw------- 1 root 3, 4 Dec 31 1969 /dev/hda4 crw------- 1 root 4, 0 Dec 31 1969 /dev/tty0 crw------- 1 root 4, 1 Jan 18 15:36 /dev/tty1 The first two arguments to the program are directories (/ and /home/sar), and the next two are the device names /dev/tty[01]. (We use the shell's regular expression language to shorten the amount of typing we need to do. The shell will expand the string /dev/tty[01] to /dev/tty0 /dev/tty1.) We expect the devices to be character special files. The output from the program shows that the root directory has a different device number than does the /home/sar directory. This indicates that they are on different file systems. Running the mount(1) command verifies this. We then use ls to look at the two disk devices reported by mount and the two terminal devices. The two disk devices are block special files, and the two terminal devices are character special files. (Normally, the only types of devices that are block special files are those that can contain random-access file systems: disk drives, floppy disk drives, and CD-ROMs, for example. Some older versions of the UNIX System supported magnetic tapes for file systems, but this was never widely used.) Note that the filenames and i-nodes for the two terminal devices (st_dev) are on device 0/7the devfs pseudo file system, which implements the /devbut that their actual device numbers are 4/0 and 4/1. Figure 4.25. Print st_dev and st_rdev values#include "apue.h" #ifdef SOLARIS #include <sys/mkdev.h> #endif int main(int argc, char *argv[]) { int i; struct stat buf; for (i = 1; i < argc; i++) { printf("%s: ", argv[i]); if (stat(argv[i], &buf) < 0) { err_ret("stat error"); continue; } printf("dev = %d/%d", major(buf.st_dev), minor(buf.st_dev)); if (S_ISCHR(buf.st_mode) || S_ISBLK(buf.st_mode)) { printf(" (%s) rdev = %d/%d", (S_ISCHR(buf.st_mode)) ? "character" : "block", major(buf.st_rdev), minor(buf.st_rdev)); } printf("\n"); } exit(0); } |