1

このコードを 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 バージョン ::

コンパイルしない:

   tur@aso:~$ 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)

コンパイル

   git@srvcode:/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)

全てに感謝!!

アルトゥール。

4

1 に答える 1

0

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

第 2 に、古いバージョンの gcc では、レジスタを入力/出力リストとクロバー リストの両方に含めることはできません。もちろん、入力/出力リストのレジスタは「破壊された」と見なされます。下位互換性のために、その動作に合わせて調整することをお勧めします。

また、インライン アセンブリのレジスタ オペランドは、実際の名前を使用して指定されないことに注意してください (クロバー リストを除く)。代わりに、レジスターを説明する単一の文字が使用されます。したがって、afor eaxbforebxなどがあります。また、おそらくGCC Inline Assembly HOWTOも読みたいと思うでしょう。これは、この主題に関する情報の優れたリソースです。

すべてを要約すると、そのようなものははるかにうまく機能するはずです:

__asm__("nop"
        : /* no output */
        : /* no input */
        : "%eax" /* eax is clobbered */
);
于 2012-04-23T11:59:46.207 に答える