pod裡的redis用nfs存aof及rdb資料,報錯Stale file handle
log裡報:
1:M 13 Jan 2022 21:00:43.015 * Asynchronous AOF fsync is taking too long (disk is busy?). Writing the AOF buffer without waiting for fsync to complete, this may slow down Redis.
1:M 13 Jan 2022 21:00:52.137 # Fail to fsync the AOF file: Stale file handle
1:M 13 Jan 2022 21:12:24.529 # Error writing to the AOF file: Stale file handle
Stale file handle是一個檔案系統的普遍問題,主要是linode變了,但外部沒變。相當於元資訊沒了,但外部檔案還在,成了野指標。
而特別在nfs裡又是個普遍問題。
相關分析:
https://cloud.tencent.com/developer/article/1593914
這個問題通過百度搜索能得出一片的結果,但是其中的結果沒有幾個是有營養的。
使用google能搜到就比百度有用的多,但是也沒有個說是怎麼怎麼出來的。
因為中工作中遇到了這個問題,也花費了不少的時間去處理 這個問題。希望這篇分析和總結是有用個的。
1.問題描述
這個英文的雖然說的NFS,但是實際上不僅僅NFS系統會遇到這個問題。當然如果你的系統就是NFS的,那麼你排查這個問題會簡單很多。本文不是針對NFS系統。
Stale NFS file handle具體是什麼意思,為還沒有看到中文是怎麼解釋的。英文的意思:檔案是變得不可用了。當使用ls, stat,cat等等命令去檢視檔案的時候會發現無法看到檔案的任何資訊。
有個問題大家都很熟悉的,就是寫程式的時候經常會避免野指標的問題,這個問題與此類似,只是這個野指標是存在於磁碟上的。
2.復現該問題的方法
要重現這個問題不是一般般的簡單的,光靠運氣會搞死人的。下面給出一種為知道的重現方法:
假設檔案系統是/dev/sda2,則可以進行如下操作:
debugfs -w /dev/sda2
這時候會進入到debugfs的命令列中,假設壞掉的檔案是/dev/sda2中的file檔案,那麼使用
stat ./file 命令查看出檔案對應的inode,假設是62345
然後使用命令 mi <62345>
修改該檔案的Link count數為0
然後quit。
這時候ls去看/dev/sda2的file檔案就會出現Stale NFS file handle的報錯了(如果不出現,重啟系統必定出現)。
3.問題分析
從重現方法就大概知道,是Link count計數不對導致的這個問題。這個報錯是系統保持來的。是的沒錯,就是檔案的引用計數出現問題了。一般的,對linux系統來說,檔案的引用計數為0表示檔案被刪除了。這個時候它佔用的inode節點要被回收,被它所在目錄要去除改檔案的目錄項。(不清楚檔案儲存方法的請自行查閱)。
然後,通過debugfs的修改,我們發現,目錄還是有這個檔案的目錄項,但是由於檔案的引用計數是0,檔案系統認為改檔案已經被刪除了,那麼就意味著根據目錄項的該檔案的記錄是找不到該檔案的,即這個目錄項是一個野指標。
4.出現的原因
檔案系統出問題的原因太複雜了,這裡總結兩個大家認為不可能但是又十分可能的原因:
系統正在刪除檔案的時候發生斷電,即檔案的link count被標記為0,但是對應的目錄項還沒有來得及刪除;
5.解決方法
- 如果檔案系統是ext2,那麼你會高概率的遇到這個問題,請將系統升級為ext3.(請自行腦補ext2和ext3的對比)
- 使用fsck -y修復檔案系統,並且確保系統中啟動的過程中會自行修復,這樣當系統發生這個問題時可以中啟動的時候就自行處理好,而不至於導致系統啟動中斷掉。
ps
從整個的排查過程來說,個人覺得這個報錯資訊真的應該改改,有點南轅北轍的意思,如下的連結也在吐槽該問題: