I have embedded C code which I'm unit testing with a C++ framework. C and C++ handle inline functions differently, so when I want to create inline functions which are used in two source files, I do this:
In a header file:
#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
}
In exactly one of the two .c files:
#define INLINE
Now both C and C++ compilers are satisfied, but when I build, I get this warning:
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
Is there a way I can silence this warning?
Use #ifndef
#ifndef INLINE
# ifdef __cplusplus
# define INLINE inline
# else
# define INLINE extern inline
# endif
#endif
You're probably including the define multiple times in the same translation unit. You can add include guards:
#ifndef INLINE_DEFINED
#define INLINE_DEFINED
#ifdef __cplusplus
# define INLINE inline
#else
# ifndef INLINE
# define INLINE extern inline
# endif
#endif
//...
#endif
or undefine the directive:
#undef INLINE
#ifdef __cplusplus
# define INLINE inline
#else
# ifndef INLINE
# define INLINE extern inline
# endif
#endif
A harder approach would be to just silence the warning:
#pragma warning( disable : /*warning number*/ )
Not sure if this is cross-platform though.
First as Charles says in his comment, you shouldn't do this, C and C++ are substantially different languages. In particular their rules for inline
functions are different. It will cause you pain.
Then, you have another design flaw. This is apparent since you are trying to redefine a macro. You have two different contexts for your INLINE
so these represent two different things. I think the following model is much easier and direct:
inline
for the header files. no macro or stuff like that and no extern
you should decide if your instantiation is C or C++, don't play games here. In C such an instantiation is
extern inline Uint8 my_inline_function( Uint8 stuff );
(C doesn't call that instantiation but let's just use the same term as C++)
in C++ it would be
Uint8 my_inline_function( Uint8 stuff );
That's it, no need for magic:
Edit:
Seeing your comment (which doesn't convince me completely) I think you would be better off by just having one macro for the instantiation in a header file
#ifdef __cplusplus
# define INSTANT
#else
# define INSTANT extern inline
#endif
and then in one .c or .C or whatever you will need to convince the compiler
INSTANT Uint8 my_inline_function( Uint8 stuff );
I suspect that this is what causing the problem
#ifdef __cplusplus
# define INLINE inline
Try to change this to
#ifdef __cplusplus
# ifndef INLINE
# define INLINE inline
#endif
You should have the #define INLINE...
in its own header file with its own header guard:
(inline.h)
#ifndef INLINE_DEFINED
#ifdef __cplusplus
# define INLINE inline
#else
# ifndef INLINE
# define INLINE extern inline
# endif
#endif
#endif
You should then put #include "inline.h"
near the top of any file that needs it.
I appreciate the advice to avoid combining C and C++, but we feel the benefits of stricter type checking and simpler-to-use unit test frameworks outweigh these hiccups. Given that, the approach I find cleanest is in the .c file replacing
#define INLINE
with
#ifndef __cplusplus
# define INLINE
#endif
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.