2011-06-24 122 views
2

我正在檢查我的程序是否存在內存泄漏和損壞問題以及 我在使用setpwent時遇到了問題。 考慮簡單的程序爲:setpwent在valgrind中顯示內存泄漏

#include<stdio.h> 
#include<stdlib.h> 

main() 
{ 
    struct passwd *ent=NULL; 
    setpwent(); 
     while ((ent = getpwent()) != NULL) { } 
    endpwent(); 
} 

,當我在Valgrind的運行這段代碼,我得到這個:

> valgrind --track-origins=yes 
> --tool=memcheck --leak-check=yes --show-reachable=yes --num-callers=20 --track-fds=yes ./a.out . . . 160 (40 direct, 120 indirect) bytes in 1 
> blocks are definitely lost in loss 
> record 11 of 11 
> ==6471== at 0x4025BD3: malloc (vg_replace_malloc.c:236) 
> ==6471== by 0x411CA9C: nss_parse_service_list 
> (nsswitch.c:622) 
> ==6471== by 0x411D216: __nss_database_lookup (nsswitch.c:164) 
> ==6471== by 0x459BEAB: ??? 
> ==6471== by 0x459C1EC: ??? 
> ==6471== by 0x411D864: __nss_setent (getnssent_r.c:84) 
> ==6471== by 0x40D304F: setpwent (getXXent_r.c:127) 
> ==6471== by 0x8048469: main (in /root/workspace/cdk-examples/MMC-0.64/a.out) 
> ==6471== 
> ==6471== LEAK SUMMARY: 
> ==6471== definitely lost: 40 bytes in 1 blocks 
> ==6471== indirectly lost: 120 bytes in 10 blocks 
> ==6471==  possibly lost: 0 bytes in 0 blocks 
> ==6471== still reachable: 0 bytes in 0 blocks 
> ==6471==   suppressed: 0 bytes in 0 blocks 

我應該擔心嗎? 我該如何解決這個問題?

第二個問題: 我需要釋放密碼輸入:

main() 
{ 
    struct passwd *ent=NULL; 
    setpwent(); 
     while ((ent = getpwent()) != NULL) { 
      free(ent); 
     } 
     endpwent(); 
} 

謝謝你對我的幫助。

回答

3

對於第一個問題。無論如何,我認爲你不需要撥打setpwent。這是第一次致電getpwent(開始後或開始endpwent後),這可以追溯到開始。

如果你想後調用getpwent但沒有調用endpwent倒帶你只需要setpwent

單個set可能比一個end/get對更快,尤其是如果作爲我懷疑,整個(或一個相當大的比例)文件可以在存儲器被高速緩存的(a)


對於第二個問題,不,你不釋放它。見here。它很可能使用靜態緩衝區(用於單線程)或線程本地存儲(用於多線程)。

在這兩種情況下,都是管理緩衝區的調用本身,而不是您的代碼(a)


的(a)有趣的是,ent傳遞迴的值上,這當然看起來像獨立的分配每次迭代不同。

但是,由於地址間隔僅32字節,並且struct pwd的大小爲32字節,因此不會留下干預內部信息的空間。

因此,無論內務處理信息是不是內聯(不太可能),或者您實際上是在處理一系列結構而不是單個分配。

以下程序顯示了這個動作:

#include <stdio.h> 
#include <stdlib.h> 
#include <pwd.h> 

int main (void) { 
    struct passwd *ent = NULL; 
    printf ("ent struct is %d bytes\n", sizeof(*ent)); 
    while ((ent = getpwent()) != NULL) { 
     printf ("pointer is %p, user is %s\n", ent, ent->pw_name); 
     // free (ent); 
    } 
    endpwent(); 
    return 0; 
} 

它輸出:

ent struct is 32 bytes 
pointer is 0x4708d0, user is alan 
pointer is 0x4708f0, user is bill 
pointer is 0x470910, user is carl 
pointer is 0x470930, user is dawn 
pointer is 0x470950, user is ella 
pointer is 0x470970, user is fran 

這是什麼導致我上述結論。無論如何,我在我的代碼中取消註釋free這一行後,我得到一個核心轉儲,給予我的理論更多的支持。

現在,我想我可能剛剛過去,有一個看getpwent源代碼,但我喜歡好的拼圖:-)

+0

良好和合理的答案,答案 – rahman