[英]SEGFAULT in -O3 mode?
我將我的問題總結為以下簡短程序。
它僅在-O3模式下導致SEGFAULT(-O2正常工作)。 根據gdb
它發生在*f = 0
行。
#include <iostream>
void func1(int s, int t)
{
char* buffer = new char[s + t*sizeof(float)];
if (!buffer)
{
std::cout << "new failed\n";
return;
}
float* f = (float*)(buffer + s);
for (int i = 0; i < t; ++i)
{
*f = 0;
//std::cout << i << std::endl; // if uncomment this line everything will work fine
++f;
}
delete [] buffer;
std::cout << "done\n";
}
int main()
{
int s = 31, t = 12423138;
std::cout << s << " " << t << std::endl;
func1(s, t);
return 0;
}
請讓我知道,我做錯了什么?
SEGFAULT的來源不僅僅違反嚴格的別名規則,因為即使使用-fno-strict-aliasing標志,問題仍然存在。
它確實是在訪問未對齊的內存,但並非如此簡單。 作為現代處理器,通常允許未對齊的內存訪問,並且如今甚至沒有太多的開銷。 我已經進行了一些基准測試,並且在2.80GHz的Intel®Xeon®CPU E5-2680 v2上觀察到的未校對讀量和未校對讀量沒有顯着差異。 網絡上也有一些非常相似(或多或少是最近的)結果。
我的問題是-O3
模式啟用-ftree-vectorize
標志,因此我的for
循環已矢量化(如使用-ftree-vectorizer-verbose
標志-ftree-vectorizer-verbose
)。 而且(AFAIU)還不支持使用矢量化指令進行未對齊的內存訪問(還?),因此存在運行時異常。
這篇文章對我的理論理解有很大幫助,盡管看起來今天未對齊的內存訪問雖然沒有那么麻煩,但是仍然很棘手。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.