In the process of getting rid of old macros in our code, I need to define the old macro as an error with a meaningful compiler message.
E.g., old code:
#define DIVIDE_BY_TWO(x) x/2
In the new code, to prevent the usage of this macro I'd like to write:
#define DIVIDE_BY_TWO(x) #error DIVIDE_BY_TWO is obsolete, use DIV_2 instead
But when I compile the above line I get:
error C2162: expected macro formal parameter
What is the correct way to do it?
A macro can't have directives or change the preprocessor state. You could leave DIVIDE_BY_TWO undefined, but then it doesn't help to find the replacement macro. The only way to do it portably is to define it as something like this:
#define DIVIDE_BY_TWO error_DIVIDE_BY_TWO_is_obsolete_use_DIV_2_instead
Which should give an error that error_DIVIDE_BY_TWO_is_obsolete_use_DIV_2_instead is not defined and hopefully that will give enough hints has to how to replace it.
The problem with using #error is that creates an error at the time that part of the code is analyzed by the preprocessor. You want to create an error when the macro is expanded. You can't, unfortunately, use #error for that.
I don't believe there is a way to generate a clear human-readable error message reliably in portable C. (You can, of course, make the macro expand to something that's syntactically invalid, though, which will at least stop compilation.) gcc supports doing it with _Pragma. Your question is effectively equivalent to this question and the answer there explains how to use _Pragma as well as other options for creating a fatal error.
You cannot use a preprocessor directive in #define since what you're asking for is to run the preprocessor twice.
If a line begins with an # it is a directive to the preprocessor and would be interpreted. If it doesn't, then it is subjected to macro substituion and replacement if such a macro exists.
The best you could do is to define the deprecated macro as some expression that would return an error for sure.
Related
gcc's manual says the following:
If a macro is redefined with a definition that is not effectively the same as the old one, the preprocessor issues a warning and changes the macro to use the new definition. If the new definition is effectively the same, the redefinition is silently ignored. This allows, for instance, two different headers to define a common macro. The preprocessor will only complain if the definitions do not match.
(emphasis mine)
Is there a way to make gcc more strict and issue a warning when a macro is redefined, regardless of definition?
Example:
#define TEST 1
#define TEST 1
int main(void) {
return 0;
}
Compiling with gcc -Wall -Wextra -Wpedantic does not generate any warning whatsoever.
Techincally speaking, if a header defines an apple as being red, then another wants to make sure everybody knows the apple is red, this should not be an issue. This is the reason behind it. And also to not compromise linking between multiple libraries if they have the same macro definition and the same value.
some h/hxx/hpp header
#define apples red
It's the usual attitude when you see some people wanting to make sure everyone knows they know (we all have these friends or co-workers, don't we? :) ) that apples are red so they state the obvious.
Preprocessor definitions are "compiled" (so-to-speak, rather said, interpreted and replaced or evaluated accordingly) at, well, compile-time. So having the same token defined multiple times is no real overhead on the app, it might just add a bit of compilation time.
The problem is when some wise-guy wants to let you know apples can also be green.
some other h/hxx/hpp header
#define apples green
Then, when you need to use some apples, you end up with:
some c/cxx/cpp file
#include "some_header.h/hxx/hpp"
#include "some_other_header.h/hxx/hpp"
And you end up with "apples " redefined.
Putting aside the daunting task of seeing where the conflict comes from (usually when combining multiple third-party libs/framerworks that might use similar names in macros or have the same acronyms prefixing a macro), this should be enough for you to know there is a conflict.
Keep in mind, this is a warning, so it will not stop the compilation. To treat warnings as errors, use -Werror.
I wouldn't worry about duplicate definitions, to be honest. They won't harm the code. If you really wanna go overkill-mode, you can always do some testing:
#if defined(apples) ...
... or ...
#ifdef apples ...
I have found the large-precision code of MPFR C++ to be very useful, and have used it successfully in the past. Recently, while developing a new app, I encountered an enormous number of compiler errors in their header code (mpreal.h). I have identified the cause of all these errors: the the use of a name both in a typedef and as the name of a function, coupled with an unintuitive result of a macro. The relevant macro was in the mpfr package, and occurred between mpfr 4.0.2-5 and 4.1.0-6. I am using the latest version of mpreal.h (version 3.6.8), but other earlier versions behave the same.
The compiler errors vary somewhat, but the following is typical:
In file included from mpreal.h:125:
mpreal.h:624:32: error: no matching function for call to ‘mpfr::mpreal::mpfr_srcptr(const __mpfr_struct*&)’
624 | mpfr_init2(mpfr_ptr(), mpfr_get_prec(u));
| ^~~~~~~~~~~~~
mpreal.h:324:19: note: candidate: ‘const __mpfr_struct* mpfr::mpreal::mpfr_srcptr() const’
324 | ::mpfr_srcptr mpfr_srcptr() const;
| ^~~~~~~~~~~
mpreal.h:324:19: note: candidate expects 0 arguments, 1 provided
The relevant lines of code (int addition to the above) are:
mpreal.h:125 #include <mpfr>
mpfr.h:866 #define mpfr_get_prec(_x) MPFR_VALUE_OF(MPFR_SRCPTR(_x)->_mpfr_prec)
mpfr.h:845 #define MPFR_VALUE_OF(x) (0 ? (x) : (x))
mpfr.h:847 #define MPFR_SRCPTR(x) ((mpfr_srcptr) (0 ? (x) : (mpfr_srcptr) (x)))
The problem seems to be in the macro of line 847. The (mpfr_srcptr) (x) appearing in MPFR_SRCPTR(x) is meant to be a type-cast of x to the type mpfr_srcptr, but is being interpreted to mean a call to mpfr_srcptr() with argument x. Outside of a macro, gcc can tell the difference between (mpfr_srcptr)(x) and mpfr_srcptr(x), but the macro is apparently ignoring the parentheses. Can anyone explain this macro behavior? I know that gcc has a huge number of switches to control almost everything, but is there an option somewhere that would affect the interpretation of parentheses in macros?
I suppose that this behavior could be unique to my system, but I find that hard to believe. But I also find it hard to believe that such a bug has gone unnoticed by the rest of the community; I found no suggestion of any problem either on the website or on github, to which the project has recently been transferred.
The macro SRCPTR is not ignoring parentheses as I originally thought; the behavior is explained by the difference in scopes. The SRCPTR macro, while occurring within the mpfr coding at global scope, is actually being called from mpreal's scope. Since mpreal has redefined srcptr as a function, that definition is the only one used when SRCPTR is executed from mpreal. (SRCPTR, being a macro, has no scope.) When mpfr's functions are called from mpreal, the functions operate with the global scope, and the SRCPTR macro invoked there would therefore use the global definition.
I want to know if it is possible to select different parts of my Fortran 95 routine to compile.
For example, if I pass certain flag to gfortran, then the compiler chooses which section to use for a certain function. I know I can do it using if inside the routine, but the drawback is that I don't want the program to run the if all the time due to speed concerns. I suppose solution should be similar to this one
I am working specifically with a program that calculates energies in a many-body system (say, a million). Then I don't want to put an if each time that I need to use a different energy definition at compilation time.
I hope this is possible and that my question is clear.
You can use the C like preprocessor. The -cpp command line option to your command line. That option is not turned on by default (As per Vladimir F comment below), although it looks like using the .F90 filename extension (i.e. capital F, instead of .f90) will do the trick without the -cpp option.
Details about the option:
https://gcc.gnu.org/onlinedocs/gfortran/Preprocessing-Options.html
Then you can do the same as you pointed out, so the:
#ifdef <some-var>
code when <some-var> is true
#elif defined(<other-var>)
code when <other-var> is true
#endif
As required.
There are more examples on this page with actual code.
Also, like with C/C++, you can define macros on your command line with the-D option:
gfortran -DCASE1=3 ...
This will define CASE1 with the value 3. If you do not specify the value, then 1 is automatically assigned to the macro. This is documented on the same page.
The make a lisp docs contain the following instructions:
This allows you to run tests against your implementation like this:
make "test^quux^stepX"
I've never seen ^ used with make before. It's proving very difficult to search for information on this (Google ignores it and Symbolhound hasn't found anything relevant).
What does ^ mean here? Where is this documented?
In GNU make, ^ has no particular meaning (except when used in the automatic variables ^, ^D, and ^F). The makefile of the project you linked to seems to use it as a separator for variable substitution, but this has nothing to do with make itself.
the ^ (Circumflex) seems to have to do with macro substitution. I could be wrong but this is all I could find for you. Hope it helps.
http://www.cs.nccu.edu.tw/~lien/UNIX/Command/make.htm
I am working on a project with the library ADOL-C (for automatic differentiation) using gcc. Right now I am trying to recompile the library to use the parallelization features however the make process does not working apparently due to some preprocessor stuff.
I think the problematic line is :
#define ADOLC_OPENMP_THREAD_NUMBER int ADOLC_threadNumber
However I could not find what it means. Does it make a link between two variables? Also ADOLC_threadNumber has not been declared before...
The preprocessor doesn't even know what a variable is. All that #define does is define a short(long?)hand for declaring a variable. I.e., if you type
ADOLC_OPENMP_THREAD_NUMBER;
It becomes
int ADOLC_threadNumber;
It's just a text substitution. Everywhere in code where ADOLC_OPENMP_THREAD_NUMBER appears, it's substituted by int ADOLC_threadNumber.
As far as I see it, the line with the define itself is not problematic, but maybe the subsequent appearance of ADOLC_OPENMP_THREAD_NUMBER. However, to check this, we need to know more about the context.
#define is a directive used often in .h files,
it creates a macro, which is the association of an identifier or parameterized identifier with a token string.
After the macro is defined, the compiler can substitute the token string for each occurrence of the identifier in the source file.
#define may be associated with #ifndef directive to avoid to delare the identifier more than once :
#ifndef ADOLC_OPENMP_THREAD_NUMBER
#define ADOLC_OPENMP_THREAD_NUMBER int ADOLC_threadNumber
#endif