以前看一些Linux網絡編程的文章的時候總是會遇到文件描述符fd這個東西,也沒太搞清楚。看了下面這篇文章講的還不錯,記錄下來吧。html
原文連接node
維基百科:文件描述符在形式上是一個非負整數。實際上,它是一個索引值,指向內核爲每個進程所維護的該進程打開文件的記錄表。當程序打開一個現有文件或者建立一個新文件時,內核向進程返回一個文件描述符。在程序設計中,一些涉及底層的程序編寫每每會圍繞着文件描述符展開。nginx
Linux 系統中,把一切都看作是文件,當進程打開現有文件或建立新文件時,內核向進程返回一個文件描述符,文件描述符就是內核爲了高效管理已被打開的文件所建立的索引,用來指向被打開的文件,全部執行I/O操做的系統調用都會經過文件描述符。web
每一個文件描述符會與一個打開的文件相對應編程
不一樣的文件描述符也可能指向同一個文件segmentfault
相同的文件能夠被不一樣的進程打開,也能夠在同一個進程被屢次打開bash
進程級的文件描述符表網絡
系統級的文件描述符表ui
文件系統的i-node表 (轉到:阮一峯——理解inode)spa
PS:總結一下軟硬連接。
硬連接的話,新文件和原文件的iNode號碼是同樣的。原文件的iNode的連接數會加一。刪除原文件,新文件不受影響。 軟鏈接的話,新文件和原文件的iNode號碼是不同的。原文件的iNode的連接數不變。刪除原文件,訪問新文件會報文件不存在錯誤。
在進程A中,文件描述符1和30都指向了同一個打開的文件句柄(#23),這多是該進程屢次對執行打開操做
進程A中的文件描述符2和進程B的文件描述符2都指向了同一個打開的文件句柄(#73),這種狀況有幾種可能,1.進程A和進程B多是父子進程關係;2.進程A和進程B打開了同一個文件,且文件描述符相同(低機率事件=_=);3.A、B中某個進程經過UNIX域套接字將一個打開的文件描述符傳遞給另外一個進程。
進程A的描述符0和進程B的描述符3分別指向不一樣的打開文件句柄,但這些句柄均指向i-node表的相同條目(#1936),換言之,指向同一個文件。發生這種狀況是由於每一個進程各自對同一個文件發起了打開請求。同一個進程兩次打開同一個文件,也會發生相似狀況。
前人的思考,咱們的階梯,這部分參考自網絡:連接
有資源的地方就有戰爭,「文件描述符」也是一種資源,系統中的每一個進程都須要有「文件描述符」才能進行改變世界的宏圖霸業。世界須要秩序,因而就有了「文件描述符限制」的規定。
以下表:
永久修改用戶級限制時有三種設置類型:soft 指的是當前系統生效的設置值
hard 指的是系統中所能設定的最大值
命令講解:
ulimit
複製代碼
sysctl
複製代碼
4、檢查某個進程的文件描述符相關內容 步驟(以nginx爲例,*注意權限問題,此示例是在本地環境):
找到須要檢查的進程id
如圖,找到的進程id爲 1367
查看該進程的限制
如圖,在 Max open files 那一行,能夠看到當前設置中最大文件描述符的數量爲1024
查看該進程佔用了多少個文件描述符
如圖所示,使用了17個文件描述符實際應用過程當中,若是出現「Too many open files」 , 能夠經過增大進程可用的文件描述符數量來解決,但每每故事不會這樣結束,不少時候,並非由於進程可用的文件描述符過少,而是由於程序bug,打開了大量的文件鏈接(web鏈接也會佔用文件描述符)而沒有釋放。程序申請的資源在用完後及時釋放,纔是解決「Too many open files」的根本之道。