APUE-文件和目录(二)函数access,mask,chmod和粘着位
4.7 函數(shù)access和faccessat
當(dāng)一個(gè)進(jìn)程使用了設(shè)置用戶(hù)ID和設(shè)置組ID作為另一個(gè)用戶(hù)(或者組)運(yùn)行時(shí),這時(shí)候有效用戶(hù)(組)ID和實(shí)際用戶(hù)(組)ID不一樣,但進(jìn)程仍然希望測(cè)試實(shí)際用戶(hù)(組)ID的訪(fǎng)問(wèn)能力。這時(shí)候就可以使用access和faccessat。測(cè)試步驟同4.5節(jié)一樣,但將有效改為實(shí)際。
#include <unistd.h> int access(const char *pathname,int mode); int faccessat(int fd,const char*pathname,int mode,int flag); //兩個(gè)函數(shù)的返回值:若成功煩怒I0;若出錯(cuò),返回-1其中,如果測(cè)試文件是否已經(jīng)存在,mode就為F_OK;否則mode是圖4-7中所列常量的按位或。
flag參數(shù)可以用于改變faccessat的行為,如果flag設(shè)置為AT_EACCESS,訪(fǎng)問(wèn)檢查用的是調(diào)用進(jìn)程的有效用戶(hù)ID和有效組ID,而不是實(shí)際用戶(hù)ID和實(shí)際組ID。
4.8 函數(shù)umask
umask函數(shù)為進(jìn)程設(shè)置文件模式創(chuàng)建屏蔽字,并返回之前的值。
#include <sys/stat.h> mode_t umask(mode_t cmask);其中,參數(shù)cmask是由圖4-6中列出的9個(gè)常量中的若干個(gè)按位"或“構(gòu)成的。
在文件模式創(chuàng)建屏蔽字中為1的位,在文件mode中的相應(yīng)位一定被關(guān)閉。
看下面的例子:
首先將屏蔽位設(shè)為0,然后創(chuàng)建一個(gè)文件,發(fā)現(xiàn)默認(rèn)創(chuàng)建的文件mode為u=rw,g=rw,o=rw(666)
harlan@DESKTOP-KU8C3K5:/github/APUE/chapter_4/myexamples$ umask 0 harlan@DESKTOP-KU8C3K5:/github/APUE/chapter_4/myexamples$ umask -S u=rwx,g=rwx,o=rwx harlan@DESKTOP-KU8C3K5:/github/APUE/chapter_4/myexamples$ touch test.txt harlan@DESKTOP-KU8C3K5:/github/APUE/chapter_4/myexamples$ ll test.txt -rw-rw-rw- 1 harlan harlan 0 6月 5 21:02 test.txt下面更新文件模式屏蔽字,并創(chuàng)建文件:
harlan@DESKTOP-KU8C3K5:/github/APUE/chapter_4/myexamples$ umask 027 harlan@DESKTOP-KU8C3K5:/github/APUE/chapter_4/myexamples$ umask -S u=rwx,g=rx,o= harlan@DESKTOP-KU8C3K5:/github/APUE/chapter_4/myexamples$ touch test2.txt harlan@DESKTOP-KU8C3K5:/github/APUE/chapter_4/myexamples$ ll test2.txt -rw-r----- 1 harlan harlan 0 6月 5 21:05 test2.txt因?yàn)間roup的x和other的rwx被屏蔽掉了,因此得到上面的結(jié)果。
umask值表示為8進(jìn)制數(shù),一位代表一種要屏蔽的權(quán)限,見(jiàn)下圖所示:
注意: 用數(shù)字和符號(hào)表示文件模式屏蔽字的不同,數(shù)字中的1表示的是要屏蔽的權(quán)限,而符號(hào)中顯示的是支持的權(quán)限。
4.9 函數(shù)chmod
chmod使得我們可以更改現(xiàn)有文件的訪(fǎng)問(wèn)權(quán)限。
#include <sys/stat.h> int chmod(const char*pathname,mode_t name); 成功返回0;出錯(cuò)返回-1為了改變一個(gè)文件的權(quán)限位,進(jìn)程的有效用戶(hù)ID必須等于文件的所有者ID,或者該用戶(hù)必須具有超級(jí)用戶(hù)權(quán)限。
疑問(wèn):可讀可寫(xiě)可執(zhí)行權(quán)限和chmod有關(guān)系么?
答:沒(méi)有任何關(guān)系。
看下面一個(gè)簡(jiǎn)單的例子,創(chuàng)建一個(gè)其他用戶(hù)可讀可寫(xiě)可執(zhí)行的文件所有者為root的文件:
harlan@DESKTOP-KU8C3K5:/github/APUE/chapter_4/myexamples$ ll chmod.txt -rw-r--rwx 1 root root 0 6月 5 21:16 chmod.txt在harlan用戶(hù)下創(chuàng)建下面的程序:
#include <fcntl.h> #include <stdio.h> int main(void) {struct stat statbuf;if(stat("chmod.txt",&statbuf)<0)printf("stat error!\n");int rv = chmod("chmod.txt",statbuf.st_mode & ~S_IRWXO);//remove the other's read write and executeif(rv < 0){printf("chmod error!\n");}return 0; }上面的程序嘗試在harlan用戶(hù)下來(lái)修改chmod.txt文件的權(quán)限位,harlan用戶(hù)對(duì)chmod.txt是可讀可寫(xiě)可執(zhí)行的。但是它不能修改此文件的權(quán)限位,結(jié)果打印:
harlan@DESKTOP-KU8C3K5:/github/APUE/chapter_4/myexamples$ ./a.out chmod error!參數(shù)mode是圖4-11中所示的常量的按位或:
注意:chmod函數(shù)修改的是i節(jié)點(diǎn)最近一次被更改的時(shí)間,而并不是最后修改文件內(nèi)容的時(shí)間。
注意:如果新文件的組ID不等于進(jìn)程的有效組ID或者進(jìn)程附屬組ID中的一個(gè),并且進(jìn)程沒(méi)有超級(jí)用戶(hù)權(quán)限,那么設(shè)置組ID位會(huì)被自動(dòng)關(guān)閉。在linux3.2.0中,如果沒(méi)有超級(jí)用戶(hù)權(quán)限的進(jìn)程寫(xiě)一個(gè)文件,則設(shè)置用戶(hù)ID位和設(shè)置組ID位會(huì)被自動(dòng)清除。看下面的例子:
對(duì)于文件chmod.txt,我們同時(shí)設(shè)置了設(shè)置用戶(hù)ID和設(shè)置組ID,
harlan@DESKTOP-KU8C3K5:/github/APUE/chapter_4/myexamples$ ll chmod.txt -rwSr-srwx 1 root root 4 6月 5 22:16 chmod.txt寫(xiě)一段代碼來(lái)用普通用戶(hù)權(quán)限寫(xiě)這個(gè)文件
#include <fcntl.h> #include <stdio.h>void PrintSetUserID(unsigned int st_mode) {if(st_mode&S_ISUID){printf("set-user-ID is 1.\n");}else{printf("set-user-ID is 0.\n");} }void PrintSetGroupID(unsigned int st_mode) {if(st_mode&S_ISGID){printf("set-group-ID is 1.\n");}else{printf("set-group-ID is 0.\n");} } void ClearSetUserID_SetGroupID() {struct stat statbuf;if(stat("chmod.txt",&statbuf)<0)printf("stat error!-");else{PrintSetUserID(statbuf.st_mode);PrintSetGroupID(statbuf.st_mode);}int fd = open("chmod.txt",O_RDWR);ssize_t num = write(fd,"test",4);printf("write num:%d\n",(int)num);if(stat("chmod.txt",&statbuf)<0)printf("stat error!--\n");else{PrintSetUserID(statbuf.st_mode);PrintSetGroupID(statbuf.st_mode);} } int main(void) { ClearSetUserID_SetGroupID(); return 0; }運(yùn)行結(jié)果:
harlan@DESKTOP-KU8C3K5:/github/APUE/chapter_4/myexamples$ ./a.out set-user-ID is 1. set-group-ID is 1. write num:4 set-user-ID is 0. set-group-ID is 0.4.10 粘著位
- 對(duì)于文件的粘著位,因?yàn)楝F(xiàn)今的UNIX系統(tǒng)大多都配置了虛擬存儲(chǔ)系統(tǒng)以及快速文件系統(tǒng),所以不再需要這個(gè)設(shè)置。
- 對(duì)于目錄的粘著位,如果你為一個(gè)目錄設(shè)置了粘著位,只有對(duì)該目錄具有寫(xiě)權(quán)限的用戶(hù)并且滿(mǎn)足下列條件之一,才能刪除或重命名該目錄下的文件:
看下面的例子:
harlan@DESKTOP-KU8C3K5:/github/APUE/chapter_4/myexamples$ mkdir dir harlan@DESKTOP-KU8C3K5:/github/APUE/chapter_4/myexamples$ chmod 777 dir harlan@DESKTOP-KU8C3K5:/github/APUE/chapter_4/myexamples$ ll ... drwxrwsrwx 2 harlan harlan 0 6月 5 22:47 dir ... harlan@DESKTOP-KU8C3K5:/github/APUE/chapter_4/myexamples$ chmod o+t dir harlan@DESKTOP-KU8C3K5:/github/APUE/chapter_4/myexamples$ ll ... drwxrwsrwt 2 harlan harlan 0 6月 5 22:47 dir ...疑問(wèn):粘著位和其他寫(xiě)是否同時(shí)存在?見(jiàn)下面的代碼:
#include <fcntl.h> #include <stdio.h> void main() { struct stat statbuf; if(stat("dir",&statbuf)) printf("stat error!\n"); if(statbuf.st_mode & S_ISVTX) { printf("sticky bit is set!\n"); } if(statbuf.st_mode & S_IXOTH) { printf("other execute bit is set!\n"); } }輸出結(jié)果為:
harlan@DESKTOP-KU8C3K5:/github/APUE/chapter_4/myexamples$ ./a.out sticky bit is set! other execute bit is set!可見(jiàn)是可以同時(shí)存在的。同時(shí)存在和只存在黏著位的顯示有什么區(qū)別呢?見(jiàn)下面的例子:
harlan@DESKTOP-KU8C3K5:/github/APUE/chapter_4/myexamples$ chmod 776 dir drwxrwsrw- 2 harlan harlan 0 6月 5 22:47 dir harlan@DESKTOP-KU8C3K5:/github/APUE/chapter_4/myexamples$ chmod o+t dir drwxrwsrwT 2 harlan harlan 0 6月 5 22:47 dir可見(jiàn)如果只有粘著位其它的第三位為大寫(xiě)的T,如果是小寫(xiě)表示粘著位+可執(zhí)行。
/var/tmp 目錄設(shè)置了粘著位+任意用戶(hù)的可讀可寫(xiě)可執(zhí)行
harlan@DESKTOP-KU8C3K5:/var$ ll 總用量 12 drwxr-xr-x 2 root root 0 4月 11 2014 backups drwxr-xr-x 2 root root 0 3月 30 14:52 cache drwxrwxrwt 2 root root 0 3月 30 14:52 crash drwxr-xr-x 2 root root 0 4月 27 22:17 lib drwxrwsr-x 2 root staff 0 4月 11 2014 local lrwxrwxrwx 1 root root 9 3月 30 14:50 lock -> /run/lock drwxrwxr-x 2 root syslog 0 5月 1 21:38 log drwxrwsr-x 2 root mail 0 3月 30 14:50 mail drwxr-xr-x 2 root root 0 3月 30 14:50 opt lrwxrwxrwx 1 root root 4 3月 30 14:50 run -> /run drwxr-xr-x 2 root root 0 3月 30 14:50 spool drwxrwxrwt 2 root root 0 6月 5 22:28 tmp我們用root用戶(hù)在tmp目錄下面創(chuàng)建一個(gè)文件:
root@DESKTOP-KU8C3K5:/var/tmp# ll 總用量 4 drwxrwxrwt 2 root root 0 6月 5 22:28 ./ drwxr-xr-x 2 root root 0 3月 30 14:53 ../ -rw-r--r-- 1 root root 0 6月 5 22:28 test.txt嘗試在harlan用戶(hù)下刪除:
harlan@DESKTOP-KU8C3K5:/var/tmp$ rm test.txt rm:是否刪除有寫(xiě)保護(hù)的普通空文件 "test.txt"? y rm: 無(wú)法刪除"test.txt": 不允許的操作雖然harlan用戶(hù)對(duì)這個(gè)目錄具有寫(xiě)權(quán)限,但因?yàn)樗谀夸浽O(shè)置了粘著位,并且不滿(mǎn)足上述任意三個(gè)條件之一,因此不訥訥個(gè)刪除文件。
作者: HarlanC
博客地址: http://www.cnblogs.com/harlanc/
個(gè)人博客: http://www.harlancn.me/
本文版權(quán)歸作者和博客園共有,歡迎轉(zhuǎn)載,但未經(jīng)作者同意必須保留此段聲明,且在文章頁(yè)面明顯位置給出, 原文鏈接
如果覺(jué)的博主寫(xiě)的可以,收到您的贊會(huì)是很大的動(dòng)力,如果您覺(jué)的不好,您可以投反對(duì)票,但麻煩您留言寫(xiě)下問(wèn)題在哪里,這樣才能共同進(jìn)步。謝謝!
總結(jié)
以上是生活随笔為你收集整理的APUE-文件和目录(二)函数access,mask,chmod和粘着位的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。
- 上一篇: 利用gulp对项目html,js,css
- 下一篇: iOS11和机器学习CoreML库