青青草原综合久久大伊人导航_色综合久久天天综合_日日噜噜夜夜狠狠久久丁香五月_热久久这里只有精品

統計

  • 隨筆 - 50
  • 文章 - 42
  • 評論 - 147
  • 引用 - 0

留言簿(6)

隨筆分類

文章分類

Link

搜索

  •  

積分與排名

  • 積分 - 167183
  • 排名 - 159

最新評論

閱讀排行榜

評論排行榜

如何檢測內存泄漏——重載new和delete
版權申明
本文可以被自由轉載,但是必須遵循如下版權約定:
1、保留本約定,并保留在文章的開頭部分。
2、不能任意修改文章內容,或者刪節,增加。如果認為本文內容有不當之處需要修改,請
與作者聯系。
3、不能摘抄本文的內容,必須全文發表或者引用。
4、必須保留作者署名、注明文章出處。(本文授權給www.linuxaid.com.cn)
5、如不遵守本規定,則無權轉載本文。 
作者
ariesram
電子郵件地址
ariesram@linuxaid.com.cn, 或 ariesram@may10.ca
本文及本人所有文章均收集在bambi.may10.ca/~ariesram/articles/中。
本文授權給www.linuxaid.com.cn。

正文:
我曾經參與過一個比較大的項目,在這個項目里面,我們沒有一個完全確定的設計文檔,所以程序的實現常常變動。雖然我們有一個比較靈活的框架,但是從程序的角度來講,它使我們的程序非常的混亂。直到發布的日期臨近,我們還沒有一個穩定的可以用來做alpha測試的版本。所以我們必須盡快的刪除掉無用的代碼,讓這個版本足夠的穩定。但是,在這個沒有足夠規范的軟件公司,我們沒有時間也沒有足夠的精力來做邊界測試之類的工作。所以我們只能采用變通的辦法。在軟件中最大的問題就是內存泄漏。因為往往出現這樣的情況,我們在一段代碼中分配了內存,但是卻沒有釋放它。這造成了很大的問題。我們需要一個簡單的解決方案,能夠簡單的編譯進這個項目,在運行的時候,它能夠產生一個沒有被釋放的內存的列表,用這個列表,我們能夠改正程序的錯誤。這就是我們稱之為內存跟蹤的方法。首先,我們需要一種代碼,能夠被加入到源代碼中去,而且這種代碼能夠被重用。代碼重用是一種很重要的特性,能夠節省大量的時間和金錢以及程序員的勞動。另外,我們的這種代碼必須簡單,因為我們當時已經沒有那么多的時間和精力去完全重看一遍所有的代碼來重新編寫以及改正錯誤從而使內存跟蹤能夠起作用。

好在,我們總能夠找到解決的辦法。首先,我們檢查了代碼,發現所有的代碼都是用new來分配內存,用delete來釋放內存。那么,我們能夠用一個全程替換,來替換掉所有的new和delete操作符嗎?不能。因為代碼的規模太大了,那樣做除了浪費時間沒有別的任何好處。好在我們的源代碼是用C++來寫成的,所以,這意味著沒有必要替換掉所有的new和delete,而只用重載這兩個操作符。對了,值用重載這兩個操作符,我們就能在分配和釋放內存之前做點什么。這是一個絕對的好消息。我們也知道該如何去做。因為,MFC也是這么做的。我們需要做的是:跟蹤所有的內存分配和交互引用以及內存釋放。我們的源代碼使用Visual C++寫成,當然這種解決方法也可以很輕松的使用在別的C++代碼里面。要做的第一件事情是重載new和delete操作符,它們將會在所有的代碼中被使用到。我們在stdafx.h中,加入:
#ifdef _DEBUG
inline void * __cdecl operator new(unsigned int size, 
const char *file, int line)
{
};

inline void __cdecl operator delete(void *p)
{
};
#endif
這樣,我們就重載了new和delete操作符。我們用$ifdef和#endif來包住這兩個重載操作符,這樣,這兩個操作符就不會在發布版本中出現。看一看這段代碼,會發現,new操作符有三個參數,它們是,分配的內存大小,出現的文件名,和行號。這對于尋找內存泄漏是必需的和重要的。否則,就會需要很多時間去尋找它們出現的確切地方。加入了這段代碼,我們的調用new()的代碼仍然是指向只接受一個參數的new操作符,而不是這個接受三個參數的操作符。另外,我們也不想記錄所有的new操作符的語句去包含__FILE__和__LINE__參數。我們需要做的是自動的讓所有的接受一個參數的new操作符調用接受三個參數的new操作符。這一點可以用一點點小的技巧去做,例如下面的這一段宏定義,
#ifdef _DEBUG
#define DEBUG_NEW new(__FILE__, __LINE__)
#else
#define DEBUG_NEW new
#endif
#define new DEBUG_NEW
現在我們所有的接受一個參數的new操作符都成為了接受三個參數的new操作符號,__FILE__和__LINE__被預編譯器自動的插入到其中了。然后,就是作實際的跟蹤了。我們需要加入一些例程到我們的重載的函數中去,讓它們能夠完成分配內存和釋放內存的工作。這樣來做, #ifdef _DEBUG
inline void * __cdecl operator new(unsigned int size,
const char *file, int line)
{
void *ptr = (void *)malloc(size);
AddTrack((DWORD)ptr, size, file, line);
return(ptr);
};
inline void __cdecl operator delete(void *p)
{
RemoveTrack((DWORD)p);
free(p);
};
#endif
另外,還需要用相同的方法來重載new[]和delete[]操作符。這里就省略掉它們了。
最后,我們需要提供一套函數AddTrack()和RemoveTrack()。我用STL來維護存儲內存分配記錄的連接表。
這兩個函數如下:
typedef struct {
DWORD address;
DWORD size;
char file[64];
DWORD line;
} ALLOC_INFO;

typedef list<ALLOC_INFO*> AllocList;

AllocList *allocList;

void AddTrack(DWORD addr, DWORD asize, const char *fname, DWORD lnum)
{
ALLOC_INFO *info;

if(!allocList) {
allocList = new(AllocList);
}

info = new(ALLOC_INFO);
info->address = addr;
strncpy(info->file, fname, 63);
info->line = lnum;
info->size = asize;
allocList->insert(allocList->begin(), info);
};

void RemoveTrack(DWORD addr)
{
AllocList::iterator i;

if(!allocList)
return;
for(i = allocList->begin(); i != allocList->end(); i++)
{
if((*i)->address == addr)
{
allocList->remove((*i));
break;
}
}
};
現在,在我們的程序退出之前,allocList存儲了沒有被釋放的內存分配。為了看到它們是什么和在哪里被分配的,我們需要打印出allocList中的數據。我使用了Visual C++中的Output窗口來做這件事情。
void DumpUnfreed()
{
AllocList::iterator i;
DWORD totalSize = 0;
char buf[1024];

if(!allocList)
return;

for(i = allocList->begin(); i != allocList->end(); i++) {
sprintf(buf, "%-50s: LINE %d, ADDRESS %d %d unfreed ",
(*i)->file, (*i)->line, (*i)->address, (*i)->size);
OutputDebugString(buf);
totalSize += (*i)->size;
}
sprintf(buf, "----------------------------------------------------------- ");
OutputDebugString(buf);
sprintf(buf, "Total Unfreed: %d bytes ", totalSize);
OutputDebugString(buf);
};
現在我們就有了一個可以重用的代碼,用來監測跟蹤所有的內存泄漏了。這段代碼可以用來加入到所有的項目中去。雖然它不會讓你的程序看起來更好,但是起碼它能夠幫助你檢查錯誤,讓程序更加的穩定。

posted on 2009-03-11 14:33 pear_li 閱讀(1982) 評論(0)  編輯 收藏 引用 所屬分類: C++

青青草原综合久久大伊人导航_色综合久久天天综合_日日噜噜夜夜狠狠久久丁香五月_热久久这里只有精品
  • <ins id="pjuwb"></ins>
    <blockquote id="pjuwb"><pre id="pjuwb"></pre></blockquote>
    <noscript id="pjuwb"></noscript>
          <sup id="pjuwb"><pre id="pjuwb"></pre></sup>
            <dd id="pjuwb"></dd>
            <abbr id="pjuwb"></abbr>
            一区二区欧美激情| 日韩一二三在线视频播| 亚洲国产精品99久久久久久久久| 国产精品久久久久aaaa| 91久久在线| 欧美日韩免费高清一区色橹橹| 亚洲国产91精品在线观看| 亚洲精品一级| 欧美日韩欧美一区二区| 亚洲欧美在线aaa| 美女图片一区二区| 夜夜嗨av一区二区三区中文字幕| 国产精品实拍| 欧美成人有码| 欧美一区二区视频观看视频| 亚洲电影免费| 久久精品久久综合| 亚洲看片网站| 在线成人激情视频| 国产精品在线看| 欧美日韩成人综合在线一区二区| 亚洲欧美日韩另类| 亚洲欧洲日本专区| 女生裸体视频一区二区三区| 亚洲视频在线观看视频| 亚洲电影成人| 激情国产一区| 99re8这里有精品热视频免费 | 欧美一区二区免费| 亚洲高清123| 亚洲黄色一区二区三区| 黑人中文字幕一区二区三区| 国产精品天美传媒入口| 欧美日韩国产电影| 欧美黄色大片网站| 欧美成人国产| 欧美欧美全黄| 欧美亚洲成人精品| 国产精品久久午夜夜伦鲁鲁| 欧美日韩人人澡狠狠躁视频| 欧美视频导航| 国产欧美日韩精品专区| 国产一区二区av| 尤物99国产成人精品视频| 狠狠色伊人亚洲综合成人| 在线观看亚洲视频| 亚洲精品在线一区二区| 中文在线不卡| 久久精品一区二区三区不卡牛牛 | 亚洲乱码久久| 亚洲欧美另类在线观看| 久久久久久91香蕉国产| 免费观看成人| 国产精品成人一区二区| 国产尤物精品| 一本到高清视频免费精品| 久久久久**毛片大全| 亚洲国产裸拍裸体视频在线观看乱了中文 | 羞羞漫画18久久大片| 国产亚洲在线观看| 亚洲国产精品va在线看黑人动漫| 亚洲精品影视在线观看| 欧美专区日韩专区| 亚洲激情成人| 欧美一区二区三区免费观看视频 | 久久婷婷国产综合精品青草| 欧美激情中文字幕乱码免费| 亚洲伊人观看| 欧美日韩国产va另类| 激情久久久久久久| 欧美一区永久视频免费观看| 亚洲精品小视频在线观看| 欧美gay视频| 激情久久久久| 久久噜噜噜精品国产亚洲综合| 一区二区三区视频观看| 欧美精品久久久久久久久老牛影院 | 亚洲精品久久7777| 久久夜色精品| 老牛国产精品一区的观看方式| 狠狠色噜噜狠狠色综合久| 久久精品国产在热久久| 久久不射中文字幕| 国产综合色在线| 乱中年女人伦av一区二区| 午夜视频在线观看一区二区| 亚洲承认在线| 国产精品v欧美精品∨日韩| 亚洲在线观看免费| 亚洲一区二区三区视频播放| 国产麻豆午夜三级精品| 久久嫩草精品久久久久| 蜜桃久久精品一区二区| 亚洲视频欧美视频| 午夜精品久久久久久久99黑人| 国产精品一区二区你懂的| 久久狠狠亚洲综合| 欧美mv日韩mv国产网站| 中文精品视频| 久久成人精品无人区| 亚洲国产三级网| 亚洲欧美日韩区| 亚洲第一福利在线观看| 亚洲天堂网站在线观看视频| 午夜在线观看免费一区| 夜夜夜精品看看| 欧美一级在线视频| 99国产精品久久久久久久| 亚洲一区二区成人在线观看| 亚洲国产精品一区二区第一页| 99国产精品视频免费观看| 国产伦精品一区二区三区免费 | 在线精品一区| 日韩视频免费| 亚洲精品乱码久久久久久蜜桃91| 亚洲自拍高清| 亚洲欧美不卡| 欧美日韩视频| 日韩午夜高潮| 亚洲视频www| 欧美激情黄色片| 99re6热只有精品免费观看| 久久精品国产一区二区三区免费看| 一区二区久久| 欧美三级小说| 99精品视频免费在线观看| 亚洲精品一品区二品区三品区| 久久久久一区二区三区| 欧美资源在线观看| 国产精品日本精品| 一区二区三区欧美激情| 亚洲一区久久久| 国产精品外国| 欧美怡红院视频一区二区三区| 欧美一区午夜精品| 黄色影院成人| 免费国产自线拍一欧美视频| 亚洲三级观看| 久久av一区二区三区| 狠狠干狠狠久久| 欧美88av| 亚洲欧美成人精品| 毛片基地黄久久久久久天堂| 午夜精品久久久久久久99水蜜桃 | 久久国产精品久久国产精品| 国产日韩欧美| 欧美日韩免费观看一区二区三区 | 另类图片综合电影| 亚洲人屁股眼子交8| 亚洲一级黄色av| 伊人色综合久久天天| 欧美精品91| 久久最新视频| 欧美一级欧美一级在线播放| 亚洲国产毛片完整版| 久久激情视频| 亚洲一区二区三区免费视频| 亚洲国产中文字幕在线观看| 国产欧美一区二区精品性色| 欧美黄色精品| 麻豆av一区二区三区| 亚洲一级在线观看| 亚洲毛片在线| 亚洲久色影视| 亚洲精品1区| 亚洲欧洲日产国码二区| 男女视频一区二区| 欧美成人精品一区| 裸体一区二区| 欧美激情一区二区三区全黄| 免费观看成人www动漫视频| 久久精品国产99国产精品| 亚洲欧美日韩成人高清在线一区| 亚洲私拍自拍| 亚洲一区免费在线观看| 亚洲一区二区三区777| 一区二区91| 久久精品一本| 亚洲电影网站| 一区二区三区视频观看| 亚洲欧美日韩中文在线制服| 西西裸体人体做爰大胆久久久| 久久精品一二三区| 欧美激情综合色| 国产一区三区三区| 亚洲人成小说网站色在线| 一区二区三区欧美日韩| 久久九九热re6这里有精品| 噜噜噜噜噜久久久久久91| 欧美激情视频网站| 一本色道久久| 久久精品亚洲一区| 亚洲国产欧美在线人成| 亚洲网站在线播放| 欧美成人国产va精品日本一级| 欧美日韩视频专区在线播放 | 一区二区久久久久久| 欧美专区在线| 亚洲精品美女在线| 久久久久久69|