Pages: 1 2 [3] 4   Go Down
Author Topic: if(a=b) is not if(a==b) could IDE check this b4 upload?  (Read 4627 times)
0 Members and 1 Guest are viewing this topic.
Earth
Offline Offline
Newbie
*
Karma: 0
Posts: 5
This sentence would have been wittier had it been mathphreak's idea.
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Novel idea I'm surprised nobody else has suggested:
Add lint (or any similar tool) integration to Tools menu.  Seems to me that "the oldest gotcha in the C book" would certainly be flagged down by something like lint, along with several similar problems.
Logged

Anybody with a signature is a liar.

Global Moderator
Netherlands
Offline Offline
Shannon Member
*****
Karma: 168
Posts: 12430
In theory there is no difference between theory and practice, however in practice there are many...
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Lint is a good idea, that was long ago that I used it...  not necessary in the IDE but as commandlinetool also OK
Logged

Rob Tillaart

Nederlandse sectie - http://arduino.cc/forum/index.php/board,77.0.html -
(Please do not PM for private consultancy)

Earth
Offline Offline
Newbie
*
Karma: 0
Posts: 5
This sentence would have been wittier had it been mathphreak's idea.
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Lint is a good idea, that was long ago that I used it...  not necessary in the IDE but as commandlinetool also OK

I think keeping things in the IDE would be a lot simpler (well, maybe not from a development perspective).  First of all, it's not like you can just lint the sketch itself, as I would be duly impressed if lint didn't complain about the lack of a main() function.  Second of all, it would be painful to track down the path to lint.
Logged

Anybody with a signature is a liar.

Offline Offline
Newbie
*
Karma: 0
Posts: 41
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Quote
do it this way if ( 54 == x)
Good point, yet for some reason I never seem to do it. I must get back into the habit.

______
Rob


Except that
 (a) as a good programmer you wouldn't be using magic numbers in expressions, and
 (b) if you are comparing variables it can't help anyway.
Logged

nr Bundaberg, Australia
Offline Offline
Tesla Member
***
Karma: 121
Posts: 8437
Scattered showers my arse -- Noah, 2348BC.
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

True, but it could be

Code:
if (CHAR_SPACE == cmd_buffer[i])

______
Rob
Logged

Rob Gray aka the GRAYnomad www.robgray.com

Offline Offline
Newbie
*
Karma: 0
Posts: 41
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

True, but it could be

Code:
if (CHAR_SPACE == cmd_buffer[i])

______
Rob


How would
Code:
if (CHAR_SPACE = cmd_buffer[i])
be caught?
Logged

SF Bay Area (USA)
Offline Offline
Tesla Member
***
Karma: 106
Posts: 6371
Strongly opinionated, but not official!
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Quote
How would if (CHAR_SPACE = cmd_buffer) be caught?
If CHAR_SPACE is a typical C macro that expands to "32", the compiler will see "32 = cmd_buffer", which isn't legal...
Logged

nr Bundaberg, Australia
Offline Offline
Tesla Member
***
Karma: 121
Posts: 8437
Scattered showers my arse -- Noah, 2348BC.
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

If CHAR_SPACE is a #define then you get

lvalue required as left operand of assignment

if it's a constant you get

assignment of read-only variable 'CHAR_SPACE'

In my programming anything in uppercase is a const or define, but that may not have been obvious from the example if you don't follow the same convention.

______
Rob
Logged

Rob Gray aka the GRAYnomad www.robgray.com

Offline Offline
Newbie
*
Karma: 0
Posts: 41
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Understood - a case of the dog that didn't bark :-)
I didn't realise that CHAR_SPACE was a #define, or I would have twigged.
Logged

Dallas, TX USA
Offline Offline
Edison Member
*
Karma: 47
Posts: 2329
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Guys,
I see this request come up a lot
and lots of bashing back and forth between the novices wanting
the tools to catch their mistakes and the purists saying
just learn how to better use the tools.

Because "arduino" is not a language, and the IDE simply passes
the sketch to gcc for C++ parsing, it is the compiler that must check
for this condition.

Good news is that there is already a compiler option to do this.
(Has been for like 20+ years in gcc.....)

Currently, it is -Wparentheses

If you simply use this option to the compiler, then if you do something like:

Code:
if( a = 50)
vs
Code:
if (a == 50)

or even with dual variables like
Code:
if( a = b)

You will get a warning like:

bs.cpp:25: warning: suggest parentheses around assignment used as truth value

If you really need to do the assignment inside the if, you can avoid the warning by
simply using:

Code:
if( (a = 50) )
instead.
To me this actually emphasizes the assignment,
which seems like a good thing for clarity.


===

Now if the Arduino guys would just let you set the compiler flags.......
(but thats another issue)

Now for the really bad news. Nobody and and I mean nobody has seen a warning
from the compiler using the IDE. The IDE explicitly disables ALL warnings from the compiler!!
(again you'll have to ask the arduino team why they decided to do this)

For now, you can go in and hack the IDE java code and rebuild
the IDE yourself: (the beauty of open source)
It is in app/src/processing/app/debug/Compiler.java around line #443

You will need to remove the -w option which suppresses all warnings and
replace it with -Wparentheses and rebuild the IDE.

It does work. I've tested it.

But be prepared to get many warnings because none of the code has been built
with warnings enabled for quite some time now,
So you will see that lots of the code out there (including some of the core arduino code) has slight
issues that generate warnings.

But you will  actually get a warning for the dreaded "accidental" assignment
inside an if statement.


--- bill
Logged

Offline Offline
Newbie
*
Karma: 0
Posts: 41
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Probably just a lot easier to put a posit-it note on your screen, reminding you to watch for
if (x=y)

if your code  !

Logged

Turku
Offline Offline
Full Member
***
Karma: 0
Posts: 201
Arduino rocks
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Well, C was written to help write an operating system (UNIX), where you are hitting the hardware and want to be able to do pretty much anything.

And now I'll duck. :-)
Heh. Where do you hide, I'll need to hide after this. My turn. One thing which irritates me in C is: I started with assembly programming a long time ago. There you had to know exactly what was a address and what was data in that address. And how to mix and handle both. Exactly. In C a variable is sometimes data and sometime address. I hate that a lot. Please note I like (valid)pointers.

It feels like C was designed by an idiot(s) who didn't understand indirect addressing.
Logged

Left Coast, CA (USA)
Online Online
Brattain Member
*****
Karma: 331
Posts: 16513
Measurement changes behavior
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Well, C was written to help write an operating system (UNIX), where you are hitting the hardware and want to be able to do pretty much anything.

And now I'll duck. :-)
Heh. Where do you hide, I'll need to hide after this. My turn. One thing which irritates me in C is: I started with assembly programming a long time ago. There you had to know exactly what was a address and what was data in that address. And how to mix and handle both. Exactly. In C a variable is sometimes data and sometime address. I hate that a lot. Please note I like (valid)pointers.

It feels like C was designed by an idiot(s) who didn't understand indirect addressing.

Still, I don't think any company today could afford the time and costs to write a complete modern graphical OS in assembly language. C/C++ can be used to write such an OS. How many other higher level languagues (higher then asm) can make that claim?

Lefty
Logged

Dallas, TX USA
Offline Offline
Edison Member
*
Karma: 47
Posts: 2329
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Well, C was written to help write an operating system (UNIX), where you are hitting the hardware and want to be able to do pretty much anything.

And now I'll duck. :-)
Heh. Where do you hide, I'll need to hide after this. My turn. One thing which irritates me in C is: I started with assembly programming a long time ago. There you had to know exactly what was a address and what was data in that address. And how to mix and handle both. Exactly. In C a variable is sometimes data and sometime address. I hate that a lot. Please note I like (valid)pointers.

It feels like C was designed by an idiot(s) who didn't understand indirect addressing.

Can you give a specific C (not C++) example of how the same variable referenced the same way
is sometimes data and sometimes a pointer?
I'm kind of struggling with that comment.

How is the difference between "data" and "pointer" in a variable in C any different than the
contents of a register or memory location in assembler?

In assembler you have the same problem. If you look at the contents of a register that was passed
to a routine, how do you know if it is the data or an address that points to data?
You don't. It is only because you know (because it was defined somewhere)
what the register is supposed to contain that you know how to use it.
Same is true for a memory location. The memory location can be the actual data or a pointer
to the real data.

C is exactly the same way.
The only difference is that C allows you to easily declare how the "register" is used
and create as many "registers" as you like.
In C the way the "register"/variable/memory-location is declared determines how it is used and how the data
is referenced and the compiler will ensure that the code treats the variable consistently according
to its definition.

vs in Assembler there is no such declaration nor any sanity checking
and the actual code must be hard-coded to be consistent.
In a complex system that becomes very difficult especially on projects that involve many
team members.

And I think the designers of C very much understood indirect addressing and used
it accordingly.

Now I'll agree that to many novice C coders there may be some perhaps strange/non-obvious
things that happen when calling functions. Things like the address of the first
element of an array being passed vs the entire array.
But those are well defined and are very logical.

--- bill

Logged

SF Bay Area (USA)
Offline Offline
Tesla Member
***
Karma: 106
Posts: 6371
Strongly opinionated, but not official!
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Quote
Can you give a specific C (not C++) example of how the same variable referenced the same way
is sometimes data and sometimes a pointer?
There's the example from another recent thread.  An array as a parameter is a pointer, but as a local or global variable is a sized array (and sizeof(x) is different.)
Code:
#include <stdio.h>

void func(int x[10])
{
    int y[10];

    printf("sizeof x=%d, sizeof y=%d\n", sizeof(x), sizeof(y));
}

int main()
{
    int z[10];
    func(z);
}
It's also somewhat annoying that structs are passed by value by default, but arrays are passed by reference by default.  You get used to it...

Quote
In assembler you have the same problem.
I agree completely with that.  And sometimes you do extensive math on an address before you use it as a pointer.  Just recently I was writing:
Code:
     a = (a + ps) & ~(ps-1);
Logged

Pages: 1 2 [3] 4   Go Up
Jump to: