質問

私は、私がシリアルを介して受け取る指示、コマンドを保存する必要があります。コマンドの長さは8ビットです。

コマンド名とその価値の間の透明性を維持する必要があります。シリアルで受信した8ビット番号をあらゆるタイプに翻訳する必要がないように。

私のコードでそれらに対処するために列挙を使用したいと思います。このプラットフォーム上のA 16ビット整数に対応する列挙のみが対応します。

プラットフォームは、AVR ATMEGA169Vマイクロコントローラーです バタフライデモボード. 。これは、16ビット操作のサポートが限られている8ビットシステムです。速いシステムではなく、約1kbのRAMがあります。ファイルI/Oやオペレーティングシステムなどの贅沢はありません。

では、8ビットコマンドを保存するために私が使用すべきタイプについての提案はありますか?
#definesの大規模なヘッダーよりも良いものがなければなりません。

役に立ちましたか?

解決

gcc's -fshort-enums 便利かもしれません:

宣言された可能性のある値の範囲に必要な数のバイトのみを「enum」タイプに割り当てます。具体的には、「列挙」タイプは、十分なスペースがある最小の整数タイプに相当します。

実際には、 ここ'関連情報がたくさんあるSAページ。あなたが存在することを知らなかった多くのGCCスイッチに出くわすことを願っています。 ;)

他のヒント

あなたは存在しない問題を解決しようとしています。

質問にはタグ付けされています。C言語の列挙型の列型は、積分タイプと完全に互換性があり、他の積分型と同じように動作します。式で使用する場合、それらは他の積分タイプとまったく同じ積分プロモーションにさらされます。それを考慮に入れたら、8ビットの積分タイプの列挙定数で記述された値を保存する場合は、適切な汎用8ビット積分タイプを選択するだけであることを認識する必要があります(たとえば int8_t)そして、列挙タイプの代わりにそれを使用します。タイプのオブジェクトに一定の値を保存することで、絶対に何も失うことはありません int8_t (列挙タイプで明示的に宣言されたオブジェクトとは対照的に)。

あなたが説明する問題は、C ++に存在します。ここでは、列挙タイプは他の積分型からはるかに遠くに分離されています。 C ++では、メモリを保存する目的で列挙タイプの代わりに積分タイプを使用することはより困難です(可能ですが)。しかし、Cではなく、追加の労力をまったく必要としません。

列挙が機能しない理由がわかりません。列挙との比較と割り当てはすべて、デフォルトの拡大で正常に動作するはずです。 8ビット値が正しく署名されていることに注意してください(署名されていない拡張機能が必要だと思います)。

この方法で16ビットの比較が得られます。それがパフォーマンスの問題にならないことを願っています(特に、プロセッサが16ビットのように思われる場合は、そうではないはずです)。

MicrosoftのCコンパイラを使用すると、このようなことを行うことができますが、それは拡張機能です(C ++ 0xの標準です):

enum Foo : unsigned char {
    blah = 0,
    blargh = 1
};

GCCにタグを付けたので、同じことが可能かどうかは完全にはわかりませんが、GCCには延長があるかもしれません gnu99 モードか何か。やってみて。

次の理由で、いずれにせよ、列挙にとどまることをお勧めします。

  • このソリューションにより、コマンド値をシリアルプロトコルが期待するものに直接マッピングできます。
  • 16ビットアーキテクチャを実際に使用している場合、8ビットタイプに移動する利点はそれほど大きくありません。保存された1つのメモリバイト以外の側面について考えてください。
  • 一部のコンパイラでは、実際の列挙サイズを使用して、最小限のビット数(バイトのみを使用しているバイトに収まる可能性がある列挙、その後16ビット、32)を使用しました。

まず、実際の型幅を気にしないでください。実際に効果的なストレージ方法が必要な場合にのみ、GNUコンパイラの-fshort -enumなどのコンパイラフラグを使用する必要がありますが、実際に必要な場合を除き、お勧めしません。

最後のオプションとして、「Enum」をコマンドのプレゼンテーションデータとして定義し、2つの簡単な操作でバイトへの変換を使用して、メモリにfromからコマンド値を保存 /復元する(そしてこれを1つの場所でカプセル化します)。これはどうですか?これらは非常に単純な操作であるため、インライン化することさえできます(ただし、これにより、ストレージに1バイトのみを使用し、反対側からは、好きなように定義された最も使用可能な列挙を使用して操作を実行できます。

関連する回答 アークコンパイラ (Designware Metaware C/C ++プログラマーガイドのARCから引用、セクション11.2.9.2)

列挙のサイズ列挙タイプのサイズは、トグル *long_enums *のステータスに依存します。

■トグル * long_enums *がオフの場合、列挙タイプのマップは1、2、または4バイトの最小にマップされ、すべての値を表すことができます。

■トグル * long_enums *がオンになっている場合、列挙は4バイトにマップします(AT&TポータブルCコンパイラコンベンションに一致します)。

ライセンス: CC-BY-SA帰属
所属していません StackOverflow
scroll top