Pragma in define macro
Asked Answered
C

4

121

Is there some way to embed pragma statement in macro with other statements?

I am trying to achieve something like:

#define DEFINE_DELETE_OBJECT(type)                      \
    void delete_ ## type_(int handle);                  \
    void delete_ ## type(int handle);                                                \
    #pragma weak delete_ ## type_ = delete_ ## type

I am okay with boost solutions (save for wave) if one exists.

Canady answered 12/6, 2010 at 21:9 Comment(4)
Arguably it is neither - #pragmas are not defined by either the C or C++ standards.Kunstlied
The preprocessor is, even if the specific allowed subcommand he wants to run isn't.Overside
@DeadMG: There are a great many things that are common between C and C++. While preprocessing is mostly common, there are major differences in how preprocessing is specified depending on which language standard is being used (C89, C99, C++, and the C++0x FCD).Geocentric
@James McNellis: Just because technically, most C programs are portable to C++, does not make that genuinely common functionality, since no C++ programmer would do the vast majority of it. The two languages do not actually have much in common.Overside
F
138

If you're using c99 or c++0x there is the pragma operator, used as

_Pragma("argument")

which is equivalent to

#pragma argument

except it can be used in macros (see section 6.10.9 of the c99 standard, or 16.9 of the c++0x final committee draft)

For example,

#define STRINGIFY(a) #a
#define DEFINE_DELETE_OBJECT(type)                      \
    void delete_ ## type ## _(int handle);                  \
    void delete_ ## type(int handle);                   \
    _Pragma( STRINGIFY( weak delete_ ## type ## _ = delete_ ## type) )
DEFINE_DELETE_OBJECT(foo);

when put into gcc -E gives

void delete_foo_(int handle); void delete_foo(int handle);
#pragma weak delete_foo_ = delete_foo
 ;
Fears answered 12/6, 2010 at 22:22 Comment(2)
As an FYI: MSVC has the __pragma() preprocessor operator, which unfortunately is slightly different from C99's _Pragma() operator (C99's takes a string literal, MSVC's takes tokens that aren't in a string): msdn.microsoft.com/en-us/library/d9x1s805.aspxRoup
@MichaelBurr MSVC always has to be different, doesn't it?Expensive
B
6

One nice thing you can do with _Pragma("argument") is use it to deal with some compiler issues such as

#ifdef _MSC_VER
#define DUMMY_PRAGMA _Pragma("argument")
#else
#define DUMMY_PRAGMA _Pragma("alt argument")
#endif
Brinker answered 28/2, 2012 at 15:34 Comment(0)
M
2

No, there is no portable way of doing that. Then again, there are no portable ways to use #pragma at all. Because of this, many C/C++ compilers define their own methods for doing pragma-like things, and they often can be embedded in macros, but you need a different macro definition on every compiler. If you are willing to go that route, you often end up doing stuff like this:

#if defined(COMPILER_GCC)
#define Weak_b
#define Weak_e __attribute__((weak))
#elif defined(COMPILER_FOO)
#define Weak_b __Is_Weak
#define Weak_e
#endif

#define DEFINE_DELETE_OBJECT(type)                      \
    Weak_b void delete_ ## type_(int handle) Weak_e;    \
    Weak_b void delete_ ## type(int handle)  Weak_e;    

In case its not obvious you want to define Weak_b and Weak_e as begin-and-end bracketing constructs because some compilers like GCC add the attributes as an addendum to a type signature, and some, like MSC add it as a prefix (or at least it did once, its been years since I've used MSC). Having bracketing contructs allows you to define something that always works, even if you have to pass the entire type signature into a compiler construct.

Of course, if you try porting this to a compiler without the attributes you want, there's nothing you can do but leave the macros expand to nothing and hope your code still runs. In case of purely warning or optimizing pragmas, this is likely. In other cases, not so much.

Oh, and I suspect you'd actually need to define Weak_b and Weak_e as macros that take parameters, but I wasn't willing to read through the docs for how to create a weak definition just for this example. I leave that as an exercise for the reader.

Molybdate answered 12/6, 2010 at 22:12 Comment(0)
S
-3

is there some way to embed pragma statement in macro with other statements?

No, you cannot put preprocessor statements into preprocessor statements. You could, however, put it into an inline function. That defeats the C tag, though.

Skipper answered 12/6, 2010 at 21:32 Comment(6)
What good would putting it into an inline function do? Preprocessor directives are processed before anything that could recognise a function.Kunstlied
C99 has inline, and most major C89 implementations have some variation.Vadavaden
@Chris Assuming your comment was directed at me - your point is - what?Kunstlied
@Neil - No, sorry. I was directing it at @sbi's last sentence.Vadavaden
@Neil: I have no idea what that pragma is supposed to do.Skipper
@Chris: Ah, so inline is yet another thing C borrowed from C++! :)Skipper

© 2022 - 2024 — McMap. All rights reserved.