2014-01-06 43 views
0

我編寫了一個用於處理命令行輸入的程序。當長字符串用作輸入時,我在memcpy()函數期間出現分段錯誤。memcpy(),更改預定義變量的值時的分段錯誤

下面是代碼:

int main(int argc, char * argv[]) 
{ 
    // initialize input variables 
    char inputFileName[] = "sequence.txt"; //default input file name 
    //check if a different file name is given 
    for(int i = 0; i < argc-1; i++){ 
     if(string(argv[i])=="-i"){ 
      cerr << "string: " << string(argv[i+1]).c_str() << endl; 
      cerr << "string size: " << string(argv[i+1]).size() << endl; 
      inputFileName[string(argv[i+1]).size()]=0; 
      cerr << "filename: " << inputFileName << endl; 
      memcpy(inputFileName,string(argv[i+1]).c_str(),string(argv[i+1]).size()); 
      cerr << "filename after memcpy: " << inputFileName << endl; 
      break; 
     } 
    } 
} 

當短文件名被賦予(-i sequence.fasta)它正常工作:

$ ./Program -i sequence.fasta 

string: sequence.fasta 
string size: 14 
filename: sequence.txt 
filename after memcpy: sequence.fasta 
filename final: sequence.fasta 

但是長的名字引起分段錯誤:

$ ./Program -i sequencesequencesequencesequencesequencesequencesequencesequencesequencesequence.fasta 

string: sequencesequencesequencesequencesequencesequencesequencesequencesequencesequence.fasta 
string size: 86 
filename: sequence.txt 
Segmentation fault: 11 

我錯過了什麼嗎?我應該如何處理memcpy()?

+2

'inputFileName'將不會足夠大以存儲結果,因此您將寫入未分配的內存,這是未定義的行爲,崩潰是一種可能的結果。 –

+0

最簡單的方法是不使用'memcpy'。 – juanchopanza

+1

只需將'std :: string'用於'inputFileName',並省略'operator ='的'memcpy'。 – Chad

回答

1

這是你的問題:

inputFileName[string(argv[i+1]).size()]=0; 

查找inputfilename具有預定義的大小等於strlen的爲 '\ 0'

char inputFileName[] = "sequence.txt"; //default input file name 

所以( 「sequence.txt」)+ 1個== 12bytes + 1字節如果使用字符串(argv [i + 1])。size()將其索引,則行爲不確定,如果argv [i + 1]長於13。

+0

我會建議使用'輸入文件名'的'std :: string'。 – Chad

+0

同意,修正它 – marcinj

0

除此之外陣列

char inputFileName[] = "sequence.txt"; 

的大小是固定的並且等於13的代碼具有另一錯誤。當您執行memcpy的

memcpy(inputFileName,string(argv[i+1]).c_str(),string(argv[i+1]).size()); 

那麼你不復制終止爲零,因爲表達string(argv[i+1]).size()沒有考慮到這一點。