Velocity Reviews - Computer Hardware Reviews

Velocity Reviews > Newsgroups > Programming > C Programming > Macro redefinition

Reply
Thread Tools

Macro redefinition

 
 
Tor Rustad
Guest
Posts: n/a
 
      08-31-2007
I'm implementing a parser, where there is a lot of different data
elements defined. Now instead of hand-coding X defines, and the massive
number of lines needed for table initialization, I decided to generate
this source instead.


So, I basically used this trick:

void gen_source_function(FILE *out)
{
#define EXPAND_DEF(num, name) generate_source_1(out, num, #name)
#include "iso8583_defs"

#define EXPAND_DEF(num, name) generate_source_2(out, num, #name)
#include "iso8583_defs"

}

where the "iso8583_defs" file, did contain a lot of lines like this:

EXPAND_DEF(1, FIELD_NAME);
EXPAND_DEF(2, ANOTHER_FIELD_NAME);


My question is simply, is the above C code allowed?


--
Tor <torust [at] online [dot] no>
 
Reply With Quote
 
 
 
 
Ben Pfaff
Guest
Posts: n/a
 
      08-31-2007
Tor Rustad <(E-Mail Removed)> writes:

> void gen_source_function(FILE *out)
> {
> #define EXPAND_DEF(num, name) generate_source_1(out, num, #name)
> #include "iso8583_defs"
>
> #define EXPAND_DEF(num, name) generate_source_2(out, num, #name)
> #include "iso8583_defs"
>
> }
>
> where the "iso8583_defs" file, did contain a lot of lines like this:
>
> EXPAND_DEF(1, FIELD_NAME);
> EXPAND_DEF(2, ANOTHER_FIELD_NAME);
>
>
> My question is simply, is the above C code allowed?


Sure. Lots of code uses this trick to avoid redundancy.

If you don't like the idea of using an include file for this, you
can also use a macro:

void gen_source_function(FILE *out)
{
#define ISO8583_DEFS \
EXPAND_DEF(1, FIELD_NAME); \
EXPAND_DEF(2, ANOTHER_FIELD_NAME);

#define EXPAND_DEF(num, name) generate_source_1(out, num, #name)
ISO8583_DEFS

#define EXPAND_DEF(num, name) generate_source_2(out, num, #name)
ISO8583_DEFS
}

I think it's a toss-up which is better. Neither is pretty, both
are functional.
--
char a[]="\n .CJacehknorstu";int putchar(int);int main(void){unsigned long b[]
={0x67dffdff,0x9aa9aa6a,0xa77ffda9,0x7da6aa6a,0xa6 7f6aaa,0xaa9aa9f6,0x11f6},*p
=b,i=24;for(;p+=!*p;*p/=4)switch(0[p]&3)case 0:{return 0;for(p--;i--;i--)case+
2:{i++;if(i)break;else default:continue;if(0)case 1utchar(a[i&15]);break;}}}
 
Reply With Quote
 
 
 
 
Dave Hansen
Guest
Posts: n/a
 
      08-31-2007
On Aug 31, 11:04 am, Tor Rustad <(E-Mail Removed)> wrote:
> I'm implementing a parser, where there is a lot of different data
> elements defined. Now instead of hand-coding X defines, and the massive
> number of lines needed for table initialization, I decided to generate
> this source instead.
>
> So, I basically used this trick:
>
> void gen_source_function(FILE *out)
> {
> #define EXPAND_DEF(num, name) generate_source_1(out, num, #name)
> #include "iso8583_defs"
>
> #define EXPAND_DEF(num, name) generate_source_2(out, num, #name)
> #include "iso8583_defs"
>
> }
>
> where the "iso8583_defs" file, did contain a lot of lines like this:
>
> EXPAND_DEF(1, FIELD_NAME);
> EXPAND_DEF(2, ANOTHER_FIELD_NAME);
>
> My question is simply, is the above C code allowed?


It's a pretty common idiom in the code I work with. One caveat: don't
forget to #undef EXPAND_DEF before redefining it.

Regards,

-=Dave

 
Reply With Quote
 
Tor Rustad
Guest
Posts: n/a
 
      08-31-2007
Ben Pfaff wrote:
> Tor Rustad <(E-Mail Removed)> writes:
>
>> void gen_source_function(FILE *out)
>> {
>> #define EXPAND_DEF(num, name) generate_source_1(out, num, #name)
>> #include "iso8583_defs"
>>
>> #define EXPAND_DEF(num, name) generate_source_2(out, num, #name)
>> #include "iso8583_defs"
>>
>> }
>>
>> where the "iso8583_defs" file, did contain a lot of lines like this:
>>
>> EXPAND_DEF(1, FIELD_NAME);
>> EXPAND_DEF(2, ANOTHER_FIELD_NAME);
>>
>>
>> My question is simply, is the above C code allowed?

>
> Sure. Lots of code uses this trick to avoid redundancy.


Yup, that's the idea.

> If you don't like the idea of using an include file for this, you
> can also use a macro:
>
> void gen_source_function(FILE *out)
> {
> #define ISO8583_DEFS \
> EXPAND_DEF(1, FIELD_NAME); \
> EXPAND_DEF(2, ANOTHER_FIELD_NAME);
>
> #define EXPAND_DEF(num, name) generate_source_1(out, num, #name)
> ISO8583_DEFS
>
> #define EXPAND_DEF(num, name) generate_source_2(out, num, #name)
> ISO8583_DEFS
> }


Interesting, I haven't seen this solution before.

However, there is a translation limit of "509 characters in a logical
source line", and isn't logical source lines made up after line-splicing
your ISO8583_DEFS above?

--
Tor <torust [at] online [dot] no>
 
Reply With Quote
 
Tor Rustad
Guest
Posts: n/a
 
      08-31-2007
Dave Hansen wrote:

<snip>

>> My question is simply, is the above C code allowed?

>
> It's a pretty common idiom in the code I work with. One caveat: don't
> forget to #undef EXPAND_DEF before redefining it.


Is really the #undef needed in this case? This is a function-like macro,
and the re-definition had identical argument list.

--
Tor <torust [at] online [dot] no>
 
Reply With Quote
 
Keith Thompson
Guest
Posts: n/a
 
      08-31-2007
Tor Rustad <(E-Mail Removed)> writes:
> Dave Hansen wrote:
>
> <snip>
>
>>> My question is simply, is the above C code allowed?

>> It's a pretty common idiom in the code I work with. One caveat:
>> don't
>> forget to #undef EXPAND_DEF before redefining it.

>
> Is really the #undef needed in this case? This is a function-like
> macro, and the re-definition had identical argument list.


C99 6.10.3p2:

An identifier currently defined as an object-like macro shall not
be redefined by another #define preprocessing directive unless the
second definition is an object-like macro definition and the two
replacement lists are identical. Likewise, an identifier currently
defined as a function-like macro shall not be redefined by another
#define preprocessing directive unless the second definition is a
function-like macro definition that has the same number and
spelling of parameters, and the two replacement lists are
identical.

This is a constraint.

--
Keith Thompson (The_Other_Keith) http://www.velocityreviews.com/forums/(E-Mail Removed) <http://www.ghoti.net/~kst>
San Diego Supercomputer Center <*> <http://users.sdsc.edu/~kst>
"We must do something. This is something. Therefore, we must do this."
-- Antony Jay and Jonathan Lynn, "Yes Minister"
 
Reply With Quote
 
Ben Pfaff
Guest
Posts: n/a
 
      08-31-2007
Tor Rustad <(E-Mail Removed)> writes:

> However, there is a translation limit of "509 characters in a logical
> source line", and isn't logical source lines made up after
> line-splicing your ISO8583_DEFS above?


Interesting point. I've not run into an implementation (yet)
that has such a stringent limit. I notice that C99 expanded the
limit to 4095 characters.
--
int main(void){char p[]="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuv wxyz.\
\n",*q="kl BIcNBFr.NKEzjwCIxNJC";int i=sizeof p/2;char *strchr();int putchar(\
);while(*q){i+=strchr(p,*q++)-p;if(i>=(int)sizeof p)i-=sizeof p-1;putchar(p[i]\
);}return 0;}
 
Reply With Quote
 
Richard Tobin
Guest
Posts: n/a
 
      08-31-2007
In article <(E-Mail Removed)>,
Tor Rustad <(E-Mail Removed)> wrote:

>Keith, I don't get your point. Doesn't the
>
>"unless the second definition is a function-like macro definition that
>has the same number and spelling of parameters, and the two replacement
>lists are identical"
>
>apply?


The replacement lists were different. One had generate_source_1,
the other generate_source_2. There wouldn't have been much point
if they were the same.

-- Richard
--
"Consideration shall be given to the need for as many as 32 characters
in some alphabets" - X3.4, 1963.
 
Reply With Quote
 
Tor Rustad
Guest
Posts: n/a
 
      08-31-2007
Keith Thompson wrote:
> Tor Rustad <(E-Mail Removed)> writes:
>> Dave Hansen wrote:
>>
>> <snip>
>>
>>>> My question is simply, is the above C code allowed?
>>> It's a pretty common idiom in the code I work with. One caveat:
>>> don't
>>> forget to #undef EXPAND_DEF before redefining it.

>> Is really the #undef needed in this case? This is a function-like
>> macro, and the re-definition had identical argument list.

>
> C99 6.10.3p2:
>
> An identifier currently defined as an object-like macro shall not
> be redefined by another #define preprocessing directive unless the
> second definition is an object-like macro definition and the two
> replacement lists are identical. Likewise, an identifier currently
> defined as a function-like macro shall not be redefined by another
> #define preprocessing directive unless the second definition is a
> function-like macro definition that has the same number and
> spelling of parameters, and the two replacement lists are
> identical.
>
> This is a constraint.


Keith, I don't get your point. Doesn't the

"unless the second definition is a function-like macro definition that
has the same number and spelling of parameters, and the two replacement
lists are identical"

apply?

--
Tor <torust [at] online [dot] no>
 
Reply With Quote
 
Tor Rustad
Guest
Posts: n/a
 
      08-31-2007
Ben Pfaff wrote:
> Tor Rustad <(E-Mail Removed)> writes:
>
>> However, there is a translation limit of "509 characters in a logical
>> source line", and isn't logical source lines made up after
>> line-splicing your ISO8583_DEFS above?

>
> Interesting point. I've not run into an implementation (yet)
> that has such a stringent limit. I notice that C99 expanded the
> limit to 4095 characters.


In my case, there will be _at least_ 128 lines to splice, each line on
average ca. 50 characters long, in total 6400 characters minimum.

--
Tor <torust [at] online [dot] no>
 
Reply With Quote
 
 
 
Reply

Thread Tools

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off
Trackbacks are On
Pingbacks are On
Refbacks are Off


Similar Threads
Thread Thread Starter Forum Replies Last Post
'class' type redefinition squallions@yahoo.com C++ 1 11-07-2004 05:51 AM
'class' type redefinition Son C++ 0 11-07-2004 05:02 AM
redefinition, different types Gernot Frisch C++ 13 09-14-2004 03:06 PM
Bar: 'class' type redefinition compile time error A C++ 1 10-22-2003 10:34 AM
Template redefinition problem Attila Feher C++ 5 09-22-2003 04:48 PM



Advertisments