2013-02-12 13 views
-1

我有使用-O2編譯gcc(4.1.2)的C++代碼。使用GCC優化的C++代碼導致內核具有無效的free()字符串

當此代碼被編譯並且在沒有優化的情況下運行時,程序執行時沒有任何問題。

與O1/O2/O3一起編譯時,代碼會崩潰,並顯示valgrind指示無效空閒。 這已被縮小到函數內部的字符串變量。

代碼將在文件中讀取,並將迭代內容。 我已刪除了所有的處理代碼,和下面的代碼片段會導致核心...

int MyParser::iParseConfig(Config &inConfig) 
{ 
    bool keepGoing = true; 

    while(keepGoing) 
    { 
     string valueKey = ""; 
     keepGoing = false; 
    } 
    return 0; 
} 

當此非優化的,它工作正常運行。 當我構建和運行這個優化,它不會工作。

它看起來是GCC優化字符串類的一個問題。

任何想法,我們可以繞過這個?

+0

你是否檢查過所有'free()'或'delete'調用? – Synxis 2013-02-12 17:22:24

+0

似乎對我很好。然而,缺少'else'子句似乎是可疑的。 – StoryTeller 2013-02-12 17:22:45

+0

在墜機時''我的價值是多少?如果它超過99,你的'charIndex'數組會遇到緩衝區溢出問題。 – 2013-02-12 17:24:21

回答

2

我無法解釋到底爲什麼當優化編譯,也許i獲得超過2個位數,你有一個緩衝區溢出這個代碼崩潰對你來說,也許是不同的東西,但無論如何,我會改變代碼:

sprintf(charIndex, "%d", i++); 
    string valueKey = ""; 
    valueKey.append("Value").append(charIndex); 
    string value = inConfig.sFindField(valueKey); 

這樣的:

stringstream ss; 
    ss << "Value" << i++; 
    string value(ss.str()); 

更C++ - 樣,應該工作。嘗試一下。調用printf

assert(i < 99); 

如果你是好奇,如果這真的是一個緩衝區溢出的情況下,插入行。或者使用snprintf

snprintf(charIndex, sizeof(charIndex), "%d", i++); 

或者使緩衝區變大。

+2

一個猜測:在優化時,charIndex被封裝到三個字節中。未優化時,'charIndex'有一些填充。另一種可能性是優化器正在移動東西,所以被溢出的項目正在改變。 – 2013-02-12 17:31:03

2

如果你溢出了charIndex(當我得到高於99)誰知道你的程序狀態是在...你聲明的存儲空間不是很大(2個字符和一個空)。

0

這是頭文件被錯誤地包含的問題 - 在包含列表中有MyParser.h文件的重複包含。 這導致了GCC優化級別內字符串優化的一些奇怪場景。