Встроенные функции в C и C ++;предупреждение компилятора глушителя - PullRequest
3 голосов
/ 20 декабря 2011

У меня есть встроенный C-код, который я тестирую с помощью фреймворка C ++.C и C ++ обрабатывают встроенные функции по-разному, поэтому, когда я хочу создать встроенные функции, которые используются в двух исходных файлах, я делаю это:

В заголовочном файле:

#ifdef __cplusplus
# define INLINE inline
#else
# ifndef INLINE
#  define INLINE extern inline
# endif
#endif

INLINE Uint8 my_inline_function( Uint8 stuff )
{
    return stuff;  // not really, but it's not germane to the example
}

В точностиодин из двух файлов .c:

#define INLINE

Теперь компиляторы C и C ++ удовлетворены, но при сборке я получаю это предупреждение:

In file included from ../MyFile.c:28:0,
             from utest_MyFile.cpp:10:
../MyFile.h:53:0: warning: "INLINE" redefined
../MyFile.c:26:0: note: this is the location of the previous definition

Есть ли способ, которым яможет замолчать это предупреждение?

Ответы [ 6 ]

4 голосов
/ 20 декабря 2011

Использовать # ifndef

#ifndef INLINE
# ifdef __cplusplus
#  define INLINE inline
# else
#  define INLINE extern inline
# endif
#endif
1 голос
/ 20 декабря 2011

Во-первых, как говорит Чарльз в своем комментарии, вы не должны этого делать, C и C ++ - это существенно разные языки. В частности, их правила для inline функций различны. Это причинит вам боль.

Тогда у вас есть еще один недостаток дизайна. Это очевидно, поскольку вы пытаетесь переопределить макрос. У вас есть два разных контекста для вашего INLINE, поэтому они представляют две разные вещи. Я думаю, что следующая модель намного проще и прямолинейнее:

  • используйте inline для заголовочных файлов. нет макроса или чего-то в этом роде
  • в одном файле C или C ++ поместить «экземпляр» для той же функции

Вы должны решить, является ли ваш экземпляр C или C ++, не играйте в игры здесь. В C такой экземпляр является

extern inline Uint8 my_inline_function( Uint8 stuff );

(C не вызывает этот экземпляр, но давайте просто использовать тот же термин, что и C ++)

в C ++ это будет

Uint8 my_inline_function( Uint8 stuff );

Вот и все, магия не нужна:

  • все модули компиляции, которые включают файл заголовка, будут иметь определение доступно
  • для всех ситуаций, где вам все еще нужен символ компоновщика будет использоваться экземпляр

Edit:

Видя ваш комментарий (который не убеждает меня полностью), я думаю, вам будет лучше, если у вас будет один макрос для экземпляра в заголовочном файле

#ifdef __cplusplus
# define INSTANT
#else
# define INSTANT extern inline
#endif

и затем в одном .c или .C или что-то еще, что вам понадобится, чтобы убедить компилятор

INSTANT Uint8 my_inline_function( Uint8 stuff );
1 голос
/ 20 декабря 2011

Возможно, вы включаете определение несколько раз в одну и ту же единицу перевода.Вы можете добавить защитные элементы:

#ifndef INLINE_DEFINED
#define INLINE_DEFINED

#ifdef __cplusplus
# define INLINE inline
#else
# ifndef INLINE
#  define INLINE extern inline
# endif
#endif

//...
#endif

или отменить указание:

#undef INLINE

#ifdef __cplusplus
# define INLINE inline
#else
# ifndef INLINE
#  define INLINE extern inline
# endif
#endif

Более сложный подход - просто отключить предупреждение:

#pragma warning( disable : /*warning number*/ )

Неконечно, если это кроссплатформенный.

0 голосов
/ 20 декабря 2011

Я ценю совет избегать сочетания C и C ++, но мы считаем, что преимущества более строгой проверки типов и более простых в использовании инфраструктур для модульных тестов перевешивают эти ошибки. Учитывая это, подход, который я считаю наиболее чистым, заключается в замене

на файл .c
#define INLINE

с

#ifndef __cplusplus
# define INLINE
#endif
0 голосов
/ 20 декабря 2011

Вы должны иметь #define INLINE... в своем собственном заголовочном файле со своей собственной защитой заголовка:

(inline.h)

#ifndef INLINE_DEFINED

#ifdef __cplusplus
# define INLINE inline
#else
# ifndef INLINE
#  define INLINE extern inline
# endif
#endif

#endif

Затем вы должны поставить #include "inline.h" рядом сначало любого файла, который нуждается в этом.

0 голосов
/ 20 декабря 2011

Я подозреваю, что это является причиной проблемы

#ifdef __cplusplus
# define INLINE inline

Попробуйте изменить это на

#ifdef __cplusplus
# ifndef INLINE
# define INLINE inline
#endif
...