簡體   English   中英

gcc自動矢量化在減少循環中失敗

[英]gcc auto-vectorization fails in a reduction loop

我試圖用自動矢量化標志編譯我的代碼,但我在一個非常簡單的減少循環中遇到了失敗:

double node3::GetSum(void){
    double sum=0.;
    for(int i=0;i<8;i++) sum+=c_value[i];
    return sum;
}

其中c_value[i]數組定義為

class node3{
private:
    double c_value[9];

自動向量化編譯返回:在node3.cpp處分析循環:10

node3.cpp:10: note: step unknown.
node3.cpp:10: note: reduction: unsafe fp math optimization: sum_6 = _5 + sum_11;

node3.cpp:10: note: Unknown def-use cycle pattern.
node3.cpp:10: note: Unsupported pattern.
node3.cpp:10: note: not vectorized: unsupported use in stmt.
node3.cpp:10: note: unexpected pattern.
node3.cpp:8: note: vectorized 0 loops in function.

node3.cpp:10: note: Failed to SLP the basic block.
node3.cpp:10: note: not vectorized: failed to find SLP opportunities in basic block.

我真的不明白為什么它無法確定SLP的基本塊例如。 此外,我想我不明白什么是“stmt中不支持的使用”:這里的循環簡單地總結了一個順序訪問數組。

c_value[]是否在類的private中定義,是否會導致此類問題?

提前致謝。

注意:編譯為g++ -c -O3 -ftree-vectorizer-verbose=2 -march=native node3.cpp ,並嘗試使用更具體的-march=corei7但結果相同。 GCC版本:4.8.1

我設法使用以下技巧在結尾處對循環進行矢量化:

double node3::GetSum(void){
    double sum=0.,tmp[8];
    tmp[0]=c_value[0]; tmp[1]=c_value[1]; tmp[2]=c_value[2]; tmp[3]=c_value[3];
    tmp[4]=c_value[4]; tmp[5]=c_value[5]; tmp[6]=c_value[6];tmp[7]=c_value[7];
    for(int i=0;i<8;i++) sum+=tmp[i];
    return sum;
}

我在哪里創建了虛擬數組tmp[] 這個技巧,再加上另一個編譯標志,即-funsafe-math-optimizations (@Mysticial:這實際上是我唯一需要的東西, -ffast-math與其他我顯然不需要的東西),使自動矢量化成功。

現在,我真的不知道這個解決方案是否真的加快了執行速度。 它確實是矢量化,但我添加了一個賦值操作,所以我不確定它是否應該運行得更快。 我的感覺是,從長遠來看(多次調用該功能)它會加速一點,但我無法證明這一點。 無論如何,這是矢量化問題的可能解決方案,所以我發布了答案。

令人討厭的是,矢量化減少的自由與其他(字面上)不安全的優化相結合。 在我的示例中,使用-mavx和-funsafe-math-optimizations組合出現了一個錯誤(使用gcc而不是g ++),其中一個永遠不會被觸及的指針會被破壞。 自動向量化並不能始終如一地加速這種短循環,特別是因為在更常見的CPU上使用hadd指令的總和減少結尾很慢。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM