Skip to main content
GameDev.net gamedev.net
🔒 Locked

VC++6.0 - compiler bug?

Started by Gabriel Fleseriu Apr 22, 2002 at 9:07 AM 11 replies 400+ views
Original Post
Gabriel Fleseriu
Gabriel Fleseriu
A buddy of mine posted a piece of code on another BB, pointing that it might be a compiler bug. The problem boils down to this code:
// VC++6.0 SP5, on W2k SP2
// Win32 Console App, debug build (default configuration)

class a
{
private:
	int m_i;
public:
	a operator << (int i);
};

a a::operator <<(int i)
{
	m_i = i;	// breakpoint here
	return *this;
}

int main(int argc, char* argv[])
{	
	int z = 10;	
	a aa;
	aa << ++z << z;
	return 0;
}

 
When the breakpoint is touched the first time, the operator << gets 11 as function parameter (as expected). When the breakpoint is touched the second time, the parameter is 10. I think this is a compiler bug. What do you think? Forever trusting who we are And nothing else matters - Metallica
Forever trusting who we areAnd nothing else matters - Metallica
CGameProgrammer
CGameProgrammer
It works if it''s z++, right?

~CGameProgrammer( );

~CGameProgrammer( ); Developer Image Exchange -- New Features: Upload screenshots of your games (size is unlimited) and upload the game itself (up to 10MB). Free. No registration needed.
Gabriel Fleseriu
Gabriel Fleseriu
quote:
Original post by CGameProgrammer
It works if it's z++, right?

~CGameProgrammer( );



No idea, I didn't try that. And it's not the point of the story. It SHOULD work this way, too.



Forever trusting who we are
And nothing else matters
- Metallica


[edited by - Gabriel Fleseriu on April 22, 2002 10:15:41 AM]
Forever trusting who we areAnd nothing else matters - Metallica
SabreMan
SabreMan
This isn''t a compiler bug. The C++ Standard doesn''t guarantee the order of evaluation of function calls between sequence points. The solution is quite simple, and I think you can guess what it is...


[C++ FAQ Lite | ACCU | Boost | Stroustrup on Learning C++]
Shrew
Shrew
IIRC the evaluation order for unrelated operations within one expression are indeterminate:

Meaning that the usage and evaluation of z and ++z within the expression can not be gauranteed (I expect different compilers would give different results). C++ will only gaurantee that the value of z will be 11 after the entire expression.

I say this because it looks like a variation of the oft-used example to show this behaviour:

printf( "%d %d %d", z, ++z, z++);

where you cannot gaurantee at all what will get printed out; just the value of z before and after this function call.

Robert Swan
My company - Aah Games - http://www.aahgames.com
Shrew
Shrew
ah, sequence points - i knew there had to be a better way of putitng it

Robert Swan
My company - Aah Games - http://www.aahgames.com
pieman
pieman
You''re making assumptions about the order in which the expressions are going to get evaluated. There''s no reason why the compiler has to evaluate the expression from left to right (despite that being the obvious thing to do).

Here''s an expression tree for what you''re doing :

aa
/ \
/ \
<< z
/ \
/ \
aa ++z

The compiler will convert this into reverse-polish notation so that it can evaluate it, which would produce something like this (assuming a stack-based evaluation) :

PUSH z
PUSH ++z
PUSH aa
CALL <<
CALL <<


Basically you can''t make any assumptions about the order in which the compiler will evaluate each section of an expression (especially when some bits of it have side effects, like the ++ and -- operators).


Iain Hutchison
Programmer, Silicon Dreams
The views expressed here are my own, not those of my employer.
Iain HutchisonProgrammer, Silicon DreamsThe views expressed here are my own, not those of my employer.
Gabriel Fleseriu
Gabriel Fleseriu
Undefined behaviour: I guess you (all) are right. THX.

Forever trusting who we are
And nothing else matters
- Metallica
Forever trusting who we areAnd nothing else matters - Metallica
Gabriel Fleseriu
Gabriel Fleseriu
quote:
Original post by Oluseyi
I think your insertion operator should return a reference. As it is right now, it returns a copy of the object.

[ GDNet Start Here | GDNet Search Tool | GDNet FAQ ]
[ MS RTFM [MSDN] | SGI STL Docs | Boost ]
[ Google! | Asking Smart Questions | Jargon File ]
Thanks to Kylotan for the idea!



Yes, you're right, of course . I just boiled the code down in a hurry
[edit] The original code was using cout<<...
Forever trusting who we are
And nothing else matters
- Metallica


[edited by - Gabriel Fleseriu on April 22, 2002 11:39:37 AM]
Forever trusting who we areAnd nothing else matters - Metallica
fallenang3l
fallenang3l
In VC++ 7.0 I get 11 both times at the breakpoint.
Gabriel Fleseriu
Gabriel Fleseriu
quote:
Original post by fallenang3l
In VC++ 7.0 I get 11 both times at the breakpoint.


As far as I understand this issue, the behaviour of the compiler is not defined (read the other posts). This means that the result may differ over different compilers (or compiler versions), different build modes (VC6.0 release build also displays 11, 11) and probably over different optimization switches, too.



Forever trusting who we are
And nothing else matters
- Metallica
Forever trusting who we areAnd nothing else matters - Metallica

Topic Locked

This topic has been locked by a moderator. New replies are not allowed.

Sign in to reply to this topic.