Chapter 3 檔案I/O

來源:互聯網
上載者:User

1.檔案描述符

檔案描述符是一個非負整數,當開啟一個現有檔案或建立一個新檔案時候,核心向進程返回一個檔案描述符。Unix系統shell使用檔案描述符0與進程的標準輸入相關聯,檔案描述符1與進程的標準輸出相關聯,檔案描述符2與進程的標準出錯相關聯,在POSIX標準中,幻數0、1、2應當替換為符號常量STDIN_FILENO、STDOUT_FILENO和STDERR_FILENO,另外檔案描述符變化範圍:0~OPEN_MAX,現在很多系統將OPEN_MAX置為63

 

 

2.open函數

調要open函數可以開啟或建立一個檔案。

函數原型

#include <fcnt1.h>int open(const char *pathname,int oflag,/*mode_t made*/);

      pathname是需要開啟的檔案;

      oflag參數用來說明此函數的多個選項。用 O_RDONLY(唯讀),O_WRONLY(唯寫),O_REWR(讀寫)。這三個常量必須指定,有且只能指定一個,並且和下列多個常量進行或運算構成:

      O_APPEND        每次寫時都追加到檔案的尾端

      O_CREAT          若檔案不存在則建立它,需要第三個參數為指定檔案的存取權限

      O_EXCL            若同時指定O_CREAT,而檔案存在則會出錯,用此則可以測試檔案是否存在,若不存在則建立這個檔案

      O_TRUNC         如果此檔案不存在,而且為唯寫或讀寫成功開啟,則將其長度截短為0

      O_NOCTTY        若pathname指的是終端裝置,則不將該裝置分配為此進程的控制端

      O_NONBLOCK    非阻塞模式

      這些常量是可選擇的

 

 

3.create函數

函數原型

#include <fcnt1.h>int create(const char *pathname,mode_t mode);

此函數等效於

open(pathname,O_WRONLY | O_CREAT | O_TRUNC,mode);

 

 

4.close函數

函數原型

#include<fcnt1.h>int close (int filedes);  //傳回值若成功返回0不成功返回-1

 

 

5.lseek函數

可以用lseek顯式地為一個開啟的檔案設定其位移量。

函數原型

#include<unistd.h>off_t lseek(int fileds,off_t offset,int whence);//若成功則返回新的檔案位移量,若出錯則返回-1

參數whence可以置為下值

SEEK_SET,則將該檔案的位移量設定為距檔案開始出offset個位元組

SEEK_CUR,則將該檔案的位移量設定為其當前值加offset,offset可正可負

SEEK_END,則將該檔案的位移量設定為檔案長度加offset,offset可正可負

若lseek成功執行,則返回新的檔案位移量,為此可以用下列方式確定開啟檔案的當前位移量

off_t currpos;currpos = lseek(fd,0,SEEK_CUR);

這種方法也可以用來確定所涉及的檔案是否可以設定位移量,如果檔案描述符引用的是一個管道、FIFO進而網路通訊端,則lseek返回-1,並將errorn設定為ESPIPE。

注意:

1).lseek僅將當前的檔案位移量記錄在核心中,它並不引起任何I/O操作

2).檔案位移量可以大於檔案的當前長度,在這種情況下,對該檔案下一次的寫將加長該檔案,並在檔案構成一個空洞,這一點是允許的。位於檔案中但沒有寫過的位元組都被設為 0

3).檔案中的空洞並不要求在磁碟上佔用儲存區。

 

 

6.read函數

從開啟的檔案中讀資料到buf

#include <unistd.h>ssize_t read(int filedes,void *buf,size_t nbytes);

傳回值:若成功則返回讀到的位元組數,若已到檔案結尾則返回0,若出錯返回-1;

 

 

7.write函數

調用write函數向開啟的檔案寫資料

#include <unistd.h>ssize_t write(int filedes,const void *buf,size_t nbytes);

傳回值:若成功則返回位元組數,若出錯返回-1

註:write出錯的一個常見原因是:磁碟已寫滿,或者超過了一個給定進程的檔案長度限制

 

 

8.dup和dup2函數

這兩個函數都用來複製一個現存的檔案描述符

#include <unistd.h> int dup(int filedes);    int dup2(int filedes,int filedes2);   //filedes2參數指定新描述符的數值。如果filedes2已經開啟,則先關閉。

傳回值:若成功返回新的檔案描述符,若出錯則返回-1

調用

dup(filedes);

等效於

fcntl(filedes, F_DUPFD, 0);

而調用

dup2(filedes, filedes2);

等效於

close(filedes2);fcntl(filedes, F_DUPFD, filedes2);

區別

1).dup2是一個原子操作,而close及fcntl則包括兩個函數調用,有可能在close和fcntl之間插入執行訊號捕獲函數

2).dup2和fcntl有某些不同errorno

 

9.sync,fsync ,fdatasync函數

為瞭解決延遲寫的問題,保證磁碟上實際檔案系統和緩衝區快取中內容的一致性。

  #include <unistd.h> int fsync(int filedes);           // 只對由檔案描述符filedes指定的單一檔案其作用,並且等待寫磁碟操作結束 int fdatesync(int filedes);       //功能和fsync差不多,但它還同步更新檔案的屬性 void sync(void);                  //將所有修改過的快緩衝區排入寫隊列,然後返回,它並不等待實際寫磁碟操作結束

 

10.fcntl函數

可以改變已開啟的檔案性質

#include <fcnt1.h> int fcnt1(int filedes,int cmd, /* int arg *);

第三個參數總是一個整數,與上面所示函數原型中的注釋部分相對應。但是在作為記錄鎖用時,第三個參數則是指向一個結構的指標。

fcntl函數有5種功能:

1).複製一個現有的描述符(cmd=F_DUPFD).
2).獲得/設定檔案描述符標記(cmd=F_GETFD或F_SETFD).
3).獲得/設定檔案狀態標記(cmd=F_GETFL或F_SETFL).
4).獲得/設定非同步I/O所有權(cmd=F_GETOWN或F_SETOWN).
5).獲得/設定記錄鎖(cmd=F_GETLK,F_SETLK或F_SETLKW).

 

11.ioctl函數

ioctl函數是I/O操作的雜物箱,完成其他函數都無法完成的操作

#include <unistd.h>          /*System V*/#include <sys/ioctl.h>       /*BSD and Linux*/#include <stropts.h>         /*XSI STREAMS*/int ioctl(int filedes, int request, . . .);

詳見APUE第十八章

12./dev/fd

   比較新的unix/linux系統都提供名為/dev/fd的目錄,其中有檔案0、1、2等檔案,開啟這些檔案,相當於複製這些檔案描述符

例如:

fd=open("/dev/fd/0",mode);

等價於

fd=dup(0);

檔案描述符fd和0將共用一個檔案表記錄項。

 

13.檔案分享權限設定

檔案分享權限設定是指不同進程間開啟檔案的共用。核心通過三種資料結構來表示開啟的檔案,

1).每個進程有個進程表項,表中是開啟檔案的描述符向量。每個向量包含了檔案描述符標記和一個指向檔案表項的指標;

2).核心為所有開啟的檔案維護一個檔案表,每個檔案表項包括了a,檔案狀態標記,如讀、寫、添加、非阻塞等b,當前的檔案位移量c,指向檔案v-node表項的指標;

3).每個開啟檔案或裝置都有一個v-node結構   ,包含檔案類型和指向操作檔案的函數的指標。

 

當兩個以上獨立進程開啟同一個檔案實現檔案分享權限設定時,核心維護不同的檔案表項,就是兩個以上進程表項中的檔案表項指標指向不同的檔案表項,而不同的檔案表項中的v-node指標指向同一個v-node而實現檔案分享權限設定。由於每個進程有自己的開啟檔案表項,所以有自己的檔案開啟狀態以及檔案位移量。

 

需要注意的是Linux沒有將相關資料分為i節點和v節點,而是採用了一個獨立於檔案系統的i節點(通用i-node結構)和一個依賴於檔案系統的i節點

 

 

 

 

 

 

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.