#include <unistd.h> int access(const char *pathname, int mode); int faccessat(int fd, const char *pathname, int mode, int flag); /* 返回值:若成功,都返回 0;否则,都返回 -1 */
其中,如果要测试文件是否已经存在,mode 就为 F_OK;否则 mode 就是下表中的常量的按位或(这些常量均位于头文件 <unistd.h>):
mode | 说明 |
R_OK | 测试读权限 |
W_OK | 测试写权限 |
X_OK | 测试执行权限 |
faccessat 函数与 access 函数在下列两种情况下是相同的:
1、pathname 参数为绝对路径。
2、fd 参数为 AT_FDCWD,而 pathname 为相对路径。否则,faccessat 计算相对于打开目录(由 fd 指向)的 pathname。
flag 参数可以用于改变 faccessat 的行为,如果 flag 设置为 AT_EACCESS,那么访问检查用的将是进程的有效用户 ID 和有效组 ID,而非实际用户 ID 和实际组 ID。
下面是一个 access 函数示例:
#include <stdio.h> #include <stdlib.h> #include <unistd.h> #include <fcntl.h> int main(int argc, char *argv[]){ if(argc != 2){ printf("Usage: %s <pathname>\n", argv[0]); exit(1); } if(access(argv[1], R_OK) < 0) printf("access error for %s\n", argv[1]); else printf("read access OK\n"); if(open(argv[1], O_RDONLY) < 0) printf("open error for %s\n", argv[1]); else printf("open for reading OK\n"); exit(0); }
执行结果:
$ ls -l accessDemo.out -rwxr-xr-x. 1 lei root 7194 7月 2 00:16 accessDemo.out $ $ ./accessDemo.out accessDemo.out read access OK open for reading OK $ $ ls -l /etc/shadow -r--------. 1 root root 1297 10月 3 2016 /etc/shadow $ $ ./accessDemo.out /etc/shadow access error for /etc/shadow open error for /etc/shadow $ $ su # 成为超级用户 密码: # chown root accessDemo.out # 改变用户 ID 为 root # chmod u+s accessDemo.out # 打开设置用户 ID 位 # ls -l accessDemo.out -rwsr-xr-x. 1 root root 7194 7月 2 00:16 accessDemo.out # # exit # 恢复为原来用户 exit $ ./accessDemo.out /etc/shadow access error for /etc/shadow open for reading OK $
从运行结果可以看出,尽管打开了 /etc/shadow 的设置用户 ID 位(改变了进程的有效用户 ID),使 open 函数能打开该文件,但因为进程的实际用户 ID 并不等于有效 ID,所以 access 函数不能正常打开 /etc/shadow 文件。