2012-02-09 66 views
1

我跑Valgrind的,我收到以下錯誤.. 之前我做了一個備份我固定的,但現在我不記得如何。物通過的malloc產生錯誤,但在代碼Unitialised值(S)的valgrind

>Insert password for admin: ==5720== Conditional jump or move depends on uninitialised value(s) 
==5720== at 0x40299EB: strcmp (mc_replace_strmem.c:538) 
==5720== by 0x80496C6: adm_log_request (commands_man.c:169) 
==5720== by 0x80521CA: main (mmboxman.c:9) 
==5720== Uninitialised value was created by a heap allocation 
==5720== at 0x4028876: malloc (vg_replace_malloc.c:236) 
==5720== by 0x8049683: adm_log_request (commands_man.c:165) 
==5720== by 0x80521CA: main (mmboxman.c:9) 
==5720== 

這是函數 線commands_man我無法找到該錯誤:165是,如果後(大小> 0)

int adm_log_request(void){ 

FILE *password; 
char *pwdin, *frompwd = NULL; 
int primo = 0/*indica se è un primo avvio*/, tentativi = 2, p, size; 

if(!(password = fopen(F_PWD_ADM, "rb"))){ 
    primo = 1; 
    printf("First server boot\n>Insert password for admin: "); 
} 
else{ 
    primo = 0; 
    printf(">Insert password for admin: "); 
} 
p = get_hid_pass(&pwdin); 
if(p < 0) 
    return -1; 
switch(primo){ 
    case 0: 
     if(!(password = fopen(F_PWD_ADM, "r"))) 
      return -1; 
     fread(&size, sizeof(int), 1, password); 
     if(size > 0){ 
      frompwd = (char*)malloc(size + 1); 
      fread(frompwd,sizeof(frompwd),1,password); 
     }else return 0; 
     while(tentativi > 0){ 
      if(strcmp(pwdin, frompwd) != 0){ 
       printf("\nIncorrect password\n%d attempts left\n>Insert password for admin: ", tentativi); 
       tentativi--; 
      } 
      else return 1; 
      p = get_hid_pass(&pwdin); 
      if(p < 0) 
       return -1; 
     } 
     fclose(password); 
     break; 
    case 1:  //primo avvio del server 
     if(!(password = fopen(F_PWD_ADM, "w"))) 
      return -1; 
     size = strlen(pwdin) + 1; 
     fwrite(&size, sizeof(int), 1, password); 
     fwrite(pwdin, sizeof(pwdin), 1, password); 
     fclose(password); 
     break; 
} 
if(tentativi == 0) 
    return -1; 

return 1; 
} 

莫非有人幫我解決他們?謝謝你的問題

回答

1

部分看起來像sizeof一個問題:

 fread(frompwd,sizeof(frompwd),1,password); 

在上面的線,將的sizeof有4個(假設32位體系結構)的值。這可能是因爲你需要通過size的長度。然後它仍然需要在此之後被終止。

frompwd[size] = '\0'; 

fwrite通話也有類似的問題,將只寫4個字節的密碼。

+0

我發現問題..它在 size = strlen(pwdin)+ 1; +1錯了!謝謝!! =) – roccocullo 2012-02-09 15:46:53

+0

@roccocullo:這取決於你是否想寫空終止符字節或不。並且請注意,'fwrite'調用仍然需要被賦予正確的長度(大小)而不是sizeof結果。 – 2012-02-09 15:49:15

0

也許fread實際上並沒有設置size什麼嗎?

它不會保證它會。見(從the man page)其返回值:

返回值

的功能的fread()和fwrite()由數字超前的文件位置指示器 用於流的字節讀出或寫入。他們返回讀取或寫入的對象數量。如果發生錯誤或達到文件結尾,則返回值爲短對象計數(或零)。

函數的fread()之間沒有區分結束文件和錯誤;呼叫者必須使用feof(3)和ferror(3)來確定發生了哪一個。只有在發生寫入錯誤 時,函數fwrite()纔會返回一個小於nitems的值。

如果返回值是例如0,則size仍然未初始化管線165。一個好的做法是檢查fread返回的內容並確認實際讀取的值是否成功。

0

首先,從文件中讀取4個字節(或8個64位):

fread(frompwd,sizeof(frompwd),1,password); 

你可能並不意味着在這裏使用sizeof(frompwd)

然後你,比較使用STRCMP:

strcmp(pwdin, frompwd) 

strcmp進行比較,直到兩個字符串一個包含NUL '\ 0' 字符。在這種情況下,你從來沒有終止你的密碼字符串,因此消息。

您應該a)使用正確的讀取大小,並b)使用strncmp以確保您沒有像這樣的緩衝區溢出錯誤。

+0

實際上錯誤來自pwd [size] ='\ 0'; :) – roccocullo 2012-02-09 16:03:44

+0

不要忘記爲終結者分配空間。你需要字符串大小加1。 – ams 2012-02-10 09:25:13