0

I want to use a variadic macro but it appears to be designed to only treat the first parameter specially. I want the first two parameters to be named and the rest not, like so:

#define FOO(AA,BB,...) AA->BB(AA,##...)

FOO(mystruct,funcname,123)

However this is not working with LLVM. Am I doing something wrong, or is there a limitation to how the variadic macro works?


UPDATE

The correct answer is, use ##VA_ARGS instead of ##...

There are some webpages that claim that "..." is valid but at least with the MacOS llvm it is not.

popoe
  • 21
  • 2

2 Answers2

1

The macro arguments are not expanded with ... in the macro expansion - how could they, because then you couldn't have a macro that used ellipsis in the expansion. Instead it will be available as a special parameter __VA_ARGS__.

With this, the following program

#define FOO(AA,BB,...) AA->BB(AA, __VA_ARGS__)

FOO(mystruct,funcname,123)
FOO(mystruct,funcname,123,456)

will be preprocessed to


The ## is a token-pasting operator. It will make a single preprocessing token out of 2 parts. , ## ... attempts to make a preprocessing token ,.... It is not a valid C token, and that is why Clang will report

<source>:3:1: error: pasting formed ',...', an invalid preprocessing token 
  • I need to use ##__VA_ARGS__. Your solution covers the >=1 params cases but not 0. – popoe Dec 30 '18 at 17:45
  • I don't know why I was seeing webpages claiming that "..." would work. I used to have the original C programming book-- that would have been a better source of truth than blogs. – popoe Dec 30 '18 at 17:48
  • @popoe that's a [GNU extension](https://stackoverflow.com/questions/37206118/va-args-not-swallowing-comma-when-zero-args-under-c99) – Antti Haapala -- Слава Україні Dec 30 '18 at 18:06
  • @popoe: variadic macros aren't described at all in K&R, because the original C didn't have variadic macros. They were added in C99, although they were already implemented as a gcc extension. Afaik, `...` has never been used to indicate where varargs should be expanded. At least, not in C. – rici Dec 30 '18 at 18:41
1

... macro arguments are pasted into macro bodies with __VA_ARGS__. The problem is how to allow for it to be empty. If it is empty, you'll usually want to comma before it erased and you can use the GNU ##__VA_ARGS__ extension to achieve that.

#define FOO(AA,BB,...) AA->BB(AA,##__VA_ARGS__) /*GNU extension*/
FOO(mystruct,funcname) //warning with -pedantic
FOO(mystruct,funcname,123)

The above, however, will trigger warnings if compiled with -pedantic. If you want your macro usable without warnings at -pedantic, you could perhaps achieve that by swapping the first two arguments in the macro definition.

#define FIRST(...)  FIRST_(__VA_ARGS__,)
#define FIRST_(X,...) X
#define BAR_(CallExpr,...) CallExpr(__VA_ARGS__)
#define BAR(BB,/*AA,*/...) BAR_(FIRST(__VA_ARGS__)->BB,__VA_ARGS__)

BAR(funcname,mystruct) //no warning
BAR(funcname,mystruct,123)
Petr Skocik
  • 58,047
  • 6
  • 95
  • 142