From: Ulrich Eckhardt on
Ben Bacarisse wrote:
> And I am sorry to hear that! So many compilers that don't get it
> right even though the same rules have applied for many, many, years:

In that case, I think it was around -2 years. VC5 and even VC6 predate the
C++ standard.

/* Note: MSC13 (from VC7.0) was the first to get this right, for all earlier
MSCs add this workaround for the wrong for() variable scope. */
#if defined(_MSC_VER) && _MSC_VER<1300
# define for if(0) {} else for
#endif

That said, to the OP, never omit documenting workarounds!

Uli

From: Ulrich Eckhardt on
Ulrich Eckhardt wrote:
> That said, to the OP, never omit documenting workarounds!

I retract that statement, it was documented.

Uli

From: Ben Bacarisse on
Ulrich Eckhardt <doomster(a)knuut.de> writes:

> Ben Bacarisse wrote:
>> And I am sorry to hear that! So many compilers that don't get it
>> right even though the same rules have applied for many, many, years:
>
> In that case, I think it was around -2 years. VC5 and even VC6 predate the
> C++ standard.

Are we talking about the same thing? I am talking about /##/ in a
macro not generating a comment. The same rules for comments and macro
expansion have applied for 20 years, though it is conceivable the MS
VC choose to use a different rule for // comments since these are no
covered by the ancient C rules.

> /* Note: MSC13 (from VC7.0) was the first to get this right, for all earlier
> MSCs add this workaround for the wrong for() variable scope. */
> #if defined(_MSC_VER) && _MSC_VER<1300
> # define for if(0) {} else for
> #endif

This suggests we were talking about different code.

<snip>
--
Ben.
From: Kaz Kylheku on
On 2010-01-04, Wolfgang Lorenz <wl924236(a)arcor.de> wrote:
> This works fine with VC5. The cast allows me to concentrate on my
> algorithm and not having to worry about if the array contains real data
> or just pointers to it.
>
> But when compiling with VC2008, I get 3 warnings:
>
> (30) : warning C4700: uninitialized local variable 'i_ref' used
> (35) : warning C4700: uninitialized local variable 'i_ptr' used
> (47) : warning C4700: uninitialized local variable 'i_ref' used
>
> And it works only in release mode. With _DEBUG enabled, it stops with a
> runtime error :(
>
> -- Wolfgang
>
> // make loop counter local to prevent error C2374 with old compilers
> #if _MSC_VER <= 1200 // behaviour unknown for VC6 < version < VC2005
> #define for if (1) for
> #endif
>
> #include <stdio.h>
>
> template<class T> inline T& cast_to(T&, T& x) { return x; }
> template<class T> inline T& cast_to(T&, T* x) { return *x; }
> template<class T> inline T* cast_to(T*, T& x) { return &x; }
>
> #define lengthof(a) (sizeof(a) / sizeof(a[0]))

> #define foreach(e, T, a) for (int e##i = 0; e##i < lengthof(a); e##i++)
> { T e = cast_to(e, (a)[e##i]); /##/

These two lines look like they should be part of one macro definition,
but they got wrapped. A preprocessor directive must be all noe logical
line. To break a logical line into multiple physical lines, you have
to use a backslash-newline sequence, e.g:

#define multi_line(FOO) \
do { \
FOO; \
while (0)

Secondly, just exactly what do you think /##/ does? This is invalid
syntax. The ## token pasting operator must involve parameter of a macro.
I.e. either the left side, or the right side, or both, must be a macro
parameter.

// valid
#define paste2(x,y) x ## y
#define paste1(x) x ## __foo

// invalid: neither 1 nor a are a parameter
#define foo(z) 1 ## a

Moreover, the token pasting operator must produce a valid token.
The // sequence is not a token; it's a comment.
Macro expansion cannot produce lexical syntax which is then scanned as a
comment. Macro expansion. happens in translation stages which follow the
recognition of comments.

This /##/ is undefined behavior; it is not a correct
way to remove the extra opening brace.

> printf("\nforeach (i_cpy, int , is) =");
> foreach (i_cpy, int , is) {
> printf(" %d", i_cpy);
> }
>
> printf("\nforeach (i_ref, int&, is) =");
> foreach (i_ref, int&, is) {
> printf(" %d", i_ref);
> }

You have forgotten that your macro sticks an extra e onto the
identifiers using ## e . The variable defined is actually i_refe;
i_ref refers to nothing.

Until your brain grows to the point where you don't confuse the
hell out of yourself with this kind of preprocessor abuse,
do not attempt it.
From: Ulrich Eckhardt on
Ben Bacarisse wrote:
> Ulrich Eckhardt <doomster(a)knuut.de> writes:
>> Ben Bacarisse wrote:
>>> And I am sorry to hear that! So many compilers that don't get it
>>> right even though the same rules have applied for many, many, years:
>>
>> In that case, I think it was around -2 years. VC5 and even VC6 predate
>> the C++ standard.
>
> Are we talking about the same thing?

No, we aren't. Sorry for the confusion.

> I am talking about /##/ in a macro not generating a comment. The
> same rules for comments and macro expansion have applied for 20
> years, though it is conceivable the MS VC choose to use a different
> rule for // comments since these are no covered by the ancient C
> rules.

Token-pasting two slashes into a single-line comment works at least under
some versions of VC. Thought I found a smart hack with that until I tried
porting that to a different compiler...

Cheers!

Uli