I'm using Oxygen with CDT 9.3.0 built-in.
When I use a macro I defined that uses _Generic, all those macro uses are underlined with "syntax error", but the project compiles fine (which is setup to use my makefiles).
After reading a similar so question, and since _Generic begin from C11 possibly not supported by eclipse's code analysis, I tried defining a symbol for my macro definition to empty but it didn't work. (At project settings, C/C++ General->Paths and Symbols->Symbols Tab, GNU C, added symbol CONVERT(...) without a value and added a symbol CONVERT(X), and CONVERT() and CONVERT without a value).
For example my macro is:
#define FIRST_(_1, ...) _1
#define FIRST(...) FIRST_(__VA_ARGS__, _1, _2, _3)
#define CONVERT(...) \
_Generic((FIRST(__VA_ARGS__)), \
char* : toText, \
int : toInt, \
) (__VA_ARGS__)
and usage point, that gives the syntax error:
void* test = CONVERT("testme");
As #ErikW pointed out, _Generic is a C11 feature that Eclipse CDT's parser does not support yet. This bug tracks adding support for it.
(By the way, contributions to Eclipse CDT's C11 support are very welcome!)
It is possible to work around this using macros.
The problem with trying to define another version of the CONVERT(...) macro in "Paths and Symbols" is that the macros defined there are treated as if you wrote them at the very top of your file. A subsequent redefinition in your actual code overwrites the definition from "Paths and Symbols".
I can think of two approaches to go about this:
Approach 1
CDT defines a special macro __CDT_PARSER__ which evaluates to true when it's parsing the code, but false when the code is actually compiled.
You can take advantage of this to define a different version of CONVERT(...) for CDT's purposes:
#ifdef __CDT_PARSER__
#define CONVERT(...)
#else
#define CONVERT(...) \
_Generic((FIRST(__VA_ARGS__)), \
char* : toText, \
int : toInt, \
) (__VA_ARGS__)
#endif
This almost works, but not quite. We still get a syntax error, because this line:
void* test = CONVERT("testme", 42);
will now expand to:
void* test = ;
As you can see, we don't actually want an empty expansion for CONVERT(...). We want an expansion that will parse as a variable's initializer. 0 will work:
#ifdef __CDT_PARSER__
#define CONVERT(...) 0
#else
...
#endif
Approach 2
Instead of defining a different version of CONVERT(...), we could define _Generic(...) itself to be a macro for CDT's purposes.
This time, we can do it in "Paths and Symbols", because there is no redefinition of _Generic(...) in the code that would mess it up.
So let's define a symbol in "Paths and Symbols", with _Generic(...) as the name and an empty value.
Now, this line:
void* test = CONVERT("testme", 42);
will expand to:
void* test = _Generic((FIRST("testme", 42)), \
char* : toText, \
int : toInt, \
) ("testme", 42)
which will in turn expand to:
void* test = ("testme", 42);
which parses (("testme", 42) parses as a parenthesized comma-expression and is thus a valid initializer).
This approach has the advantage that you don't need to modify your actual code, and that it handles all uses of the _Generic macro rather than just the one in CONVERT.
On the other hand, it's possible that for some other uses of the _Generic macro, this particular expansion won't parse. If that's the case, you might be able to come up with a different expansion that will parse for all uses, or else you can go with Approach 1.
Related
static_assert() is a pretty great capability available since C11.
For pre-C11 compilers though, this capability must be emulated.
It's not too hard, there are many examples available over Internet.
For example :
#define STATIC_ASSERT(CONDITION, MSG) \
typedef char static_assert_##MSG[(CONDITION)?1:-1]
This makes it possible to transfer an error message in the condition, which is handy to explain what's going wrong if it ever gets triggered.
However, this MSG is a lot different from the one in C11's static_assert() :
It must be a single word
It must use only identifier characters
It cannot be a string with double quotes
This is so different from C11's static_assert() that it seems impossible to create a macro which would switch transparently between the C11 and the C90 version depending on the compiler.
In an effort to accept an error message which "looks like C11", aka a string with double quote, I've tested a new macro :
#define STATIC_ASSERT(CONDITION, MSG) \
typedef char static_assert[((void)(MSG), ((CONDITION)?1:-1))]
Using the , comma operator, this macro should accept MSG as a string, and just disregard it. But it will be displayed in case of error, which is the intention.
It works fine on clang, but not of gcc : error: variably modified at file scope.
I'm trying to understand why, and if there is a work around
If you replace the typedef-array-trick with the enum-trick, then you will get something that seems to work with both clang and gcc:
#define CONDITION 1
#define TOKENPASTE(a, b) a ## b // "##" is the "Token Pasting Operator"
#define TOKENPASTE2(a,b) TOKENPASTE(a, b) // expand then paste
#define static_assert(x, msg) enum { TOKENPASTE2(ASSERT_line_,__LINE__) \
= 1 / (msg && (x)) }
static_assert( CONDITION, "This should pass");
static_assert(!CONDITION, "This should fail");
This gives me, with gcc for example, on line 9 of foo.c:
foo.c:9: warning: division by zero [-Wdiv-by-zero]
static_assert(!CONDITION, "This should fail");
^
foo.c:9: error: enumerator value for 'ASSERT_line_9' is not an integer constant
static_assert(!CONDITION, "This should fail");
^~~~~~~~~~~~~
(Here the gcc switch -ftrack-macro-expansion=0 is used, as the extra error messages are not that helpful and just add noise.)
Note that some mangling of the name is still necessary, which you omitted. Here the text ASSERT_line_ is combined with the variable __LINE__. This ensures a unique name, provided:
You don't use it twice on a single line.
You don't use it in header files (or trust to luck).
Your code doesn't happen to use the identifiers like ASSERT_line_9 elsewhere.
For header files, you will need to add somewhere a single word with only identifier characters. For example:
#define static_assert3(x, msg, file) enum { TOKENPASTE2(file,__LINE__) = \
1 / (msg && (x)) }
#define static_assert(x, msg) static_assert3(x, msg, my_header_h_)
If this fails on line 17, gcc will give an error such as:
error: enumerator value for 'my_header_h_17' is not an integer constant
An alternative for the mangling in header files is to replace __LINE__ with __COUNTER__. I've not used it, because it is non-standard and because clang was slow to adopt it. But now it has been in gcc, msvc, and clang for about five years.
You could try the same modification with your typedef-array idea, and replace the comma operator with &&. Then your gcc error changes into a warning. For example, modifying your godbolt example to:
typedef char static_assert_2["hello world!" && (CONDITION) ? 1 : -1];
gives the unwanted warning: variably modified 'static_assert_2' at file scope for gcc.
One-liner
#define STATIC_ASSERT(CONDITION, MSG) { typedef char test[(CONDITION)?1:-1]; (void)(test*) #MSG; } (void)0
I'm writing some libraries for a microcontroller, and for that purpose, I use macro-like functions. For example, a macro-like function to enable an I2C module is defined as:
#define I2C_MODULE_ENABLE(_x) \
I2C##_x##CONLbits.I2CEN = 1
where _x is the module number (e.g.,1 or 2 in my case).
If a user calls this macro-like function as I2C_MODULE_ENABLE(1), it would be expanded by a preprocessor as I2C1CONLbits. I2CEN = 1.
However, if a user calls this macro-like function as I2C_MODULE_ENABLE(MY_I2C), where MY_I2C is a macro constant defined in a user-defined config.h file that is included by my i2c.h library (e.g., the macro constant is defined as #define MY_I2C 1), the macro-like function would be expanded as I2CMY_I2CCONLbits. I2CEN = 1.
I know that I need to somehow evaluate the MY_I2C macro constant before concatenation, and I can do that by adding another macro level:
#define __I2CxCONLbits(_x) I2C##_x##CONLbits
#define I2C_MODULE_ENABLE(_x) \
__I2CxCONLbits.I2CEN = 1
My question is: is there a more elegant solution to this problem since I have multiple registers like the CONLbits register. Using this approach I would need to define a special __I2CxREGISTER(_x) macro for every register.
I tried to do something like this:
#define __I2Cx(_x) I2C##_x
#define I2C_MODULE_ENABLE(_x) \
__I2Cx(_x)##CONLbits.I2CEN = 1
but that produces an output like this: I2C1 CONLbits .I2CEN = 1, and my compiler is complaining about the whitespace between I2C1 and CONLbits tokens.
You aren't adding the macro level properly, as I see it. The usual idiom is to define a wrapper that does nothing but forward the argument. That way, if the argument is itself a macro, it will be expanded before being passed to the macro that is wrapped:
#define I2C_MODULE_ENABLE__(x_) \
I2C##x_##CONLbits.I2CEN = 1
#define I2C_MODULE_ENABLE(x_) \
I2C_MODULE_ENABLE__(x_)
I took the liberty of renaming your macro parameter, since identifiers with leading underscores are defined as reserved for the implementation, I think it's better to be safe than sorry.
To solve your problem of the space I'd go with the proverbial level of indirection, and use a function like macro to generate the correct prefix token, and pass it along two levels to make sure it's expanded correctly:
#define I2Cx__(x_) I2C##x_
#define I2C_MODULE_ENABLE__(IC_) \
IC_##CONLbits.I2CEN = 1
#define I2C_MODULE_ENABLE_(IC_) \
I2C_MODULE_ENABLE__(IC_)
#define I2C_MODULE_ENABLE(x_) \
I2C_MODULE_ENABLE_(I2Cx__(x_))
See it live here
The whole shtick is to make sure the preprocessor sees and produces valid tokens at each step. Which can be a bit tiresome.
I regularly use object-like preprocessor macros as boolean flags in C code to turn on and off sections of code.
For example
#define DEBUG_PRINT 1
And then use it like
#if(DEBUG_PRINT == 1)
printf("%s", "Testing");
#endif
However, it comes a problem if the header file that contains the #define is forgotten to be included in the source code. Since the macro is not declared, the preprocessor treats it as if it equals 0, and the #if statement never runs.
When the header file is forgotten to be included, non-expected, unruly behaviour can occur.
Ideally, I would like to be able to both check that a macro is defined, and check that it equals a certain value, in one line. If it is not defined, the preprocessor throws an error (or warning).
I'm looking for something along the lines of:
#if-def-and-true-else-throw-error(DEBUG_PRINT)
...
#endif
It's like a combination of #ifdef and #if, and if it doesn't exist, uses #error.
I have explored a few avenues, however, preprocessor directives can't be used inside a #define block, and as far as I can tell, there is no preprocessor option to throw errors/warnings if a macro is not defined when used inside a #if statement.
This may not work for the general case (I don't think there's a general solution to what you're asking for), but for your specific example you might consider changing this sequence of code:
#if(DEBUG_PRINT == 1)
printf("%s", "Testing");
#endif
to:
if (DEBUG_PRINT == 1) {
printf("%s", "Testing");
}
It's no more verbose and will fail to compile if DEBUG_PRINT is not defined or if it's defined to be something that cannot be compared with 1.
as far as I can tell, there is no preprocessor option to throw errors/warnings if a macro is not defined when used inside a #if statement.
It can't be an error because the C standard specifies that behavior is legal. From section 6.10.1/3 of ISO C99 standard:
After all replacements due to macro expansion and the defined unary
operator have been performed, all remaining identifiers are replaced with the pp-number
0....
As Jim Balter notes in the comment below, though, some compilers (such as gcc) can issue warnings about it. However, since the behavior of substituting 0 for unrecognized preprocessor tokens is legal (and in many cases desirable), I'd expect that enabling such warnings in practice would generate a significant amount of noise.
There's no way to do exactly what you want. If you want to generate a compilation failure if the macro is not defined, you'll have to do it explicitly
#if !defined DEBUG_PRINT
#error DEBUG_PRINT is not defined.
#endif
for each source file that cares. Alternatively, you could convert your macro to a function-like macro and avoid using #if. For example, you could define a DEBUG_PRINT macro that expands to a printf call for debug builds but expands to nothing for non-debug builds. Any file that neglects to include the header defining the macro then would fail to compile.
Edit:
Regarding desirability, I have seen numerous times where code uses:
#if ENABLE_SOME_CODE
...
#endif
instead of:
#ifdef ENABLE_SOME_CODE
...
#endif
so that #define ENABLE_SOME_CODE 0 disables the code rather than enables it.
Rather than using DEBUG_PRINT directly in your source files, put this in the header file:
#if !defined(DEBUG_PRINT)
#error DEBUG_PRINT is not defined
#endif
#if DEBUG_PRINT
#define PrintDebug([args]) [definition]
#else
#define PrintDebug
#endif
Any source file that uses PrintDebug but doesn't include the header file will fail to compile.
If you need other code than calls to PrintDebug to be compiled based on DEBUG_PRINT, consider using Michael Burr's suggestion of using plain if rather than #if (yes, the optimizer will not generate code within a false constant test).
Edit:
And you can generalize PrintDebug above to include or exclude arbitrary code as long as you don't have commas that look like macro arguments:
#if !defined(IF_DEBUG)
#error IF_DEBUG is not defined
#endif
#if IF_DEBUG
#define IfDebug(code) code
#else
#define IfDebug(code)
#endif
Then you can write stuff like
IfDebug(int count1;) // IfDebug(int count1, count2;) won't work
IfDebug(int count2;)
...
IfDebug(count1++; count2++;)
Yes you can check both:
#if defined DEBUG && DEBUG == 1
# define D(...) printf(__VA_ARGS__)
#else
# define D(...)
#endif
In this example even when #define DEBUG 0 but it is not equal to 1 thus nothing will be printed.
You can do even this:
#if defined DEBUG && DEBUG
# define D(...) printf(__VA_ARGS__)
#else
# define D(...)
#endif
Here if you #define DEBUG 0 and then D(1,2,3) also nothing will be printed
DOC
Simply create a macro DEBUG_PRINT that does the actual printing:
#define DEBUG_PRINT(n, str) \
\
if(n == 1) \
{ \
printf("%s", str); \
} \
else if(n == 2) \
{ \
do_something_else(); \
} \
\
#endif
#include <stdio.h>
int main()
{
DEBUG_PRINT(1, "testing");
}
If the macro isn't defined, then you will get a compiler error because the symbol is not recognized.
#if 0 // 0/1
#define DEBUG_PRINT printf("%s", "Testing")
#else
#define DEBUG_PRINT printf("%s")
#endif
So when "if 0" it'll do nothing and when "if 1" it'll execute the defined macro.
I declare macros which would make it easy to replicate the logic of writing to a file Log
I end up getting the error C2065: 'flog' : undeclared identifier.
But I don't get this error for log_buffer.
I am using Visual Studios 2008 IDE.
What am i doing wrong?
#ifndef ERROR_LOG_MACRO
#define ERROR_LOG_MACRO 1
#define SETERRORPARAMS char log_buffer[MAX_PATH]; \
char flog[MAX_PATH]; \
FILE *err_log_fp;
/*
Arguments: x (Name of the File)
y (File Path without the Filename)
z (Mode)
*/
#define OPENFILE(x,y,z) strcpy(flog,y); \
strcat(flog,"\\"); \
strcat(flog,x); \
err_log_fp = fopen(flog, z);
#define WRITELOG(x) if(err_log_fp) \
fwrite(log_buffer, sizeof(char), strlen(log_buffer), err_log_fp);
#define CLOSEFILE if(err_log_fp) \
fclose(err_log_fp);
#endif
I even tried to do
#define OPENFILE(x,y,z) SETERRORPARAMS \
... \
But even this did not work.
You probably have trailing whitespaces after the first line of your macro:
#define SETERRORPARAMS char log_buffer[MAX_PATH]; \______ <-- make sure you have no whitespaces
char flog[MAX_PATH]; \
FILE *err_log_fp;
Either that, or you're not using the macro and log_buffer is declared elsewhere.
Have you actually checked that flog is in scope wherever you're using the OPENFILE macro?
Such as with the code segment:
SETERRORPARAMS
OPENFILE (fileStr, pathStr, modeStr)
Worst case, you'll have to examine the code after the preprocessor has done its work. Most compilers will let you examine the output produced by that preprocessor stage. GCC would use gcc -E but I'm not sure what the equivalent is to MSVC.
This link seems to indicate you can enter /P into the project settings to get the preprocoessed files written to *.i files.
But, I've got to say this, using macros for this is not really a good idea. In the old days, it used to be good for speed purposes but it's not really necessary in these days of inline functions and very good code optimisers.
As mentioned in many of my previous questions, I'm working through K&R, and am currently into the preprocessor. One of the more interesting things — something I never knew before from any of my prior attempts to learn C — is the ## preprocessor operator. According to K&R:
The preprocessor operator ##
provides a way to concatenate actual
arguments during macro expansion. If a
parameter in the replacement text is
adjacent to a ##, the parameter is
replaced by the actual argument, the
## and surrounding white space are
removed, and the result is re-scanned.
For example, the macro paste
concatenates its two arguments:
#define paste(front, back) front ## back
so paste(name, 1) creates the token
name1.
How and why would someone use this in the real world? What are practical examples of its use, and are there gotchas to consider?
One thing to be aware of when you're using the token-paste ('##') or stringizing ('#') preprocessing operators is that you have to use an extra level of indirection for them to work properly in all cases.
If you don't do this and the items passed to the token-pasting operator are macros themselves, you'll get results that are probably not what you want:
#include <stdio.h>
#define STRINGIFY2( x) #x
#define STRINGIFY(x) STRINGIFY2(x)
#define PASTE2( a, b) a##b
#define PASTE( a, b) PASTE2( a, b)
#define BAD_PASTE(x,y) x##y
#define BAD_STRINGIFY(x) #x
#define SOME_MACRO function_name
int main()
{
printf( "buggy results:\n");
printf( "%s\n", STRINGIFY( BAD_PASTE( SOME_MACRO, __LINE__)));
printf( "%s\n", BAD_STRINGIFY( BAD_PASTE( SOME_MACRO, __LINE__)));
printf( "%s\n", BAD_STRINGIFY( PASTE( SOME_MACRO, __LINE__)));
printf( "\n" "desired result:\n");
printf( "%s\n", STRINGIFY( PASTE( SOME_MACRO, __LINE__)));
}
The output:
buggy results:
SOME_MACRO__LINE__
BAD_PASTE( SOME_MACRO, __LINE__)
PASTE( SOME_MACRO, __LINE__)
desired result:
function_name21
CrashRpt: Using ## to convert macro multi-byte strings to Unicode
An interesting usage in CrashRpt (crash reporting library) is the following:
#define WIDEN2(x) L ## x
#define WIDEN(x) WIDEN2(x)
//Note you need a WIDEN2 so that __DATE__ will evaluate first.
Here they want to use a two-byte string instead of a one-byte-per-char string. This probably looks like it is really pointless, but they do it for a good reason.
std::wstring BuildDate = std::wstring(WIDEN(__DATE__)) + L" " + WIDEN(__TIME__);
They use it with another macro that returns a string with the date and time.
Putting L next to a __ DATE __ would give you a compiling error.
Windows: Using ## for generic Unicode or multi-byte strings
Windows uses something like the following:
#ifdef _UNICODE
#define _T(x) L ## x
#else
#define _T(x) x
#endif
And _T is used everywhere in code
Various libraries, using for clean accessor and modifier names:
I've also seen it used in code to define accessors and modifiers:
#define MYLIB_ACCESSOR(name) (Get##name)
#define MYLIB_MODIFIER(name) (Set##name)
Likewise you can use this same method for any other types of clever name creation.
Various libraries, using it to make several variable declarations at once:
#define CREATE_3_VARS(name) name##1, name##2, name##3
int CREATE_3_VARS(myInts);
myInts1 = 13;
myInts2 = 19;
myInts3 = 77;
Here's a gotcha that I ran into when upgrading to a new version of a compiler:
Unnecessary use of the token-pasting operator (##) is non-portable and may generate undesired whitespace, warnings, or errors.
When the result of the token-pasting operator is not a valid preprocessor token, the token-pasting operator is unnecessary and possibly harmful.
For example, one might try to build string literals at compile time using the token-pasting operator:
#define STRINGIFY(x) #x
#define PLUS(a, b) STRINGIFY(a##+##b)
#define NS(a, b) STRINGIFY(a##::##b)
printf("%s %s\n", PLUS(1,2), NS(std,vector));
On some compilers, this will output the expected result:
1+2 std::vector
On other compilers, this will include undesired whitespace:
1 + 2 std :: vector
Fairly modern versions of GCC (>=3.3 or so) will fail to compile this code:
foo.cpp:16:1: pasting "1" and "+" does not give a valid preprocessing token
foo.cpp:16:1: pasting "+" and "2" does not give a valid preprocessing token
foo.cpp:16:1: pasting "std" and "::" does not give a valid preprocessing token
foo.cpp:16:1: pasting "::" and "vector" does not give a valid preprocessing token
The solution is to omit the token-pasting operator when concatenating preprocessor tokens to C/C++ operators:
#define STRINGIFY(x) #x
#define PLUS(a, b) STRINGIFY(a+b)
#define NS(a, b) STRINGIFY(a::b)
printf("%s %s\n", PLUS(1,2), NS(std,vector));
The GCC CPP documentation chapter on concatenation has more useful information on the token-pasting operator.
This is useful in all kinds of situations in order not to repeat yourself needlessly. The following is an example from the Emacs source code. We would like to load a number of functions from a library. The function "foo" should be assigned to fn_foo, and so on. We define the following macro:
#define LOAD_IMGLIB_FN(lib,func) { \
fn_##func = (void *) GetProcAddress (lib, #func); \
if (!fn_##func) return 0; \
}
We can then use it:
LOAD_IMGLIB_FN (library, XpmFreeAttributes);
LOAD_IMGLIB_FN (library, XpmCreateImageFromBuffer);
LOAD_IMGLIB_FN (library, XpmReadFileToImage);
LOAD_IMGLIB_FN (library, XImageFree);
The benefit is not having to write both fn_XpmFreeAttributes and "XpmFreeAttributes" (and risk misspelling one of them).
A previous question on Stack Overflow asked for a smooth method of generating string representations for enumeration constants without a lot of error-prone retyping.
Link
My answer to that question showed how applying little preprocessor magic lets you define your enumeration like this (for example) ...;
ENUM_BEGIN( Color )
ENUM(RED),
ENUM(GREEN),
ENUM(BLUE)
ENUM_END( Color )
... With the benefit that the macro expansion not only defines the enumeration (in a .h file), it also defines a matching array of strings (in a .c file);
const char *ColorStringTable[] =
{
"RED",
"GREEN",
"BLUE"
};
The name of the string table comes from pasting the macro parameter (i.e. Color) to StringTable using the ## operator. Applications (tricks?) like this are where the # and ## operators are invaluable.
You can use token pasting when you need to concatenate macro parameters with something else.
It can be used for templates:
#define LINKED_LIST(A) struct list##_##A {\
A value; \
struct list##_##A *next; \
};
In this case LINKED_LIST(int) would give you
struct list_int {
int value;
struct list_int *next;
};
Similarly you can write a function template for list traversal.
The main use is when you have a naming convention and you want your macro to take advantage of that naming convention. Perhaps you have several families of methods: image_create(), image_activate(), and image_release() also file_create(), file_activate(), file_release(), and mobile_create(), mobile_activate() and mobile_release().
You could write a macro for handling object lifecycle:
#define LIFECYCLE(name, func) (struct name x = name##_create(); name##_activate(x); func(x); name##_release())
Of course, a sort of "minimal version of objects" is not the only sort of naming convention this applies to -- nearly the vast majority of naming conventions make use of a common sub-string to form the names. It could me function names (as above), or field names, variable names, or most anything else.
I use it in C programs to help correctly enforce the prototypes for a set of methods that must conform to some sort of calling convention. In a way, this can be used for poor man's object orientation in straight C:
SCREEN_HANDLER( activeCall )
expands to something like this:
STATUS activeCall_constructor( HANDLE *pInst )
STATUS activeCall_eventHandler( HANDLE *pInst, TOKEN *pEvent );
STATUS activeCall_destructor( HANDLE *pInst );
This enforces correct parameterization for all "derived" objects when you do:
SCREEN_HANDLER( activeCall )
SCREEN_HANDLER( ringingCall )
SCREEN_HANDLER( heldCall )
the above in your header files, etc. It is also useful for maintenance if you even happen to want to change the definitions and/or add methods to the "objects".
SGlib uses ## to basically fudge templates in C. Because there's no function overloading, ## is used to glue the type name into the names of the generated functions. If I had a list type called list_t, then I would get functions named like sglib_list_t_concat, and so on.
I use it for a home rolled assert on a non-standard C compiler for embedded:
#define ASSERT(exp) if(!(exp)){ \
print_to_rs232("Assert failed: " ## #exp );\
while(1){} //Let the watchdog kill us
I use it for adding custom prefixes to variables defined by macros. So something like:
UNITTEST(test_name)
expands to:
void __testframework_test_name ()
One important use in WinCE:
#define BITFMASK(bit_position) (((1U << (bit_position ## _WIDTH)) - 1) << (bit_position ## _LEFTSHIFT))
While defining register bit description we do following:
#define ADDR_LEFTSHIFT 0
#define ADDR_WIDTH 7
And while using BITFMASK, simply use:
BITFMASK(ADDR)
It is very useful for logging. You can do:
#define LOG(msg) log_msg(__function__, ## msg)
Or, if your compiler doesn't support function and func:
#define LOG(msg) log_msg(__file__, __line__, ## msg)
The above "functions" logs message and shows exactly which function logged a message.
My C++ syntax might be not quite correct.