Hacker Newsnew | past | comments | ask | show | jobs | submitlogin

Possibly.

Whereas definitions are lazily evaluated, so that if we have:

  #define COUNT __COUNTER__
each occurrence of COUNT behaves like an invocation of __COUNTER__.

But, this is not true of parameters because they get expanded before substitution.

  $ gcc -E -
  #define MAC(PARAM) PARAM PARAM PARAM

  MAC(__COUNTER__)

  # 1 "<stdin>"
  # 1 "<built-in>"
  # 1 "<command-line>"
  # 31 "<command-line>"
  # 1 "/usr/include/stdc-predef.h" 1 3 4
  # 32 "<command-line>" 2
  # 1 "<stdin>"


  0 0 0
Thus perhaps you may be able to get something like __EXP_COUNTER__ by splitting your macros into interface and implementation:

  #define MAC_IMPL(A, B, EXP_COUNTER)

  #define MAC(A, B) MAC_IMPL(A, B, __COUNTER__)
I'm guessing this is what you mean by forwarding.

This could be a pretty major inconvenience, if you have to do it in the middle of a situation that is already stuffed with preprocessing contortions. Like say you had to define 32 macros that are similar to each other, for whatever reason, and you want this hack: now you have 64.



Yes the interface/impl split is what I had in mind.

Even only moderately complex PP metaprogramming requires multiple rounds of wrapping, so I'm not sure it is such a big burden.


By the way, I'm also interested in solving the "no recursive macro" problem hinted at in this submission. While working on __EXP_COUNTER__, I looked into it a bit.

The big issue is that the GNU C preprocessor uses global state for tracking expansion. In effect, it takes advantage of the no-recursion rule and says that during a macro's expansion, only one context for that expansion needs to exist. That context is patched into the macro definition, or something like that. (I don't have the code in front of me and it's been a few months.) The preprocessor knows that there is a current macro being expanded, and there is a stack of those; but that is referenced by its static definition, which has a 1:1 relationship to expansion state, like parameters, location and whatnot. That might have to turn into a stack, perhaps; there is a refactoring job there, and the code is a bit of a hornet's nest.

In terms of syntax/deployment, it would be easy. I envision that there could be a #defrec directive that is like #define, but which creates a macro that is blessed for recursive expansion. Or other possibilities: #pragma rec(names, of, macros, ...) which is better for code that has to work without the extension, since it uses #define.




Guidelines | FAQ | Lists | API | Security | Legal | Apply to YC | Contact

Search: