Context: all the compilers except __MY_CC__ are not supported. However, how to permit only preprocessing with a 3rd-party compiler?
#if cc -E
/* permit only preprocessing with a 3rd-party compiler */
#elif ! __MY_CC__
#error unsupported compiler
#endif
UPD. The underlying problem I'm trying to solve:
Consider source file named
t0.c.Requirements for
t0.c:a.
t0.cis permitted to be compiled using onlymy_cccompiler. No other compiler is supported (becauset0.ccontains target-specific code).b.
t0.ccontains some meta information as well. The meta information is available aftert0.cwas preprocessed.c. The meta information will be used in an environment which does not have
my_cccompiler. (It means thatt0.cis designed not only to be compiled, but to be just preprocessed, i.e. w/o execution of the subsequent translation phases.) So,t0.cneeds to be permitted to be preprocessed using any conforming implementation (hereafter calledcc), which is notmy_cc.How to satisfy such requirements?
User Paul Hankin proposed the following approach:
#if ! __MY_CC__
"compiler not supported"
#endif
This code:
- Will be compiled with
my_cc. Good. - Will not be compiled with
cc, because of syntax error (ex. is given for clang):
t0.c:4:1: error: expected identifier or '('
"compiler not supported"
^
1 error generated.
Good.
After being preprocessed using
cc -Ethe resulting translation unit will contain"compiler not supported", which is undesirable, because:a. It is expected that the translation unit does not contain any additional overhead (such as strings).
b. It breaks the requirements: the
cc -Eis supported.
Not good.
We can change the "compiler not supported" to "compilation using non __MY_CC__ is not supported". However, it is expected that after t0.c was prepossessed the resulting translation unit does not contain any additional overhead (such as strings). Is there any overhead-less solution?
There is no standard way to request "preprocessor-only" compilation. In fact, there is no standard definition of what "preprocessor-only" compilation might do, since the standard (a) does not mandate that preprocessing be a separable module of the compiler and (b) to the extent that the preprocessor phases are defined, mandates that the result after preprocessing phase be a sequence of tokens without whitespace, which is not the same thing as a sequence of characters.
That being the case, there is certainly no standard way to detect whether a given compiler is doing something non-standard, like fabricating a preprocessed output.
If you're not actually concerned with 100% portability, you could probably do this most easily with a build script.