GNU/Linux >> Linux の 問題 >  >> Linux

エラー:'asm' が宣言されていません (この関数で最初に使用)

オプション -std=c99 でコンパイルしています .

これにより、asm などの一部の非標準 GCC 拡張機能が無効になります。

一部の (あまり正確ではない) ドキュメントについては、https://gcc.gnu.org/onlinedocs/gcc/C-Dialect-Options.html#index-std-112 を参照してください。

set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -std=c99") を削除または変更します インライン アセンブリが必要な場合は、cmakefile から。


__asm__ を使用 asm の代わりに -std=c99 で 、または -std=gnu99 を使用

GCC ドキュメントから https://gcc.gnu.org/onlinedocs/gcc-7.2.0/gcc/Extended-Asm.html

<ブロック引用>

asm キーワードは GNU 拡張です。 -ansi およびさまざまな -std オプションでコンパイルできるコードを記述する場合は、__asm__ を使用します。 asm の代わりに (代替キーワードを参照)。

および https://gcc.gnu.org/onlinedocs/gcc-7.2.0/gcc/Alternate-Keywords.html#Alternate-Keywords:

<ブロック引用>

-ansi およびさまざまな -std オプションは、特定のキーワードを無効にします。これは、GNU C 拡張機能、または ISO C プログラムを含むすべてのプログラムで使用できる汎用ヘッダー ファイルを使用する場合に問題を引き起こします。キーワード asm、typeof、および inline は、-ansi または -std でコンパイルされたプログラムでは使用できません (ただし、inline は -std=c99 または -std=c11 でコンパイルされたプログラムで使用できます)。 ISO C99 キーワードの restrict は、-std=gnu99 (最終的にはこれがデフォルトになります) または -std=c99 (または同等の -std=iso9899:1999)、またはそれ以降の標準バージョンのオプションが使用される場合にのみ使用できます。

これらの問題を解決する方法は、 __ を置くことです 問題のある各キーワードの最初と最後に。たとえば、__asm__ を使用します asm の代わりに __inline__

他の C コンパイラは、これらの代替キーワードを受け入れません。別のコンパイラでコンパイルする場合は、代替キーワードをマクロとして定義して、通常のキーワードに置き換えることができます。次のようになります:

#ifndef __GNUC__
#define __asm__ asm
#endif

-pedantic およびその他のオプションは、多くの GNU C 拡張機能に対して警告を発します。 __extension__ を記述することで、1 つの式内でこのような警告を防ぐことができます。 表情の前。 __extension__ これ以外には何の効果もありません。

-std=gnu99 asm などの GNU 拡張を有効にします 、C99 ライクな言語を維持しながら。

C99 標準

GCC は、2 つのアンダースコア記号を予約済みとしてマークする C99 標準に準拠するために、このように動作します。

C99 N1256 標準ドラフト 7.1.3「予約済み識別子」1 から:

<ブロック引用>

各ヘッダーは、関連する副次節にリストされているすべての識別子を宣言または定義し、オプションで、関連する将来のライブラリの方向性副次節にリストされている識別子と、任意の使用またはファイルスコープ識別子として使用するために常に予約されている識別子を宣言または定義します。

  • アンダースコアと大文字または別のアンダースコアで始まるすべての識別子は、常に予約されています。

asm の場合 事前定義された、次のような合法的なプログラム:

int asm = 0;

テスト プログラム

#include <assert.h>
#include <stdint.h>

int main(void) {
    uint32_t io = 0;
    __asm__ volatile (
        "movl %0, %%eax;"
        "inc %%eax;"
        "movl %%eax, %0;"
        : "+m" (io)
        :
        : "%eax"
    );
    assert(io == 1);
}

Ubuntu 17.10、GCC 7.2 でテスト済み。


asm は gcc 拡張であるため、std=c99 のようなフラグでは使用できません または ansi

詳細については、https://gcc.gnu.org/onlinedocs/gcc/C-Extensions.html#C-Extensions

をご覧ください。
Linux
  1. Linux カーネルにはメイン機能がありますか?

  2. cygwinでlocateを使用するには?

  3. この smartctl (smartmon) データの解釈方法

  1. Rubyインストールエラーを修正する方法:EC_GROUP_new_curve_GF2mが宣言されていません(この関数での最初の使用)?

  2. 未定義の関数simplexml_load_file()の呼び出し–PHPエラー[解決済み]

  3. Runitを使用したUpstart/systemdに関するこのエラー?

  1. GPROF チュートリアル – Linux GNU GCC プロファイリング ツールの使用方法

  2. Linux でコマンド ライン シェル関数を使用する方法

  3. 致命的なエラー:未定義関数 curl_init() の呼び出し