2017-06-28 12 views
-4

プログラムを高速化するために_mm256_load_ps()イントリンシックを使用しようとしました。私が一度に8つの浮動小数点をロードし、それらをさらに計算に使用するために266bベクトルに格納することを意味します。_mm256_load_ps()を使用したときのエラーインテルイントリンシック

/* code snipet */ 
a_vec = _mm256_load_ps(&a[0]) 
b_vec = _mm256_load_ps(&b[0]) 
res = _mm256_addsub_ps(a,b) 
/* code snipet */ 

また、私は私のメイクにこれらのフラグを使用:

CC=gcc 
CFLAGS=-g -c -Wall -O5 -mavx -mfma -ffast-math 

そして私は、私のプロセッサがAVX拡張をサポートしていることを確認作りました。しかし、私は私のコードをコンパイルするとき、私はこの警告を得続ける:

警告:私はUbuntuの12.04 LTSの64-ビットに

を使用しています:AVXベクトルリターンをAVXせずに有効にすると、ABI [-Wpsabi]

PSを変更します

+0

この32ビットコードはありますか?どのオペレーティングシステムをターゲットにしていますか?おそらくABIはAVXレジスタで値を返すことはできません。私は*あなたが私たちから隠した '/ * code snipet * /'部分に 'return'ステートメントがあると仮定します。 –

+0

もう1つ追加するには...私は128bベクトルから256bベクトルへ私のコードを変換していますが、私はその問題があるかもしれないというアライメントを変更していません!!また、インプレースコードを作成してリターンはありません。 –

+1

@ A.nechi AVXはSSEと比較してアラインメント要件を緩和しますが、 '_mm256_load_ps()'は明示的にアライメントされたロード( 'MOVAPS')です。 – EOF

答えて

2

あなたのMakefileまたはあなたのビルドの何かが壊れています。 -O5 -mavxは確実にAVXを有効にします。そのため、コンパイラにこれらのオプションが表示されていないことを示す警告が表示されます。

おそらく、コードはまったくコンパイルされず、後でエラーメッセージが表示されることがあります。 _mm256_load_psは、AVXサポートが有効になっていないと認識されません。

このコード:gcc -march=haswell -O3-march=haswell-mavxを意味する)と

#include <immintrin.h> 

__m256 foo(const float *a, const float *b) 
{ 
    __m256 a_vec = _mm256_load_ps(&a[0]); // assumes a and b are 32-byte aligned. 
    __m256 b_vec = _mm256_load_ps(&b[0]); 
    __m256 res = _mm256_addsub_ps(a_vec, b_vec); 
    return res; 
} 

は、私のためにうまくコンパイル。 The asm output is-cは、通常のMakefileの設定でCFLAGSの一部であってはならないことを

vmovaps  ymm0, YMMWORD PTR [rdi] 
    vaddsubps  ymm0, ymm0, YMMWORD PTR [rsi] 
    ret 

は注意してください。これは.c.oパターンルールの一部である必要があります。

また、より現代的なコンパイラを使用すれば、より良い結果が得られます。 Ubuntu 12.04は5年以上経過しており、AVXはまだまだ新しいものです。新しいコンパイラは最近のCPU拡張でより良い仕事をします。 gcc6.3は良い選択です。 gcc7.1は廃止されましたが、まだまだ新しいものです。

+1

コードはGCC 6.3でよく見えます64ビットを対象としていますが、32ビットに切り替えると、[オプティマイザは愚かになります](https://godbolt.org/g/v1ypgb)。その「LEA」の指示は何ですか?他のコンパイラはそれを正しく取っているので、これはGCCコードのバグのように見えますが、まだトランクでは修正されていません。 –

+0

@CodyGray:yuck。 'ecx'のセーブ/リストアも狂っています。これは古いgccのコードとは異なりますが、 '__m256'変数のすべての流出を最適化した後でもスタックを32Bに整列させることができます。うーん、['-O1'コード](https:// godbolt。org/g/9b6Uyj)は、おそらく軽い光を当てるでしょう: 'lea ecx、[esp + 8]'/'mov edx、[ecx]'/'mov eax、[ecx + 4]'を使ってポインタはスタックからargsします。それはgccのように見える(それはいくつかの狂った理由のために) "考えている"が、それからいくつかのものを最適化する。まだ上流に報告しましたか?そうでなければ、私はそうするでしょう。 –

+0

ありがとう、@Cody。私は通常、どのコンポーネントを選ぶべきかを推測しなければなりません。なぜなら、ボンネットの下のものの専門家ではないので、IDLはRTLであり、中間エンドなどです。この場合、x86固有のものに見えるので、 "target"は良い選択です。もし私が確信が持てないなら、gccのデベロッパーが必要に応じてタグを付け直すことができるように、本文で言及したいと思います。 –

関連する問題