當前位置:首頁 » 操作系統 » linux內存泄露

linux內存泄露

發布時間: 2022-06-26 08:30:14

① 嵌入式linux怎麼檢內存泄漏雨

1. 在需要內存泄漏檢查的代碼的開始調用void mtrace(void) (在mcheck.h中? 有聲明). mtrace為malloc等函數安裝hook, 用於記錄內存分配信息.在需要內存泄漏檢查的代碼的結束調用void muntrace(void).
注意: 一般情況下不要調用muntrace, 而讓程序自然結束. 因為可能有些釋放內存代碼要到muntrace之後才運行.

2. 用debug模式編譯被檢查代碼(-g或-ggdb)

3. 設置環境變數MALLOC_TRACE為一文件名, 這一文件將存有內存分配信息.

4. 運行被檢查程序, 直至結束或muntrace被調用.

5. 用mtrace命令解析內存分配Log文件($MALLOC_TRACE)
(mtrace foo $MALLOC_TRACE, where foo is the executible name)
如果有內存泄漏, mtrace會輸出分配泄漏
內存的代碼位置,以及分配數量.

附加說明
1. 可以將mtrace, muntrace放入信號處理函數(USR1, USR2), 以動態地進行內存泄漏檢查控制.
2. mtrace是個perl代碼, 如果你對符號地址與代碼文本的轉換感興趣, 可以讀一下.
3. again, 盡量不要用muntrace()
For C++ Leak:
檢查內存泄漏的方法除glibc提供外;還可以試試一些專用的程序。
很奇怪,redhat 9 居然不帶mtrace perl腳本,只好下載gcc源碼編譯了
wget --passive-ftp ftp://rpmfind.net/linux/redhat/9 ... -2.3.2-11.9.src.rpm
rpm -ivh glibc*.src.rpm
cd /usr/src/redhat/SPECS/
rpmbuild -ba glibc-9.spec
cd /var/tmp/glibc-2.3.2-root/usr/bin/
cp mtrace /usr/bin/
調試方法如下:
vi a.c
1 #include
2
3 int main()
4 {
5 mtrace();
6 malloc(10);
7 malloc(16);
8 return 0;
9 }
$gcc -g a.c #記得編譯帶-g調試選項
$export MALLOC_TRACE=a.log
$./a.out
$unset MALLOC_TRACE #記得執行完後unset變數,否則可能運行其他命令可能覆蓋log
$mtrace a.out a.log
Memory not freed:
-----------------
Address Size Caller
0x09b08378 0xa at /XXX/a.c:6
0x09b08388 0x10 at /XXX/a.c:7
可以看到,會顯示未釋放動態空間的代碼具體位置。

② linux內存泄漏怎麼查

可以使用對應的軟體測試工具來查,如parasoft的c/c++等

③ 怎麼樣來檢查Linux系統下內存泄漏

內存泄漏是指程序動態申請的內存在使用完後沒有釋放,導致這段內存不能被操作系統回收再利用。 例如這段程序,申請了4個位元組的空間但沒有釋放,有4個位元組的內存泄漏。
#include <iostream>using namespace std;int main()
{ int *p = new int(1); cout <<*p<<endl; return 0}
1
2
3
4
5
6
7
8
9
隨著時間的推移,泄漏的內存越來越多,可用的內存越來越少,輕則性能受損,重則系統崩潰。
一般情況下,發生內存泄漏時,重啟就可以回收泄漏的內存。但是對於Linux,通常跑的是伺服器程序,不可以隨意重啟,在內存泄漏問題上就要格外小心。
內存泄漏特點
難復現 — 要運行到足夠長的時間才會暴露。
難定位 — 出錯位置是隨機的,看不出與內存泄漏的代碼有什麼聯系。
最簡單的方法
為了避免寫出內存泄漏的程序,通常會有這樣的編程規范,要求我們在寫程序時申請和釋放成對出現的。因為每一次申請都意味著必須有一次釋放與它相對應。
基於這個特點,一種簡單的方法就是在代碼中統計申請和釋放的次數,如果申請和釋放的數量不同,就認為是內存泄漏了。
#include "stdio.h"#include "stdlib.h"int malloc_count, free_count;void * my_malloc(int size)
{
malloc_count++; return malloc(size);
}void my_free(void *p)
{
free_count++; free(p);
}int main()
{
count = 0; int *p1 = (int *)my_malloc(sizeif(int)) int *p2 = (int *)my_malloc(sizeif(int)) printf("%d, %d", p1, p2);
my_free(p1); if(malloc_count != free_count) printf("memory leak!\n"); return 0}

④ 如何定位分析linux內存泄漏問題

1、閱讀源代碼及分析動態內存的使用
由於之前沒有做過類似的問題(純屬小白了,慘遭鄙視....),所以就想著通過自己去看代碼,查找裡面涉及到使用動態內存的代碼段去定位問題(現在想想,真是太幼稚了,大家見笑了...),但是自己還是去通過對源代碼跟蹤、分析,主要是對動態分配的內存(如malloc函數分配的內存)、一些文件描述符等進行跟蹤,分析在程序邏輯中對動態分配的內存有沒有手動進行釋放,打開的文件描述符有沒有關閉等這些代碼一點點的去分析,當然這也是熟悉代碼,了解的一個過程。
2、利用memwatch內存檢測工具對程序進行內存分析
Memwatch是一款C語言的內存檢測工具。memwatch使用它自己定義的功能函數取代所有在你的程序中用ANSI C定義的內存分配函數,memwatch的內存分配函數包含了所有的分配記錄信息。memwatch功能默認不是開啟的,除非定義了MEMWATCH,否則在代碼中不會跟蹤相關的內存使用情況。memwatch通常將它的數據寫入到memwatch.log文件中,它也可以被重定向.更多Linux操作知識,可以網路《Linux就該這么學》。

⑤ 如何在linux操作系統下檢測內存泄漏

內存泄漏是指程序動態申請的內存在使用完後沒有釋放,導致這段內存不能被操作系統回收再利用。
例如這段程序,申請了4個位元組的空間但沒有釋放,有4個位元組的內存泄漏。

#include <iostream>using namespace std;int main()
{ int *p = new int(1); cout <<*p<<endl; return 0}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9

隨著時間的推移,泄漏的內存越來越多,可用的內存越來越少,輕則性能受損,重則系統崩潰。

一般情況下,發生內存泄漏時,重啟就可以回收泄漏的內存。但是對於Linux,通常跑的是伺服器程序,不可以隨意重啟,在內存泄漏問題上就要格外小心。

內存泄漏特點
  1. 難復現 — 要運行到足夠長的時間才會暴露。

  2. 難定位 — 出錯位置是隨機的,看不出與內存泄漏的代碼有什麼聯系。

最簡單的方法

為了避免寫出內存泄漏的程序,通常會有這樣的編程規范,要求我們在寫程序時申請和釋放成對出現的。因為每一次申請都意味著必須有一次釋放與它相對應。

基於這個特點,一種簡單的方法就是在代碼中統計申請和釋放的次數,如果申請和釋放的數量不同,就認為是內存泄漏了。

#include "stdio.h"#include "stdlib.h"int malloc_count, free_count;void * my_malloc(int size)
{
malloc_count++; return malloc(size);
}void my_free(void *p)
{
free_count++; free(p);
}int main()
{
count = 0; int *p1 = (int *)my_malloc(sizeif(int)) int *p2 = (int *)my_malloc(sizeif(int)) printf("%d, %d", p1, p2);
my_free(p1); if(malloc_count != free_count) printf("memory leak! "); return 0}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
方法分析
  • 優點:

直觀,容易理解,容易實現

  • 缺點:

1.該方法要求運行結束時對運行中產生的列印分析才能知道結果。

2.該方法要求封裝所有申請和釋放空間的函數,並在調用的地方修改成調用封裝後的函數。雖然C中申請/釋放內存介面並不多,但是對於一個大型的項目,調用這些介面的地方卻是很多的,要全部替換是一個比較大的工作量。

3.只對C語言適用,不能應用於C++

4.對於所調用的庫不適用。如果希望應用於庫,則要修改庫代碼

5.只能檢測是否泄漏,卻沒有具體信息,比如泄漏了多少空間

6.不能說明是哪一行代碼引起了泄漏

改進

這種方法雖然簡單的,卻有許多的不足,無法真正應用於項目中。欲知怎樣改進,且看下回分解。

⑥ linux內存泄漏如何定位

1、閱讀源代碼及分析動態內存的使用 由於之前沒有做過類似的問題(純屬小白了,慘遭鄙視.),所以就想著通過自己去看代碼,查找...
2、利用memwatch內存檢測工具對程序進行內存分析Memwatch是一款C語言的內存檢測工具。memwatch使用它自己定義的功能函數取代所有在你的程...

⑦ linux中檢查內存泄漏的工具有哪些

Valgrind 是一款 Linux下(支持 x86、x86_64和ppc32)程序的內存調試工具,它可以對編譯後的二進製程序進行內存使用監測(C語言中的malloc和free,以及C++中的new和delete),找出內存泄漏問題。

⑧ 如何在Linux操作系統下檢測內存泄漏

Linux操作系統應用專區1.開發背景:
在 Windows 下使用 VC 編程時,我們通常需要 DEBUG 模式下運行程序,而後調試器將在退出程序時,列印出程序運行過程中在堆上分配而沒有釋放的內存信息,其中包括代碼文件名、行號以及內存大小。該功能是 MFC Framework 提供的內置機制,封裝在其類結構體系內部。
在 Linux 或者 Unix 下,我們的 C++ 程序缺乏相應的手段來檢測內存信息,而只能使用 top 指令觀察進程的動態內存總額。而且程序退出時,我們無法獲知任何內存泄漏信息。為了更好的輔助在 linux 下程序開發,我們在我們的類庫項目中設計並實現了一個內存檢測子系統。下文將簡述 C++ 中的 new 和 delete 的基本原理,並講述了內存檢測子系統的實現原理、實現中的技巧,並對內存泄漏檢測的高級話題進行了討論。2.New和delete的原理
當我們在程序中寫下 new 和 delete 時,我們實際上調用的是 C++ 語言內置的 new operator 和 delete operator。所謂語言內置就是說我們不能更改其含義,它的功能總是一致的。以 new operator 為例,它總是先分配足夠的內存,而後再調用相應的類型的構造函數初始化該內存。而 delete operator 總是先調用該類型的析構函數,而後釋放內存(圖1)。我們能夠施加影響力的事實上就是 new operator 和 delete operator 執行過程中分配和釋放內存的方法。
new operator 為分配內存所調用的函數名字是 operator new,其通常的形式是 void * operator new(size_t size); 其返回值類型是 void*,因為這個函數返回一個未經處理(raw)的指針,未初始化的內存。參數 size 確定分配多少內存,你能增加額外的參數重載函數 operator new,但是第一個參數類型必須是 size_t。
delete operator 為釋放內存所調用的函數名字是 operator delete,其通常的形式是 void operator delete(void *memoryToBeDeallocated);它釋放傳入的參數所指向的一片內存區。
這里有一個問題,就是當我們調用 new operator 分配內存時,有一個 size 參數表明需要分配多大的內存。但是當調用 delete operator 時,卻沒有類似的參數,那麼 delete operator 如何能夠知道需要釋放該指針指向的內存塊的大小呢?答案是:對於系統自有的數據類型,語言本身就能區分內存塊的大小,而對於自定義數據類型(如我們自定義的類),則 operator new 和 operator delete 之間需要互相傳遞信息。
當我們使用 operator new 為一個自定義類型對象分配內存時,實際上我們得到的內存要比實際對象的內存大一些,這些內存除了要存儲對象數據外,還需要記錄這片內存的大小,此方法稱為 cookie。這一點上的實現依據不同的編譯器不同。(例如 MFC 選擇在所分配內存的頭部存儲對象實際數據,而後面的部分存儲邊界標志和內存大小信息。g++ 則採用在所分配內存的頭 4 個自己存儲相關信息,而後面的內存存儲對象實際數據。)當我們使用 delete operator 進行內存釋放操作時,delete operator 就可以根據這些信息正確的釋放指針所指向的內存塊。
以上論述的是對於單個對象的內存分配/釋放,當我們為數組分配/釋放內存時,雖然我們仍然使用 new operator 和 delete operator,但是其內部行為卻有不同:new operator 調用了operator new 的數組版的兄弟- operator new[],而後針對每一個數組成員調用構造函數。而 delete operator 先對每一個數組成員調用析構函數,而後調用 operator delete[] 來釋放內存。需要注意的是,當我們創建或釋放由自定義數據類型所構成的數組時,編譯器為了能夠標識出在 operator delete[] 中所需釋放的內存塊的大小,也使用了編譯器相關的 cookie 技術。

⑨ 如何在linux下檢測內存泄漏

linux操作系統應用專區
1.開發背景:

windows
下使用
vc
編程時,我們通常需要
debug
模式下運行程序,而後調試器將在退出程序時,列印出程序運行過程中在堆上分配而沒有釋放的內存信息,其中包括代碼文件名、行號以及內存大小。該功能是
mfc
framework
提供的內置機制,封裝在其類結構體系內部。

linux
或者
unix
下,我們的
c++
程序缺乏相應的手段來檢測內存信息,而只能使用
top
指令觀察進程的動態內存總額。而且程序退出時,我們無法獲知任何內存泄漏信息。為了更好的輔助在
linux
下程序開發,我們在我們的類庫項目中設計並實現了一個內存檢測子系統。下文將簡述
c++
中的
new

delete
的基本原理,並講述了內存檢測子系統的實現原理、實現中的技巧,並對內存泄漏檢測的高級話題進行了討論。
2.new和delete的原理
當我們在程序中寫下
new

delete
時,我們實際上調用的是
c++
語言內置的
new
operator

delete
operator。所謂語言內置就是說我們不能更改其含義,它的功能總是一致的。以
new
operator
為例,它總是先分配足夠的內存,而後再調用相應的類型的構造函數初始化該內存。而
delete
operator
總是先調用該類型的析構函數,而後釋放內存(圖1)。我們能夠施加影響力的事實上就是
new
operator

delete
operator
執行過程中分配和釋放內存的方法。
new
operator
為分配內存所調用的函數名字是
operator
new,其通常的形式是
void
*
operator
new(size_t
size);
其返回值類型是
void*,因為這個函數返回一個未經處理(raw)的指針,未初始化的內存。參數
size
確定分配多少內存,你能增加額外的參數重載函數
operator
new,但是第一個參數類型必須是
size_t。
delete
operator
為釋放內存所調用的函數名字是
operator
delete,其通常的形式是
void
operator
delete(void
*memorytobedeallocated);它釋放傳入的參數所指向的一片內存區。
這里有一個問題,就是當我們調用
new
operator
分配內存時,有一個
size
參數表明需要分配多大的內存。但是當調用
delete
operator
時,卻沒有類似的參數,那麼
delete
operator
如何能夠知道需要釋放該指針指向的內存塊的大小呢?答案是:對於系統自有的數據類型,語言本身就能區分內存塊的大小,而對於自定義數據類型(如我們自定義的類),則
operator
new

operator
delete
之間需要互相傳遞信息。
當我們使用
operator
new
為一個自定義類型對象分配內存時,實際上我們得到的內存要比實際對象的內存大一些,這些內存除了要存儲對象數據外,還需要記錄這片內存的大小,此方法稱為
cookie。這一點上的實現依據不同的編譯器不同。(例如
mfc
選擇在所分配內存的頭部存儲對象實際數據,而後面的部分存儲邊界標志和內存大小信息。g++
則採用在所分配內存的頭
4
個自己存儲相關信息,而後面的內存存儲對象實際數據。)當我們使用
delete
operator
進行內存釋放操作時,delete
operator
就可以根據這些信息正確的釋放指針所指向的內存塊。
以上論述的是對於單個對象的內存分配/釋放,當我們為數組分配/釋放內存時,雖然我們仍然使用
new
operator

delete
operator,但是其內部行為卻有不同:new
operator
調用了operator
new
的數組版的兄弟-
operator
new[],而後針對每一個數組成員調用構造函數。而
delete
operator
先對每一個數組成員調用析構函數,而後調用
operator
delete[]
來釋放內存。需要注意的是,當我們創建或釋放由自定義數據類型所構成的數組時,編譯器為了能夠標識出在
operator
delete[]
中所需釋放的內存塊的大小,也使用了編譯器相關的
cookie
技術。

⑩ linux c 內存泄漏問題

具體來說,myfree中的num變數在內存中緊鄰著p變數,如果你將num申明為int,那他只佔四個位元組,而你初始化num的時候 memcpy(&num, p, sizeof(size_t)); 卻會將8個位元組拷進去,這會修改緊鄰這num的變數p,直接導致p被清零(如果malloc free外加修改的話,清的不一定是0),而free函數在傳入空指針是不做處理的。我把代碼修改了一下,你可以看一下下面程序的輸出,對應myfree的free那一行,實際被free的是空指針。

#include<stdio.h>
#include<malloc.h>
#include<pthread.h>
#include<unistd.h>

intfCnt=0,mCnt=0;

pthread_mutex_tmutex;

void*mynew(size_tsz){
void*p=malloc(sizeof(size_t)+sz);
memcpy(p,&sz,sizeof(size_t));
pthread_mutex_lock(&mutex);
mCnt+=sz+sizeof(size_t);
printf("mallocsz[%d],mCnt[%d],fCnt[%d] ",sz+sizeof(size_t),mCnt,
fCnt);
pthread_mutex_unlock(&mutex);
returnp+sizeof(size_t);
}

voidmyfree(void*prt){
void*p=prt-sizeof(size_t);
if(p==NULL){
printf("pbufisNULL ");
return;
}
intnum=0;//error!
//size_tnum=0;
printf("%p,%p ",&p,&num);
memcpy(&num,p,sizeof(size_t));
pthread_mutex_lock(&mutex);
fCnt+=num+sizeof(size_t);
printf("freesz[%d],fCnt[%d],mCnt[%d] ",num,fCnt,mCnt);
pthread_mutex_unlock(&mutex);
printf("trytofree%p ",p);
free(p);
}

intmain(){
void*p=mynew(100);
printf("pis%p ",p);
myfree(p);
usleep(1000000);
return0;
}
熱點內容
壓縮某個文件夾 發布:2024-11-15 09:03:11 瀏覽:891
網址能解壓嗎 發布:2024-11-15 08:54:09 瀏覽:933
python更改目錄 發布:2024-11-15 08:41:08 瀏覽:265
伺服器快閃記憶體可以裝在一般電腦上嗎 發布:2024-11-15 08:36:46 瀏覽:8
安卓手機怎麼查詢自己的路線軌跡 發布:2024-11-15 08:32:19 瀏覽:969
phpdatet 發布:2024-11-15 08:32:17 瀏覽:507
HDB3編解碼實驗 發布:2024-11-15 08:17:31 瀏覽:212
怪星球編程 發布:2024-11-15 08:15:55 瀏覽:844
慧編程價格 發布:2024-11-15 08:14:09 瀏覽:459
python多行注釋的快捷鍵 發布:2024-11-15 08:09:14 瀏覽:957