CC-RXもGNURXもC99仕様では_Pragmaプリプロセッサ演算子というものが使えるのですね(FITのコンパイラ対応の効率化に役立ちそうかも)

こんにちは。NoMaYです。

別スレッド『Amazon FreeRTOSだそうです。ルネサスさんのRXは参加しないのかな?』でCC-RX用プロジェクトをGNURX用プロジェクトへ移植する作業をぽつりぽつりとやっていて、CC-RXの#pragma pack / #pragma packoption相当のものとしてGNURXで#pragma pack(1) / #pragma pack()が使えることに気付いたのですが、たまたま同じタイミングで更に別スレッドの作業をやっていてGNURXで#pragma address 変数名 アドレスという記述が使えるらしいことに気付き、調べているうちにFITが前提としているC99仕様では_Pragmaプリプロセッサ演算子(関連リンク参照)というものが使えることを知りました。_Pragmaを使うと以下のように#pragmaをプリプロセッサで扱うことが出来るようになり、FITのコンパイラ対応の効率化に役立ちそうかも知れないと思いました。

#define R_PRAGMA(...) _Pragma(#__VA_ARGS__)

#if defined(__CCRX__)

#define R_PRAGMA_PACK       R_PRAGMA(pack)
#define R_PRAGMA_PACKOPTION R_PRAGMA(packoption)

#elif defined(__GNUC__)

#define R_PRAGMA_PACK       R_PRAGMA(pack(1))
#define R_PRAGMA_PACKOPTION R_PRAGMA(pack())

#endif
/*
 * EDMAC descriptor as defined in the hardware manual. It is
 * modified to support little endian CPU mode.
 */
    R_PRAGMA_PACK

typedef struct DescriptorS
{
    __evenaccess uint32_t           status;
    #if __LIT
    /* Little endian */
    __evenaccess uint16_t           size;
    __evenaccess uint16_t           bufsize;
    #else
    /* Big endian */
    __evenaccess uint16_t bufsize;
    __evenaccess uint16_t size;

    #endif
    uint8_t            *buf_p;
    struct DescriptorS *next;
} descriptor_t;

/*
 * Ethernet buffer type definition.  
 */
typedef struct EtherBufferS
{
    uint8_t buffer[EMAC_NUM_BUFFERS][ETHER_CFG_BUFSIZE];

} etherbuffer_t;

typedef struct pause_resolutionS
{
    pausemask_t mask;
    pauseval_t  value;
    uint8_t     transmit;
    uint8_t     receive;
} pauseresolution_t;

typedef struct
{
    volatile struct st_etherc __evenaccess * petherc; /* ETHERC module */
    volatile struct st_edmac __evenaccess * pedmac; /* EDMAC */
    volatile uint32_t         __evenaccess * preg_pir;
    uint32_t                  phy_address;
    uint8_t                   port_connect;
} ether_control_t;

typedef struct
{
    const ether_control_t * pether_control;
    uint32_t              phy_access;
} ether_ch_control_t;

    R_PRAGMA_PACKOPTION

[関連リンク]

クローバーフィールド.jp/_pragma演算子を使ってみた。
embedded.cloverfield.jp/2016/04/12/_pragma演算子ではまりました。
infocenter.arm.com/help/topic/com.arm.doc.dui0472ij/BABDIJDD.html
cpprefjp.github.io/lang/cpp11/pragma_operator.html
Google検索: _Pragma

[補足]

gcc-renesas.comのドキュメントには記載無いがGCC本家のドキュメントの#pragma pack(1) / #pragma pack()が使えました。(実はiodefine.hでも使われていました。)

GNURX
gcc-renesas.com/migration-guides/rx/index.html#Compiler_directives

GCC本家
gcc.gnu.org/onlinedocs/gcc-4.7.1/gcc/Structure_002dPacking-Pragmas.html#Structure_002dPacking-Pragmas
 

Parents
  • こんにちは。NoMaYです。

    IARコンパイラでワーニングレベルを上げてFITモジュールをコンパイルしてみて、CC-RX/GNURX/ICCRX共通化インラインアセンブラ記述マクロでワーニングが出てしまうことに気付きました。これについては、以下のように共通化マクロを変更したところ、コンパイルオプションで個別ワーニング抑止指定を設定しなくても、抑止することが出来るようになりました。(もっとも、何がしかの設定をしませんと、ワーニング検出箇所が多過ぎたり、エラー扱いされてしまって厳し過ぎたり、ということで後々大変になりますので、どうせ何がしかの設定をしないといけないのであれば、マクロ定義をややこしくするまでも無いのではないか、という考え方もあるかとは思いましたけれど、、、) これはFITモジュール側での採用を働きかけたいですね、、、

    EWRXでワーニングレベルを上げる設定の画面コピー (CC-RXはインフォメーションメッセージですがICCRXはリマークメッセージでした)


    EWRXでワーニングレベルを上げると表示されるワーニング(というかリマーク)メッセージの例(ちなみに他の箇所にも大量に表示されます)

    リマーク[Pe007]: unrecognized token C:\Renesas\...\r_bsp_common.c 108 
    リマーク[Pe007]: unrecognized token C:\Renesas\...\r_bsp_common.c 109
    リマーク[Pe007]: unrecognized token C:\Renesas\...\r_bsp_common.c 110
    リマーク[Pe007]: unrecognized token C:\Renesas\...\r_bsp_common.c 111
    リマーク[Pe010]: "#" not expected here C:\Renesas\...\r_bsp_common.c 112
    リマーク[Pe010]: "#" not expected here C:\Renesas\...\r_bsp_common.c 112
    リマーク[Pe007]: unrecognized token C:\Renesas\...\r_bsp_common.c 112
    リマーク[Pe007]: unrecognized token C:\Renesas\...\r_bsp_common.c 113
    リマーク[Pa174]: inline assembler statement has no declared side-effect. All optimizations around it will be disabled.  C:\Renesas\...\r_bsp_common.c 107
    Either add side-effect declarations or add volatile.



    変更対象: src/smc_gen/r_bsp/mcu/all/r_rx_compiler.h

    変更前

    /* ---------- Inline Expansion of Assembly-Language Function (part2) ---------- */
    #if defined(__CDT_PARSER__)

    #define R_BSP_ASM(...)            /* none */
    #define R_BSP_ASM_LAB_NEXT(n)     /* none */
    #define R_BSP_ASM_LAB_PREV(n)     /* none */
    #define R_BSP_ASM_LAB(n_colon)    /* none */
    #define R_BSP_ASM_BEGIN           /* none */
    #define R_BSP_ASM_END             /* none */

    #else

    #if defined(__CCRX__)

    #if !defined(__cplusplus)
    #define R_BSP_ASM(...)            __VA_ARGS__
    #else
    /* CC-RX' C++ mode does not support variadic macros */
    #endif
    #define R_BSP_ASM_LAB_NEXT(n)     ?+
    #define R_BSP_ASM_LAB_PREV(n)     ?-
    #define R_BSP_ASM_LAB(n_colon)    R_BSP_ASM(?:)
    #define R_BSP_ASM_BEGIN           /* none */
    #define R_BSP_ASM_END             /* none */

    #elif defined(__GNUC__)

    #define _R_BSP_ASM(...)           #__VA_ARGS__
    #define R_BSP_ASM(...)            _R_BSP_ASM(__VA_ARGS__\n)
    #define R_BSP_ASM_LAB_NEXT(n)     ?+
    #define R_BSP_ASM_LAB_PREV(n)     ?-
    #define R_BSP_ASM_LAB(n_colon)    R_BSP_ASM(?:)
    #define R_BSP_ASM_BEGIN           __asm__ volatile (
    #define R_BSP_ASM_END             R_BSP_ASM(rts));

    #elif defined(__ICCRX__)

    #define _R_BSP_ASM(...)           #__VA_ARGS__
    #define R_BSP_ASM(...)            _R_BSP_ASM(__VA_ARGS__\n)
    #define R_BSP_ASM_LAB_NEXT(n)     _lab##n
    #define R_BSP_ASM_LAB_PREV(n)     _lab##n
    #define R_BSP_ASM_LAB(n_colon)    R_BSP_ASM(_lab##n_colon)
    #define R_BSP_ASM_BEGIN           asm(
    #define R_BSP_ASM_END             );

    #endif

    #endif /* defined(__CDT_PARSER__) */

    変更後

    /* ---------- Inline Expansion of Assembly-Language Function (part2) ---------- */
    #if defined(__CDT_PARSER__)

    。。。略。。。

    #else

    #if defined(__CCRX__)

    。。。略。。。

    #elif defined(__GNUC__)

    。。。略。。。

    #elif defined(__ICCRX__)

    #define _R_BSP_ASM(...)           #__VA_ARGS__ "\n"    ← ちなみにGNURXもこれで可でした
    #define R_BSP_ASM(...)            _R_BSP_ASM(__VA_ARGS__)    ← ちなみにGNURXもこれで可でした
    #define R_BSP_ASM_LAB_NEXT(n)     _lab##n
    #define R_BSP_ASM_LAB_PREV(n)     _lab##n
    #define R_BSP_ASM_LAB(n_colon)    R_BSP_ASM(_lab##n_colon)
    #define R_BSP_ASM_BEGIN           R_BSP_PRAGMA(diag_suppress = Pa174)\
                                      R_BSP_PRAGMA(diag_suppress = Pe010)\
                                      __asm volatile(
    #define R_BSP_ASM_END             );\
                                      R_BSP_PRAGMA(diag_default = Pe010)\
                                      R_BSP_PRAGMA(diag_default = Pa174)

    #endif

    #endif /* defined(__CDT_PARSER__) */

    変更後はEWRXで該当箇所でのワーニング(というかリマーク)メッセージの表示は抑止されるようになりました


    ちなみに、CC-RXでもワーニングレベルを上げてFITモジュールをコンパイルした時には、CC-RX/GNURX/ICCRX共通化インラインアセンブラ記述マクロでワーニングが出てしまいます。IARコンパイラでは#pragmaで個別ワーニング抑止指定(と解除指定)が出来ますが、CC-RXではそれが出来ませんので、コンパイルオプションで個別ワーニング抑止指定を設定して抑止することになります。

    CS+でワーニングレベルを上げると該当マクロ起因で表示されるワーニング(というかインフォーメーション)メッセージの例

    src\smc_gen\r_bsp\mcu\all\r_bsp_common.c(112):M0520010:"#" not expected here



    CS+でワーニングレベルを上げた時に該当マクロ起因で表示されるワーニング(というかインフォーメーション)メッセージを抑止する設定の画面コピー


    #しばらく前から、日本語Windows10上でCS+を英語モード表示(というか起動)させる方法を試していますが、その影響で、画面コピーではメニューやファンクションキーの表示がおかしくなっています。気にしないで下さい。

Reply
  • こんにちは。NoMaYです。

    IARコンパイラでワーニングレベルを上げてFITモジュールをコンパイルしてみて、CC-RX/GNURX/ICCRX共通化インラインアセンブラ記述マクロでワーニングが出てしまうことに気付きました。これについては、以下のように共通化マクロを変更したところ、コンパイルオプションで個別ワーニング抑止指定を設定しなくても、抑止することが出来るようになりました。(もっとも、何がしかの設定をしませんと、ワーニング検出箇所が多過ぎたり、エラー扱いされてしまって厳し過ぎたり、ということで後々大変になりますので、どうせ何がしかの設定をしないといけないのであれば、マクロ定義をややこしくするまでも無いのではないか、という考え方もあるかとは思いましたけれど、、、) これはFITモジュール側での採用を働きかけたいですね、、、

    EWRXでワーニングレベルを上げる設定の画面コピー (CC-RXはインフォメーションメッセージですがICCRXはリマークメッセージでした)


    EWRXでワーニングレベルを上げると表示されるワーニング(というかリマーク)メッセージの例(ちなみに他の箇所にも大量に表示されます)

    リマーク[Pe007]: unrecognized token C:\Renesas\...\r_bsp_common.c 108 
    リマーク[Pe007]: unrecognized token C:\Renesas\...\r_bsp_common.c 109
    リマーク[Pe007]: unrecognized token C:\Renesas\...\r_bsp_common.c 110
    リマーク[Pe007]: unrecognized token C:\Renesas\...\r_bsp_common.c 111
    リマーク[Pe010]: "#" not expected here C:\Renesas\...\r_bsp_common.c 112
    リマーク[Pe010]: "#" not expected here C:\Renesas\...\r_bsp_common.c 112
    リマーク[Pe007]: unrecognized token C:\Renesas\...\r_bsp_common.c 112
    リマーク[Pe007]: unrecognized token C:\Renesas\...\r_bsp_common.c 113
    リマーク[Pa174]: inline assembler statement has no declared side-effect. All optimizations around it will be disabled.  C:\Renesas\...\r_bsp_common.c 107
    Either add side-effect declarations or add volatile.



    変更対象: src/smc_gen/r_bsp/mcu/all/r_rx_compiler.h

    変更前

    /* ---------- Inline Expansion of Assembly-Language Function (part2) ---------- */
    #if defined(__CDT_PARSER__)

    #define R_BSP_ASM(...)            /* none */
    #define R_BSP_ASM_LAB_NEXT(n)     /* none */
    #define R_BSP_ASM_LAB_PREV(n)     /* none */
    #define R_BSP_ASM_LAB(n_colon)    /* none */
    #define R_BSP_ASM_BEGIN           /* none */
    #define R_BSP_ASM_END             /* none */

    #else

    #if defined(__CCRX__)

    #if !defined(__cplusplus)
    #define R_BSP_ASM(...)            __VA_ARGS__
    #else
    /* CC-RX' C++ mode does not support variadic macros */
    #endif
    #define R_BSP_ASM_LAB_NEXT(n)     ?+
    #define R_BSP_ASM_LAB_PREV(n)     ?-
    #define R_BSP_ASM_LAB(n_colon)    R_BSP_ASM(?:)
    #define R_BSP_ASM_BEGIN           /* none */
    #define R_BSP_ASM_END             /* none */

    #elif defined(__GNUC__)

    #define _R_BSP_ASM(...)           #__VA_ARGS__
    #define R_BSP_ASM(...)            _R_BSP_ASM(__VA_ARGS__\n)
    #define R_BSP_ASM_LAB_NEXT(n)     ?+
    #define R_BSP_ASM_LAB_PREV(n)     ?-
    #define R_BSP_ASM_LAB(n_colon)    R_BSP_ASM(?:)
    #define R_BSP_ASM_BEGIN           __asm__ volatile (
    #define R_BSP_ASM_END             R_BSP_ASM(rts));

    #elif defined(__ICCRX__)

    #define _R_BSP_ASM(...)           #__VA_ARGS__
    #define R_BSP_ASM(...)            _R_BSP_ASM(__VA_ARGS__\n)
    #define R_BSP_ASM_LAB_NEXT(n)     _lab##n
    #define R_BSP_ASM_LAB_PREV(n)     _lab##n
    #define R_BSP_ASM_LAB(n_colon)    R_BSP_ASM(_lab##n_colon)
    #define R_BSP_ASM_BEGIN           asm(
    #define R_BSP_ASM_END             );

    #endif

    #endif /* defined(__CDT_PARSER__) */

    変更後

    /* ---------- Inline Expansion of Assembly-Language Function (part2) ---------- */
    #if defined(__CDT_PARSER__)

    。。。略。。。

    #else

    #if defined(__CCRX__)

    。。。略。。。

    #elif defined(__GNUC__)

    。。。略。。。

    #elif defined(__ICCRX__)

    #define _R_BSP_ASM(...)           #__VA_ARGS__ "\n"    ← ちなみにGNURXもこれで可でした
    #define R_BSP_ASM(...)            _R_BSP_ASM(__VA_ARGS__)    ← ちなみにGNURXもこれで可でした
    #define R_BSP_ASM_LAB_NEXT(n)     _lab##n
    #define R_BSP_ASM_LAB_PREV(n)     _lab##n
    #define R_BSP_ASM_LAB(n_colon)    R_BSP_ASM(_lab##n_colon)
    #define R_BSP_ASM_BEGIN           R_BSP_PRAGMA(diag_suppress = Pa174)\
                                      R_BSP_PRAGMA(diag_suppress = Pe010)\
                                      __asm volatile(
    #define R_BSP_ASM_END             );\
                                      R_BSP_PRAGMA(diag_default = Pe010)\
                                      R_BSP_PRAGMA(diag_default = Pa174)

    #endif

    #endif /* defined(__CDT_PARSER__) */

    変更後はEWRXで該当箇所でのワーニング(というかリマーク)メッセージの表示は抑止されるようになりました


    ちなみに、CC-RXでもワーニングレベルを上げてFITモジュールをコンパイルした時には、CC-RX/GNURX/ICCRX共通化インラインアセンブラ記述マクロでワーニングが出てしまいます。IARコンパイラでは#pragmaで個別ワーニング抑止指定(と解除指定)が出来ますが、CC-RXではそれが出来ませんので、コンパイルオプションで個別ワーニング抑止指定を設定して抑止することになります。

    CS+でワーニングレベルを上げると該当マクロ起因で表示されるワーニング(というかインフォーメーション)メッセージの例

    src\smc_gen\r_bsp\mcu\all\r_bsp_common.c(112):M0520010:"#" not expected here



    CS+でワーニングレベルを上げた時に該当マクロ起因で表示されるワーニング(というかインフォーメーション)メッセージを抑止する設定の画面コピー


    #しばらく前から、日本語Windows10上でCS+を英語モード表示(というか起動)させる方法を試していますが、その影響で、画面コピーではメニューやファンクションキーの表示がおかしくなっています。気にしないで下さい。

Children