精品国产人成在线_亚洲高清无码在线观看_国产在线视频国产永久2021_国产AV综合第一页一个的一区免费影院黑人_最近中文字幕MV高清在线视频

0
  • 聊天消息
  • 系統消息
  • 評論與回復
登錄后你可以
  • 下載海量資料
  • 學習在線課程
  • 觀看技術視頻
  • 寫文章/發帖/加入社區
會員中心
創作中心

完善資料讓更多小伙伴認識你,還能領取20積分哦,立即完善>

3天內不再提示

一文搞懂文件描述符

阿銘linux ? 來源:阿銘linux ? 2023-02-10 13:56 ? 次閱讀

Linux中的文件描述符

我們知道在Linux系統中一切皆可以看成是文件,文件又可分為:普通文件、目錄文件、鏈接文件和設備文件。在操作這些所謂的文件的時候,我們每操作一次就找一次名字,這會耗費大量的時間和效率。所以Linux中規定每一個文件對應一個索引,這樣要操作文件的時候,我們直接找到索引就可以對其進行操作了。

e699e7d8-a8db-11ed-bfe3-dac502259ad0.png

文件描述符(file descriptor)就是內核為了高效管理這些已經被打開的文件所創建的索引,其是一個非負整數(通常是小整數),用于指代被打開的文件,所有執行I/O操作的系統調用都通過文件描述符來實現。同時還規定系統剛剛啟動的時候,0是標準輸入,1是標準輸出,2是標準錯誤。這意味著如果此時去打開一個新的文件,它的文件描述符會是3,再打開一個文件文件描述符就是4......

Linux內核對所有打開的文件有一個文件描述符表格,里面存儲了每個文件描述符作為索引與一個打開文件相對應的關系,簡單理解就是下圖這樣一個數組,文件描述符(索引)就是文件描述符表這個數組的下標,數組的內容就是指向一個個打開的文件的指針。

上面只是簡單理解,實際上關于文件描述符,Linux內核維護了3個數據結構:

進程級的文件描述符表

系統級的打開文件描述符表

文件系統的i-node表

一個 Linux 進程啟動后,會在內核空間中創建一個 PCB 控制塊,PCB 內部有一個文件描述符表(File descriptor table),記錄著當前進程所有可用的文件描述符,也即當前進程所有打開的文件。進程級的描述符表的每一條記錄了單個進程所使用的文件描述符的相關信息,進程之間相互獨立,一個進程使用了文件描述符3,另一個進程也可以用3。除了進程級的文件描述符表,系統還需要維護另外兩張表:打開文件表、i-node 表。這兩張表存儲了每個打開文件的打開文件句柄(open file handle)。一個打開文件句柄存儲了與一個打開文件相關的全部信息。

系統級的打開文件描述符表:

當前文件偏移量(調用read()和write()時更新,或使用lseek()直接修改)

打開文件時的標識(open()的flags參數

文件訪問模式(如調用open()時所設置的只讀模式、只寫模式或讀寫模式)

信號驅動相關的設置

對該文件i-node對象的引用,即i-node 表指針

文件系統的i-node表:

文件類型(例如:常規文件、套接字或FIFO)和訪問權限

一個指針,指向該文件所持有的鎖列表

文件的各種屬性,包括文件大小以及與不同類型操作相關的時間戳

文件描述符、打開的文件句柄以及i-node之間的關系如下圖:

e6ac3960-a8db-11ed-bfe3-dac502259ad0.png

在進程 A 中,文件描述符 1 和 20 都指向了同一個打開文件表項,標號為 23(指向了打開文件表中下標為 23 的數組元素),這可能是通過調用 dup()、dup2()、fcntl() 或者對同一個文件多次調用了 open() 函數形成的。

進程 A 的文件描述符 2 和進程 B 的文件描述符 2 都指向了同一個文件,這可能是在調用 fork() 后出現的(即進程 A、B 是父子進程關系),或者是不同的進程獨自去調用 open() 函數打開了同一個文件,此時進程內部的描述符正好分配到與其他進程打開該文件的描述符一樣。

進程 A 的描述符 0 和進程 B 的描述符 3 分別指向不同的打開文件表項,但這些表項均指向 i-node 表的同一個條目(標號為 1976); 換言之,它們指向了同一個文件。 發生這種情況是因為每個進程各自對同一個文件發起了 open() 調用。 同一個進程兩次打開同一個文件,也會發生類似情況。

這就說明:同一個進程的不同文件描述符可以指向同一個文件; 不同進程可以擁有相同的文件描述符; 不同進程的同一個文件描述符可以指向不同的文件(一般也是這樣,除了 0、1、2 這三個特殊的文件); 不同進程的不同文件描述符也可以指向同一個文件。

Linux系統文件描述符示例

比如在Linux上用 vim test.py 打開一個文件,保持打開狀態,再新打開一個新的shell,輸入命令pidof vim 獲取vim進程的pid號,然后 ll /proc/$pid/fd 查看vim 進程所使用的文件描述符列表。

e6c40630-a8db-11ed-bfe3-dac502259ad0.png

/dev/pts是遠程登錄(telnet,ssh等)后創建的控制臺設備文件所在的目錄。 因為我是通過Xshell遠程登錄的,所以標準輸入0,標準輸出1,標準錯誤2的文件描述符都指向虛擬終端控制臺 /dev/pts/6 。 再看下面是新打開的 test.py 的文件描述符,竟然是4,說好的從3開始呢?

因為vim這種編輯器的原理是先打開源文件并拷貝,然后關閉源文件再打開自己的副本,修改完文件保存的時候直接將副本重命名覆蓋源文件。 所以打開源文件的時候用的文件描述符3,然后打開自己的副本是時候就該用文件描述符4了,然后關閉源文件,文件描述符3就被釋放了,我們查看的時候就只剩下了4,這里它指向的是vim創建的副本文件。

審核編輯:湯梓紅

聲明:本文內容及配圖由入駐作者撰寫或者入駐合作網站授權轉載。文章觀點僅代表作者本人,不代表電子發燒友網立場。文章及其配圖僅供工程師學習之用,如有內容侵權或者其他違規問題,請聯系本站處理。 舉報投訴
  • 內核
    +關注

    關注

    3

    文章

    1366

    瀏覽量

    40235
  • Linux
    +關注

    關注

    87

    文章

    11232

    瀏覽量

    208949
  • Linux系統
    +關注

    關注

    4

    文章

    592

    瀏覽量

    27357
  • 文件
    +關注

    關注

    1

    文章

    561

    瀏覽量

    24703
  • 描述符
    +關注

    關注

    0

    文章

    3

    瀏覽量

    6051

原文標題:一文搞懂文件描述符

文章出處:【微信號:aming_linux,微信公眾號:阿銘linux】歡迎添加關注!文章轉載請注明出處。

收藏 人收藏

    評論

    相關推薦

    USB描述符詳解

    對于實現USB功能的項目,不管是實現CDC,大容量存儲、HID等都必須使用實現USB標準描述符,從而實現USB枚舉過程。這里共享個USB描述符的詳解。
    發表于 06-12 14:46

    傳遞文件描述符是什么?

    我買了本書《Linux網絡編程》。 看到第11章高級套接字。有個例子,傳遞文件描述符。 其中,進程A根據用戶輸入的文件名打開
    發表于 05-07 02:18

    ARM中,Linux 文件描述符到底是什么?

    個 Linux 進程啟動后,會在內核空間中創建個 PCB 控制塊,PCB 內部有文件描述符表(File descriptor tab
    發表于 10-23 16:11

    usb標準描述符之技巧

    usb標準描述符之技巧 USB是個通用的總線,端口都是統的。但是USB設備卻各種各樣,例如USB鼠標,USB鍵盤,U盤等等,那么USB主機是如何識別出不同的設備的呢?這就要依賴
    發表于 04-12 11:09 ?1521次閱讀

    USB HID報告及報告描述符簡介

    在USB中,USB HOST是通過各種描述符來識別設備的,有設備描述符,配置描述符,接口描述符,端點描述符,字符串
    發表于 04-12 11:13 ?4007次閱讀

    Descriptor描述符解釋

    Descriptor即描述符,是個完整的數據結構,可以通過C語言等編程實現,并存儲在USB設備中,用于描述個USB設備的所有屬性,USB主機是通過
    發表于 07-16 09:39 ?2629次閱讀

    Linux中文件文件描述符概述

    、鏈接文件和設備文件。 那么,內核如何區分和引用特定的文件呢?這里用到了個重要的概念文件描述符
    發表于 10-18 14:35 ?0次下載

    USB設備鍵值表描述符說明資料免費下載

    本文檔的主要內容詳細介紹的是USB設備鍵值表描述符說明資料免費下載包括了:1.設備描述符的結構,2. 配置描述符的結構,3. 接口描述符的結構,4. HID
    發表于 07-16 16:56 ?35次下載
    USB設備鍵值表<b class='flag-5'>描述符</b>說明資料免費下載

    USB各描述符之間的依賴是怎么樣的

    USB 是個通用的總線,端口都是統的。但是USB 設備卻各種各樣,例如USB 鼠標, USB鍵盤, U盤等等,那么USB 主機是如何識別出不同的設備的呢?這就要依賴于描述符了。USB 的描述符主要有設備
    發表于 07-23 16:53 ?8次下載
    USB各<b class='flag-5'>描述符</b>之間的依賴是怎么樣的

    Linux系統編程中的文件描述符調用

    文件描述符 進程每打開文件的時候,會獲得該文件文件描述
    的頭像 發表于 09-02 09:50 ?1648次閱讀
    Linux系統編程中的<b class='flag-5'>文件</b><b class='flag-5'>描述符</b>調用

    科普下什么是USB的描述符

    以及行為呢?這就要通過描述符來實現了。那么什么是USB的描述符呢?其實就是些傳遞的協議信息,比如設備的類型、廠商ID、產品ID、端點情況、版本號等信息。 既然描述符是協議信息,那么不
    的頭像 發表于 12-02 14:41 ?3925次閱讀

    Gadget框架構造描述符

    假設你要【模擬】個 USB 設備: 這個 USB 設備含有廠家信息:它記錄在設備描述符里,所以設備描述符應該由你提供 這個芯片可能有多種配置,這也是由你決定,所以配置描述符應該由你提
    的頭像 發表于 07-13 11:34 ?616次閱讀
    Gadget框架構造<b class='flag-5'>描述符</b>

    從獲取描述符的角度理解Gadget框架

    操作: 使用控制傳輸,讀取設備信息(設備描述符):第次讀取時,它只需要得到 8 字節數據,因為第 8 個數據表示端點 0 能傳輸的最大數據長度。 Host 分配地址給設備,然后把新地址發給設備。 使用新地址,重新讀取設備描述符
    的頭像 發表于 07-13 11:38 ?867次閱讀
    從獲取<b class='flag-5'>描述符</b>的角度理解Gadget框架

    基于DWC_ether_qos的以太網驅動開發-描述符格式介紹

    前面我們介紹了描述符鏈表的工作模式,重點是了解環形鏈表是如何環形的,以及相關的寄存器。驅動編寫就需要更進步,了解描述符的具體內容,即4個描述符的每個字段的含義。
    的頭像 發表于 09-04 14:14 ?2454次閱讀
    基于DWC_ether_qos的以太網驅動開發-<b class='flag-5'>描述符</b>格式介紹

    Python的優雅之處:Descriptor(描述符

    語法糖的實現上也有使用到(在下面的文章會一一介紹)。 當你點進這篇文章時 你也許沒學過描述符,甚至沒聽過描述符。 或者你對描述符只是知半解 無論你是哪種,本篇都將帶你全面的學習
    的頭像 發表于 11-02 10:52 ?970次閱讀
    Python的優雅之處:Descriptor(<b class='flag-5'>描述符</b>)