4.9. chmod and fchmod FunctionsThese two functions allow us to change the file access permissions for an existing file.
The chmod function operates on the specified file, whereas the fchmod function operates on a file that has already been opened. To change the permission bits of a file, the effective user ID of the process must be equal to the owner ID of the file, or the process must have superuser permissions. The mode is specified as the bitwise OR of the constants shown in Figure 4.6. We've added the two set-ID constants (S_ISUID and S_ISGID), the saved-text constant (S_ISVTX), and the three combined constants (S_IRWXU, S_IRWXG, and S_IRWXO). The saved-text bit (S_ISVTX) is not part of POSIX.1. It is defined as an XSI extension in the Single UNIX Specification. We describe its purpose in the next section. ExampleRecall the final state of the files foo and bar when we ran the program in Figure 4.9 to demonstrate the umask function: $ ls -l foo bar -rw------- 1 sar 0 Dec 7 21:20 bar -rw-rw-rw- 1 sar 0 Dec 7 21:20 foo The program shown in Figure 4.12 modifies the mode of these two files. After running the program in Figure 4.12, we see that the final state of the two files is $ ls -l foo bar -rw-r--r-- 1 sar 0 Dec 7 21:20 bar -rw-rwSrw- 1 sar 0 Dec 7 21:20 foo In this example, we have set the permissions of the file bar to an absolute value, regardless of the current permission bits. For the file foo, we set the permissions relative to their current state. To do this, we first call stat to obtain the current permissions and then modify them. We have explicitly turned on the set-group-ID bit and turned off the group-execute bit. Note that the ls command lists the group-execute permission as S to signify that the set-group-ID bit is set without the group-execute bit being set. Finally, note that the time and date listed by the ls command did not change after we ran the program in Section 4.18 that the chmod function updates only the time that the i-node was last changed. By default, the ls -l lists the time when the contents of the file were last modified. Figure 4.12. Example of chmod function#include "apue.h" int main(void) { struct stat statbuf; /* turn on set-group-ID and turn off group-execute */ if (stat("foo", &statbuf) < 0) err_sys("stat error for foo"); if (chmod("foo", (statbuf.st_mode & ~S_IXGRP) | S_ISGID) < 0) err_sys("chmod error for foo"); /* set absolute mode to "rw-r--r--" */ if (chmod("bar", S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH) < 0) err_sys("chmod error for bar"); exit(0); }The chmod functions automatically clear two of the permission bits under the following conditions:
|