1、前言:html
有的程序能夠經過編譯, 但在運行時會出現Segment fault(段錯誤). 這一般都是指針錯誤引發的. 但這不像編譯錯誤同樣會提示到文件某一行, 而是沒有任何信息, 使得咱們的調試變得困難起來.
gdb: 有一種辦法是, 咱們用gdb的step, 一步一步尋找. 這放在短小的代碼中是可行的, 但要讓你step一個上萬行的代碼, 我想你會今後厭惡程序員這個名字, 而把他叫作調試員. 咱們還有更好的辦法, 這就是core file.
ulimit: 若是想讓系統在信號中斷形成的錯誤時產生core文件, 咱們須要在shell中按以下設置: #設置core大小爲無限 ulimit -c unlimited #設置文件大小爲無限 ulimit unlimited 這些須要有root權限, 在ubuntu下每次從新打開中斷都須要從新輸入上面的第一條命令, 來設置core大小爲無限.
用gdb查看core文件: 下面咱們能夠在發生運行時信號引發的錯誤時發生core dump了. 發生core dump以後, 用gdb進行查看core文件的內容, 以定位文件中引起core dump的行. gdb [exec file] [core file] 如: gdb ./test test.core 在進入gdb後, 用bt命令查看backtrace以檢查發生程序運行到哪裏, 來定位core dump的文件->行.
1. 什麼是Core:
Sam以前一直覺得Core Dump中Core是 Linux Kernel的意思. 今天才發如今這裏,Core是另外一種意思:
在使用半導體做爲內存的材料前,人類是利用線圈看成內存的材料(發明者爲王安),線圈就叫做 core ,用線圈作的內存就叫做 core memory。現在 ,半導體工業澎勃發展,已經沒有人用 core memory 了,不過,在許多狀況下, 人們仍是把記憶體叫做 core 。
2. 什麼是Core Dump:
咱們在開發(或使用)一個程序時,最怕的就是程序莫明其妙地當掉。雖然系統沒事,但咱們下次仍可能遇到相同的問題。因而這時操做系統就會把程序當掉 時的內存內容 dump 出來(如今一般是寫在一個叫 core 的 file 裏面),讓 咱們或是 debugger 作爲參考。這個動做就叫做 core dump。
3. Core Dump時會生成何種文件:
Core Dump時,會生成諸如 core.進程號 的文件。
4. 爲什麼有時程序Down了,卻沒生成 Core文件。
Linux下,有一些設置,標明瞭resources available to the shell and to processes。 可使用#ulimit -a 來看這些設置。 (ulimit是bash built-in Command)
-a All current limits are reported
-c The maximum size of core files created
-d The maximum size of a process鈥檚 data segment
-e The maximum scheduling priority ("nice")
-f The maximum size of files written by the shell and its children
-i The maximum number of pending signals
-l The maximum size that m ay be locked into memory
-m The maximum resident set size (has no effect on Linux)
-n The maximum number of open file descriptors (most systems do not allow this value to be set)
-p The pipe size in 512-byte blocks (this may not be set)
-q The maximum number of bytes in POSIX message queues
-r The maximum real-time scheduling priority
-s The maximum stack size
-t The maximum amount of cpu time in seconds
-u The maximum number of processes available to a single user
-v The maximum amount of virtual memory available to the shell
-x The maximum number of file locks
從這裏能夠看出,若是 -c是顯示:core file size (blocks, -c) 若是這個值爲0,則沒法生成core文件。因此可使用:
#ulimit -c 1024 或者 #ulimit -c unlimited 來使能 core文件。
若是程序出錯時生成Core 文件,則會顯示Segmentation fault (core dumped) 。
5. Core Dump的核心轉儲文件目錄和命名規則:
/proc/sys/kernel /core_uses_pid能夠控制產生的core文件的文件名中是否添加pid做爲擴展,若是添加則文件內容爲1,不然爲0
6. 如何使用Core文件:
在Linux下,使用:
#gdb -c core.pid program_name
就能夠進入gdb模式。
輸入where,就能夠指出是在哪一行被Down掉,哪一個function內,由誰調用等等。
(gdb) where
或者輸入 bt。
(gdb) bt
7. 如何讓一個正常的程序down:
#kill -s SIGSEGV pid
8. 察看Core文件輸出在何處:
存放Coredump的目錄即進程的當前目錄,通常就是當初發出命令啓動該進程時所在的目錄。但若是是經過腳本啓動,則腳本可能會修改當前目錄,這時進程真正的當前目錄就會與當初執行腳本所在目錄不一樣。這時能夠查看」/proc/<進程pid>/cwd「符號連接的目標來肯定進程真正的當前目錄地址。經過系統服務啓動的進程也可經過這一方法查看。
9. 嵌入式設備下如何使用Core dump:
linux coredump配置與調試
Linux
2、Core Dump 配置與調試
1.core文件的生成開關和大小限制
---------------------------------
1)使用ulimit -c 命令可查看core文件的生成開關。若結果爲0,則表示關閉了此功能,不會生成core文件。
2)使用ulimit -c filesize命令,能夠限制core文件的大小(filesize的單位爲kbyte)。若ulimit -c unlimited,則表示core文件的大小不受限制。若是生成的信息超過此大小,將會被裁剪,最終生成一個不完整的core文件。在調試此core文件的時候,gdb會提示錯誤。
2.core文件的名稱和生成路徑
----------------------------
若系統生成的core文件不帶其它任何擴展名稱,則所有命名爲core。新的core文件生成將覆蓋原來的core文件 。
1)/proc/sys /kernel/core_uses_pid能夠控制core文件的文件名中是否添加pid做爲擴展。文件內容爲1,表示添加pid做爲擴展名,生成的 core文件格式爲core.xxxx;爲0則表示生成的core文件同一命名爲core。
可經過如下命令修改此文件:
echo"1" >/proc/sys/kernel/core_uses_pid
2)proc/sys/kernel/core_pattern能夠控制core文件保存位置和文件名格式。
可經過如下命令修改此文件:
echo"/corefile/core-%e-%p-%t" >core_pattern,能夠將core文件統一輩子成到/corefile目錄下,產生的文件名爲core-命令名-pid-時間戳
如下是參數列表:
%p - insert pid into filename 添加pid
%u - insert current uid into filename 添加當前uid
%g - insert current gid into filename 添加當前gid
%s - insert signal that caused the coredump into the filename 添加致使產生core的信號
%t - insert UNIX time that the coredump occurred into filename 添加core文件生成時的unix時間
%h - insert hostname where the coredump happened into filename 添加主機名
%e - insert coredumping executable name into filename 添加命令名
3.用gdb查看core文件:
下面咱們能夠在發生運行時信號引發的錯誤時發生core dump了.
發生 core dump以後,用gdb進行查看core文件的內容,以定位文件中引起core dump的行.
gdb [exec file] [core file]
如:gdb ./test test.core
在進入gdb後,用 bt命令查看backtrace以檢查發生程序運行到哪裏,來定位core dump的文件->行.
4.開發板上使用core文件調試
-----------------------------
若是開發板的操做系統也是linux,core調試方法依然適用。若是開發板上不支持gdb,可將開發板的環境(頭文件、庫)、可執行文件和core文件拷貝到PC的linux下,運行相關命令便可。
注意:待調試的可執行文件,在編譯的時候須要加-g,core文件才能正常顯示出錯信息!
注意的問題:
在Linux下要保證程序崩潰時生成 Coredump要注意這些問題:
1、要保證存放Coredump的目錄存在且進程對該目錄有寫權限。存放Coredump 的目錄即進程的當前目錄,通常就是當初發出命令啓動該進程時所在的目錄。但若是是經過腳本啓動,則腳本可能會修改當前目錄,這時進程真正的當前目錄就會與當初執行腳本所在目錄不一樣。這時能夠查看」/proc/進程pid>/cwd「符號連接的目標來肯定進程真正的當前目錄地址。經過系統服務啓動的進程也可經過這一方法查看。
2、若程序調用了seteuid()/setegid()改變了進程的有效用戶或組,則在默認狀況下系統不會爲這些進程生成Coredump。不少服務程序都會調用seteuid(),如MySQL,不論你用什麼用戶運行 mysqld_safe啓動MySQL,mysqld進行的有效用戶始終是msyql用戶。若是你當初是以用戶A運行了某個程序,但在ps裏看到的
這個程序的用戶倒是B的話,那麼這些進程就是調用了seteuid了。爲了可以讓這些進程生成core dump,須要將/proc/sys/fs/suid_dumpable 文件的內容改成1(通常默認是0)。
3、這個通常都知道,就是要設置足夠大的Core文件大小限制了。程序崩潰時生成的 Core文件大小即爲程序運行時佔用的內存大小。但程序崩潰時的行爲不可按日常時的行爲來估計,好比緩衝區溢出等錯誤可能致使堆棧被破壞,所以常常會出現某個變量的值被修改爲亂七八糟的,而後程序用這個大小去申請內存就可能致使程序比日常時多佔用不少內存。所以不管程序正常運行時佔用的內存多麼少,要保證生成Core文件仍是將大小限制設爲unlimited爲好。
ulimit -- 用戶資源限制命令
一、說明 :ulimit用於shell啓動進程所佔用的資源.
二、類別 :shell內建命令
三、語法格式 :ulimit [-acdfHlmnpsStvw] [size]
四、參數介紹 :
-H 設置硬件資源限制.
-S 設置軟件資源限制.
-a 顯示當前全部的資源限制.
-c size:設置core文件的最大值.單位:blocks
-d size:設置數據段的最大值.單位:kbytes
-f size:設置建立文件的最大值.單位:blocks
-l size:設置在內存中鎖定進程的最大值.單位:kbytes
-m size:設置可使用的常駐內存的最大值.單位:kbytes
-n size:設置內核能夠同時打開的文件描述符的最大值.單位:n
-p size:設置管道緩衝區的最大值.單位:kbytes
-s size:設置堆棧的最大值.單位:kbytes
-t size:設置CPU使用時間的最大上限.單位:seconds
-v size:設置虛擬內存的最大值.單位:kbytes 5,簡單實例:
五、舉例
在Linux下寫程序的時候,若是程序比較大,常常會遇到「段錯誤」(segmentationfault)這樣的問題,這主要就是因爲Linux系統初始的堆棧大小(stack size)過小的緣故,通常爲10M。我通常把stacksize設置成256M,這樣就沒有段錯誤了!命令爲:ulimit -s 262140
若是要系統自動記住這個配置,就編輯/etc/profile文件,在 「ulimit -S -c 0 > /dev/null 2>&1」行下,添加「ulimit -s 262140」,保存重啓系統就能夠了!
1] 在RH8的環境文件/etc/profile中,咱們能夠看到系統是如何配置ulimit的:
#grep ulimit /etc/profile
ulimit -S -c 0 > /dev/null 2>&1
這條語句設置了對軟件資源和對core文件大小的設置
2] 若是咱們想要對由shell建立的文件大小做些限制,如:
#ll h
-rw-r--r-- 1 lee lee 150062 7月 22 02:39 h
#ulimit -f 100 #設置建立文件的最大塊(一塊=512字節)
#cat h>newh
File size limit exceeded
#ll newh
-rw-r--r-- 1 lee lee 51200 11月 8 11:47 newh
文件h的大小是150062字節,而咱們設定的建立文件的大小是512字節x100塊=51200字節,固然系統就會根據你的設置生成了51200字節的newh文件.
3] 能夠像實例1]同樣,把你要設置的ulimit放在/etc/profile這個環境文件中.
用途:設置或報告用戶資源極限。
語法:ulimit [ -H ] [ -S ] [ -a ] [ -c ] [ -d ] [ -f ] [ -m ] [ -n ] [ -s ] [ -t ] [ Limit ]
描述:ulimit 命令設置或報告用戶進程資源極限,如 /etc/security/limits 文件所定義。文件包含如下缺省值極限:
fsize = 2097151
core = 2097151
cpu = -1
data = 262144
rss = 65536
stack = 65536
nofiles = 2000
當新用戶添加到系統中時,這些值被做爲缺省值使用。當向系統中添加用戶時,以上值經過 mkuser 命令設置,或經過 chuser 命令更改。
極限分爲軟性或硬性。經過 ulimit 命令,用戶可將軟極限更改到硬極限的最大設置值。要更改資源硬極限,必須擁有 root 用戶權限。
不少系統不包括以上一種或數種極限。 特定資源的極限在指定 Limit 參數時設定。Limit 參數的值能夠是每一個資源中指定單元中的數字,或者爲值 unlimited。要將特定的 ulimit 設置爲 unlimited,可以使用詞 unlimited。
注:在 /etc/security/limits 文件中設置缺省極限就是設置了系統寬度極限, 而不只僅是建立用戶時用戶所需的極限。
省略 Limit 參數時,將會打印出當前資源極限。除非用戶指定 -H 標誌,不然打印出軟極限。當用戶指定一個以上資源時,極限名稱和單元在值以前打印。若是未給予選項,則假定帶有了 -f 標誌。
因爲 ulimit 命令影響當前 shell 環境,因此它將做爲 shell 常規內置命令提供。若是在獨立的命令執行環境中調用該命令,則不影響調用者環境的文件大小極限。如下示例中正是這種狀況:
nohup ulimit -f 10000
env ulimit 10000
一旦經過進程減小了硬極限,若無 root 特權則沒法增長,即便返回到原值也不可能。
關於用戶和系統資源極限的更多信息,請參見 AIX 5L Version 5.3 Technical Reference: BaseOperating System and Extensions Volume 1 中的 getrlimit、setrlimit 或vlimit 子例程。
標誌
-a 列出全部當前資源極限。
-c 以 512 字節塊爲單位,指定核心轉儲的大小。
-d 以 K 字節爲單位指定數據區域的大小。
-f 使用 Limit 參數時設定文件大小極限(以塊計),或者在未指定參數時報告文件大小極限。缺省值爲 -f 標誌。
-H 指定設置某個給定資源的硬極限。若是用戶擁有 root 用戶權限,能夠增大硬極限。任何用戶都可減小硬極限。
-m 以 K 字節爲單位指定物理存儲器的大小。
-n 指定一個進程能夠擁有的文件描述符的數量的極限。
-s 以 K 字節爲單位指定堆棧的大小。
-S 指定爲給定的資源設置軟極限。軟極限可增大到硬極限的值。若是 -H 和 -S 標誌均未指定,極限適用於以上兩者。
-t 指定每一個進程所使用的秒數 。
退出狀態
返回如下退出值:
0 成功完成。 mysql
參考:https://www.cnblogs.com/Anker/p/6079580.htmllinux