Velocity Reviews - Computer Hardware Reviews

Velocity Reviews > Newsgroups > Programming > C++ > C preprocessor function macros with empty aguments

Reply
Thread Tools

C preprocessor function macros with empty aguments

 
 
Sabyasachi Basu
Guest
Posts: n/a
 
      09-02-2003
While trying to port some stuff from Unix to Windows, I encountered a
strange behaviour of function macros with empty arguments. Here is a small
snippet which illustrates the problem:

#include <iostream>
#include <string>
using namespace std;

#define B(X, Y) Y

int main()
{
string mystr (B(, "hello world"));
cout << mystr << std::endl;

return 0;
}

This correctly prints 'hello world' when compiled with g++. However, this
program fails to compile on VC++. On going through the preprocessor output
in VC++, I found that the macro call line is:
string mystr ();
This expansion is incorrect.
g++ does the correct expansion (as documented:
http://gcc.gnu.org/onlinedocs/gcc-3....p_3.html#SEC15 )
and the output for the same statement for the g++ preprocessor is:
string mystr ("hello world");

On fiddling around a little more, I realised that the VC++ preprocessor
shifts to the left the non-empty arguments passed, if any. For instance, on
changing the macro definition to:
#define B(X, Y) X X
the statement string mystr (B(, "hello world")); got incorrectly
expanded on VC++ to
string mystr ("hello world" "hello world");
while g++ correctly expanded it to
string mystr ( );

I am using VC++ 6.0

-- Saby






 
Reply With Quote
 
 
 
 
Aggro
Guest
Posts: n/a
 
      09-02-2003
Sabyasachi Basu wrote:

> This correctly prints 'hello world' when compiled with g++. However, this
> program fails to compile on VC++.


So why don't you compile it with g++ then? You can use that in Windows
also to compile windows binaries. You can get mingw from here:

http://www.mingw.org/

 
Reply With Quote
 
 
 
 
Paul Mensonides
Guest
Posts: n/a
 
      09-02-2003
Sabyasachi Basu wrote:

> int main()
> {
> string mystr (B( , "hello world"));

^^^

Passing nothing as an argument results in undefined behavior, so neither
preprocessor is "correct." In C99, this behavior is well-defined and
more-or-less works like you'd assume an empty argument should work, but this is
not yet a part of C++.

Regards,
Paul Mensonides


 
Reply With Quote
 
red floyd
Guest
Posts: n/a
 
      09-02-2003
Paul Mensonides wrote:
> Sabyasachi Basu wrote:
>
>
>>int main()
>>{
>> string mystr (B( , "hello world"));

>
> ^^^
>
> Passing nothing as an argument results in undefined behavior, so neither
> preprocessor is "correct." In C99, this behavior is well-defined and
> more-or-less works like you'd assume an empty argument should work, but this is
> not yet a part of C++.
>
> Regards,
> Paul Mensonides
>
>


I guess the OP could use:

#define EMPTY

// yada yada yada

string mystr(B(EMPTY, "Hello World"));


 
Reply With Quote
 
Paul Mensonides
Guest
Posts: n/a
 
      09-02-2003
red floyd wrote:

> I guess the OP could use:
>
> #define EMPTY
>
> // yada yada yada
>
> string mystr(B(EMPTY, "Hello World"));


Yes, so long as it only goes through one level of expansion:

#define EMPTY

#define A(x) x

A(EMPTY) // okay

#define X(p) Y(p)
#define Y(p) p

X(EMPTY) // undefined behavior

Regards,
Paul Mensonides


 
Reply With Quote
 
Sabyasachi Basu
Guest
Posts: n/a
 
      09-02-2003
I don't think this behaviour is undefined, going by the GNU documentation,
at least.

Here is what it has to say:
http://gcc.gnu.org/onlinedocs/gcc-3....p_3.html#SEC16
"You can leave macro arguments empty; this is not an error to the
preprocessor (but many macros will then expand to invalid code). You cannot
leave out arguments entirely; if a macro takes two arguments, there must be
exactly one comma at the top level of its argument list. "

Regards,
Saby


"Paul Mensonides" <> wrote in message
news:7aW4b.246870$cF.79001@rwcrnsc53...
> Sabyasachi Basu wrote:
>
> > int main()
> > {
> > string mystr (B( , "hello world"));

> ^^^
>
> Passing nothing as an argument results in undefined behavior, so neither
> preprocessor is "correct." In C99, this behavior is well-defined and
> more-or-less works like you'd assume an empty argument should work, but

this is
> not yet a part of C++.
>
> Regards,
> Paul Mensonides
>
>



 
Reply With Quote
 
Sabyasachi Basu
Guest
Posts: n/a
 
      09-02-2003
I am afraid, the path is not open for me. This is a small contrived snippet
of code that I wrote to illustrate the problem. The actual software that I
need to port, runs into hundreds of thousands of lines and it needs to be
compiled with VC++ on Windows.

Regards,
Sabya

"Aggro" <> wrote in message
news:T7W4b.38$...
> Sabyasachi Basu wrote:
>
> > This correctly prints 'hello world' when compiled with g++. However,

this
> > program fails to compile on VC++.

>
> So why don't you compile it with g++ then? You can use that in Windows
> also to compile windows binaries. You can get mingw from here:
>
> http://www.mingw.org/
>



 
Reply With Quote
 
Peter van Merkerk
Guest
Posts: n/a
 
      09-02-2003
> I don't think this behaviour is undefined, going by the GNU
documentation,
> at least.
>
> Here is what it has to say:
> http://gcc.gnu.org/onlinedocs/gcc-3....p_3.html#SEC16
> "You can leave macro arguments empty; this is not an error to the
> preprocessor (but many macros will then expand to invalid code). You

cannot
> leave out arguments entirely; if a macro takes two arguments, there

must be
> exactly one comma at the top level of its argument list. "


It may be defined behaviour for the G++ compiler, however that doesn't
mean it is defined behaviour according to the C++ standard. The G++
compiler supports several features that are not defined in the C++
standard.

--
Peter van Merkerk
peter.van.merkerk(at)dse.nl


 
Reply With Quote
 
Jack Klein
Guest
Posts: n/a
 
      09-02-2003
On Tue, 2 Sep 2003 14:05:03 +0530, "Sabyasachi Basu" <sabya_01 AT hot
mail DOTcom> wrote in comp.lang.c:

> I don't think this behaviour is undefined, going by the GNU documentation,
> at least.
>
> Here is what it has to say:
> http://gcc.gnu.org/onlinedocs/gcc-3....p_3.html#SEC16
> "You can leave macro arguments empty; this is not an error to the
> preprocessor (but many macros will then expand to invalid code). You cannot
> leave out arguments entirely; if a macro takes two arguments, there must be
> exactly one comma at the top level of its argument list. "
>
> Regards,
> Saby


The GNU compiler does not define the language, the ISO standard does.
Omitting arguments from macros is not now, and never has been, legal
in the C++ language. It is possible to write macros with variable
arguments under the latest C standard, but not in this form.

Visual C++, at least through version 6, does not support this in
either C or C++.

If you want portability, write portable code and do not use
non-standard compiler extensions.

--
Jack Klein
Home: http://JK-Technology.Com
FAQs for
comp.lang.c http://www.eskimo.com/~scs/C-faq/top.html
comp.lang.c++ http://www.parashift.com/c++-faq-lite/
alt.comp.lang.learn.c-c++ ftp://snurse-l.org/pub/acllc-c++/faq
 
Reply With Quote
 
Sabyasachi Basu
Guest
Posts: n/a
 
      09-02-2003
Yes, that would work if there were only level of macro expansion. However,
the following program is closer to what actually exists in my code. The
preprocessor correctly expands EMPTY to blank when expanding the first
level; however, it ends up in the same situation as before when it passes
that blank to the next macro.

#include <iostream>
#include <string>
using namespace std;

#define EMPTY
#define B(X, Y) Y
#define XY(X, Y) \
B(X, Y)

int main()
{
string mystr (XY(EMPTY, "hello world"));
cout << mystr << std::endl;
return 0;
}

Compiling...
testmacro.cpp
C:\Work\testmacro\testmacro.cpp(14) : warning C4003: not enough actual
parameters for macro 'B'
Linking...
testmacro.obj : error LNK2001: unresolved external symbol "class
std::basic_string<char,struct std::char_traits<char>,class
std::allocator<char> > __cdecl mystr(void)"
(?mystr@@YA?AV?$basic_string@DU?$char_traits@D@std @@V?$allocator@D@2@@std@@X
Z)
Debug/testmacro.exe : fatal error LNK1120: 1 unresolved externals
Error executing link.exe.

testmacro.exe - 2 error(s), 1 warning(s)


"red floyd" <> wrote in message
news:9KW4b.10210$ om...

> #define EMPTY
>
> // yada yada yada
>
> string mystr(B(EMPTY, "Hello World"));
>
>



 
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
function and arguments as aguments Telmo Costa Javascript 40 02-20-2006 02:09 PM
Macros within function-like macros? Anthony de Almeida Lopes C Programming 13 12-27-2005 08:38 PM
Compiler error occurred when try to use a flexible template expression in preprocessor definesCompiler error occurred when try to use a flexible template expression in preprocessor defines snnn C++ 6 03-14-2005 04:09 PM
preprocessor, token concatenation, no valid preprocessor token Cronus C++ 1 07-14-2004 11:10 PM
C preprocessor function macros with empty aguments Sabyasachi Basu C Programming 26 09-05-2003 10:19 AM



Advertisments
 



1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57