APUE-文件和目录(三)函数chown 和lchown

小编 2026-06-24 阅读:1700 评论:0
下面的几个chown函数可用于更改文件的用户ID和组ID。如果两个参数owner或group中的...

下面的几个chown函数可用于更改文件的用户ID和组ID。如果两个参数owner或group中的任意一个是-1,则对应的ID不变。

#include<unistd.h>int chown(const char *pathname,uid_t owner,gid_t group);int fchown(int fd,uid_t owner,gid_t group);int fchownat(int fd,const char *pathname,uid_t owner,gid_t group,int flag);int lchown(const char *pathname,uid_t owner,gid_t group);若成功返回0;若出错返回-1

在符号链接下,lchown和fchownat(设置了AT_SYMLINK_NOFOLLOW标志)更改符号链接本身的所有者,而不是该符号链接所指向的文件的所有者。

看下面的例子:

#include <unistd.h>#include <fcntl.h>#include <stdio.h>#include <errno.h>#define RWRWRW  (S_IRUSR |S_IWUSR|S_IRGRP|S_IWGRP|S_IROTH|S_IWOTH)//#define  _POSIX_CHOWN_RESTRICTED -1int main(void){    umask(0);//remove the mask    int rv = creat("source.txt",RWRWRW);//creat a file whose mode is -rw-rw-rw-    system("ln -s source.txt source_l.txt");//create a soft link to "source.txt" whose mode is lrwxrwxrwx    rv = lchown("source_l.txt",0,0);//update the user ID and group ID to 0    printf("rv:%d
",rv);    printf("errno:%d
",errno);    return 0;}

首先创建一个文件source.txt,然后创建一个符号链接source_1.txt,最后修改此符号链接的所有者和所属组。

harlan@DESKTOP-KU8C3K5:/github/APUE/chapter_4/myexamples$ gcc 4-11.charlan@DESKTOP-KU8C3K5:/github/APUE/chapter_4/myexamples$ ./a.out          rv:-1                                                                      errno:1                                                                    harlan@DESKTOP-KU8C3K5:/github/APUE/chapter_4/myexamples$ ll               总用量 29                                                                     -rw-r----- 1 harlan harlan  282  6月  5 22:52 4-10.c                        -rw-rw-r-- 1 harlan harlan  516  6月  6 21:51 4-11.c                        -rw-rw-r-- 1 harlan harlan  290  6月  1 22:13 4-7.c                         -rw-rw-r-- 1 harlan harlan 1168  6月  5 22:15 4-9.c                         -rw-rw-r-- 1 harlan harlan 4950  6月  1 09:07 4.c                           -rwxrwxr-x 1 harlan harlan 8788  6月  6 21:51 a.out                         lrwxrwxrwx 1 harlan harlan   10  6月  6 22:00 source_l.txt -> source.txt    -rw-rw-rw- 1 harlan harlan    0  6月  6 22:00 source.txt                    

在harlan用户下生成可执行文件,并执行,文件和符号链接生成成功,但是lchown执行失败,errno为1,表示“Operation not permitted”。

原因因为如下:

基于BSD的系统一直规定只有超级用户才能更改一个文件的所有者。

切换到root用户下执行,最后成功:

harlan@DESKTOP-KU8C3K5:/github/APUE/chapter_4/myexamples$ su密码:root@DESKTOP-KU8C3K5:/github/APUE/chapter_4/myexamples# rm source*root@DESKTOP-KU8C3K5:/github/APUE/chapter_4/myexamples# ./a.outrv:0errno:0root@DESKTOP-KU8C3K5:/github/APUE/chapter_4/myexamples# ll总用量 37drwxrwsr-t 2 harlan harlan    0  6月  6 22:03 ./drwxrwxrwx 2 harlan harlan    0  5月 18 21:16 ../-rw-r----- 1 harlan harlan  282  6月  5 22:52 4-10.c-rw-rw-r-- 1 harlan harlan  516  6月  6 21:51 4-11.c-rw-rw-r-- 1 harlan harlan  290  6月  1 22:13 4-7.c-rw-rw-r-- 1 harlan harlan 1168  6月  5 22:15 4-9.c-rw-rw-r-- 1 harlan harlan 4950  6月  1 09:07 4.c-rwxrwxr-x 1 harlan harlan 8788  6月  6 21:51 a.out*lrwxrwxrwx 1 root   root     10  6月  6 22:03 source_l.txt -> source.txt-rw-rw-rw- 1 root   harlan    0  6月  6 22:03 source.txt

接下来看一下怎么才能修改文件的组,满足如下条件就能够修改文件的组:
如果进程拥有此文件(有效用户ID等于该文件的用户ID),参数owner等于-1或文件的用户ID,并且参数group等于进程的有效组ID或进程的附属组ID之一,那么一个非超级用户进程可以更改该文件的组ID。
看下面的例子:

首先我们为当前用户harlan添加一个附属组ID,改之前:

harlan@DESKTOP-KU8C3K5:/github/APUE/chapter_4/myexamples$ id harlanuid=1000(harlan) gid=1000(harlan) group=1000(harlan)

改之后:

harlan@DESKTOP-KU8C3K5:/github/APUE/chapter_4/myexamples$ sudo usermod -G zexu harlan   [sudo] password for harlan:harlan@DESKTOP-KU8C3K5:/github/APUE/chapter_4/myexamples$ id harlanuid=1000(harlan) gid=1000(harlan) group=1000(harlan),1001(zexu)

为了是当前设置生效,执行如下命令:

harlan@DESKTOP-KU8C3K5:/github/APUE/chapter_4/myexamples$ newgrp zexu

最后看下面的代码:

#include <unistd.h>#include <fcntl.h>#include <stdio.h>#include <errno.h>#define RWRWRW  (S_IRUSR |S_IWUSR|S_IRGRP|S_IWGRP|S_IROTH|S_IWOTH)void test_chownGID(){    int rv = creat("testGID.txt",RWRWRW);    if(rv<0)    {        printf("create file error!
");    }    struct stat statbuf;    if(stat("testGID.txt",&statbuf)<0)    {        printf("stat error!
");    }    else    {        printf("The current user's group ID is %d
",statbuf.st_gid);    }    rv = chown("testGID.txt",-1,1001);    printf("rv:%d
",rv);    if(stat("testGID.txt",&statbuf)<0)    {        printf("stat error!
");    }    else    {        printf("After chown,the user's group ID is %d
",statbuf.st_gid);    }}int main(void){        test_chownGID();    return 0;}

执行结果:

harlan@DESKTOP-KU8C3K5:/github/APUE/chapter_4/myexamples$ ./a.outThe current user's group ID is 1000rv:0After chown,the user's group ID is 1001


作者:HarlanC

博客地址:http://www.cnblogs.com/harlanc/
个人博客: http://www.harlancn.me/
本文版权归作者和博客园共有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出, 原文链接

如果觉的博主写的可以,收到您的赞会是很大的动力,如果您觉的不好,您可以投反对票,但麻烦您留言写下问题在哪里,这样才能共同进步。谢谢!

版权声明

本文仅代表作者观点,不代表百度立场。
本文系作者授权百度百家发表,未经许可,不得转载。

热门文章
  • 机房智能化温湿度解决方式之POE供电以太网温湿度传感器

    机房智能化温湿度解决方式之POE供电以太网温湿度传感器
    机房智能化温湿度解决方式之POE供电以太网温湿度传感器 北京盈创力和电子科技有限公司 智能型TCP网口温湿度记录仪 北京IP网络温湿度记录仪厂家,北京盈创力和 北京智能型TCP网口温湿度记录仪IP网络温湿度记录仪是一种新型的基于TCP/IP协议双绞线以太网标准温湿度采集模块,利用它可以实现现场温度值、相对湿度值的采集,同时利用其自身的RJ45通信接口可以方便地和机房监控主机或交换机集线器进行联网。 工作于-40℃~85℃工业级带...
  • Sequential Monte Carlo Methods (SMC) 序列蒙特卡洛/粒子滤波/Bootstrap Filtering

    Sequential Monte Carlo Methods (SMC) 序列蒙特卡洛/粒子滤波/Bootstrap Filtering
    Problem Statement 我们考虑一个具有马尔可夫性质、非线性、非高斯的状态空间模型(State Space Model):对于一个时间序列上的观测结果{yt,t∈N}\\{ y_t , t \\in N \\}{yt​,t∈N},我们认为每个观测结果yty_tyt​的生成依赖于一个无法直接观察的隐变量xt∈{xt,t∈N}x_t \\in \\{x_t , t \\in N \\}xt​∈{xt​,t∈N},即:p(...
  • HTTP状态保持的原理

    HTTP状态保持的原理
    a)在用户登录之后,浏览器返回响应的时候会在响应中添加上cookieb)浏览器接收到cookie之后会自动保存c)当用户再次请求同一服务器中的其他网页的时候,浏览器会自动带上之前保存的cookied)服务接收到请求之后可以请 request 对象中取到cookie 判断当前用户是否登录  Http是无状态的,就是连接时数据互通,关闭后...
  • Hive 系统函数及示例

    Hive 系统函数及示例
    查看所有系统函数 show functions; 函数分类 内置函数【系统函数】 数学函数: floor、round、ceil、cos、log2等 字符串函数: length、reverse、trim、lower、get_json_object、repeat等 收集函数: size 转换函数: cast 日期函数: year、month、datediff、date、date_add等 条件函数: coalesce、case…w...
  • CSRF的原理和防范措施

    CSRF的原理和防范措施
    a)攻击原理:i.用户C访问正常网站A时进行登录,浏览器保存A的cookieii.用户C再访问攻击网站B,网站B上有某个隐藏的链接或者图片标签会自动请求网站A的URL地址,例如表单提交,传指定的参数iii.而攻击网站B在访问网站A的时候,浏览器会自动带上网站A的cookieiv.所以网站A在接收到请求之后可判断当前用户是登录状态,所以...
标签列表