473,399 Members | 3,302 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,399 software developers and data experts.

m##__LINE__

Hello,

I wrote this:

#define M(x) enum { m##__LINE__ = x };
#line 1000
M(126)
M(341)
M(565)
...

expecting the preprocessor to build

enum { m1000 = 126 };
enum { m1001 = 341 };
enum { m1002 = 565 };
...

but instead got

enum { m__LINE__ = 126};
enum { m__LINE__ = 341};
enum { m__LINE__ = 565};
...

which of course did not copile.

Is there any solution to produce the expected result,
without entering the a sequence like 1000 1001 1002.. ?

I tried

#define M(l,x) enum { m##l = x };
#line 1000
M(__LINE__,126)
M(__LINE__,341)
M(__LINE__,565)
...

and similarly failed.

Note: I do not want to put these values into an array; I want
them as enum, which allows me to sort them using the compiler
with a sorting network, rather than at runtime.
TIA,

François Grieu
Nov 15 '05 #1
9 2326
sat

Hi Francois
lets assume that we do end up creating preprocessed enums like what you
have mentioned here. But, what are you trying to achieve by such a thing.
You would end up with
enum { m1000 = 126 };
enum { m1001 = 341 };
enum { m1002 = 565 };
which are generated before compile time, but how are you going to access
them in the code.. How do you know if 126 was the first (1000) enum and 341
was the second ( 1001) enum..
May be if you give the use case it would be easier to look at it and
appreciate the whole effort ..
sat
"Francois Grieu" <fg****@francenet.fr> wrote in message
news:fg**************************@news.free.fr... Hello,

I wrote this:

#define M(x) enum { m##__LINE__ = x };
#line 1000
M(126)
M(341)
M(565)
..

expecting the preprocessor to build

enum { m1000 = 126 };
enum { m1001 = 341 };
enum { m1002 = 565 };
..

but instead got

enum { m__LINE__ = 126};
enum { m__LINE__ = 341};
enum { m__LINE__ = 565};
..

which of course did not copile.

Is there any solution to produce the expected result,
without entering the a sequence like 1000 1001 1002.. ?

I tried

#define M(l,x) enum { m##l = x };
#line 1000
M(__LINE__,126)
M(__LINE__,341)
M(__LINE__,565)
..

and similarly failed.

Note: I do not want to put these values into an array; I want
them as enum, which allows me to sort them using the compiler
with a sorting network, rather than at runtime.
TIA,

François Grieu

Nov 15 '05 #2
Le mardi 11 octobre 2005 à 10:28:05, Francois Grieu a écrit dans
comp.lang.c*:
I wrote this:

#define M(x) enum { m##__LINE__ = x };
#line 1000
M(126)
M(341)
M(565)
..

expecting the preprocessor to build

enum { m1000 = 126 };
enum { m1001 = 341 };
enum { m1002 = 565 };
..

but instead got

enum { m__LINE__ = 126};
enum { m__LINE__ = 341};
enum { m__LINE__ = 565};


You need more macros to make sure __LINE__ is evaluated before being
glued to "m":

#define M__(l) m##l
#define M_(l) M__(l)
#define M(x) enum { M_(__LINE__) = x };

--
___________ 11/10/2005 13:10:12
_/ _ \_`_`_`_) Serge PACCALIN -- sp ad mailclub.net
\ \_L_) Il faut donc que les hommes commencent
-'(__) par n'être pas fanatiques pour mériter
_/___(_) la tolérance. -- Voltaire, 1763
Nov 15 '05 #3
Serge Paccalin <sp@mailclub.no.spam.net.invalid> wrote:
You need more macros to make sure __LINE__ is evaluated before
being glued to "m"


Many thanks, it works!
Anyone care to explain why THREE nested macros are necessary ?

#define M__(l) m##l
#define M_(l) M__(l)
#define M(x) enum { M_(__LINE__) = x };

#line 1000
M(565)
M(126)
M(341)
M(747)
enum {MustHave4Lines = 0/(__LINE__-1000==4)};

#define C(a,b) M_(a)>M_(b) // or another order
// for sorting networks, see TAOCP Vol 3
#define S(a,b,c,d) enum{M_(c)=C(a,b)?M_(a):M_(b),\
M_(d)=C(a,b)?M_(b):M_(a)};
S(1000,1002,2000,2002);S(1001,1003,2001,2003);
S(2000,2001,4000,3001);S(2002,2003,3002,4003);
S(3001,3002,4001,4002);
const int t[] = {M_(4000),M_(4001),M_(4002),M_(4003)};

#include<stdio.h>
int main(void)
{int j;
for(j=sizeof t/sizeof*t;j;)printf("%d\n",t[--j]);
return 0;}

François Grieu

PS: This is not an entry to the obfuscated C contest; I need
a table of constants sorted according to a such a complex
criteria that it is unpractical to sort it by hand, an I am
dealing with the limitations of an embedded platform, where
sorting in RAM is not an option.
Nov 15 '05 #4
Francois Grieu wrote:
PS: This is not an entry to the obfuscated C contest; I need
a table of constants sorted according to a such a complex
criteria that it is unpractical to sort it by hand, an I am
dealing with the limitations of an embedded platform, where
sorting in RAM is not an option.


Sort it by machine and generate C code.

--
Chris "electric hedgehog" Dollin
Essare - to be. Essen - to be at Messe Essen for SPIEL 05.
Nov 15 '05 #5
Chris Dollin <ke**@hpl.hp.com> wrote:
Sort it by machine and generate C code.


[OT] Yes, I did this previously, but I can't figure out
how to invoke an external tool and craft make rules within
the IDE (MW CW 4.2...) hosting the only known C compiler
for my target. And the table to sort changes several
times a day, during development, and I fear we forget to
invoke the sort tool.

So I decided to make a tool generating (once only)
C source code for a sorting network so that the C
compiler will do the job without an external tool.
Thanks to your trick, it is gona work ! And it's fun.
Francois Grieu
Nov 15 '05 #6
Chris Dollin <ke**@hpl.hp.com> wrote:
Sort it by machine and generate C code.


[OT] Yes, I did this previously, but I can't figure out
how to invoke an external tool and craft make rules within
the IDE (MW CW 4.2...) hosting the only known C compiler
for my target. And the table to sort changes several
times a day, during development, and I fear we forget to
invoke the sort tool.
So I decided to make a tool generating (once only)
C source code for a sorting network so that the C
compiler will do the job without an external tool.
Thanks to Serge's trick, it is gona work ! And it's fun.
Francois Grieu
Nov 15 '05 #7
Francois Grieu wrote:
Serge Paccalin <sp@mailclub.no.spam.net.invalid> wrote:
You need more macros to make sure __LINE__ is evaluated before
being glued to "m"


Many thanks, it works!
Anyone care to explain why THREE nested macros are necessary ?

#define M__(l) m##l
#define M_(l) M__(l)
#define M(x) enum { M_(__LINE__) = x };


IIRC With the following macros:

#define M_(l) m##l
#define M(x) enum { M_(__LINE__) = x };

the preprocessor will do the following sequence of replacements:
1) M(565)
2) enum { M_(__LINE__) = 565 }; /* Replace macro M and arguments */
3) enum { m##__LINE__ = 565 }; /* Replace macro M_ as next on line */
4) enum { m__LINE__ = 565 }; /* Process ## highest precedence */

Where as with the three macro version it will do the following:
1) M(565)
2) enum { M_(__LINE__) = 565 }; /* Replace macro M and arguments */
3) enum { M__(__LINE__) = 565 }; /* Replace macro M_ as next on line */
4) enum { M__(1001) = 565 }; /* Replace __LINE__ with the current
line number */
3) enum { m##1001 = 565 }; /* Replace macro M__ */
4) enum { m__LINE__ = 565 }; /* Process ## highest precedence */

So basically as soon as a preprocessor see a # or a ## in the current
stream of tokens to be preprocessed the very next thing that it will do
is to either convert the argument to a string or concatenate the two
arguments.

Kevin.
Nov 15 '05 #8
Kevin Bagust wrote:
Francois Grieu wrote:
Serge Paccalin <sp@mailclub.no.spam.net.invalid> wrote:
You need more macros to make sure __LINE__ is evaluated before
being glued to "m"

Many thanks, it works!
Anyone care to explain why THREE nested macros are necessary ?

#define M__(l) m##l
#define M_(l) M__(l)
#define M(x) enum { M_(__LINE__) = x };


IIRC With the following macros:

#define M_(l) m##l
#define M(x) enum { M_(__LINE__) = x };

the preprocessor will do the following sequence of replacements:
1) M(565)
2) enum { M_(__LINE__) = 565 }; /* Replace macro M and arguments */
3) enum { m##__LINE__ = 565 }; /* Replace macro M_ as next on line */
4) enum { m__LINE__ = 565 }; /* Process ## highest precedence */

Where as with the three macro version it will do the following:
1) M(565)
2) enum { M_(__LINE__) = 565 }; /* Replace macro M and arguments */
3) enum { M__(__LINE__) = 565 }; /* Replace macro M_ as next on line */
4) enum { M__(1001) = 565 }; /* Replace __LINE__ with the current
line number */
3) enum { m##1001 = 565 }; /* Replace macro M__ */
4) enum { m__LINE__ = 565 }; /* Process ## highest precedence */

Unfortunate copy/pasting here; last two lines should be

5) enum { m##1001 = 565 }; /* Replace macro M__ */
6) enum { m1001 = 565 }; /* Process ## */

S.
Nov 15 '05 #9
Kevin Bagust <ke**********@ntlworld.com> and Skarmander explained:
Francois Grieu wrote:
Anyone care to explain why THREE nested macros are necessary ?
When expanding
#define M_(l) m##l
#define M(x) enum { M_(__LINE__) = x };

the preprocessor will do the following sequence of replacements:
1) M(565)
2) enum { M_(__LINE__) = 565 }; /* Replace macro M and arguments */
3) enum { m##__LINE__ = 565 }; /* Replace macro M_ as next on line */
4) enum { m__LINE__ = 565 }; /* Process ## highest precedence */ but
#define M__(l) m##l
#define M_(l) M__(l)
#define M(x) enum { M_(__LINE__) = x };

this three macro version it will do the following:
1) M(565)
2) enum { M_(__LINE__) = 565 }; /* Replace macro M and arguments */
3) enum { M__(__LINE__) = 565 }; /* Replace macro M_ as next on line */
4) enum { M__(1001) = 565 }; /* Replace __LINE__ with current line nb */
5) enum { m##1001 = 565 }; /* Replace macro M__ */
6) enum { m1001 = 565 }; /* Process ## */


I now see the light. The M_ to M__ replacement delays reaching ## until
__LINE__ has been expanded. Clever. Is this par ANSI/ISO C89/90 ?
François Grieu
Nov 15 '05 #10

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

Similar topics

4
by: Imre | last post by:
Is there a Visual C++ newsgroup? I guess this question should go there, but I couldn't find it. Please take a look at the following little program: template <int Line> struct Test { enum {...
4
by: Dom Gilligan | last post by:
Is there any way to get the preprocessor to produce the current line number in double quotes? At first sight, gcc seems to replace __LINE__ last (which would make sense), and so won't replace it at...
1
by: Spry | last post by:
Hi, I wanted to write macros for finding the number of memory allocations and deallocations also wanted to find the locations. The code I have is a pretty big one. I have a wrapper on top of...
18
by: Paul Shipley | last post by:
Hi, Does anyone know a way of converting the __LINE__ macro to a string at compile time? The reason I ask it because I want to put some debug information in to tell me if memory is not being...
5
by: jake1138 | last post by:
I couldn't find an example of this anywhere so I post it in the hope that someone finds it useful. I believe this is compiler specific (I'm using gcc), as C99 defines __VA_ARGS__. Comments are...
5
by: Carlos | last post by:
I have a macro #define DIE(msg) do { fprintf(stderr, "%s (l.%d)\n", msg, __LINE__);\ exit(1); }\ while (0) and it works :). But later I thought, that if I use it like this: s =...
5
by: Generic Usenet Account | last post by:
Can someone kindly explain why stringification of the compiler preprocessor macro __LINE__ requires two steps, instead of one? I wanted to pass the error location of a system call to perror() and...
5
by: Neo | last post by:
Hie, Can I put __FILE__ and __LINE__ macros inside the class function which may not be inline. And void function() { classobject::LogInfo(...); } Internally LogInfo should log file name...
3
by: travis.downs | last post by:
Hi, I'm trying to use a macro to create a unique temporary variable name, such as #define TEMP_OBJ(string) MyType obj_ <some magic here(string); So something like TEMP_OBJ("foo")
0
by: Charles Arthur | last post by:
How do i turn on java script on a villaon, callus and itel keypad mobile phone
1
by: nemocccc | last post by:
hello, everyone, I want to develop a software for my android phone for daily needs, any suggestions?
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
jinu1996
by: jinu1996 | last post by:
In today's digital age, having a compelling online presence is paramount for businesses aiming to thrive in a competitive landscape. At the heart of this digital strategy lies an intricately woven...
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
tracyyun
by: tracyyun | last post by:
Dear forum friends, With the development of smart home technology, a variety of wireless communication protocols have appeared on the market, such as Zigbee, Z-Wave, Wi-Fi, Bluetooth, etc. Each...
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,...
0
isladogs
by: isladogs | last post by:
The next Access Europe User Group meeting will be on Wednesday 1 May 2024 starting at 18:00 UK time (6PM UTC+1) and finishing by 19:30 (7.30PM). In this session, we are pleased to welcome a new...

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.