chmod和fchmod函数用于保存stat.st_mode成员所代表的文件属性到磁盘。函数原型:
#include <sys/stat.h>
int chmod(const char *pathname, mode_t mode);
int fchmod(int filedes, mode_t mode);
返回值:若成功则返回0,若出错则返回-1
参数:
pathname 文件路径
filedes 文件标识符
mode 权限模式字,是一些权限常数的组合。
两个函数的作用相同,只是参数略有不同:chmod函数在指定的文件上进行操作,而fchmod函数则对以打开的文件进行操作。
因为涉及到文件访问权限的更改,所以调用这两个函数需要以下两个特权之一:
(1)进程的有效用户ID必须等于文件的所有者ID;
(2)进程必须具有超级用户权限(例如root)。
函数调用并不复杂,只是mode值的构造有点繁琐。参考《4.5 文件访问权限》和《4.4 S_ISUID、S_ISGID位与文件访问权限检查》。
注意:直接修改文件的stat.st_mode成员的值不会对文件产生实际影响,这些修改只是发生在内存,不会影响到文件在文件系统中的实际属性。需要调用这两个函数才能保存更改后的st_mode属性到磁盘。
实例 x.4.9.1.c
#include <fcntl.h>
#include <sys/stat.h>
#include <stdio.h>
#include <stdlib.h>
int main(int argc, char *argv[])
{
char pathname1[] = "/tmp/myfile1";
char pathname2[] = "/tmp/myfile2";
int filedes;
if (chmod(pathname1, (S_IRUSR | S_IWUSR)) == -1)
printf("chmod error for %s\n", pathname1);
if ((filedes = open(pathname2, (O_RDONLY | O_CREAT))) == -1)
printf("open error for %s\n", pathname2);
else if (fchmod(filedes, (S_IRUSR | S_IWUSR | S_IRGRP | S_IWGRP)) == -1)
printf("chmod error for %s\n", pathname2);
exit(0);
}
编译与执行:
[root@localhost unixc]# cc x.4.9.1.c
[root@localhost unixc]# echo "This is file1" > /tmp/myfile1
[root@localhost unixc]# echo "This is file2" > /tmp/myfile2
[root@localhost unixc]# ls -l /tmp/myfile1 /tmp/myfile2
-rw-r--r--. 1 root root 14 Nov 4 09:11 /tmp/myfile1
-rw-r--r--. 1 root root 14 Nov 4 09:11 /tmp/myfile2
[root@localhost unixc]# ./a.out
[root@localhost unixc]# ls -l /tmp/myfile1 /tmp/myfile2
-rw-------. 1 root root 14 Nov 4 09:11 /tmp/myfile1
-rw-rw----. 1 root root 14 Nov 4 09:11 /tmp/myfile2
[root@localhost unixc]#
本例为了简化直接用组合值来更改文件的属性而不理睬文件原来的属性。实际应用中,我们只是关心某个或某些权限位而无需知道其他的权限位状态。所以实际修改流程是这样:
1、先用stat函数取得文件原来的mode值;(参考《4.2 stat函数》)
2、以原来的mode值为基础做一些位运算;(参考《4.5 文件访问权限》和《4.4 S_ISUID、S_ISGID位与文件访问权限检查》)
3、用chmod或fchmod函数把新mode值保存到文件。(参考本例)