Escaping a # symbol in a #define macro?
As far as I remember you cannot use another preprocessor directive in define.
How to escape a # in a macro
Using an indirection through another macro should do the trick:
#define HASH_LIT #
#define HASH() HASH_LIT
#define create_me(name) \
__asm\
mov name,HASH()0x1021\
__endasm
How to print a pound / hash via C preprocessor?
The answer is:
#define hash #
#define f(x) x
#define label(a) f(hash)a
then
label(foobar)
creates
#foobar
I found it with the help of all of you, but especially wintermute.
Thanks a lot!
(Using gcc 4.3.3)
Construct string/char escape sequence using C macro
You can do this by generating a large header file, e.g. using a little bit of Python:
for x in range(0,256):
print '#define BODGE_0x%x \\x%x' % (x,x)
And then use the output of that in C:
#include <stdio.h>
#include "bodge.h"
#define xstr(s) str(s)
#define str(s) #s
#define XCHR(x,y) (xstr(x##y))
#define CHR(x) xstr(BODGE_##x)
int main() {
return printf("%s\n", CHR(0x20));
}
Which does exactly what you asked for, gcc -E
shows:
return printf("%s\n", "\x20");
It's possible (but fiddly) to do something less crude if you accept calling CHR(20)
to imply hex without the 0x
prefix.
The obvious solution would be to build a macro that expands to:
printf("%s", "\x" "20");
which is fairly easy to do with one level of indirection, and the obvious assumption would be that the compile time concatenation of strings would handle this. Unfortunately that solution isn't viable because of the point in translation when the escape sequence gets handle. GCC therefore gives the error:
error: \x used with no following hex digits
We can however work around that and cause the string "\x20" to be generated by using a pre-processor concatenation (##
) in conjunction with the "usual" preprocessor stringification indirection:
#include <stdio.h>
#define xstr(s) str(s)
#define str(s) #s
#define XCHR(x,y) (xstr(x##y))
#define CHR(y) XCHR(\x,y)
int main() {
return printf("%s", CHR(20));
}
This does work and, gcc -E shows:
return printf("%s", ("\x20"));
which is what we'd hope to see when the macro works.
You could also do:
#define CHR(x) ((char[2]){(x), 0x0})
which has the desired effect.
Is there a way to escape a C preprocessor directive?
A slight variant of Marcelo Cantos's answer works for me on GNU cpp 4.4.3:
#define HASH(x) x
...
HASH(#)ifdef __cplusplus
class foo { };
HASH(#)endif
How should I escape a comma inside the arguments to esyscmd?
As configured in autoconf, the M4 quote characters are [
and ]
. Commas inside a quote will not be interpreted as argument separators. Thus you should simply quote the command you are passing to esyscmd
, by surrounding it with [
and ]
.
Unlike in other programming languages you may be used to, quoting doesn't make the argument a string or anything like that -- quoting is simply a way to treat some text as fixed, and not to interpret macros or special characters within that text.
The M4 manual is really the only way to learn about M4.
C Macro utilizing immediate values in embedded arm asm - armcc
The second of your referenced questions shows you how to do it:
#define hash #
#define mash(x) x
#define immediate(a) mash(hash)a
#define ISR_THREAD_MGMT(ISR_FUNC,FUNC_NAME) \
__asm void FUNC_NAME ( void ); \
__asm void FUNC_NAME ( void ) \
{ \
STMDB sp!, {r0-r3}; \
MRS r0, SPSR; \
SUB lr, lr, immediate(4); \
STMDB sp!, {r0, r10, r12, lr}; \
bl _thread_vectored_context_save; \
bl ISR_FUNC; \
b _thread_context_restore; \
}
ISR_THREAD_MGMT(abc,def)
Output:
# 1 "x.c"
# 1 "<command-line>"
# 1 "x.c"
# 17 "x.c"
__asm void def ( void ); __asm void def ( void ) { STMDB sp!, {r0-r3}; MRS r0, SPSR; SUB lr, lr, #4; STMDB sp!, {r0, r10, r12, lr}; bl _thread_vectored_context_save; bl abc; b _thread_context_restore; }
Output reformatted:
# 1 "x.c"
# 1 "<command-line>"
# 1 "x.c"
# 17 "x.c"
__asm void def ( void );
__asm void def ( void )
{
STMDB sp!, {r0-r3};
MRS r0, SPSR;
SUB lr, lr, #4;
STMDB sp!, {r0, r10, r12, lr};
bl _thread_vectored_context_save;
bl abc;
b _thread_context_restore;
}
I'm not convinced it is a good idea, but it does at least work.
Related Topics
Why Can't I Capture This By-Reference ('&This') in Lambda
Compile the Python Interpreter Statically
Search a Vector of Objects by Object Attribute
How Does the Standard Library Implement Std::Swap
Why Don't Stl Containers Have Virtual Destructors
Multiple Preincrement Operations on a Variable in C++(C )
Why Can't I Define a Function Inside Another Function
In What Ways Do C++ Exceptions Slow Down Code When There Are No Exceptions Thown
Class Variables: Public Access Read-Only, But Private Access Read/Write
How to Generate a Random Double Uniformly Distributed Between 0 and 1 from C++
Why Is My Log in the Std Namespace