2013-09-27 59 views
1

我在寫一段代碼來檢查文件是否存在。當用戶傳入帶有名稱的文件參數時(無斜槓),我將檢查PATH環境變量中是否存在使用路徑的文件。我在Ubuntu上使用gcc編譯並使用gdb。我找到了引起SIGABRT的行,但我不確定信息告訴我什麼。這是我第一次使用gdb。這是我的片段:打開電話的SIGABRT

char* PATH = NULL; 
PATH = (char*)getenv("PATH"); 
char* pathtoken = strtok(PATH, ":"); 
int index = 0; 

while (pathtoken != NULL) 
{ 
    index++; 
    printf("%s\n", pathtoken); 
    char* pathdir = (char*)malloc(sizeof(pathtoken)); 
    strcpy(pathdir, pathtoken); 
    GetFullPath(pathdir, filename); 
    inputstream = fopen(pathdir, "r"); 

    if (inputstream != NULL) 
    { 
     free(pathdir); 
     break; 
     } 

     free(pathdir); 
     pathtoken = strtok(NULL, ":"); 
    } 

char* GetFullPath(char* dirpath, char* filename) 
{ 
    //Append back slash 
    int len = strlen(dirpath); 
    dirpath[len] = '/'; 
    dirpath[len+1] = '\0'; 

    return strcat(dirpath, filename); 
} 

它發生在fopen行的第一次迭代。這裏是我的gdb的輸出

啓動程序:text1的/home/seapoe/Documents/OsClass/CodePractice/a.out /usr/lib目錄/ lightdm/lightdm

斷點1,主(ARGC = 2, argv = 0xbffff3a4)at xssh.c:87

87 GetFullPath(pathdir,filename);

(GDB)下

89的InputStream =的fopen(pathdir, 「R」);

(GDB)打印pathdir

$ 5 = 0x804c008 「/ usr/lib中/ lightdm/lightdm/text1」 中

(GDB)打印pathdir [strlen的(pathdir)]

$ 6 = 0 '\ 000'

(GDB)打印pathdir [strlen的(pathdir)+1]

$ J = 0 '\ 000'

(GDB)打印pathdir [strlen的(pathdir)+2]

$ 8 = 0 '\ 000'

(GDB)打印pathdir [strlen的(pathdir)-1]

$ 9 = 49' 1'

(GDB)下

* glibc的檢測 /home/seapoe/Documents/OsClass/CodePractice/a.out:免費():無效 下一尺寸(正常):0x0804c018 * *

=======回溯:=========

/lib/i386-linux-gnu/libc.so.6(+0x75ee2)[0xb7e97ee2]

/lib/i386-linux-gnu/libc.so.6(+0x65db5)[0xb7e87db5]

/lib/i386-linux-gnu/libc.so.6(fopen+0x2b)[0xb7e87deb]

/home/seapoe/Documents/OsClass/CodePractice/a.out[0x8048a77]

/lib/i386-linux-gnu/libc.so。6(__ libc_start_main + 0xf3)[0xb7e3b4d3]

/home/seapoe/Documents/OsClass/CodePractice/a.out[0x8048771]

=======存儲器映射:====== ==

08048000-0804a000 R-XP 00000000 08:01 536263 /家庭/ seapoe /文檔/ OsClass /CodePractice/a.out

0804a000-0804b000 [R - p 00001000 08:01 536263 /家/seapoe/Documents/OsClass/CodePractice/a.out

0804b000-0804c000 rw-p 00002000 08:01 536263 /home/seapoe/Documents/OsClass/CodePractice/a.out

0804c000-0806d000 RW-P 00000000 00:00 0 [堆]

b7df3000-b7e0f000 R-XP 00000000 08:01 394136/lib中/i386-linux-gnu/libgcc_s.so.1

b7e0f000-b7e10000 - [R - p 0001b000 08:01 394136 /lib/i386-linux-gnu/libgcc_s.so.1

b7e10000-b7e11000 RW -p 0001c000 08:01 394136 /lib/i386-linux-gnu/libgcc_s.so.1

b7e21000-b7e22000 rw-p 00000000 00:00 0

b7e22000-b7fc5000 R-XP 00000000 08:01 394115 /lib/i386-linux-gnu/libc-2.15.so

b7fc5000-b7fc7000 - [R - P 001a3000 08:01 394115/LIB/i386- Linux的GNU/libc-2.15.so

b7fc7000-b7fc8000 RW-p 08:01 001a5000 394115 /lib/i386-linux-gnu/libc-2.15.so

b7fc8000-b7fcb000 RW-p 00000000 00 :00 0

b7fd9000-b7fdd000 rw -p 00000000 00:00 0

b7fdd000-b7fde000 R-XP 00000000 00:00 0 [VDSO]

b7fde000-b7ffe000 R-XP 00000000 08:01 394095 /lib/i386-linux-gnu/ld-2.15.so

b7ffe000 -b7fff000 r - p 0001f000 08:01 394095 /lib/i386-linux-gnu/ld-2.15.so

b7fff000-b8000000 rw -p 00020000 08:01 394095/lib/i386-linux-gnu/ld -2.15.so

bffdf000-C0000000 RW-p 00000000 00:00 0 [堆]

方案recei ved信號SIGABRT,中止。

在__kernel_vsyscall 0xb7fdd424()

調用GetFullPath後,你可以看到fopen的調用

回答

5
char* pathdir = (char*)malloc(sizeof(pathtoken)); 

是錯誤之前返回一個有效路徑。 sizeof(pathtoken)會給你係統上指針的大小(4或8)。 你想

pathdir = strdup(pathtoken) 

這也是錯誤的,因爲你正試圖追加到它。只要讓pathdir成爲MAX_PATH(或PATH_MAX,取決於您的操作系統)長度的char數組。

+0

哇非常感謝來自malloc()投的回報。我瘋了這個問題是微不足道的大聲笑 – Seapoe

2

問題是這樣的:

sizeof(pathtoken) 

sizeof操作者不工作的方式,它只是給你一個指針變量的大小,而不是提供了足夠的空間。你真正想要的是:

char* pathdir = malloc(strlen(pathtoken) + 1); 

或,作爲MK。如果你在GetFullPath()期間沒有試圖填充更多的字符,這就是你想要的。爲了彌補,要麼建立一個足夠大的靜態數組,他暗示,或做類似:

pathdir = GetFullPath(pathdir, filename); 

.... 

char* GetFullPath(char* dirpath, char* filename) 
{ 
    char * temp_path = malloc(strlen(dirpath) + strlen(filename) + 2); 
    if (temp_path == NULL) { 
     fprintf(stderr, "No memory!\n"); 
     exit(EXIT_FAILURE); 
    } 

    sprintf(temp_path, "%s/%s", dirpath, filename); 
    free(dirpath); 
    return temp_path; 
} 

不要在C.

+0

絕對像這樣更好 – Seapoe