EmbeddedRelated.com
Forums

IAR project port to Crossworks issue

Started by finefrenzyrolling November 14, 2009
I am attempting to convert a working IAR embedded workbench project to crossworks CrossStudio and am having some difficulty with the difference between compilers. I believe I have worked out the interrupt issues and the program does run but it does not behave as expected, in fact it does not do anything I can see. The crossworks compiler did give several of the following warnings:

"result of '==' is always zero"
referring to this line:

while ((I2CDCTL & I2CBUSY) == TRUE)// Wait for I2C module to go idle

As best I can see, it would only give this warning if I2CDCTL is static since I2CBUSY, and of course TRUE are both constants. I am wondering if the compiler skips this comparison since it believes the statement to always be zero and, hence, breaks my I2C code. I am using the msp430x16x.h file from crossworks but noticed I2CDCTL is defined somewhat differently in the IAR version of the same file.
Here is the definition in the crossworks header file:
#define I2CDCTL_ (0x0072) /* I2C Data Control */
sfrb I2CDCTL = I2CDCTL_;

and here is the definition in the IAR header:
....
#define DEFC(name, address) __no_init volatile unsigned char name @ address;
....
DEFC( U0RCTL , U0RCTL_)
...
#define U0RCTL_ (0x0072) /* USART 0 Receive Control */
...
#define I2CDCTL U0RCTL /* I2C Data Control */

as I understand it sfrb is a shorthand for "volatile unsigned char" so the difference between these definitions eludes me. Attempts to use the DEFC macro in the CrossStudio .h file made the compiler very unhappy.

Also, the warning,"reference to 'volatile unsigned char' removed" was given for this line:
P3OUT &= !(0xFE);
which is similarly defined as
#define P3OUT_ (0x0019) /* Port 3 Output */
sfrb P3OUT = P3OUT_;

I think I am not understanding something about 'volatile unsigned char' in crossworks. Anyone know how I am going wrong here?

Beginning Microcontrollers with the MSP430

Hi,

> "result of '==' is always zero"
> referring to this line:
>
> while ((I2CDCTL & I2CBUSY) == TRUE)// Wait for I2C module to go idle
>
> As best I can see, it would only give this warning if I2CDCTL is static
> since I2CBUSY, and of course TRUE are both constants.

Assume I2CBUSY is 0x20 (which it is for 14x/16x) and TRUE is 1. Then
I2CDCTL & I2CBUSY is either 0x20 or 0 which is never equal to 1. The
compiler may have rewritten the expression in some way, rotating the test to
the bottom (not uncommon); however, it's telling you that there is something
wrong with your expression.

> I am wondering if
> the compiler skips this comparison since it believes the statement to
> always be zero and, hence, breaks my I2C code.

I believe that you need to look at the definition of TRUE (what value is
it?) and I2CBUSY (I believe it is 0x20). If this is the case, then your
code doesn't do what you think it's doing and the compiler is 100% right to
warn you about it.

> as I understand it sfrb is a shorthand for "volatile unsigned char" so the
> difference between these definitions eludes me. Attempts to use the DEFC
> macro in the CrossStudio .h file made the compiler very unhappy.

Of course.

> Also, the warning,"reference to 'volatile unsigned char' removed" was
given
> for this line:
> P3OUT &= !(0xFE);
> which is similarly defined as
> #define P3OUT_ (0x0019) /* Port 3 Output */
> sfrb P3OUT = P3OUT_;
>
> I think I am not understanding something about 'volatile unsigned char' in
> crossworks. Anyone know how I am going wrong here?

Consider what you are writing.

P3OUT &= !(0xFE)

This is:

P3OUT = P3OUT & !(0xFE)

As !0xFE is zero, I get:

P3OUT = P3OUT & 0

Anything bitwise-anded with zero is zero. Hence the compiler is warning you
that it is eliminating the read of P3OUT because it's not necessary and
generates:

P3OUT = 0

You know, I think you should (and here we go in capitals for emphasis)
REALLY LOOK AT YOUR CODE BECAUSE I THINK CROSSWORKS IS TELLING YOU SOMETHING
USEFUL HERE.

--
Paul Curtis, Rowley Associates Ltd http://www.rowley.co.uk
CrossWorks V2 is out for LPC1700, LPC3100, LPC3200, SAM9, and more!

Oh, one more thing. Dont think you have working code when compilers issue
warnings you can't understand. In real honest-go-goodness shipping
applications with "tested, working code", CrossWorks has unearthed problems
in such code and warned during compilation. The most recent example is
TI-provided code for their RFID part which CrossWorks shows is logically
flawed, but is "tested code". I can prove it's not tested well by an
inspection of the code related to the warning the compiler issues.

Rgds,

--
Paul Curtis, Rowley Associates Ltd http://www.rowley.co.uk
CrossWorks V2 is out for LPC1700, LPC3100, LPC3200, SAM9, and more!

> -----Original Message-----
> From: m... [mailto:m...] On Behalf Of
> Paul Curtis
> Sent: 14 November 2009 09:43
> To: m...
> Subject: RE: [msp430] IAR project port to Crossworks issue
>
> Hi,
>
> > "result of '==' is always zero"
> > referring to this line:
> >
> > while ((I2CDCTL & I2CBUSY) == TRUE)// Wait for I2C module to go idle
> >
> > As best I can see, it would only give this warning if I2CDCTL is static
> > since I2CBUSY, and of course TRUE are both constants.
>
> Assume I2CBUSY is 0x20 (which it is for 14x/16x) and TRUE is 1. Then
> I2CDCTL & I2CBUSY is either 0x20 or 0 which is never equal to 1. The
> compiler may have rewritten the expression in some way, rotating the test
> to
> the bottom (not uncommon); however, it's telling you that there is
> something
> wrong with your expression.
>
> > I am wondering if
> > the compiler skips this comparison since it believes the statement to
> > always be zero and, hence, breaks my I2C code.
>
> I believe that you need to look at the definition of TRUE (what value is
> it?) and I2CBUSY (I believe it is 0x20). If this is the case, then your
> code doesn't do what you think it's doing and the compiler is 100% right
to
> warn you about it.
>
> > as I understand it sfrb is a shorthand for "volatile unsigned char" so
> the
> > difference between these definitions eludes me. Attempts to use the
DEFC
> > macro in the CrossStudio .h file made the compiler very unhappy.
>
> Of course.
>
> > Also, the warning,"reference to 'volatile unsigned char' removed" was
> given
> > for this line:
> > P3OUT &= !(0xFE);
> > which is similarly defined as
> > #define P3OUT_ (0x0019) /* Port 3 Output */
> > sfrb P3OUT = P3OUT_;
> >
> > I think I am not understanding something about 'volatile unsigned char'
> in
> > crossworks. Anyone know how I am going wrong here?
>
> Consider what you are writing.
>
> P3OUT &= !(0xFE)
>
> This is:
>
> P3OUT = P3OUT & !(0xFE)
>
> As !0xFE is zero, I get:
>
> P3OUT = P3OUT & 0
>
> Anything bitwise-anded with zero is zero. Hence the compiler is warning
> you
> that it is eliminating the read of P3OUT because it's not necessary and
> generates:
>
> P3OUT = 0
>
> You know, I think you should (and here we go in capitals for emphasis)
> REALLY LOOK AT YOUR CODE BECAUSE I THINK CROSSWORKS IS TELLING YOU
> SOMETHING
> USEFUL HERE.
>
> --
> Paul Curtis, Rowley Associates Ltd http://www.rowley.co.uk
> CrossWorks V2 is out for LPC1700, LPC3100, LPC3200, SAM9, and more!

Your problem is not with the compiler but with your understanding of C. Not uncommon as I have these problems on occasion as well. I feel pretty stupid when I figure them out.

--- In m..., "finefrenzyrolling" wrote:
>
> I am attempting to convert a working IAR embedded workbench project to crossworks CrossStudio and am having some difficulty with the difference between compilers. I believe I have worked out the interrupt issues and the program does run but it does not behave as expected, in fact it does not do anything I can see. The crossworks compiler did give several of the following warnings:
>
> "result of '==' is always zero"
> referring to this line:
>
> while ((I2CDCTL & I2CBUSY) == TRUE)// Wait for I2C module to go idle
>

"TRUE" is defined somewhere to have a definite value, probably 1. (#define TRUE 1, either in your code or an include file) Since the result of your bitwise and can never ever be 1, the compiler has very nicely warned you. Rewrite your test as:

((I2CDCTL & I2CBUSY) != 0)

and all will be well.

> Also, the warning,"reference to 'volatile unsigned char' removed" was given for this line:
> P3OUT &= !(0xFE);

Again a misunderstanding. This time confusion between the '!' and '~' operators. '!' is a logical inversion suitable for comparisons. It turns a zero (or false) value into '1' and any non-zero value into zero. '~' is one's complement which is what you want here. Assuming you want to set all but the least significant bit of P3OUT to zero.

paul, I could nott agree more strongly.. I had some "working" code that was in use for a consideerable time that when ported too crossworks, th4 compiler gave lots of warniings.. eventually I realized the compiler was correct and fixed my code.
On Sat Nov 14th, 2009 4:48 AM EST Paul Curtis wrote:

>Oh, one more thing. Don’t think you have working code when compilers issue
>warnings you can't understand. In real honest-go-goodness shipping
>applications with "tested, working code", CrossWorks has unearthed problems
>in such code and warned during compilation. The most recent example is
>TI-provided code for their RFID part which CrossWorks shows is logically
>flawed, but is "tested code". I can prove it's not tested well by an
>inspection of the code related to the warning the compiler issues.
>
>Rgds,
>
>--
>Paul Curtis, Rowley Associates Ltd   http://www.rowley.co.uk
>CrossWorks V2 is out for LPC1700, LPC3100, LPC3200, SAM9, and more!
>> -----Original Message-----
>> From: m... [mailto:m...] On Behalf Of
>> Paul Curtis
>> Sent: 14 November 2009 09:43
>> To: m...
>> Subject: RE: [msp430] IAR project port to Crossworks issue
>>
>> Hi,
>>
>> > "result of '==' is always zero"
>> > referring to this line:
>> >
>> > while ((I2CDCTL & I2CBUSY) == TRUE)// Wait for I2C module to go idle
>> >
>> > As best I can see, it would only give this warning if I2CDCTL is static
>> > since I2CBUSY, and of course TRUE are both constants.
>>
>> Assume I2CBUSY is 0x20 (which it is for 14x/16x) and TRUE is 1. Then
>> I2CDCTL & I2CBUSY is either 0x20 or 0 which is never equal to 1. The
>> compiler may have rewritten the expression in some way, rotating the test
>> to
>> the bottom (not uncommon); however, it's telling you that there is
>> something
>> wrong with your expression.
>>
>> > I am wondering if
>> > the compiler skips this comparison since it believes the statement to
>> > always be zero and, hence, breaks my I2C code.
>>
>> I believe that you need to look at the definition of TRUE (what value is
>> it?) and I2CBUSY (I believe it is 0x20). If this is the case, then your
>> code doesn't do what you think it's doing and the compiler is 100% right
>to
>> warn you about it.
>>
>> > as I understand it sfrb is a shorthand for "volatile unsigned char" so
>> the
>> > difference between these definitions eludes me. Attempts to use the
>DEFC
>> > macro in the CrossStudio .h file made the compiler very unhappy.
>>
>> Of course.
>>
>> > Also, the warning,"reference to 'volatile unsigned char' removed" was
>> given
>> > for this line:
>> > P3OUT &= !(0xFE);
>> > which is similarly defined as
>> > #define P3OUT_ (0x0019) /* Port 3 Output */
>> > sfrb P3OUT = P3OUT_;
>> >
>> > I think I am not understanding something about 'volatile unsigned char'
>> in
>> > crossworks. Anyone know how I am going wrong here?
>>
>> Consider what you are writing.
>>
>> P3OUT &= !(0xFE)
>>
>> This is:
>>
>> P3OUT = P3OUT & !(0xFE)
>>
>> As !0xFE is zero, I get:
>>
>> P3OUT = P3OUT & 0
>>
>> Anything bitwise-anded with zero is zero. Hence the compiler is warning
>> you
>> that it is eliminating the read of P3OUT because it's not necessary and
>> generates:
>>
>> P3OUT = 0
>>
>> You know, I think you should (and here we go in capitals for emphasis)
>> REALLY LOOK AT YOUR CODE BECAUSE I THINK CROSSWORKS IS TELLING YOU
>> SOMETHING
>> USEFUL HERE.
>>
>> --
>> Paul Curtis, Rowley Associates Ltd   http://www.rowley.co.uk
>> CrossWorks V2 is out for LPC1700, LPC3100, LPC3200, SAM9, and more!
>

Yes. I compiled/linked some "sample code". The compiler/linker generated no error, no warning. But the chip did not do what I want to do at all.

--- In m..., Joe Radomski wrote:
>
> paul, I could nott agree more strongly.. I had some "working" code that was in use for a consideerable time that when ported too crossworks, th4 compiler gave lots of warniings.. eventually I realized the compiler was correct and fixed my code.
>
>
> On Sat Nov 14th, 2009 4:48 AM EST Paul Curtis wrote:
>
> >Oh, one more thing. Don’t think you have working code when compilers issue
> >warnings you can't understand. In real honest-go-goodness shipping
> >applications with "tested, working code", CrossWorks has unearthed problems
> >in such code and warned during compilation. The most recent example is
> >TI-provided code for their RFID part which CrossWorks shows is logically
> >flawed, but is "tested code". I can prove it's not tested well by an
> >inspection of the code related to the warning the compiler issues.
> >
> >Rgds,
> >
> >--
> >Paul Curtis, Rowley Associates Ltd   http://www.rowley.co.uk
> >CrossWorks V2 is out for LPC1700, LPC3100, LPC3200, SAM9, and more!
> >
> >
> >
> >
> >> -----Original Message-----
> >> From: m... [mailto:m...] On Behalf Of
> >> Paul Curtis
> >> Sent: 14 November 2009 09:43
> >> To: m...
> >> Subject: RE: [msp430] IAR project port to Crossworks issue
> >>
> >> Hi,
> >>
> >> > "result of '==' is always zero"
> >> > referring to this line:
> >> >
> >> > while ((I2CDCTL & I2CBUSY) == TRUE)// Wait for I2C module to go idle
> >> >
> >> > As best I can see, it would only give this warning if I2CDCTL is static
> >> > since I2CBUSY, and of course TRUE are both constants.
> >>
> >> Assume I2CBUSY is 0x20 (which it is for 14x/16x) and TRUE is 1. Then
> >> I2CDCTL & I2CBUSY is either 0x20 or 0 which is never equal to 1. The
> >> compiler may have rewritten the expression in some way, rotating the test
> >> to
> >> the bottom (not uncommon); however, it's telling you that there is
> >> something
> >> wrong with your expression.
> >>
> >> > I am wondering if
> >> > the compiler skips this comparison since it believes the statement to
> >> > always be zero and, hence, breaks my I2C code.
> >>
> >> I believe that you need to look at the definition of TRUE (what value is
> >> it?) and I2CBUSY (I believe it is 0x20). If this is the case, then your
> >> code doesn't do what you think it's doing and the compiler is 100% right
> >to
> >> warn you about it.
> >>
> >> > as I understand it sfrb is a shorthand for "volatile unsigned char" so
> >> the
> >> > difference between these definitions eludes me. Attempts to use the
> >DEFC
> >> > macro in the CrossStudio .h file made the compiler very unhappy.
> >>
> >> Of course.
> >>
> >> > Also, the warning,"reference to 'volatile unsigned char' removed" was
> >> given
> >> > for this line:
> >> > P3OUT &= !(0xFE);
> >> > which is similarly defined as
> >> > #define P3OUT_ (0x0019) /* Port 3 Output */
> >> > sfrb P3OUT = P3OUT_;
> >> >
> >> > I think I am not understanding something about 'volatile unsigned char'
> >> in
> >> > crossworks. Anyone know how I am going wrong here?
> >>
> >> Consider what you are writing.
> >>
> >> P3OUT &= !(0xFE)
> >>
> >> This is:
> >>
> >> P3OUT = P3OUT & !(0xFE)
> >>
> >> As !0xFE is zero, I get:
> >>
> >> P3OUT = P3OUT & 0
> >>
> >> Anything bitwise-anded with zero is zero. Hence the compiler is warning
> >> you
> >> that it is eliminating the read of P3OUT because it's not necessary and
> >> generates:
> >>
> >> P3OUT = 0
> >>
> >> You know, I think you should (and here we go in capitals for emphasis)
> >> REALLY LOOK AT YOUR CODE BECAUSE I THINK CROSSWORKS IS TELLING YOU
> >> SOMETHING
> >> USEFUL HERE.
> >>
> >> --
> >> Paul Curtis, Rowley Associates Ltd   http://www.rowley.co.uk
> >> CrossWorks V2 is out for LPC1700, LPC3100, LPC3200, SAM9, and more!
>

----- Original Message -----
From: "Joe Radomski"
To:
Sent: Saturday, November 14, 2009 2:49 PM
Subject: RE: [msp430] IAR project port to Crossworks issue
paul, I could nott agree more strongly.. I had some "working" code that was
in use for a consideerable time that when ported too crossworks, th4
compiler gave lots of warniings.. eventually I realized the compiler was
correct and fixed my code.
It can be useful (and instructive) to use the -Wall switch. I just used it
on a largish CrossWorks ARM application that was running OK and lots of
warnings were generated. I'd assumed that it was enabled by default.

Leon

leon Heller wrote:
> ----- Original Message -----
> From: "Joe Radomski"
> To:
> Sent: Saturday, November 14, 2009 2:49 PM
> Subject: RE: [msp430] IAR project port to Crossworks issue
> paul, I could nott agree more strongly.. I had some "working" code that was
> in use for a consideerable time that when ported too crossworks, th4
> compiler gave lots of warniings.. eventually I realized the compiler was
> correct and fixed my code.
> It can be useful (and instructive) to use the -Wall switch. I just used it
> on a largish CrossWorks ARM application that was running OK and lots of
> warnings were generated. I'd assumed that it was enabled by default.
>
>
I would add, absolutely. I come from a box background. Our product
builds to some 4 megs now. I started with VC6 and every time I move to
the next VC product, I get new warnings. Not a lot and not necessarily
dangerous, but I fix them. With all warnings on I want to see a complete
rebuild, 0:warnings. Rare exceptions are guarded with pragmas.
Microsoft has a pretty good complier now and pretty damn strict. But I
still don't think I would ever trust it with optimization. Fortunately,
optimization isn't needed these days.

As for the:

while ((I2CDCTL & I2CBUSY) == TRUE)// Wait for I2C module to go idle

That evolved to
((I2CDCTL & I2CBUSY) != 0)

What is wrong with a simple?
for( ; I2CDCTL & I2CBUSY; )
;
Procedural wordiness belongs in the comments, not the code. (IMHO)

(To the first op...)
Except that there is no way out if the bus fails. If there is much of
this going on a, 'it does not do anything I can see', should be
expected. And that such a symptom is possible may mean you need to hire
someone that gets this stuff if a 'for sale' product...
off...

Another grip :). Why is there so much code out there that looks like it
was written on a cell phone? I can see fifty lines at a time on my
monitor. Stuff like:
if( a){ b|= c; d>>= 1; }
Is just so hard to look at.

And those short cryptic names! (damn cell phone keypads). I just
finished a routine and worked from a maxim flow chart. I used 'their'
names like, lastDiscrepancy and discrepancyMarker. it may look wordy but
this is different. I know what lastSector means. If I've slept, 'ls' or
'z' could represent anything. With touch typing and intellesense, not a
big deal.

Best, Dan.

> -----Original Message-----
> From: m... [mailto:m...] On Behalf
> Of Dan Bloomquist
> Sent: Sunday, 15 November 2009 2:07 AM
> To: m...
> Subject: Re: [msp430] IAR project port to Crossworks issue
>

[Wade, Tim (FN) @ Nautronix]


> As for the:
>
> while ((I2CDCTL & I2CBUSY) == TRUE)// Wait for I2C module to go
> idle
>
> That evolved to
> ((I2CDCTL & I2CBUSY) != 0)
>
> What is wrong with a simple?
> for( ; I2CDCTL & I2CBUSY; )
> ;
> Procedural wordiness belongs in the comments, not the code. (IMHO)

[Wade, Tim (FN) @ Nautronix]
We mostly have C++ programmers and they use the Boolean keyword and it (sometimes) protects them from this "== true" stuff -- they usually go tits up in C where true is basically anything that isn't 0 but not necessarily what you expect it to be. We used to mandate "!= FALSE" instead of "== TRUE" but Dan is probably correct in it being necessary at all...
Hello Paul,
I've a question about your recent reply:
> (...)
> Consider what you are writing.
>
> P3OUT &= !(0xFE)
>
> This is:
>
> P3OUT = P3OUT & !(0xFE)
>
> As !0xFE is zero, I get:
>
> P3OUT = P3OUT & 0
>
> Anything bitwise-anded with zero is zero. Hence the compiler is
> warning you that it is eliminating the read of P3OUT because it's
> not necessary and generates:
>
> P3OUT = 0

I'm not sure why the compiler is eliminationg the read of P3OUT. Given P3OUT is a volatile, the compiler shouldn't elliminate the read. Being it volatile, the compiler cannot assume anything about P3OUT, so the compiler cannot assume that eliminating the read operation will have no effect (for example if it were U0RXBUF).
Is this because the compiler knows the real behaviour of P3OUT as different from a 'general volatile'? Or does volatile only apply to an access of the variable (address), no matter if that access is a read or write operation? Even so, a read followed by a write are 2 accesses which is different than just one.

Regards,
Michael K.

--- In m..., "Paul Curtis" wrote:
>
> Hi,
>
> > "result of '==' is always zero"
> > referring to this line:
> >
> > while ((I2CDCTL & I2CBUSY) == TRUE)// Wait for I2C module to go idle
> >
> > As best I can see, it would only give this warning if I2CDCTL is static
> > since I2CBUSY, and of course TRUE are both constants.
>
> Assume I2CBUSY is 0x20 (which it is for 14x/16x) and TRUE is 1. Then
> I2CDCTL & I2CBUSY is either 0x20 or 0 which is never equal to 1. The
> compiler may have rewritten the expression in some way, rotating the test to
> the bottom (not uncommon); however, it's telling you that there is something
> wrong with your expression.
>
> > I am wondering if
> > the compiler skips this comparison since it believes the statement to
> > always be zero and, hence, breaks my I2C code.
>
> I believe that you need to look at the definition of TRUE (what value is
> it?) and I2CBUSY (I believe it is 0x20). If this is the case, then your
> code doesn't do what you think it's doing and the compiler is 100% right to
> warn you about it.
>
> > as I understand it sfrb is a shorthand for "volatile unsigned char" so the
> > difference between these definitions eludes me. Attempts to use the DEFC
> > macro in the CrossStudio .h file made the compiler very unhappy.
>
> Of course.
>
> > Also, the warning,"reference to 'volatile unsigned char' removed" was
> given
> > for this line:
> > P3OUT &= !(0xFE);
> > which is similarly defined as
> > #define P3OUT_ (0x0019) /* Port 3 Output */
> > sfrb P3OUT = P3OUT_;
> >
> > I think I am not understanding something about 'volatile unsigned char' in
> > crossworks. Anyone know how I am going wrong here?
>
> Consider what you are writing.
>
> P3OUT &= !(0xFE)
>
> This is:
>
> P3OUT = P3OUT & !(0xFE)
>
> As !0xFE is zero, I get:
>
> P3OUT = P3OUT & 0
>
> Anything bitwise-anded with zero is zero. Hence the compiler is warning you
> that it is eliminating the read of P3OUT because it's not necessary and
> generates:
>
> P3OUT = 0
>
> You know, I think you should (and here we go in capitals for emphasis)
> REALLY LOOK AT YOUR CODE BECAUSE I THINK CROSSWORKS IS TELLING YOU SOMETHING
> USEFUL HERE.
>
> --
> Paul Curtis, Rowley Associates Ltd http://www.rowley.co.uk
> CrossWorks V2 is out for LPC1700, LPC3100, LPC3200, SAM9, and more!
>