CCS C Software and Maintenance Offers
FAQFAQ   FAQForum Help   FAQOfficial CCS Support   SearchSearch  RegisterRegister 

ProfileProfile   Log in to check your private messagesLog in to check your private messages   Log inLog in 

CCS does not monitor this forum on a regular basis.

Please do not post bug reports on this forum. Send them to support@ccsinfo.com

Issues with structures on 24F and v4.118

 
Post new topic   Reply to topic    CCS Forum Index -> General CCS C Discussion
View previous topic :: View next topic  
Author Message
GregReadUK



Joined: 24 Jan 2011
Posts: 6
Location: Kent, UK

View user's profile Send private message Visit poster's website

Issues with structures on 24F and v4.118
PostPosted: Mon Jan 24, 2011 6:31 am     Reply with quote

Hi Folks,

I am encountering an issue with structures on a PIC24F and v4.118 of compiler (Pretty sure I saw this with a few earlier compiler versions too).

Simple code is below, I initialise structure then call a function which modifies a couple of the members.

Why is structure.a32var getting set to 0 when I subtract 1 from structure.b32var?

Interestingly if reverse the order of the structure member variables to
Code:

typedef struct
{
   unsigned int32 a32var;
   unsigned int32 b32var;
} MYSTRUCT;

the code seems to work, but I suspect if I have more structure variables after b32var they would be getting written over instead.

Any advice welcomed.
Thanks,

Greg

Expected results:

DEVICE:PIC24FJ64GA004
COMPILER VERSION:4.118
MyStruct:500 999
MyStruct:123 998

Actual results:

DEVICE:PIC24FJ64GA004
COMPILER VERSION:4.118
MyStruct:500 999
MyStruct:0 998

Simplfied Code (24F on v4.118 compiler):
Code:

#include <24FJ64GA004.h>
#device *=16

#fuses NOWDT

#fuses ICSP1
#fuses NOWRT
#fuses NOPROTECT
#fuses NOJTAG

#fuses NOCKSFSM // NO FAIL SAFE CLOCK MONITOR
#fuses OSCIO   // OSC 2 IS A GENERAL PURPOSE INPUT
#fuses NOIESO   // THIS CAUSES IT TO BOOT OFF THE INTERNAL CRYSTAL IF EXTERNAL FAILED
//#fuses IESO

#fuses HS       // USE EXTERNAL HIGH SPEED OSCILLATOR
#fuses PR       // RUN OSCILLATOR AT HS OSCILLATOR SPEED
//   #use delay(clock=22118400)
#use delay(clock=25M)

// I2C definition for clock
//#USE I2C(MASTER, I2C1, FORCE_HW, RESTART_WDT)
#USE I2C(MASTER, SCL=PIN_B6, SDA=PIN_B5, RESTART_WDT)

#use rs232(baud=115200,parity=N,bits=8,errors,XMIT=PIN_B8,RCV=PIN_B13)
void Debug_putc(BYTE Data)
{
   putc(Data);
}

typedef struct
{
   unsigned int32 b32var;
   unsigned int32 a32var;
} MYSTRUCT;


void a(MYSTRUCT *pStruct)
{
   pStruct->a32var = 123;
   pStruct->b32var -= 1;
}

void main()
{
   MYSTRUCT myStruct;   
   memset(&myStruct, 0, sizeof(MYSTRUCT));

   // Initialise structure
   myStruct.a32var = 500;
   myStruct.b32var = 999;
     
   printf(Debug_putc, "DEVICE:%s\r\n", getenv("DEVICE"));
   printf(Debug_putc, "COMPILER VERSION:%s\r\n", getenv("VERSION_STRING"));

   // dump contents of structure
   printf(Debug_putc, "MyStruct:%lu %lu\r\n", myStruct.a32var, myStruct.b32var);

   // Call simple function that modifies contents of stucture
   a(&myStruct);

   // dump contents of structure -- why is a32var now 0?
   printf(Debug_putc, "MyStruct:%lu %lu\r\n", myStruct.a32var, myStruct.b32var);
}
GregReadUK



Joined: 24 Jan 2011
Posts: 6
Location: Kent, UK

View user's profile Send private message Visit poster's website

PostPosted: Mon Jan 24, 2011 6:35 am     Reply with quote

This issue may be related to the -= operation on the structure member.
Changing to the code below makes it work as expected.

void a(MYSTRUCT *pStruct)
{
pStruct->a32var = 123;
pStruct->b32var = pStruct->b32var - 1;
}

Is the original code incorrect or is this a compiler issue?

All advice appreciated,
thanks,
Greg
FvM



Joined: 27 Aug 2008
Posts: 2337
Location: Germany

View user's profile Send private message

PostPosted: Mon Jan 24, 2011 8:22 am     Reply with quote

It's a bug, newly introduced in V4.108 or V4.109. It's caused by incrementing an address erroneously twice, in 003F0 and 003F4. Instead of writing the carryover to the highword of b32var, it's written to a32var.

It's a typical PCD arithmetic bug, they come and go, although the product is slowly improving. I fear, the only chance for CCS to get rid of it, besides of better considering compiler changes, is to implement automated test suites that must be run before a new version is released. Of course, new detected bugs have to be added to the test collection. There are several commercial products availiable, also the GCC test suites most likely would have revealed many of the bugs found during the last years.

Code:
39:                void a(MYSTRUCT *pStruct)
40:                {
 003D4  781F85     mov.w 0x000a,[0x001e++]
41:                pStruct->a32var = 123;
 003D6  200040     mov.w #0x4,0x0000
 003D8  B40808     add.w 0x0808,0x0000
 003DA  780280     mov.w 0x0000,0x000a
 003DC  2007B4     mov.w #0x7b,0x0008
 003DE  980284     mov.w 0x0008,[0x000a+0]
 003E0  200004     mov.w #0x0,0x0008
 003E2  980294     mov.w 0x0008,[0x000a+2]
42:                pStruct->b32var -= 1;
 003E4  200000     mov.w #0x0,0x0000
 003E6  B40808     add.w 0x0808,0x0000
 003E8  780280     mov.w 0x0000,0x000a
 003EA  780215     mov.w [0x000a],0x0008
 003EC  520061     sub.w 0x0008,#1,0x0000
 003EE  780A80     mov.w 0x0000,[0x000a]
 003F0  780255     mov.w [++0x000a],0x0008 // now pointing to b32var.H
 003F2  5A0060     subb.w 0x0008,#0,0x0000
 003F4  980290     mov.w 0x0000,[0x000a+2] // data moved to a32var.L
43:                }
 003F6  7802CF     mov.w [--0x001e],0x000a
 003F8  060000     return
GregReadUK



Joined: 24 Jan 2011
Posts: 6
Location: Kent, UK

View user's profile Send private message Visit poster's website

PostPosted: Mon Jan 24, 2011 8:33 am     Reply with quote

Many thanks for the detailed clarification. I can work around it for now by not using -=.

I agree that once test cases are known, automated test tools definitely help to ensure higher quality consistency in functionality.
Ttelmah



Joined: 11 Mar 2010
Posts: 19328

View user's profile Send private message

PostPosted: Mon Jan 24, 2011 10:48 am     Reply with quote

Yes, unfortunately the lack of just about any testing, is one of the biggest 'gripes' about CCS....

As a comment, I would add #case, and get rid of *=16 to your setups. *=16, is not used/needed on any chip after the PIC18 family, and you are using the same name for a typedef, and an actual variable, distinguished only by case, and if you want to do this, I would switch the compiler to use case significance.

Best Wishes
GregReadUK



Joined: 24 Jan 2011
Posts: 6
Location: Kent, UK

View user's profile Send private message Visit poster's website

PostPosted: Mon Jan 24, 2011 11:04 am     Reply with quote

Thanks for the tips, *= 16 and #case.
Variable name co-incidence was a happy accident I hadn't even noticed.
Display posts from previous:   
Post new topic   Reply to topic    CCS Forum Index -> General CCS C Discussion All times are GMT - 6 Hours
Page 1 of 1

 
Jump to:  
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum


Powered by phpBB © 2001, 2005 phpBB Group