Velocity Reviews - Computer Hardware Reviews

Velocity Reviews > Newsgroups > Programming > C Programming > strange feature... or bug

Reply
Thread Tools

strange feature... or bug

 
 
sonic
Guest
Posts: n/a
 
      08-28-2007
Please tell me what is wrong (and for me to avoid browsing through
200k something messages
) or am i missing something obvious (btw i've tested with gcc on
latest Tiger OS X and linux); or should i post to gcc?

---------------------------
#include <stdio.h>

int main()
{
int i = 2;
i = (i*=1 ? i-2 : 0);
printf("val is %d\n", i);
return 0;
}
--------------------------

you would expect to print 0 right, it does!

removed -2, like:

-------------------------
#include <stdio.h>

int main()
{
int i = 2;
i = (i*=1 ? i : 0);
printf("val is %d\n", i);
return 0;
}
--------------------------
and it returns ... 4!, while i have expected 2...

 
Reply With Quote
 
 
 
 
Keith Thompson
Guest
Posts: n/a
 
      08-28-2007
sonic <(E-Mail Removed)> writes:
> Please tell me what is wrong (and for me to avoid browsing through
> 200k something messages
> ) or am i missing something obvious (btw i've tested with gcc on
> latest Tiger OS X and linux); or should i post to gcc?
>

[snip]
>
> -------------------------
> #include <stdio.h>
>
> int main()
> {
> int i = 2;
> i = (i*=1 ? i : 0);
> printf("val is %d\n", i);
> return 0;
> }
> --------------------------
> and it returns ... 4!, while i have expected 2...


I'll just address your second example.

In both programs, you modify 'i' twice between sequence points,
invoking undefined behavior.

Also, the spacing in your expression is inconsistent with the actual
operator precedence. The '?:' operator binds more tightly than an
assignment operator. Your statement
i = (i*=1 ? i : 0);
is equivalent to
i = (i *= (1 ? i : 0));
The subexpression '(1 ? i : 0)' can be reduced to 'i', giving:
i = (i *= i);
which still invokes UB.

If you start by thinking about what you want to do, and then write C
code to express your intent, you'll never write anything like that in
the first place.

--
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
 
 
 
 
Robert Gamble
Guest
Posts: n/a
 
      08-28-2007
On Aug 28, 4:06 pm, sonic <(E-Mail Removed)> wrote:
> Please tell me what is wrong (and for me to avoid browsing through
> 200k something messages
> ) or am i missing something obvious (btw i've tested with gcc on
> latest Tiger OS X and linux); or should i post to gcc?
>
> ---------------------------
> #include <stdio.h>
>
> int main()
> {
> int i = 2;
> i = (i*=1 ? i-2 : 0);
> printf("val is %d\n", i);
> return 0;}
>
> --------------------------
>
> you would expect to print 0 right, it does!
>
> removed -2, like:
>
> -------------------------
> #include <stdio.h>
>
> int main()
> {
> int i = 2;
> i = (i*=1 ? i : 0);
> printf("val is %d\n", i);
> return 0;}
>
> --------------------------
> and it returns ... 4!, while i have expected 2...


Both examples contain undefined behavior because i is assigned to
multiple times without an intervening sequence point. The problem is
that this may not be readily apparent in your example because of the
precedences of the of the *= and conditional operators. This line:

i = (i*=1 ? i : 0);

is equivalent to this one:

i = (i*= (1 ? i : 0));

which is equivalent to this:

i = i* = (1 ? i : 0);

Since this is undefined behavior anything is allowed although it
should be easy to see why the subexpression (which doesn't contain
UB):

i* = (1 ? i : 0);

would yield 4.

Robert Gamble

 
Reply With Quote
 
sonic
Guest
Posts: n/a
 
      08-28-2007
Many thanks for both of your answers Keith and Rob




> In both programs, you modify 'i' twice between sequence points,
> invoking undefined behavior.

oops


> operator precedence. The '?:' operator binds more tightly than an
> assignment operator. Your statement


Many thanks! i understand it now!
> i = (i *= i);


> If you start by thinking about what you want to do, and then write C
> code to express your intent, you'll never write anything like that in
> the first place.

Actually i was just studying Confuscated C code and tried to exercie
mine a little bit and missed an obvious case with the precedence!

 
Reply With Quote
 
Ark Khasin
Guest
Posts: n/a
 
      08-29-2007
Keith Thompson wrote:
<snip>
> In both programs, you modify 'i' twice between sequence points,
> invoking undefined behavior.
>
> Also, the spacing in your expression is inconsistent with the actual
> operator precedence. The '?:' operator binds more tightly than an
> assignment operator. Your statement
> i = (i*=1 ? i : 0);
> is equivalent to
> i = (i *= (1 ? i : 0));
> The subexpression '(1 ? i : 0)' can be reduced to 'i', giving:
> i = (i *= i);
> which still invokes UB.
>

<snip>

Just wondering:
i = (i<2007)?(i+=0)i*=1);
Is it still UB?
Or must an expression evaluate to one of the finite set of values
determined by the freedom of compiler's choice in the order of evaluation?
-- Ark
 
Reply With Quote
 
Keith Thompson
Guest
Posts: n/a
 
      08-29-2007
Ark Khasin <(E-Mail Removed)> writes:
> Keith Thompson wrote:
> <snip>
>> In both programs, you modify 'i' twice between sequence points,
>> invoking undefined behavior.
>> Also, the spacing in your expression is inconsistent with the actual
>> operator precedence. The '?:' operator binds more tightly than an
>> assignment operator. Your statement
>> i = (i*=1 ? i : 0);
>> is equivalent to
>> i = (i *= (1 ? i : 0));
>> The subexpression '(1 ? i : 0)' can be reduced to 'i', giving:
>> i = (i *= i);
>> which still invokes UB.
>>

> <snip>
>
> Just wondering:
> i = (i<2007)?(i+=0)i*=1);
> Is it still UB?
> Or must an expression evaluate to one of the finite set of values
> determined by the freedom of compiler's choice in the order of
> evaluation?


That case (and the others) is slightly complicated by the fact that
there's a sequence point after the evaluation of the first operand of
a conditional operator. Nevertheless, I'm reasonably sure the
behavior is undefined.

--
Keith Thompson (The_Other_Keith) (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
 
Flash Gordon
Guest
Posts: n/a
 
      08-29-2007
Keith Thompson wrote, On 29/08/07 05:35:
> Ark Khasin <(E-Mail Removed)> writes:
>> Keith Thompson wrote:
>> <snip>
>>> In both programs, you modify 'i' twice between sequence points,
>>> invoking undefined behavior.
>>> Also, the spacing in your expression is inconsistent with the actual
>>> operator precedence. The '?:' operator binds more tightly than an
>>> assignment operator. Your statement
>>> i = (i*=1 ? i : 0);
>>> is equivalent to
>>> i = (i *= (1 ? i : 0));
>>> The subexpression '(1 ? i : 0)' can be reduced to 'i', giving:
>>> i = (i *= i);
>>> which still invokes UB.
>>>

>> <snip>
>>
>> Just wondering:
>> i = (i<2007)?(i+=0)i*=1);
>> Is it still UB?
>> Or must an expression evaluate to one of the finite set of values
>> determined by the freedom of compiler's choice in the order of
>> evaluation?

>
> That case (and the others) is slightly complicated by the fact that
> there's a sequence point after the evaluation of the first operand of
> a conditional operator. Nevertheless, I'm reasonably sure the
> behavior is undefined.


Unless there is a sequence point after the evaluation of the second or
third argument then it is definitely UB. I believe there is no such
sequence point, so like you I am reasonably sure it is UB.
--
Flash Gordon
 
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
*bug* *bug* *bug* David Raleigh Arnold Firefox 12 04-02-2007 03:13 AM
AVG Email Scanner activating at strange times with strange IP addresses dennispublic@hotmail.com Computer Support 1 08-26-2006 04:27 AM
Strange, Illogical ASP.NET Bug: "File or assembly name, or one of its dependencies not found" Philipp Schumann ASP .Net 2 10-25-2003 05:05 PM
Question About Strange 'C' Code Syntax ( Well strange to me anyway ) Harvey Twyman C Programming 8 10-25-2003 05:54 AM
Re: VERY STRANGE BUG? Adding a textbox control causes other textbox control to fail??? S. Justin Gengo ASP .Net 0 07-16-2003 06:51 PM



Advertisments