473,396 Members | 2,147 Online
Bytes | Software Development & Data Engineering Community
Post Job

Home Posts Topics Members FAQ

Join Bytes to post your question to a community of 473,396 software developers and data experts.

macros that build macros


Back before C++ templates, I was taught a trick whereby one built C
macros that built other C macros. I can't remember how the heck we did
it. The problem is that there seems to be no standard way to include a
'#' or '#define' in the output of a macro. The other problem is that we
might have been using some sort of non-standard preprocessor trick to do it.

Obliged if anyone can point me in the right direction or tell me what
I'm trying to do is impossible.

-thant
Sep 11 '07 #1
6 2089
On Sep 11, 11:08 am, Thant Tessman <a...@standarddeviance.comwrote:
Back before C++ templates, I was taught a trick whereby one built C
macros that built other C macros. I can't remember how the heck we did
it. The problem is that there seems to be no standard way to include a
'#' or '#define' in the output of a macro. The other problem is that we
might have been using some sort of non-standard preprocessor trick to do it.

Obliged if anyone can point me in the right direction or tell me what
I'm trying to do is impossible.

-thant
It is impossible, according to the standard (paragraph 3 of 6.10.3.4
"Rescanning and further replacement")

"The resulting completely macro-replaced preprocessing token sequence
is not processed
as a preprocessing directive even if it resembles one, but all pragma
unary operator
expressions within it are then processed as specified in 6.10.9
below."

In other words, you cannot create preprocessor directives using macro
replacement. Of course, the compiler you were using in the past may
have had a non-standard extension which may have allowed such
behaviour

Regards,
B

Sep 11 '07 #2
On Mon, 10 Sep 2007 19:08:16 -0600, Thant Tessman
<ad*@standarddeviance.comwrote in comp.lang.c:
>
Back before C++ templates, I was taught a trick whereby one built C
macros that built other C macros. I can't remember how the heck we did
it. The problem is that there seems to be no standard way to include a
'#' or '#define' in the output of a macro. The other problem is that we
might have been using some sort of non-standard preprocessor trick to do it.

Obliged if anyone can point me in the right direction or tell me what
I'm trying to do is impossible.

-thant
"borophyll" already gave you the standard answer, that you cannot
directly generate a macro to be replaced in the expansion of another
macro.

There are other ways, depending on what it is you are trying to do,
which you haven't made clear. Show us an example of the macro you
would like to generate, and the other macros that you would like to
use in the generation. It might be possible.

--
Jack Klein
Home: http://JK-Technology.Com
FAQs for
comp.lang.c http://c-faq.com/
comp.lang.c++ http://www.parashift.com/c++-faq-lite/
alt.comp.lang.learn.c-c++
http://www.club.cc.cmu.edu/~ajo/docs/FAQ-acllc.html
Sep 11 '07 #3
On Sep 10, 8:08 pm, Thant Tessman <a...@standarddeviance.comwrote:
Back before C++ templates, I was taught a trick whereby one built C
macros that built other C macros. I can't remember how the heck we did
it. The problem is that there seems to be no standard way to include a
'#' or '#define' in the output of a macro. The other problem is that we
might have been using some sort of non-standard preprocessor trick to do it.

Obliged if anyone can point me in the right direction or tell me what
I'm trying to do is impossible.

While it's not possible in general, sometimes people run C source code
through the preprocessor twice before the compiler proper. That way
any generated #defines in the first preprocessor pass get expanded in
the second.

There's no standard way of doing that, but many compilers have an
option to stop after the preprocessing phase and to emit that code.
Some compilers implement the preprocessor as a separate program, which
you can run manually. Again, all well outside the scope of the
standard.

Sep 11 '07 #4
On Sep 11, 3:08 am, Thant Tessman <a...@standarddeviance.comwrote:
Back before C++ templates, I was taught a trick whereby one built C
macros that built other C macros. I can't remember how the heck we did
it. The problem is that there seems to be no standard way to include a
'#' or '#define' in the output of a macro. The other problem is that we
might have been using some sort of non-standard preprocessor trick to do it.

Obliged if anyone can point me in the right direction or tell me what
I'm trying to do is impossible.
As indicated by others it is not possible to do this using the
standard preprocessor and compiler, you need to run the preprocessor
more than once.

A preprocessor that I used for something like this is GPP (http://
en.nothingisreal.com/wiki/GPP), which is a general purpose
preprocessor. Next to the standard evaluation rules that CPP uses it
also defines a 2-pass evaluation. This is from the manual page:

#defeval x y
This acts in a similar way to #define, but the second argument y is
evaluated immediately. Since user macro definitions are also evaluated
each time they are called, this means that the macro y will undergo
two successive evaluations.

Kind regards,
Johan Borkhuis

Sep 11 '07 #5
I (Thant Tessman) wrote:
Back before C++ templates, I was taught a trick whereby one built C
macros that built other C macros. I can't remember how the heck we did
it. [...]
My thanks to all who replied. For the curious, the basic form of what
I'm trying to do is this:

#define FOO(A,B) stuff

should produce another macro:

#define BAR_A_B(C) stuff

The macros produce code in support of type-safe inter-process message
passing routines.

This is definitely a situation where it would be inappropriate to
deviate from the standard, and the workaround is simple enough:

#define FOO(A,B) stuff
#define BAR(A,B,C) more stuff

The reason this solution is less desirable is that the latter allows for
errors that the former would catch. But it's workable.

Again, thanks for the replies.

-thant
Sep 11 '07 #6
On Sep 11, 7:24 am, Thant Tessman <a...@standarddeviance.comwrote:
[...]
My thanks to all who replied. For the curious, the basic form of what
I'm trying to do is this:

#define FOO(A,B) stuff

should produce another macro:

#define BAR_A_B(C) stuff

The macros produce code in support of type-safe inter-process message
passing routines.

This is definitely a situation where it would be inappropriate to
deviate from the standard, and the workaround is simple enough:

#define FOO(A,B) stuff
#define BAR(A,B,C) more stuff

The reason this solution is less desirable is that the latter allows for
errors that the former would catch. But it's workable.
It's not really clear to me what you're trying to do. But I've used
sort of a backwards means of doing something similar. Consider the
following macros:

#define BIT(p,b) (b)

#define PORT(p,b) (PORT ## p)
#define PIN(p,b) (PIN ## p)
#define DDR(p,b) (DDR ## p)

#define MASK(b) (1 << (b))

#define Set_Port_Bit(p,b) ((p) |= MASK(b))
#define Clr_Port_Bit(p,b) ((p) &= ~MASK(b))
#define Tgl_Port_Bit(p,b) ((p) ^= MASK(b))

#define Get_Port_Bit(p,b) (((p) & MASK(b)) != 0)

#define Set_Output(io) Set_Port_Bit(PORT(io),BIT(io))
#define Reset_Output(io) Clr_Port_Bit(PORT(io),BIT(io))

#define Get_Input(io) Get_Port_Bit(PIN(io),BIT(io))

#define Tristate(io) Clr_Port_Bit(DDR(io),BIT(io))
#define Drive(io) Set_Port_Bit(DDR(io),BIT(io))

This was for an AVR microprocessor. There were for digital I/O ports,
a, B, C, and D. There were three I/O address for each digital I/O
port, PIN for reading input, PORT for writing output, and DDR (Data
Direction Register) to set each bit to be an input or an output. The
name of each register was appended with the port it referred to, e.g.,
PORTA, DDRB, PIND.

The macros above let me specify my output bits something like this

#define STATUS_LED A,7
#define SWITCH(n) D,(n+3) // switches on D3, D4, and D5

Then I could invoke the macros something like

Set_Output(STATUS_LED);
state = Get_Input(SWITCH(1));

If the hardware changes, and the status LED moved to port B, pin 3,
all I have to do is change the STATUS_LED definition to

#define STATUS_LED B,3

and everything works.

Perhaps you can adapt something like this.

Regards,

-=Dave

Sep 11 '07 #7

This thread has been closed and replies have been disabled. Please start a new discussion.

Similar topics

37
by: seberino | last post by:
I've been reading the beloved Paul Graham's "Hackers and Painters". He claims he developed a web app at light speed using Lisp and lots of macros. It got me curious if Lisp is inherently faster...
12
by: David Powell | last post by:
Because my work area won't have an Access programmer next year, I've been asked to rebuild their coded application as a set of modular tools. The idea is that a non-programmer will be able to...
3
by: Momoko | last post by:
Hi, I have three Access Databases, say A, B and Main, in which data flows between Main and A, Main and B. Within A and B, there are macros that trigger computation within the databases. I need...
5
by: Veit Wiessner | last post by:
I wrote a program that handles the buildcount of projects (gets called every time I compile a project, it writes a header file which is #include-ed in the project). My question is this, is it...
4
by: Chronologic | last post by:
All, I have an issue I would like some expert help on. I understand, or so I believe, that C# does not support the concept of a "compile time macro". At least not in the sense I'm looking...
6
by: DBxGlock | last post by:
I'm trying to create the equivalent of a post build event for a website. I have the "Web Deployment Projects" add-in installed and am attempting to follow the instructions in the "Using Web...
1
by: Nick | last post by:
Hi There, I'm a little confused how the ActiveSolutionProjects property works in the DTE object whilst working with macros. I would have thought that this would return an array of every active...
27
by: Cephalobus_alienus | last post by:
Hello, I know that macros are evil, but I recently came across a problem that I couldn't figure out how to solve with templates. I wanted to create a set of singleton event objects, and wrote...
3
by: scolivas | last post by:
I make and run macros all the time - now I need to schedule some reports to refresh from my machine round the clock. Problem is in order for the macros that do all my refreshing won't run unless I...
0
by: Charles Arthur | last post by:
How do i turn on java script on a villaon, callus and itel keypad mobile phone
0
by: emmanuelkatto | last post by:
Hi All, I am Emmanuel katto from Uganda. I want to ask what challenges you've faced while migrating a website to cloud. Please let me know. Thanks! Emmanuel
1
by: nemocccc | last post by:
hello, everyone, I want to develop a software for my android phone for daily needs, any suggestions?
1
by: Sonnysonu | last post by:
This is the data of csv file 1 2 3 1 2 3 1 2 3 1 2 3 2 3 2 3 3 the lengths should be different i have to store the data by column-wise with in the specific length. suppose the i have to...
0
marktang
by: marktang | last post by:
ONU (Optical Network Unit) is one of the key components for providing high-speed Internet services. Its primary function is to act as an endpoint device located at the user's premises. However,...
0
by: Hystou | last post by:
Most computers default to English, but sometimes we require a different language, especially when relocating. Forgot to request a specific language before your computer shipped? No problem! You can...
0
Oralloy
by: Oralloy | last post by:
Hello folks, I am unable to find appropriate documentation on the type promotion of bit-fields when using the generalised comparison operator "<=>". The problem is that using the GNU compilers,...
0
by: Hystou | last post by:
Overview: Windows 11 and 10 have less user interface control over operating system update behaviour than previous versions of Windows. In Windows 11 and 10, there is no way to turn off the Windows...
0
agi2029
by: agi2029 | last post by:
Let's talk about the concept of autonomous AI software engineers and no-code agents. These AIs are designed to manage the entire lifecycle of a software development project—planning, coding, testing,...

By using Bytes.com and it's services, you agree to our Privacy Policy and Terms of Use.

To disable or enable advertisements and analytics tracking please visit the manage ads & tracking page.