按照Linux系統的設計哲學,內核只提供dump內存的機制,用戶想要dump什么樣的內存,dump多少內存是屬於策略問題,由用戶來決定。
在真實的使用場景中,主要有兩種使用方式:kdump和coredump
1.kdump:dump某一個進程的地址空間來供用戶在進程掛掉之后debug分析。
2.coredump:dump整個系統的內存空間,以便於系統管理員debug分析系統掛掉的原因。
本文主要描述kdump
kdump整個過程依賴kexec和一個額外的dump內核來保證整個流程正確的執行。
kdump涉及的組件:
1.kdump專用內核,通過kexec工具load到預留的內存中,供故障引導使用。
2.kexec工具,負責加載crash內核,以及一些啟動參數傳遞。
3.makedumpfile工具,負責將故障內核的內存copy,壓縮,寫入指定文件。
kdump的實現
kdump整個流程涉及到兩次內核啟動:
1.首先是工作內核啟動,包括硬件自檢初始化,BootLoader加載內核並發引導內核啟動,然后配置預留內存,並使用kexec工具將crash內核加載到保留內存中。
2.工作內核在遇到故障觸發panic之后啟動crash kernel,kexec啟動crash kernel只執行內核初始化邏輯,不再做硬件自檢初始化,啟動速度很快。
3.crash內核加載好之后可以正常管理一部分系統資源,通過/proc/vmcore內存鏡像文件,將故障內存經過壓縮之后寫入到硬盤的dump文件中保存。
4.捕獲完畢之后重啟系統,完成故障恢復。
隨着系統內存的不斷增大,故障恢復時間也隨之線性增加,兩次系統啟動時間比較固定,線性增加的時間主要是受copy內存,壓縮內存以及文件落盤影響。所以很多kdump優化方案主要也是針對以下幾個方面實現的:
1.copy內存方面:為了減少系統調用的次數,實現了vmcore的mmap方法,可以提高copy的效率。
2.內存壓縮方面:引入了壓縮效率比較高的lzo算法來替換原來的gzip算法。
3.落盤方面:主要考慮並發寫文件和優化io效率。
如何使用kdump:
1.修改啟動參數,增加crash kernel字段,通過/proc/cmdline可以觀察是否生效。
2.安裝kdump組件包,包括crash kernel和kexec組件。
3.啟動kdump服務,通過service命令或者/etc目錄中的啟動腳本啟動。
4.觀察/proc/iomem中是否成功load了crash kernel
關於kexec
kexec是一個快速啟動kernel的機制,它運行在某一正在運行的kernel中,啟動一個新的kernel(crash kernel)不用重新經過BIOS就可以完成啟動。
服務器死機后,查看kernel服務
#chkconfig --list|grep kdump
#ll /var/crash/
#rpm -qa | grep crash
#rpm -qa | grep kexec
#rpm -qa | grep $(uname -r)
追蹤crash日志:
#cd /var/crash/***
#crash /usr/lib/debug/lib/modules/2.6.32-358.el6.x86_64/vmlinux vmcore
命令語法是:crash debug內核 crashdump文件
debug內核的路徑是:/usr/lib/debug/lib/modules/2.6.32-358.el6.x86_64/vmlinux
***debug內核和現用的版本內核必須一致
crash> files (查看最后一次操作我呢見的命令和pid)
crash> files 123 (指定pid進行查看打開了哪些文件)
crash> files 1 (pid 1 是init進程的進程號,該命令可以顯示init進程打開的文件)
crash> ps (可用ps命令查看kernel crash時候的所有進程)