2017-08-16 55 views
-1

我是相當新的C,我試圖讀取一個大型文件(> 30米行)逐行,並將每行的一些值存儲到數組中。輸入文件的格式是:大數字sscanf的分段錯誤

1. inode 100660 uid 66322 gid 66068 bytes  5848 blks  128 
2. inode 100662 uid 66492 gid 66076 bytes  159 blks   0 
3. inode 100647 uid 66419 gid 66068 bytes  235 blks   0 
4. inode 100663302 uid 66199 gid 66068 bytes  131 blks   0 
5. inode 100663311 uid 66199 gid 66068 bytes  134 blks   0 

這是我的代碼:

void loadArrayFromFile(char * filename) { 
long bytesArray[380000000]; 
FILE * myfile; 
myfile = fopen(filename, "r"); 
char line[1024]; 
char inodeText[10]; 
long int inode = 0; 
int mybytes = 0; 

if(myfile == NULL) { 
    printf("No file found \n"); 
    exit(EXIT_FAILURE); 
} 

while(fgets(line, sizeof(line), myfile)) { 
    int x = (sscanf(line, "%s %ld %*s %*d %*s %*d %*[bytes] %d %*[^\n]", inodeText, &inode, &mybytes)); 
    if(x > 1) { 
     bytesArray[inode] = mybytes; 
    } 
} 

代碼工作正常,在第3行,但是當它到達4號線,我得到一個分割故障(核心轉儲)錯誤。我懷疑它與inode值太大而無法存儲到int中有關,即使int的最大值可以存儲爲2147483647.任何人都可以幫我解決問題是什麼?

+0

'inodeText'緩衝區只有10個字節長。夠了嗎? –

+0

我能看到的最長單詞是'bytes'我認爲它是 –

+2

'bytesArray'定義在哪裏? – dbush

回答

2

您正在使用inode編號作爲索引bytesArray。你不會顯示這個數組有多大,但我敢打賭它比100663302小得多。所以你寫了超過數組的末尾。這調用undefined behavior

不是使用索引節點編號作爲索引,而是使用包含索引節點編號和文件大小的struct,並使用包含索引節點編號和文件大小的數組以及數組中元素的數量。

struct entry { 
    int inode; 
    int nbytes; 
}; 

struct entry entryArray[10]; // assuming there are no more than 10 lines in the file 
int arrayLen = 0; 

... 

while(fgets(line, sizeof(line), myfile)) { 
    int x = (sscanf(line, "%s %ld %*s %*d %*s %*d %*[bytes] %d %*[^\n]", inodeText, &inode, &mybytes)); 
    if(x > 1) { 
     entryArray[arrayLen].inode = inode; 
     entryArray[arrayLen].nbytes = mybytes; 
     arrayLen++; 
    } 
} 
+0

我怎麼可能錯過了這個。這樣一個簡單的修復。謝謝! –

+0

Iam想知道爲什麼我們可以傳遞比變量更多的指定符,並且無法在任何地方找到它。你能解釋它在幾行或張貼一些鏈接? –

+0

但是在代碼中'long bytesArray [380000000];'應該適合(除非堆棧先爆炸:)) –