08 Jan, 2013, Rarva.Riendf wrote in the 1st comment:
Votes: 0
While inquiring some code (C) of mine,I found this line of code (of mine) and following code step by step I was wtf..

gain *= 0,75; // gain is put to zero whatever gain value.. I was wtf, casting it in double etc etc till I realised it was a , instead of .

(I am french so we use , for numbers, that is kind of why it took me a while to spot it as well)

Thing is, I thought that by activating most (if not all)of the warnings the compiler would catch this kind of thing. Did I miss some ?

I do not even understand why it compiles, I have no idea you could use a ',' like that, and I am wondering what it is supposed to do as well.
08 Jan, 2013, KaVir wrote in the 2nd comment:
Votes: 0
The comma separates statements, so "gain *= 0,75;" is performing two statements:

1) "gain *= 0" (gain is multiplied by 0, the result is stored in gain).

2) "75" (resolves to true as it is non-zero).
08 Jan, 2013, Hades_Kane wrote in the 3rd comment:
Votes: 0
So could a comma could be used in place of a line break for things like that?

I mean, I know I can do things like:

int count1 = 0, count2 = 0;


So later in the code, would it be feasible to do something like:

if(somecondition)
{
count1 += 1, count1 += ch->level, count2 += 1, count2 = count1 + count1;
return;
}


Not that I'd likely write code like that, this is mostly just a curiosity.
08 Jan, 2013, plamzi wrote in the 4th comment:
Votes: 0
Guys, most likely this is a period and not a comma. As in, "gain equals gain multiplied by 0.75". Otherwise it makes no sense.

As for comma-separating statements in C, it seems to work in gcc 4.6.1. Maybe it always did.
08 Jan, 2013, Hades_Kane wrote in the 5th comment:
Votes: 0
plamzi said:
Guys, most likely this is a period and not a comma. As in, "gain equals gain multiplied by 0.75". Otherwise it makes no sense.


He said pretty definitively that it is in fact a comma.

I'm sure it was supposed to be a period and it was probably just a typo, and that's what confused him as to why did it compile if it wasn't what it was supposed to be.
08 Jan, 2013, Davion wrote in the 6th comment:
Votes: 0
Hades_Kane said:
So could a comma could be used in place of a line break for things like that?

I mean, I know I can do things like:

int count1 = 0, count2 = 0;


So later in the code, would it be feasible to do something like:

if(somecondition)
{
count1 += 1, count1 += ch->level, count2 += 1, count2 = count1 + count1;
return;
}


Not that I'd likely write code like that, this is mostly just a curiosity.


You can. It truly separates statements.

Edit:
Note, that you already do stuff like this when using multiple iterators in a for loop.

for( ch=char_list, i= 0; ch ; ch = ch->next, ++i )
08 Jan, 2013, Hades_Kane wrote in the 7th comment:
Votes: 0
Cool, good to know! :)
08 Jan, 2013, Rarva.Riendf wrote in the 8th comment:
Votes: 0
So no warning to detect those ? I mean there are warnings that can tell you that a variable is set but not used, but no warning to detect totally stupid useless code like this ?

And thx KaVir, now that you says it, pretty obvious. Like in var declarations. Was so stuck on it I could not think straight. It is very easy when you are french to make a typo like this and not spot it immediately cause it is our natural way of reading numbers..

I spotted 3 occurences in my code, (and some were formatted as "1, 5" <- easier to see those when you read code as there is a space inserted by autoformatting. That and the fact I swap between qwerty and azerty regulary).
08 Jan, 2013, Twisol wrote in the 9th comment:
Votes: 0
plamzi said:
Guys, most likely this is a period and not a comma. As in, "gain equals gain multiplied by 0.75". Otherwise it makes no sense.

In many places around the world, the comma is used as the decimal mark. 0,75 is how you would write it in these locales. C mandates using the period as the decimal mark, but depending on what locale is set, atof uses the comma. :rolleyes:
08 Jan, 2013, Tyche wrote in the 10th comment:
Votes: 0
add(int x, int y) {return x+y;}
int main() {
int i;
printf("%d",add(5, (i =7 , i+4)));
return 0;
}

> 16
09 Jan, 2013, Rarva.Riendf wrote in the 11th comment:
Votes: 0
Tyche: this kind of code makes my head hurts :)

My question still stand though, no warning to detect useless code like this?

void xx() {
int toto = 2;
int titi = 3;
titi *= 2, TRUE;
}
}


Compiler will warn me that toto is set but not used, but will say nothing about the totally useles TRUE in there. I find this baffling. I bet the compiler actually ignores it when it generates the bytecode. To me it looks like obfuscated code.
10 Jan, 2013, Tyche wrote in the 12th comment:
Votes: 0
Consider this code:
#include <stdio.h>

int xx() {
int toto = 2;
int titi = 3;
toto = titi *= 2, 99;
printf("toto %d, titi %d\n",toto,titi);
toto = (titi *= 2, 99);
printf("toto %d, titi %d\n",toto,titi);
return titi, 66;
}

int main() {
printf("return - %d\n",xx());
return 0;
}


Produces…
toto 6, titi 6
toto 99, titi 12
return - 66


You will get a warning in g++,
"testcomma.c:6:16:something like "warning: right-hand operand of comma expression has no effect"

You will get a warning in gcc on the return statement:
"testcomma.c:10:14: warning: left-hand operand of comma expression has no effect"

Other C compilers like Embarcadero compiler do issue a warning:
Warning W8019 testcomma.c 6: Code has no effect in function xx

The gcc version I used did indeed optimize out the right hand side of line 6.

I have no clue what criteria the gcc and g++ teams use to include certain warnings and especially whether they are included as part of -Wall.
Some of those included in -Wall I think are downright annoying,

However there aren't any errors in the code, and there is certainly no requirement to issue any sort of warnings.
10 Jan, 2013, Telgar wrote in the 13th comment:
Votes: 0
This looks like a flaw in GCC's warnings to me. I can't find a single way to get a warning on this. And it is probably a common error in C maths code written by Europeans.

Since the comma operator creates a compound statement, and the statement actually has an effect, produces an rvalue, and assigns it to an lvalue, it doesn't seem to flag any warnings.
10 Jan, 2013, quixadhal wrote in the 14th comment:
Votes: 0
There's no warning, because it's a perfectly valid construct.

gain *= 0,75; means set gain = gain * 0, then return 75 as the result of the expression.

It's not USEFUL here, because that 75 result is (presumably) discarded. The closest thing to a warning I'd expect is the value being thrown away due to void context, but that's no different than declaring a function to return an int and then not using the return value when you call it.

It probably *IS* a typo, but the compiler can't know that.
11 Jan, 2013, Rarva.Riendf wrote in the 15th comment:
Votes: 0
Quote
There's no warning, because it's a perfectly valid construct.


Well declaring and setting a value is also perfectly valid, you can still have a warning about it :)
I compile with -Wall and usually the latest gcc (under Fedora 17 atm) , and have very few warnings (around 20) , most of them being format vulnerability in fscanf. And some warnings from Wall saved my ass a few times, detecting some typos.

I personnaly think this kind of stuff should be included in Wall. Hope my post will help some other european fellows to think about looking into their code to see if they don't have this typos as they can be hard to detect.
11 Jan, 2013, Vigud wrote in the 16th comment:
Votes: 0
Rarva.Riendf said:
Quote
There's no warning, because it's a perfectly valid construct.


Well declaring and setting a value is also perfectly valid, you can still have a warning about it :)
I compile with -Wall and usually the latest gcc (under Fedora 17 atm) , and have very few warnings (around 20) , most of them being format vulnerability in fscanf. And some warnings from Wall saved my ass a few times, detecting some typos.

I personnaly think this kind of stuff should be included in Wall. Hope my post will help some other european fellows to think about looking into their code to see if they don't have this typos as they can be hard to detect.
gcc -Wall -Wextra -pedantic [-ansi] is only the first step to learning possible problems that lie within your code. clang-analyzer is another. You probably could make use of TenDRA.

And there's this my favorite way to find bugs that sit there hidden, because your favorite compiler optimizes wrong code away or makes it irrelevant otherwise. Compile the damn thing with as many compilers on as many platforms as you can. A side effect is portability.
11 Jan, 2013, Telgar wrote in the 17th comment:
Votes: 0
Rarva.Riendf said:
Quote
There's no warning, because it's a perfectly valid construct.


Well declaring and setting a value is also perfectly valid, you can still have a warning about it :)
I compile with -Wall and usually the latest gcc (under Fedora 17 atm) , and have very few warnings (around 20) , most of them being format vulnerability in fscanf. And some warnings from Wall saved my ass a few times, detecting some typos.

I personnaly think this kind of stuff should be included in Wall. Hope my post will help some other european fellows to think about looking into their code to see if they don't have this typos as they can be hard to detect.


I'm not sure it's feasible to create a warning for this… it would require very specialized detection. Further, it might interact badly with a C construct used by a lot of programmers and in a lot of old-school softwares:

#define UPDATE(x,y) ((x).var++, (x)->update(y))

Both statements generate an rvalue; only one is assigned. This is a common way to wrap features, line counters, and all kinds of things without changing syntax in an entire program. I don't really see a good way to warn about the code in complaint and not also warn about things like the above.
11 Jan, 2013, quixadhal wrote in the 18th comment:
Votes: 0
Vigud said:
gcc -Wall -Wextra -pedantic [-ansi] is only the first step…


I use this for WileyMUD's makefile:

W_ERROR         = -Werror
W_ANSI = #-pedantic
W_UBER = -Wall
W_FORMAT = -Wformat -Wformat-security -Wmissing-format-attribute
W_MESSY = -Wmissing-braces -Wparentheses -Wshadow -Wredundant-decls
W_TYPE = -Wcast-qual -Wcast-align -Wchar-subscripts -Wreturn-type -Wswitch -Wwrite-strings
W_EXTRA = -Wunused -Wuninitialized #-Wunreachable-code
W_NITPICK = -Wpointer-arith -Winline
ifeq ($(CC), gcc)
W_CONLY = -Wmissing-declarations -Wmissing-prototypes -Wstrict-prototypes
endif

W_FLAGS = $(W_ERROR) $(W_ANSI) $(W_UBER) $(W_FORMAT) $(W_MESSY) $(W_TYPE) $(W_EXTRA) $(W_NITPICK) $(W_CONLY)


The most important one, and the one that annoys the hell out of people who download my codebase and "can't compile it", is -Werror. That turns ALL warnings in fatal errors, thus requiring you to actually try to fix them, rather than ignoring them like so many people do.
11 Jan, 2013, arendjr wrote in the 19th comment:
Votes: 0
I agree with Rarva, just because it's valid C(++) doesn't mean it's intended. And yes, the compiler can detect many code smells and bad practices, so producing a warning is often desired.

Btw, I personally prefer the Clang compiler over GCC, especially because of its much more useful warnings and error messages.

comma.cpp:
int main(int argc, char *argv[]) {
float gain = 4.0;
gain *= 0,75;
return 0;
}


Output:
$ clang++ comma.cpp
comma.cpp:3:12: warning: expression result unused [-Wunused-value]
gain *= 0,75;
^~
1 warning generated.
17 Jan, 2013, Rarva.Riendf wrote in the 20th comment:
Votes: 0
As a final conclusion to the this thread I read a little about compilers for C since then.
Seems like it is common knowledge that GCC is indeed very weak at generating useful warning messages. G++ would have detected my problem (provided I could comile in G++ heh) and of course Clang (LLVM) does detect it as well.
What is noticeable is that the static Analyzer also detected 1 actual bug finding a variable set but not used (must have felt asleep on this code), and 3 valid potential null pointer exception in my code. (need to look into them to see if they can actually happen in real running condition but still).
And a whole bunch of useless warning as well (around 180 if you wann know), but easy to sort as they were all the same basically.

Quote
It probably *IS* a typo, but the compiler can't know that.

Well actually some compilo actually are smart enough to warn that you 'may' have brain farted :) And it is real dam nice.

From what I read it is now common knowledge that you should use CLang for the warning messages, and GCC for release as GCC will provide better binary. (doubt it matter for a mud though, I never ever used any optimization as it makes the core dump mostly useless in case of a crash)

Thanx you all for the help, I have another efficient tool to proofread my slopping coding.
Random Picks
0.0/24