[轉]Linux C函數之文件及目錄函數(2)


http://apps.hi.baidu.com/share/detail/51225486

link: 建立文件硬連接 頭文件: unistd.h 函數定義: int link(const char *oldpath, const char *newpath); 說明: link()以參數newpath指定的名稱來建立一個新的連接(硬連接)到參數oldpath所指定的已存在文件. 如果參數newpath指定的名稱為一已存在的文件則不會建立連接. 成功則返回0, 失敗返回-1, 錯誤原因存於errno. 錯誤代碼:    EXDEV   參數oldpath與newpath不是建立在同一文件系統    EPERM   參數oldpath與newpath所指的文件系統不支持硬連接    EROFS   文件存在於只讀文件系統內    EFAULT 參數oldpath或newpath指針超出可存取內存空間    ENAMETOLLONG   參數oldpath或newpath太長    ENOMEM 核心內存不足    EEXIST 參數newpath所指的文件名已存在    EMLINK 參數oldpath所指的文件已達最大連接數目    ELOOP   參數pathname有過多符號連接問題    ENOSPC 文件系統的剩余空間不足    EIO     I/O存取錯誤 附加說明: link()所建立的硬連接無法跨越不同文件系統, 如果需要請改用symlink().

lstat: 由文件描述詞取得文件狀態 頭文件: sys/stat.h unistd.h 函數定義: int lstat(const char *file_name, struct stat *buf); 說明: lstat()與stat()作用完全相同, 都是取得參數file_name所指的文件狀態, 其差別在於, 當文件為符號連接時, lstat()會返回該link本身的狀態. 詳細內容請參考stat(). 執行成功則返回0, 失敗返回-1, 錯誤代碼存於errno.

nftw: 遍歷目錄樹 頭文件: ftw.h 函數定義: int nftw(const char *dir, int (*fn)(const char *file, const struct stat *sb, int flag, struct FTW *s), depth, int flags); 說明: nftw()與ftw()很像, 都是從參數dir指定的目錄開始, 往下一層層地遞歸式遍歷子目錄. 每進入一個目錄, 便會調用參數*fn定義的函數來處理. nftw()會傳四個參數給fn(), 第一個參數*file指向當時所在的目錄路徑, 第二個參數是*sb, 為stat結構指針(結構定義請參考stat()), 第三個參數為旗標, 有以下幾種可能:    FTW_F    一般文件    FTW_D    目錄    FTW_DNR 不可讀取的目錄. 此目錄以下將不被遍歷    FTW_SL   符號連接    FTW_NS   無法取得stat結構數據, 有可能是權限問題    FTW_DP   目錄, 而且其子目錄都已被遍歷過了.    FTW_SLN 符號連接, 但連接不存在文件 fn()的第四個參數是FTW結構, 定義如下: struct FTW{ int base; int level; } level代表遍歷當時的深度, nftw()第三個參數depth代表nftw()在進行遍歷目錄時可同時打開的文件數. ftw()在遍歷時每一層目錄至少需要一個文件描述詞, 如果遍歷時用完了depth所給予的限制數目, 整個遍歷將因不斷地關閉文件和打開文件操作而顯得緩慢. nftw()最后一個參數flags用來指定遍歷時的動作, 可以指定下列的操作或用OR組合:    FTW_CHDIR   在讀目錄之前用chdir()移到此目錄    FTW_DEPTH   執行深度優先搜索. 在遍歷此目錄前先將所有子目錄遍歷完    FTW_MOUNT   遍歷時不要跨越到其他文件系統    FTW_PHYS    不要遍歷符號連接的目錄. 預設會遍歷符號連接目錄 如果要結束ftw()的遍歷, fn()只需返回一非零值即可, 此值同時也會是ftw()的返回值, 否則ftw()會試着走完所有的目錄, 然后返回0. 遍歷中斷則返回fn()函數的返回值, 全部遍歷完則返回0. 如有錯誤發生則返回-1. 附加說明: 由於ftw()會動態配置內存使用, 請使用正常方式(fn函數返回非0值)來中斷遍歷, 不要在fn函數中使用longjmp().

opendir: 打開目錄 頭文件: sys/types.h dirent.h 函數定義: DIR *opendir(const char *name); 說明: opendir()用來打開參數name指定的目錄, 並返回DIR*形態的目錄流, 和open()類似, 接下來對目錄的讀取和搜索都要使用此返回值. 成功則返回DIR*型態的目錄流, 打開失敗則返回NULL. 錯誤代碼:    EACCESS 權限不足    EMFILE   已達到進程可同時打開的文件數上限    ENFILE   已達到系統可同時打開的文件數上限    ENOTDIR 參數name非真正的目錄    ENOENT   參數name指定的目錄不存在, 或是參數name為一空字符串    ENOMEM   核心內存不足

readdir: 讀取目錄 頭文件: sys/types.h dirent.h 定義函數: struct dirent *readdir(DIR *dir); 說明: readdir()返回參數dir目錄流的下個目錄進入點. 結構dirent定義如下: struct dirent{ ino_t d_ino; ff_t d_off; signed short int d_reclen; unsigned char d_type; char d_name[256]; }; d_ino    此目錄進入點的inode d_off    目錄文件開頭至此目錄進入點的位移 d_reclen _name的長度, 不包含NULL字符 d_type   d_name所指的文件類型 d_name   文件名 成功則返回下個目錄進入點, 有錯誤發生或讀取到目錄文件尾則返回NULL. EBADF參數dir為無效的目錄流. 應用舉例: /* 讀取/etc/rc.d目錄文件結構, 然后顯示目錄下的文件 */ #include <stdio.h> #include <unistd.h> #include <sys/types.h> #include <dirent.h> int main(void) { DIR *dir; struct dirent *ptr; int i; dir = opendir("/etc/rc.d"); while((ptr = readdir(dir)) != NULL) {    printf("d_name: %s\n", ptr->d_name); } return 0; } 運行結果: d_name: rc1.d d_name: rc3.d d_name: rc d_name: rc2.d d_name: rc0.d d_name: rc.sysinit d_name: .. d_name: rc6.d d_name: rc4.d d_name: init.d d_name: rc.local d_name: rc5.d d_name: .

readlink: 取得符號連接所指的文件 頭文件: unistd.h 函數定義: int readlink(const char *path, char *buf, size_t bufsize); 說明: readlink()會將參數path的符號連接內容存到參數buf所指的內存空間, 返回的內容不是以NULL作字符串結尾, 但會將字符串的字符數返回. 若參數bufsiz小於符號連接的內容長度, 過長的內容會被截斷. 執行成功則傳符號連接所指的文件路徑字符串, 失敗則返回-1, 錯誤代碼存於errno. 錯誤代碼:    EACCESS 取文件時被拒絕, 權限不夠    EINVAL   參數bufsiz為負數    EIO      I/O存取錯誤    ELOOP    欲打開的文件有過多符號連接問題    ENAMETOOLONG 參數path的路徑名稱太長    ENOENT   參數path所指定的文件不存在    ENOMEM   核心內存不足    ENOTDIR 參數path路徑中的目錄存在但卻非真正的目錄

realpath: 將相對目錄路徑轉換成絕對路徑 頭文件: limits.h stdlib.h 函數定義: char *realpath(const char *path, char *resolved_path); 說明: realpath()用來將參數path所指的相對路徑轉換成絕對路徑存於參數resolved_path所指的字符串數組中. 如果轉換成功則返回指向resolved_path的指針. 失敗返回NULL, 錯誤代碼存於errno.

remove: 刪除文件或目錄 頭文件: stdio.h 函數定義: int remove(const char *pathname); 說明: remove()會刪除參數pathname指定的文件. 如果參數pathname為一文件, 則調用unlink()處理, 若參數pathname為一目錄, 則調用rmdir()來處理. 請參考unlink()與rmdir(). 成功則返回0, 失敗則返回-1, 錯誤原因存於errno. 錯誤代碼:    EROFS    欲寫入的文件存在於只讀文件系統內    EFAULT   參數pathname指針超出可存取內存空間    ENAMETOOLONG   參數pathname太長    ENOMEM   核心內存不足    ELOOP    參數pathname有過多符號連接問題    EIO      I/O存取錯誤.

rename: 更改文件名或位置 頭文件: stdio.h 函數定義: int rename(const char *oldpath, const char *newpath); 說明: rename()會將參數oldpath所指定的文件名稱改為參數newpath所指的文件名稱. 若newpath所指定的文件已存在, 則會被刪除. 執行成功則返回0, 失敗返回-1, 錯誤原因存於errno.

rewinddir: 將讀取目錄的位置設為開頭位置 頭文件: sys/types.h dirent.h 函數定義: void rewinddir(DIR *dir); 說明: rewinddir()用來設置參數dir目錄流目前的讀取位置為原來開頭的讀取位置. EBADF表示dir為無效的目錄流.

scandir: 讀取特定的目錄數據 頭文件: dirent.h 函數定義: int scandir(const char *dir, struct dirent ***namelist, int (*select)(const struct dirent *), int (*compar)(const struct dirent**, const struct dirent**)); 說明: scandir()會掃描參數dir指定的目錄文件, 經由參數select指定的函數來挑選目錄結構至參數namelist數組中, 最后在調用參數compar指定的函數來排序namelist數組中的目錄數據. 每次從目錄文件中讀取一個目錄結構后便將此結構傳給參數select所指的函數, select函數若不想要將此目錄機構復制到namelist數組就返回0, 若select為空指針則代表選擇所有的目錄結構. scandir()會調用qsort()來排序數據, 參數compar則為qsort()的參數, 若是要排列目錄名稱字母則可使用alphasort(). 結構dirent定義請參考readdir(). 成功則返回復制到namelist數組中的數據結構數目, 有錯誤發生則返回-1. ENOMEM表示核心內存不足. 應用舉例: /* 讀取/目錄下文件名長度大於5的目錄結構 */ #include <stdio.h> #include <string.h> #include <dirent.h> int select(const struct dirent *dir) { if(strlen(dir->d_name) > 5)    return 1; else    return 0; } int main(void) { struct dirent **namelist; int i, total; total = scandir("/", &namelist, select, 0); if(total < 0)    perror("scandir"); else {    for(i = 0; i < total; i++)    {     printf("%s\n", namelist[i]->d_name);     printf("total = %d\n", total);    } } return 0; } 運行結果: selinux total = 3 .autofsck total = 3 lost+found total = 3

seekdir: 設置下回讀取目錄的位置 頭文件: dirent.h 函數定義: void seekdir(DIR *dir, off_t offset); 說明: seekdir()用來設置參數dir目錄流目前的讀取位置, 在調用readdir()時便從此新位置開始讀取. 參數offset代表距離目錄文件開頭的偏移量. EBADF表示參數dir為無效路徑.

stat: 取得文件狀態 頭文件: sys/stat.h unistd.h 函數定義: int stat(const char *file_name, struct stat *buf); 說明: stat()用來將參數file_name所指的文件狀態, 復制到參數buf所指的結構中. 下面是struct stat內各參數的說明: struct stat { dev_t   st_dev;      /* device */ ino_t   st_ino;      /* inode */ mode_t st_mode;     /* protection */ nlink_t   st_nlink; /* number of hard links */ uid_t    st_uid;     /* user ID of owner */ gid_t    st_gid;     /* group ID of owner */ dev_t    st_rdev;    /* device type */ off_t     st_size;   /* total size, in bytes */ unsigned long st_blksize; /* blocksize for filesystem I/O */ unsigned long st_blocks; /* number of blocks allocated */ time_t   st_atime;   /* time of lastaccess */ time_t   st_mtime;   /* time of last modification */ time_t   st_ctime;   /* time of last change */ }; st_dev    文件的設備編號 st_ino    文件的i-node st_mode   文件的類型和存取的權限 st_nlink 連到該文件的硬連接數目, 剛建立的文件值為1 st_uid    文件所有者的用戶識別碼 st_gid    文件所有者的組識別碼 st_rdev   若此文件為裝置設備文件, 則為其設備編號 st_size   文件大小, 以字節計算 st_blksize 文件系統的I/O緩沖區大小 st_blcoks 占用文件區塊的個數, 每一區塊大小為512個字節 st_atime 文件最近一次被存取或被執行的時間, 一般只有在用mknod, utime, read, write與tructate時改變 st_mtime 文件最后一次被修改的時間, 一般只有在用mknod, utime和write時才會改變 st_ctime i-node最近一次被更改的時間, 此參數會在文件所有者, 組, 權限被更改時更新 先前所描述的st_mode則定義了下列數種情況:    S_IFMT    0170000 文件類型的位遮罩    S_IFSOCK 0140000 scoket    S_IFLNK   0120000 符號連接    S_IFREG   0100000 一般文件    S_IFBLK   0060000 區塊裝置    S_IFDIR   0040000 目錄    S_IFCHR   0020000 字符裝置    S_IFIFO   0010000 先進先出    S_ISUID     04000 文件的(set user-id on execution)位    S_ISGID     02000 文件的(set group-id on execution)位    S_ISVTX     01000 文件的sticky位    S_IRUSR(S_IREAD)   00400 文件所有者具可讀取權限    S_IWUSR(S_IWRITE) 00200 文件所有者具可寫入權限    S_IXUSR(S_IEXEC)   00100 文件所有者具可執行權限    S_IRGRP     00040 用戶組具可讀取權限    S_IWGRP     00020 用戶組具可寫入權限    S_IXGRP     00010 用戶組具可執行權限    S_IROTH     00004 其他用戶具可讀取權限    S_IWOTH     00002 其他用戶具可寫入權限    S_IXOTH     00001 其他用戶具可執行權限 上述的文件類型在POSIX中定義了檢查這些類型的宏定義:    S_ISLNK (st_mode) 判斷是否為符號連接    S_ISREG   (st_mode) 是否為一般文件    S_ISDIR    (st_mode)是否為目錄    S_ISCHR   (st_mode)是否為字符裝置文件    S_ISBLK    (s3e)   是否為先進先出    S_ISSOCK (st_mode) 是否為socket 若一目錄具有sticky位(S_ISVTX), 則表示在此目錄下的文件只能被該文件所有者, 此目錄所有者或root來刪除或改名. 執行成功則返回0, 失敗返回-1, 錯誤代碼存於errno. 錯誤代碼:
   ENOENT   參數file_name指定的文件不存在    ENOTDIR 路徑中的目錄存在但卻非真正的目錄    ELOOP    欲打開的文件有過多符號連接問題, 上限為16符號連接    EFAULT   參數buf為無效指針, 指向無法存在的內存空間    EACCESS 存取文件時被拒絕    ENOMEM   核心內存不足    ENAMETOOLONG 參數file_name的路徑名稱太長 應用舉例: #include <stdio.h> #include <sys/stat.h> #include <unistd.h> int main(void) { struct stat buf; stat("/etc/passwd", &buf); printf("etc/passwd file size = %d\n", buf.st_size); return 0; } 運行結果: etc/passwd file size = 2529

symlink: 建立文件符號連接 頭文件: unistd.h 函數定義: int symlink(const char *oldpath, const char *newpath); 說明: symlink()以參數newpath指定的名稱來建立一個新的連接(符號連接)到參數oldpath所指定的已存在文件. 參數oldpath指定的文件不一定要存在, 如果參數newpath指定的名稱為一已存在的文件則不會建立連接. 成功則返回0, 失敗返回-1, 錯誤原因存於errno. 錯誤代碼:    EPERM   參數oldpath與newpath所指的文件系統不支持符號連接    EROFS   欲測試寫入權限的文件存在於只讀文件系統內    EFAULT 參數oldpath或newpath指針超出可存取內存空間    ENAMETOOLONG 參數oldpath或newpath太長    ENOMEM 核心內存不足    EEXIST 參數newpath所指的文件名已存在    EMLINK 參數oldpath所指的文件已達到最大連接數目    ELOOP   參數pathname有過多符號連接問題    ENOSPC 文件系統的剩余空間不足    EIO     I/O存取錯誤

telldir: 取得目錄流的讀取位置 頭文件: dirent.h 函數定義: off_t telldir(DIR *dir); 說明: telldir()返回參數dir目錄流目前的讀取位置. 此返回值代表距離目錄文件開頭的偏移量, 有錯誤發生時返回-1. EBADF表示參數dir為無效的目錄流.

truncate: 改變文件大小 頭文件: unistd.h 函數定義: int truncate(const char *path, off_t length); 說明: truncate()會將參數path指定的文件大小改為參數length指定的大小. 如果原來的文件大小比參數length大, 則超過的部分會被刪去. 執行成功則返回0, 失敗返回-1, 錯誤原因存於errno. 錯誤代碼:    EACCESS   參數path所指定的文件無法存取。    EROFS     欲寫入的文件存在於只讀文件系統內    EFAULT    參數path指針超出可存取內存空間    EINVAL    參數path包含不合法字符    ENAMETOOLONG 參數path太長    ENOTDIR   參數path路徑並非一目錄    EISDIR    參數path指向一目錄    ETXTBUSY 參數path所指的文件為共享程序, 而且正被執行中    ELOOP     參數path’有過多符號連接問題    EIO       I/O存取錯誤

umask: 設置建立新文件時的權限遮罩 頭文件: sys/types.h sys/stat.h 函數定義: mode_t umask(mode_t mask); 說明: umask()會將系統umask值設成參數mask&0777后的值, 然后將先前的umask值返回. 在使用open()建立新文件時, 該參數mode並非真正建立文件的權限, 而是(mode&~umask)的權限值. 例如, 在建立文件時指定文件權限為0666, 通常umask值默認為022, 則該文件的真正權限則為0666&~022=0644, 也就是rw-r--r--. 此調用不會有錯誤值返回, 返回值為原先系統的umask值.

unlink: 刪除文件 頭文件: unistd.h 函數定義: int unlink(const char *pathname); 說明: unlink()會刪除參數pathname指定的文件. 如果該文件名為最后連接點, 但有其他進程打開了此文件, 則在所有關於此文件的文件描述詞皆關閉后才會刪除. 如果參數pathname為一符號連接, 則此連接會被刪除. 成功則返回0, 失敗返回-1, 錯誤原因存於errno. 錯誤代碼:    EROFS   文件存在於只讀文件系統內    EFAULT 參數pathname指針超出可存取內存空間    ENAMETOOLONG 參數pathname太長    ENOMEM 核心內存不足    ELOOP   參數pathname有過多符號連接問題    EIO     I/O存取錯誤

utime: 修改文件的存取時間和更改時間 頭文件: sys/types.h utime.h 函數定義: int utime(const char *filename, struct utimebuf *buf); 說明: utime()用來修改參數filename文件所屬的inode存取時間. 結構utimbuf定義如下: struct utimbuf{ time_t actime; time_t modtime; }; 如果參數buf為空指針(NULL), 則該文件的存取時間和更改時間全部會設為目前時間. 執行成功則返回0, 失敗返回-1, 錯誤代碼存於errno. 錯誤代碼:    EACCESS 存取文件時被拒絕, 權限不足    ENOENT   指定的文件不存在

utimes: 修改文件的存取時間和更改時間 頭文件: sys/types.h utime.h 函數定義: int utimes(char *filename, struct timeval *tvp); 說明: utimes()用來修改參數filename文件所屬的inode存取時間和修改時間, 結構timeval定義如下: struct timeval{ long tv_sec; long tv_usec; /* 微妙 */ }; 參數tvp指向兩個timeval結構空間, 和utime()使用的utimebuf結構比較, tvp.tc_sec則為utimbuf.actime, tvp.tv_sec為utimbuf.modtime. 執行成功則返回0. 失敗返回-1, 錯誤代碼存於errno. 錯誤代碼:    EACCESS 存取文件時被拒絕, 權限不足    ENOENT   指定的文件不存在


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM