我懷疑我發現了一個g ++優化錯誤,它涉及取消引用具有負索引的對象(結構體)中的數組。g ++ 4.8.5具有負數組索引的循環優化錯誤
在下文中,節點是結構,其具有陣列前述它(在我的實際代碼它是一個跳躍列表,其中它的兩個數的指針和其數據包的大小是可變的和未知的節點底層的SkipList代碼,因此決定將指針放在對象引用和數據包之前 - 在這個對象之後的這段時間很長)。
#include <iostream>
#include <stdlib.h>
class Node {
public:
unsigned int ptr[1]; // really an array going backwards
long datum; // This seems to be necessary for the bug to surface
};
class NodeList {
public:
Node* hdr;
NodeList() {
void* p_v = malloc(sizeof(Node) + 32 * sizeof(unsigned int));
hdr = (Node*)((char*)p_v + 32 * sizeof(unsigned int));
hdr->ptr[-5]=100;
}
void setNodes() {
int nn=0;
while(rand() > 20 && nn<9) {
nn++;
}
if(nn < 9) {
nn = 9;
}
// It is a logical truth that nn = 9 here
//nn = 9; // IF THIS IS UNCOMMENTED EVERYTHING WORKS!
std::cout << "nn=" << nn << " (should be 9) " << std::endl;
int ctr = 0;
for(int i=0; i<=nn; i++) {
ctr++;
hdr->ptr[-i]=0;
}
std::cout << "ctr was incremented " << ctr << " times (should be 10) and hdr->ptr[-5] = " << hdr->ptr[-5] << " (should be 0)\n";
}
};
int main(int argc, char** argv) {
NodeList list;
list.setNodes();
}
預期輸出具有CTR遞增10次,HDR-> PTR [-5]爲0優化代碼只是通過循環一次進入(即不循環),和葉ptr-> HDR [ - 5]爲100.這是一個錯誤。
-fno-aggressive-loop-optimizations似乎可以解決它,但顯然如果輸出代碼是正確的話會更好。
我把這裏放在這裏(a)得到驗證,這是一個錯誤,因爲我是一個新手,這是我的第一個問題,(b)詢問任何熟知gcc dev社區的人應該怎麼做它(例如,我應該如何報告它,以及它是否在後來的版本中得到修復),以及(c)允許在CentOS 7(或任何其他4.8版本的發行版)上經歷過這個最令人沮喪和耗時的問題的人,看到確認他們已經擊中了同胞患者的錯誤!
對(C風格)數組不使用負指數是未定義的行爲? – nefas
不,對於* all * n(正數和負數),'arr [n]'被定義爲'*(arr + n)'。當然,要確保參考是正確分配的內存。見[這個問題](https://stackoverflow.com/q/3473675/8084766) – galois99
[這個問題](https://stackoverflow.com/questions/3473675/are-negative-array-indexes-allowed-in- c)可能有你想要的答案。 – nefas