2014-05-15 32 views
0

我想通過以下功能捕捉內存溢出異常:如何抓住內存溢出異常在Ubuntu

void allocMemory(buffer& thebuf, size_t size) 
{ 
try 
{ 
     thebuf = buffer(size); // new char[] here 
} 
catch(bad_alloc& ex) 
{ 
    exception handling... // print some information 
     exit(1); 
} 
} 

的處理應該顯示一些信息和關閉程序。這項工作在Windows上很好,但在Linux上,程序直接與終端上的「Killed」關閉。看起來OOM殺手在異常可以捕捉之前殺死我的程序。

這是正常的嗎?

如何捕獲Linux上的內存異常?

P.S.我正在測試Ubuntu 12.04 64位,僅使用4GB內存進行測試,沒有交換空間,語言是C++。另外,如果我一次新增大量內存,該功能在Linux上也可以使用。但是,如果我每次新增一點點(例如:在一個循環中),程序將最終以終止的「Killed」關閉。

任何幫助,將不勝感激。

回答

0

你想是這樣的:

try { 
    thebuf = new buffer[size]; 
} catch(std::bad_alloc& ex) { 
    std::cout << ex.what(); 
    exit(1); 
} 
1

您可以配置Linux不過量使用內存。

Overcommitting通常是件好事。飛機票也超賣,這偶爾會導致飛機超額預訂,他們可能需要改變某人的航班。但通常情況並非如此。這同樣適用於從Linux請求內存的應用程序。就像我所說的,你可以配置Linux不要過度使用內存。請參閱this question

+0

感謝您的鏈接。但是由於我們的用戶可能沒有root權限,因此可能無法要求他們配置Linux,是否有更好的方法來檢測Linux上的內存不足? –

4

在Linux上,您不會得到任何bad_alloc異常(除非您更改了shell中的某些默認值)。

Linux使用懶惰分配策略。任何分配請求(當不太大時)都會成功。操作系統將返回一個未映射到虛擬內存的地址。映射發生在程序實際嘗試使用內存時。只有在此時才能檢測到內存不足的情況。

但是,發生這種情況時,向計劃報告情況已爲時過晚。它不準備處理它。所以操作系統只是徹底殺死了這個程序。

谷歌linux內存不足殺手 for(lots)更多信息。

您可以用rlimit命令限制程序可用的內存量。將其設置得足夠低,以便程序在耗盡所有可用內存之前達到極限。

如果需要,您也可以禁用系統惰性分配行爲,但這很少是件好事。

+0

解釋非常清楚,所以在Linux上看起來不可能發現OOM錯誤。我想做的是在OOM發生時給用戶一個反饋,並順利關閉該程序,是否有一種在Linux上完成的好方法? –

+0

該進程因無法捕獲的信號而中止,因此您可以做的最好的做法是啓動另一個可充當監督者的小型進程。 –