7

この SO 投稿によると:
C の列挙型のサイズは?
列挙型にはsigned inttype があります。

signed int列挙型定義を からに変換したいと思いunsigned intます。

たとえば、私のプラットフォームでは、anunsigned intは 32 ビット幅です。列挙型を作成したい:

typedef enum hardware_register_e
{
    REGISTER_STATUS_BIT = (1U << 31U)
} My_Register_Bits_t;

私のコンパイラは、上記の定義が範囲外であると不平を言っています(これは a の場合ですsigned int)。

unsigned int enum値 を宣言するにはどうすればよいですか?

編集1:

  1. 64 ビットに拡張しないことをお勧めします (コードが組み込みシステムに存在するため)。
  2. スキルの制限により、このプロジェクトでは C++ は使用できません。:-(

編集2:

  • コンパイラは、ARM7 用の IAR Embedded Workbench です。
4

4 に答える 4

4

このSOの投稿によると:Cの列挙型のサイズはどれくらいですか?列挙型にはsignedint型があります。

タイプはenumタイプにすることができますが、Cintにはありません。1)では、タイプはデフォルトです。intgcc enumunsigned int

enum定数はですintが、enum型は実装によって定義されます。

あなたの場合、enum定数はintですが、に収まらない値を与えていますintunsigned int enumCが言うように、Cに定数を含めることはできませんint


1)gcc実装で定義された列挙型のドキュメント:http: //gcc.gnu.org/onlinedocs/gcc/Structures-unions-enumerations の「通常、列挙に負の値がない場合、型はunsignedintです。それ以外の場合はintです」 -and-bit_002dfields-implementation.html

于 2012-07-03T15:51:24.897 に答える
3

残念ながら、ISO C 標準 (c99 6.4.4.3) では、列挙定数の型は であると規定されていますint。上記を eggcc -W -std=c89 -pedanticでコンパイルすると、警告が発行されますISO C restricts enumerator values to range of ‘int’ [-pedantic]。一部の組み込みコンパイラは、コードをまったく受け入れない場合があります。

コンパイラがよりうるさい種類のものである場合は、次を使用して問題を回避できます。

typedef enum hardware_register_e
{
    REGISTER_STATUS_BIT = -2147483648   /* 1<<31, for 32-bit two's complement integers */
} hardware_register_t;

intただし、アーキテクチャ上で 32 ビットの 2 の補数型である場合にのみ正しく機能します。これは、私がこれまでに使用したり聞いたりしたすべての 32 ビットおよび 64 ビット アーキテクチャに搭載されています。

追加するために編集: ARM7 は 32 ビットの 2 の補数int型を使用するため、上記は正常に動作するはずです。実際の値が であることを説明するコメントを残すことをお勧めします1<<31。誰かがコードを移植したのか、別のコンパイラを使用したのかはわかりません。新しいコンパイラが警告を発行する場合、同じ行のコメントにより修正が簡単になります。個人的には、おそらくコードを条件付きでラップします。

typedef enum hardware_register_e
{
#ifdef __ICCARM__
    REGISTER_STATUS_BIT = -2147483648   /* 1<<31, for 32-bit two's complement integers */
#else
    REGISTER_STATUS_BIT = 1 << 31
#endif
} hardware_register_t;
于 2012-07-03T15:57:31.060 に答える
1

コンパイラに列挙型を無署名にするオプションまたはプラグマがあるかどうかを確認してください。そうでない場合は、列挙型の代わりにプレーンunsigned int(または などの固定幅型) を使用し、 s を使用して値を定義する必要があります。uint32_t#define

于 2012-07-03T15:50:07.113 に答える
1

列挙型のタイプを (少なくとも移植可能に) 変更することはできません。列挙型定数の型が であることは、標準で明確ですint。警告を取り除くには、キャストを使用できます。

typedef enum hardware_register_e
{
    REGISTER_STATUS_BIT = (int)(1U << 31U)
} My_Register_Bits_t;

可能な代替案

これがヘッダーにある必要がない場合はconst、列挙定数の代わりに必要なタイプのオブジェクトを使用できます。

const unsigned int REGISTER_STATUS_BIT = (1U << 31);

それ以外の場合は、定義を使用できます。

#define REGISTER_STATUS_BIT (1U << 31)
于 2012-07-03T15:50:18.067 に答える