2012-06-19 4 views
7

のgccのインラインアセンブラ早期クロバー制約が、ここではgccのドキュメントに、ここで説明されていますinputs = outputsのこのgccスタイルのasmは早いクローバーが必要ですか?

http://gcc.gnu.org/onlinedocs/gcc/Modifiers.html#Modifiers

私たちは、128ビットの追加のAMD64の実装を持っている:

#define ADD128(rh, rl, ah, al, bh, bl)          \ 
    __asm__("addq %2, %0; adcq %3, %1"          \ 
      /* outputs */ : "=r"(rl), /* %0 */       \ 
          "=r"(rh) /* %1 */       \ 
      /* inputs */ : "emr"(bl), /* %2 */       \ 
          "emr"(bh), /* %3 */       \ 
          "0"(al), /* %4 == %0 */      \ 
          "1"(ah) /* %5 == %1 */      \ 
      /* clobbers */: "cc"  /* condition registers (CF, ...) */ \ 
      ) 

これは使用しなければならない場合、私は思っていました%0の早期クロバー(&):

#define ADD128(rh, rl, ah, al, bh, bl)         \ 
    __asm__("addq %2, %0; adcq %3, %1"          \ 
      /* outputs */ : "=&r"(rl), /* %0 */       \ 
          "=r"(rh) /* %1 */       \ 
      /* inputs */ : "emr"(bl), /* %2 */       \ 
          "emr"(bh), /* %3 */       \ 
          "0"(al), /* %4 == %0 */      \ 
          "1"(ah) /* %5 == %1 */      \ 
      /* clobbers */: "cc"  /* condition registers (CF, ...) */ \ 
      ) 

しかし、私はそうはわから秒ではなかったですインプットは、amd64バージョン(%0 == %4,%1 == %5)で明示的に出力されていますか?

最初の非初期バージョンは、現在使用しているすべての最適化レベルで動作しているようです(gccはこのターゲットでネイティブint128操作をサポートするので、gccを使用する場合はこれは必要ありません) 。

インラインasmの初期clobberのgcc仕様に厳密に準拠するためには、inputs = outputs文でも%0の制約には&が必要ですか?

答えて

1

bhalと全く同じ式でこのマクロを呼び出すと、早いクローバーが必要になります。その場合、クローバーがなければ、コンパイラは%3%4(同じ%0と同じ)を使用することを選択する可能性があります。そのため、最初の命令は2番目の式がそれを読み取る前にその値を壊す可能性があります。

この問題を引き起こす可能性のある方法で実際にマクロを呼び出すことはあまりありません。そのため、クローバーなしで問題がないことは驚くことではありません。クローバーを追加すると、blと同じalと同じマクロを呼び出すと(たとえば、その場所に128ビットの値を追加するなど)余分な(不要な)レジスタコピーが導入されるため、やや望ましくありません。

関連する問題