Double macro expansion in (AVR-)GCC - macros

please excuse me if this question has already been answered elsewhere, but I'm not sure what to search for.
I am passing a value from a batch file, though a makefile, and to a header file, like so:
(Using AVR-GCC 4.5.2)
Batch:
make ADDR=FOO
Makefile:
CFLAGS += -DADDR=$(ADDR)
...
gcc $(CFLAGS) main.c
This is the header file main.h, included by main.c; it is supposed to select a specific pinout at compile-time, based on the value of ADDR:
#include "defs.h"
#if ADDR == FOO
... // Select pinout 1
#elif ADDR == BAR
... // Select pinout 2
#endif
The comparison values FOO and BAR are constants defined in a global header file defs.h included by main.h:
#define FOO 23
#define BAR 42
Now the problem: The comparisons don't work, ADDR constantly reads as 0. This seems to be because the preprocessor does not resolve ADDR before the comparison, i.e. expand FOO to 23. Telling the compiler to do this expansion would be helpful.
Of course it works if I pass ADDR=23 directly in the batch file, but for flexibility I want to use the aliases from defs.h instead of fixed numeric constants.
By the way, the following works if placed in main.c:
int addr_val = ADDR; // is now 23
Maybe there is a simple solution I am not aware of right now. Please feel free to contribute.
Have a nice day!

Related

Fortran substitute subroutine name using macro

I am writing a module that allows users to log information. I want to provide an interface that logs a string message, which can be called as
call m_log(msg)
So in file m_logger.f90, I will have
module m_logger
..
subroutine m_log(msg)
..
end module
In file main.f90, a user will have
program main
use m_logger
call m_log(msg)
end program
Now how can I substitute call m_log(msg) with call m_log(msg, __FILE__, __LINE__) ?
Because of this substitution, a different subroutine subroutine m_log(msg, filename, linenum) in the logger module will be called instead.
If I use a macro like #define m_log(msg) m_log(msg,__FILE__,__LINE__) , it will have to be added to every user file that uses the logger.
Also, I do not want to enforce the user to pass __FILE__ and __LINE__ explicitly.
Is there a way I can do this? Or are there any other alternatives altogether?
Thanks in advance
Edit:
I had a discussion on comp.lang.fortran. Adding a link for reference.
here
In this case you would have to use the same approach C uses. Define the macro you proposed
#define log(msg) m_log(msg,__FILE__,__LINE__)
in a separate file (possibly with other useful macros) and include it using #include "file.inc" (standard Fortran include won't suffice).
If the macro has a different name, than the subroutine it actually calls, you can ensure that the user has to use the include and cannot forget it.
If you don't want to force __file__ and __line__ explicitly, then you can use the optional flag, such that your subroutine looks like:
subroutine m_log(msg, filename, linenum)
character(len=*) :: msg
character(len=*), optional :: filename
integer, optional :: linenum
if(present(filename)) then
<something with filename>
endif
if(present(linenum)) then
<something with linenume>
endif
<normal stuff with msg>
end subroutine
The intrinsic function present returns a true value if filename or linenum have any values attached to it, returning false otherwise.
Since you want them to be passed as compiler macros by the user, you would first have to choose different names for your macros. __FILE__ and __LINE__ are both predefined macros. These two macros are defined by preprocessor, not passed by the user. I think that might have cause some confusion.
If you would like to allow users to optionally supply the macros through compiler options, it is probably best to include #ifdef directive in your subroutine:
subroutine m_log(msg)
implicit none
character(len=*) :: msg
character(len=something) :: file
integer ::line
!Initialize file and line to some default value
file=...
line=...
#ifdef __KVM_FILE__
file=__KVM_FILE__
#endif
#ifdef __KVM_LINE__
line=__KVM_LINE__
#endif
...
This way the user will always call the subroutine with the same syntax call m_log(something), but the effect will change according to your compilation macros. Of course, that would also require the user to recompile your code every time they change this macro. If this is too costly to do, you can set up a subroutine with optional argument (as in Kyle's answer), then enclose #define macro in #ifdef blocks, and put them into an .h file, and have your user always include that file. (similar to Vladimir's answer)

gcc giving error on printf while compiling lex output

For the example.l lex file I get the error below. If I comment out the printf it goes away. I though that the top section of the lex specification could contain any arbitrary C code between the %{ and %}. I need to be able to print some output before lex matches anything. What is wrong with what I have done and how do I fix it?
$ cat example.l
%{
#include <stdio.h>
printf("foobar\n");
%}
%%
. ECHO;
$ lex example.l
$ gcc -g -L/usr/lib/flex-2.5.4a -lfl -o example lex.yy.c
example.l:3: error: expected declaration specifiers or '...' before string constant
example.l:3: warning: data definition has no type or storage class
example.l:3: error: conflicting types for 'printf'
example.l:3: note: a parameter list with an ellipsis can't match an empty parameter name list declaration
If you look at the code here, you can see that one of two things is happening here ... either you are doing a #include inside a function body which doesn't make sense, or you are calling printf() outside any function, which is equally wrong.
Now, when you take into account this is flex, it's the latter. You were probably shooting for something a little more like this:
%{
#include <stdio.h>
%}
%%
. ECHO;
%%
int main() {
printf("foobar\n");
while (yylex() != 0);
return 0;
}

perlre length limit

From man perlre:
The "*" quantifier is equivalent to "{0,}", the "+" quantifier to "{1,}", and the "?" quantifier to "{0,1}". n and m are limited to integral values less than a preset limit defined when perl is built. This is usually 32766 on the most common platforms. The actual limit can be seen in the error message generated by code such as this:
$_ **= $_ , / {$_} / for 2 .. 42;
Ay that's ugly - Isn't there some constant I can get instead?
Edit: As daxim pointed out (and perlretut hints towards) it might be that 32767 is a magical hardcoded number. A little searching in the Perl code goes a long way, but I'm not sure how to get to the next step and actually find out where the default reg_infty or REG_INFTY is actually set:
~/dev/perl-5.12.2
$ grep -ri 'reg_infty.*=' *
regexec.c: if (max != REG_INFTY && ST.count == max)
t/re/pat.t: $::reg_infty = $Config {reg_infty} // 32767;
t/re/pat.t: $::reg_infty_m = $::reg_infty - 1;
t/re/pat.t: $::reg_infty_p = $::reg_infty + 1;
t/re/pat.t: $::reg_infty_m = $::reg_infty_m; # Surpress warning.
Edit 2: DVK is of course right: It's defined at compile time, and can probably be overridden only with REG_INFTY.
Summary: there are 3 ways I can think of to find the limit: empirical, "matching Perl tests" and "theoretical".
Empirical:
eval {$_ **= $_ , / {$_} / for 2 .. 129};
# To be truly portable, the above should ideally loop forever till $# is true.
$# =~ /bigger than (-?\d+) /;
print "LIMIT: $1\n"'
This seems obvious enough that it doesn't require explanation.
Matches Perl tests:
Perl has a series of tests for regex, some of which (in pat.t) deal with testing this max value. So, you can approximate that the max value computed in those tests is "good enough" and follow the test's logic:
use Config;
$reg_infty = $Config {reg_infty} // 2 ** 15 - 1; # 32767
print "Test-based reg_infinity limit: $reg_infty\n";
The explanation of where in the tests this is based off of is in below details.
Theoretical: This is attempting to replicate the EXACT logic used by C code to generate this value.
This is harder that it sounds, because it's affected by 2 things: Perl build configuration and a bunch of C #define statements with branching logic. I was able to delve fairly deeply into that logic, but was stalled on two problems: the #ifdefs reference a bunch of tokens that are NOT actually defined anywhere in Perl code that I can find - and I don't know how to find out from within Perl what those defines values were, and the ultimate default value (assuming I'm right and those #ifdefs always end up with the default) of #define PERL_USHORT_MAX ((unsigned short)~(unsigned)0) (The actual limit is gotten by removing 1 bit off that resulting all-ones number - details below).
I'm also not sure how to access the amount of bytes in short from Perl for whichever implementation was used to build perl executable.
So, even if the answer to both those questions can be found (which I'm not sure of), the resulting logic would most certainly be "uglier" and more complex than the straightforward "empirical eval-based" one I offered as the first option.
Below I will provide the details of where various bits and pieces of logic related to to this limit live in Perl code, as well as my attempts to arrive at "Theoretically correct" solution matching C logic.
OK, here is some investigation part way, you can complete it yourself as I have ti run or I will complete later:
From regcomp.c: vFAIL2("Quantifier in {,} bigger than %d", REG_INFTY - 1);
So, the limit is obviously taken from REG_INFTY define. Which is declared in:
rehcomp.h:
/* XXX fix this description.
Impose a limit of REG_INFTY on various pattern matching operations
to limit stack growth and to avoid "infinite" recursions.
*/
/* The default size for REG_INFTY is I16_MAX, which is the same as
SHORT_MAX (see perl.h). Unfortunately I16 isn't necessarily 16 bits
(see handy.h). On the Cray C90, sizeof(short)==4 and hence I16_MAX is
((1<<31)-1), while on the Cray T90, sizeof(short)==8 and I16_MAX is
((1<<63)-1). To limit stack growth to reasonable sizes, supply a
smaller default.
--Andy Dougherty 11 June 1998
*/
#if SHORTSIZE > 2
# ifndef REG_INFTY
# define REG_INFTY ((1<<15)-1)
# endif
#endif
#ifndef REG_INFTY
# define REG_INFTY I16_MAX
#endif
Please note that SHORTSIZE is overridable via Config - I will leave details of that out but the logic will need to include $Config{shortsize} :)
From handy.h (this doesn't seem to be part of Perl source at first glance so it looks like an iffy step):
#if defined(UINT8_MAX) && defined(INT16_MAX) && defined(INT32_MAX)
#define I16_MAX INT16_MAX
#else
#define I16_MAX PERL_SHORT_MAX
I could not find ANY place which defined INT16_MAX at all :(
Someone help please!!!
PERL_SHORT_MAX is defined in perl.h:
#ifdef SHORT_MAX
# define PERL_SHORT_MAX ((short)SHORT_MAX)
#else
# ifdef MAXSHORT /* Often used in <values.h> */
# define PERL_SHORT_MAX ((short)MAXSHORT)
# else
# ifdef SHRT_MAX
# define PERL_SHORT_MAX ((short)SHRT_MAX)
# else
# define PERL_SHORT_MAX ((short) (PERL_USHORT_MAX >> 1))
# endif
# endif
#endif
I wasn't able to find any place which defined SHORT_MAX, MAXSHORT or SHRT_MAX so far. So the default of ((short) (PERL_USHORT_MAX >> 1)) it is assumed to be for now :)
PERL_USHORT_MAX is defined very similarly in perl.h, and again I couldn't find a trace of definition of USHORT_MAX/MAXUSHORT/USHRT_MAX.
Which seems to imply that it's set by default to: #define PERL_USHORT_MAX ((unsigned short)~(unsigned)0). How to extract that value from Perl side, I have no clue - it's basically a number you get by bitwise negating a short 0, so if unsigned short is 16 bytes, then PERL_USHORT_MAX will be 16 ones, and PERL_SHORT_MAX will be 15 ones, e.g. 2^15-1, e.g. 32767.
Also, from t/re/pat.t (regex tests): $::reg_infty = $Config {reg_infty} // 32767; (to illustrate where the non-default compiled in value is stored).
So, to get your constant, you do:
use Config;
my $shortsize = $Config{shortsize} // 2;
$c_reg_infty = (defined $Config {reg_infty}) ? $Config {reg_infty}
: ($shortsize > 2) ? 2**16-1
: get_PERL_SHORT_MAX();
# Where get_PERL_SHORT_MAX() depends on logic for PERL_SHORT_MAX in perl.h
# which I'm not sure how to extract into Perl with any precision
# due to a bunch of never-seen "#define"s and unknown size of "short".
# You can probably do fairly well by simply returning 2**8-1 if shortsize==1
# and 2^^16-1 otherwise.
say "REAL reg_infinity based on C headers: $c_reg_infty";

Variadic macros with 0 arguments in C99

I have some debugging code that looks like the following:
#define STRINGIFY(x) #x
#define TOSTRING(x) STRINGIFY(x)
#define AT __FILE__ ":" TOSTRING(__LINE__)
void __my_error(const char*loc, const char *fmt, ...);
#define my_error(fmt, ...) __my_error(AT, fmt, ##__VA_ARGS__)
The last macro is used so I can insert the location into the debug output as to where the error occurred. However, when I call the function like this:
my_error("Uh oh!");
I would like my code to be C99, so I find when this compiles, I get the following error:
error: ISO C99 requires rest arguments to be used
I know I can solve this by changing the call to
my_error("Uh oh!", NULL);
But is there any way to make this look less ugly? Thanks!
I see two solutions to this problem. (Three if you count 'stick with gcc').
Extra special case macro
Add a new macro for when you want to print a fixed string.
#define my_errorf(str) my_error(str, NULL)
Pro: Minimum amount of extra code.
Con: It's easy to use the wrong macro (but at least you notice this at compile time).
Put fmt inside the '...'
Vararg macro's can have only __VA_ARGS__ as parameter (unlike vararg functions). So you can put the fmt argument inside the __VA_ARGS__ and change your function.
void __my_error(const char *loc, ...);
#define my_error(...) __my_error(AT, __VA_ARGS__)
Pro: One syntax/macro for all error messages.
Con: Requires rewriting of your __my_error function, which might not be possible.

How do I show the value of a #define at compile-time?

I am trying to figure out what version of Boost my code thinks it's using. I want to do something like this:
#error BOOST_VERSION
but the preprocessor does not expand BOOST_VERSION.
I know I could print it out at run-time from the program, and I know I could look at the output of the preprocessor to find the answer. I feel like having a way of doing this during compilation could be useful.
I know that this is a long time after the original query, but this may still be useful.
This can be done in GCC using the stringify operator "#", but it requires two additional stages to be defined first.
#define XSTR(x) STR(x)
#define STR(x) #x
The value of a macro can then be displayed with:
#pragma message "The value of ABC: " XSTR(ABC)
See: 3.4 Stringification in the gcc online documentation.
How it works:
The preprocessor understands quoted strings and handles them differently from normal text. String concatenation is an example of this special treatment. The message pragma requires an argument that is a quoted string. When there is more than one component to the argument then they must all be strings so that string concatenation can be applied. The preprocessor can never assume that an unquoted string should be treated as if it were quoted. If it did then:
#define ABC 123
int n = ABC;
would not compile.
Now consider:
#define ABC abc
#pragma message "The value of ABC is: " ABC
which is equivalent to
#pragma message "The value of ABC is: " abc
This causes a preprocessor warning because abc (unquoted) cannot be concatenated with the preceding string.
Now consider the preprocessor stringize (Which was once called stringification, the links in the documentation have been changed to reflect the revised terminology. (Both terms, incidentally, are equally detestable. The correct term is, of course, stringifaction. Be ready to update your links.)) operator. This acts only on the arguments of a macro and replaces the unexpanded argument with the argument enclosed in double quotes. Thus:
#define STR(x) #x
char *s1 = "abc";
char *s2 = STR(abc);
will assign identical values to s1 and s2. If you run gcc -E you can see this in the output. Perhaps STR would be better named something like ENQUOTE.
This solves the problem of putting quotes around an unquoted item, the problem now is that, if the argument is a macro, the macro will not be expanded. This is why the second macro is needed. XSTR expands its argument, then calls STR to put the expanded value into quotes.
BOOST_PP_STRINGIZE seems a excellent solution for C++, but not for regular C.
Here is my solution for GNU CPP:
/* Some test definition here */
#define DEFINED_BUT_NO_VALUE
#define DEFINED_INT 3
#define DEFINED_STR "ABC"
/* definition to expand macro then apply to pragma message */
#define VALUE_TO_STRING(x) #x
#define VALUE(x) VALUE_TO_STRING(x)
#define VAR_NAME_VALUE(var) #var "=" VALUE(var)
/* Some example here */
#pragma message(VAR_NAME_VALUE(NOT_DEFINED))
#pragma message(VAR_NAME_VALUE(DEFINED_BUT_NO_VALUE))
#pragma message(VAR_NAME_VALUE(DEFINED_INT))
#pragma message(VAR_NAME_VALUE(DEFINED_STR))
Above definitions result in:
test.c:10:9: note: #pragma message: NOT_DEFINED=NOT_DEFINED
test.c:11:9: note: #pragma message: DEFINED_BUT_NO_VALUE=
test.c:12:9: note: #pragma message: DEFINED_INT=3
test.c:13:9: note: #pragma message: DEFINED_STR="ABC"
For "defined as interger", "defined as string", and "defined but no value" variables , they work just fine. Only for "not defined" variable, they displayed exactly the same as original variable name. You have to used to it -- or maybe someone can provide a better solution.
If you are using Visual C++, you can use #pragma message:
#include <boost/preprocessor/stringize.hpp>
#pragma message("BOOST_VERSION=" BOOST_PP_STRINGIZE(BOOST_VERSION))
Edit: Thanks to LB for link
Apparently, the GCC equivalent is (not tested):
#pragma message "BOOST_VERSION=" BOOST_PP_STRINGIZE(BOOST_VERSION)
As far as I know '#error' only will print strings, in fact you don't even need to use quotes.
Have you tried writing various purposefully incorrect code using "BOOST_VERSION"? Perhaps something like "blah[BOOST_VERSION] = foo;" will tell you something like "string literal 1.2.1 cannot be used as an array address". It won't be a pretty error message, but at least it'll show you the relevant value. You can play around until you find a compile error that does tell you the value.
Without boost :
define same macro again and compiler HIMSELF will give warning.
From warning you can see location of the previous definition.
vi file of previous definition .
ambarish#axiom:~/cpp$ g++ shiftOper.cpp
shiftOper.cpp:7:1: warning: "LINUX_VERSION_CODE" redefined
shiftOper.cpp:6:1: warning: this is the location of the previous definition
#define LINUX_VERSION_CODE 265216
#define LINUX_VERSION_CODE 666
int main ()
{
}
In Microsoft C/C++, you can use the built-in _CRT_STRINGIZE() to print constants. Many of my stdafx.h files contain some combination of these:
#pragma message("_MSC_VER is " _CRT_STRINGIZE(_MSC_VER))
#pragma message("_MFC_VER is " _CRT_STRINGIZE(_MFC_VER))
#pragma message("_ATL_VER is " _CRT_STRINGIZE(_ATL_VER))
#pragma message("WINVER is " _CRT_STRINGIZE(WINVER))
#pragma message("_WIN32_WINNT is " _CRT_STRINGIZE(_WIN32_WINNT))
#pragma message("_WIN32_IE is " _CRT_STRINGIZE(_WIN32_IE))
#pragma message("NTDDI_VERSION is " _CRT_STRINGIZE(NTDDI_VERSION))
and outputs something like this:
_MSC_VER is 1915
_MFC_VER is 0x0E00
_ATL_VER is 0x0E00
WINVER is 0x0600
_WIN32_WINNT is 0x0600
_WIN32_IE is 0x0700
NTDDI_VERSION is 0x06000000
#define a <::BOOST_VERSION>
#include a
MSVC2015: fatal error C1083: Cannot open include file: '::106200': No such file or directory
Pros:
Works on builtin macroses
Works even if preprocess to file is enabled, even if invalid tokens are present:
#define a <::'*/`#>
#include a
MSVC2015: fatal error C1083: Cannot open include file: '::'*/`#': No such file or directory
GCC4.x: warning: missing terminating ' character [-Winvalid-pp-token]
#define a <::'*/`#>
Cons:
Sometime fails because of invalid characters in the include file path. Can be fixed by change a prefix (see update section below).
Update:
For GCC 4.7.x and lower the output throws the error:
error: #include expects "FILENAME" or <FILENAME>
To fix that you can change the prefix:
#define a <.__cplusplus>
#include a
fatal error: .201103L: No such file or directory
You could also preprocess the source file and see what the preprocessor value evaluates to.
You could write a program that prints out BOOST_VERSION and compile and run it as part of your build system. Otherwise, I think you're out of luck.
Are you looking for
#if BOOST_VERSION != "1.2"
#error "Bad version"
#endif
Not great if BOOST_VERSION is a string, like I've assumed, but there may also be individual integers defined for the major, minor and revision numbers.
Looking at the output of the preprocessor is the closest thing to the answer you ask for.
I know you've excluded that (and other ways), but I'm not sure why. You have a specific enough problem to solve, but you have not explained why any of the "normal" methods don't work well for you.
BOOST_VERSION is defined in the boost header file version.hpp.
Take a look at the Boost documentation as well, regarding how you are using the macro:
In reference to BOOST_VERSION, from http://www.boost.org/doc/libs/1_37_0/libs/config/doc/html/boost_config/boost_macro_reference.html#boost_config.boost_macro_reference.boost_helper_macros:
Describes the boost version number in
XXYYZZ format such that:
(BOOST_VERSION % 100) is the sub-minor
version, ((BOOST_VERSION / 100) %
1000) is the minor version, and
(BOOST_VERSION / 100000) is the major
version.
Instead of #error, try redefining the macro, just before it is being used. Compilation will fail and compiler will provide the current value it thinks applies to the macro.
#define BOOST_VERSION blah