2012-04-23 19 views
1

エラーx86_32で(エラー_ __asm__では不可能contraint)私はx86_64版でこのコードを書いて、コンパイルしても実行

__asm__("nop" 
      : "=eax"(foo) 
      : //"eax"(foo),"ebx"(bar) 
      : "eax" 
    ); 

が、私は他のマシンでコンパイルしようとすると(x86_32)gccのトリガーをコンパイルしません:S

inline1.c:6: error: impossible constraint in _asm_ 

私はそれを修正することはできません..:S

GCCのバージョン::

をコンパイルできません:

[email protected]:~$ gcc -v 
    Using built-in specs. 
    Target: i486-linux-gnu 
    Configured with: ../src/configure -v --with-pkgversion='Ubuntu 4.4.3-4ubuntu5.1' --      with-bugurl=file:///usr/share/doc/gcc-4.4/README.Bugs --enable-  languages=c,c++,fortran,objc,obj-c++ --prefix=/usr --enable-shared --enable-multiarch --  enable-linker-build-id --with-system-zlib --libexecdir=/usr/lib --without-included-gettext --enable-threads=posix --with-gxx-include-dir=/usr/include/c++/4.4 --program-suffix=-4.4 --enable-nls --enable-clocale=gnu --enable-libstdcxx-debug --enable-plugin --enable-objc-gc --enable-targets=all --disable-werror --with-arch-32=i486 --with-tune=generic --enable-checking=release --build=i486-linux-gnu --host=i486-linux-gnu --target=i486-linux-gnu 

スレッドモデル:POSIX gccのバージョン4.4.3(Ubuntuの4.4.3-4ubuntu5.1)

COMPILE

[email protected]:/home/git/code/asm$ gcc -v 
    Using built-in specs. 
    COLLECT_GCC=gcc 
    COLLECT_LTO_WRAPPER=/usr/lib/gcc/x86_64-linux-gnu/4.6.1/lto-wrapper 
    Target: x86_64-linux-gnu 
    Configured with: ../src/configure -v --with-pkgversion='Ubuntu/Linaro 4.6.1-  9ubuntu3' --with-bugurl=file:///usr/share/doc/gcc-4.6/README.Bugs --enable-languages=c,c++,fortran,objc,obj-c++,go --prefix=/usr --program-suffix=-4.6 --enable-shared --enable-linker-build-id --with-system-zlib --libexecdir=/usr/lib --without-included-gettext --enable-threads=posix --with-gxx-include-dir=/usr/include/c++/4.6 --libdir=/usr/lib --enable-nls --with-sysroot=/ --enable-clocale=gnu --enable-libstdcxx-debug --enable-libstdcxx-time=yes --enable-plugin --enable-objc-gc --disable-werror --with-arch-32=i686 --with-tune=generic --enable-checking=release --build=x86_64-linux-gnu --host=x86_64-linux-gnu --target=x86_64-linux-gnu 

スレッドモデル:POSIX gccバージョン4.6.1(Ubuntu/Linaro 4.6.1-9ubuntu3)

ありがとう!

Artur。

+0

あなたが32ビットのためのgcc-4.6を使用していないのはなぜも同様にコンパイル? – hirschhornsalz

答えて

0

nopはオペランドなしの命令です。インラインで使用されているオペランドがない場合、gccは使用されているオペランドにレジスタを割り当てることができません。これはおそらく入出力レジスタの設定に失敗するためです。しかし、命令によってレジスタは変更されないので、eaxを保存する必要があると思うのは非常に不思議です。

第2に、古いバージョンのgccでは、レジスタを入出力リストとクローバーリストの両方に置くことはできません。もちろん、入出力リスト上のレジスタは当然 "clobbered"であると見なされます。下位互換性のために、その動作に合わせて調整するのが最良です。

また、インラインアセンブリのレジスタオペランドは、実際の名前(クローバーリストを除く)で指定されていないことに注意してください。代わりに、レジスタを記述する1文字が使用されます。したがって、我々はeaxのためにaを、のためにebxのようにaを持っています。 GCC Inline Assembly HOWTOも読んでみたいと思うかもしれませんが、それはその件に関する情報のためのすばらしい資料です。それをすべてまとめる

、そのようなことは、より良い動作するはず:

__asm__("nop" 
     : /* no output */ 
     : /* no input */ 
     : "%eax" /* eax is clobbered */ 
); 
+0

私はsyscallsと彼のパラメータ(パラメータはレジスタにあります)をキャッチするカーネルモジュールを作成しています。 – arturn

関連する問題