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

Read and Write 16 Bit Number To Internal EEPROM

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



Joined: 06 Sep 2003
Posts: 49

View user's profile Send private message

Read and Write 16 Bit Number To Internal EEPROM
PostPosted: Sun Oct 26, 2008 2:11 pm     Reply with quote

I'm using PIC16F876A.

I need to read a two byte 16 bit number out of internal EEPROM, increment it and write it back to EEPROM. The code below works ok for reading it out and incrementing it. It does not write the values to EEPROM though. I get no errors and the code exectutes fine (per the debugger) but the values in the EEPROM dont change. I think it has something to do with how I pack the bytes before I write it back to EEPROM?? Not really sure, I could use some help or some other working sample code. Thanks.

Code:

#define AddressU 0
#define AddressL 1

int8 TempUpper, TempLower;
int16 TempValue;

//Read current value from EEPROM
TempUpper = read_eeprom(AddressU);
TempLower = read_eeprom(AddressL);

//Combine Upper and Lower into Value
TempValue = 0x0000;
TempValue = TempUpper;            
TempValue = TempValue << 8;
TempValue = TempValue | TempLower;
            
//Incrent the value
TempValue = TempValue + 1;

//Put the Value back into Upper and Lower
TempUpper = (TempValue >> 8) & 0x00FF;
TempLower = TempValue & 0x00FF;
         
//Write Upper and Lower to EEPROM
write_eeprom(AddressU, TempUpper);
write_eeprom(AddressL, TempLower);   

   
PCM programmer



Joined: 06 Sep 2003
Posts: 21708

View user's profile Send private message

PostPosted: Sun Oct 26, 2008 2:49 pm     Reply with quote

Quote:
the values in the EEPROM dont change

The MPLAB Help File for the Microchip ICD2 says this:
Quote:
Writing Data EEPROM
If data EEPROM is written during program execution, the EEPROM window
of MPLAB IDE will not reflect the changes. You will need to perform a
READ of EEPROM memory in order to update the values in the window.


Here is an example of reading/writing a 16-bit word to external eeprom.
It could be changed to work with internal eeprom.
http://www.ccsinfo.com/forum/viewtopic.php?t=27405&start=5
Freddie



Joined: 06 Sep 2003
Posts: 49

View user's profile Send private message

PostPosted: Sun Oct 26, 2008 3:45 pm     Reply with quote

Thanks PCMP, I knew about having to reload the EEPROM data.

After tinkering with this a bit more I found that the issue is with these two lines:
Code:

//Put the Value back into Upper and Lower
TempUpper = (TempValue >> 8) & 0x00FF;
TempLower = TempValue & 0x00FF;


If I change the "& 0x00FF" to "& 0xFF" like this, it works:
Code:

//Put the Value back into Upper and Lower
TempUpper = (TempValue >> 8) & 0xFF;
TempLower = TempValue & 0xFF;


It seems that I may have been inadvertantly casting TempUpper and TempLower to 16 bits and the write_eeprom() function did not like that??
PCM programmer



Joined: 06 Sep 2003
Posts: 21708

View user's profile Send private message

PostPosted: Sun Oct 26, 2008 3:57 pm     Reply with quote

If you want to split and combine bytes into a word, it can be done much
more easily and error-free if you use the make8() and make16()
functions. These are in the CCS manual.
Freddie



Joined: 06 Sep 2003
Posts: 49

View user's profile Send private message

PostPosted: Sun Oct 26, 2008 4:02 pm     Reply with quote

PCM programmer wrote:
If you want to split and combine bytes into a word, it can be done much
more easily and error-free if you use the make8() and make16()
functions. These are in the CCS manual.


Thats a good idea, thanks. I'm gonna change my code to use the make8() and make16() functions.
FvM



Joined: 27 Aug 2008
Posts: 2337
Location: Germany

View user's profile Send private message

PostPosted: Sun Oct 26, 2008 4:57 pm     Reply with quote

The make16() and make8() are useful for straightforward coding of 8/16-bit conversions. However, the C-standard compatible method in above example is generally supported and efficiently coded by CCS C. I don't see an inadvertent type cast or even incorrect coding when compiling the example with PCM V4.081. Also the generated binary code is identical when changing 0x00ff to 0xff.

It may be an issue of a previous compiler version, or there must be some special setting not shown in the posting.
Freddie



Joined: 06 Sep 2003
Posts: 49

View user's profile Send private message

PostPosted: Sun Oct 26, 2008 5:27 pm     Reply with quote

I'm using CCS compiler version 3.245.

I changed it to use the make8 and make16 functions, see below.

Everything works except that it does not actually write to the EEPROM, I'm sure of that.

What could be going on here? Can someone try this function with a later version of the compiler and let me know what happens?

Code:

void Increment16BitNumber(int8 UpperAddress, int8 LowerAddress)
{
   int8 TempUpper, TempLower;
   int16 TempValue;
   
   //Read current value from the bin
   TempUpper = read_eeprom(UpperAddress);
   TempLower = read_eeprom(LowerAddress);

   //Combine Upper and Lower into Value
   TempValue = make16(TempUpper, TempLower);
            
   //Incrent the value of the bin
   TempValue = TempValue + 1;

   //Write the value back into the bin
   TempUpper = make8(TempValue,1);
   TempLower = make8(TempValue,0);
         
   write_eeprom(UpperAddress, TempUpper);
   write_eeprom(LowerAddress, TempLower);   
}
PCM programmer



Joined: 06 Sep 2003
Posts: 21708

View user's profile Send private message

PostPosted: Sun Oct 26, 2008 5:36 pm     Reply with quote

Post a test program that calls your function. Post the #include, #fuses,
#use delay(), and main(). There should be a printf statement that
displays the values on the terminal window.

Examples of eeprom test programs:
http://www.ccsinfo.com/forum/viewtopic.php?t=17590
http://www.ccsinfo.com/forum/viewtopic.php?t=32722
The one above has two examples.
http://www.ccsinfo.com/forum/viewtopic.php?t=22109&start=17
Freddie



Joined: 06 Sep 2003
Posts: 49

View user's profile Send private message

PostPosted: Sun Oct 26, 2008 6:22 pm     Reply with quote

I built a test program per PCMP's suggestion and the test program works fine.

However, my "real" program still does not write to the EEPROM!!! There must be something else somewhere in the program that is interacting and causing this issue. I'm not sure I can post the real code because it is a project for work. I'll have to keep debugging and let you know what/if I find the root cause.

Thanks for trying to help.
PCM programmer



Joined: 06 Sep 2003
Posts: 21708

View user's profile Send private message

PostPosted: Sun Oct 26, 2008 6:35 pm     Reply with quote

Comment out sections of it until it does work. This will give you a clue
as to what is causing the problem.

For example, if you are calling a routine to get the time from a RTC chip,
comment out the guts of that routine and just make it return a preset
date-time value. This allows your program to still work overall, but
you can test if certain aspects of your program are causing a problem.
Freddie



Joined: 06 Sep 2003
Posts: 49

View user's profile Send private message

PostPosted: Sun Oct 26, 2008 6:51 pm     Reply with quote

I think I figured it out.

I use Microchip MPLAB, Microchip ICD2 and PCM 3.245.

When I made and ran the test program I was not using any breakpoints. When I ran the "real" program I have a breakpoint at the top of the "Increment16BitNumber" function and I would then step through each line of that function looking at the variables in the watch window to see what they did. When the program was done I would stop the debugger and pull the content of the EEPROM, always to see that the EEPROM was not written to.

I think the issues was that I was "stepping" through the lines that have the write_eeprom() statements. This apparently changes the timing of execution and the EEPROM was not written to properly? When I removed the breakpoint and ran it with no stepping it works fine every time!

Go figure. I spent 3 hrs debugging this. I guess that's not too bad considering that I have not programmed at pic in about 6 months. Just now getting back into the swing of things.

Is MPLAB the best environment to use with PCM? I've been thinking of getting PCW. Is PCW a stand alone development debug environment and compatible with the Microchip ICD2?
PCM programmer



Joined: 06 Sep 2003
Posts: 21708

View user's profile Send private message

PostPosted: Sun Oct 26, 2008 7:31 pm     Reply with quote

I debug by using temporary printf() statements within the program, to
display the contents of variables. Or, I will place getc() statements
between lines or sections of the program to allow stepping throught it.
Or I will place a while(1) statement to halt progress at a certain point.
This allows the program to run at full speed in the actual product
environment. I don't use the debugger. This is just my method.
It works for me.
FvM



Joined: 27 Aug 2008
Posts: 2337
Location: Germany

View user's profile Send private message

PostPosted: Mon Oct 27, 2008 1:17 am     Reply with quote

To my opinion, MPLAB debugging is irreplaceable to trace low-level coding issues, and it's also very efficient in general debugging. If you use breakpoints, the program behaviour is almost unchanged up to the first breakpoint hit. Single stepping must be used carefully. You must be aware, that some processor actions may not work as expected.
Ttelmah
Guest







PostPosted: Mon Oct 27, 2008 3:19 am     Reply with quote

Obvious comment. NOCPD fuse...

Best Wishes
Wayne_



Joined: 10 Oct 2007
Posts: 681

View user's profile Send private message

PostPosted: Mon Oct 27, 2008 8:02 am     Reply with quote

Don't know about the pic you are using but I am using an 18F6722 and my EEPROM is at address 0xF00000 not 0

#define DATA_BASE_ADDR 0xF00000

addr = DATA_BASE_ADDR;

write_eeprom(addr++, *data++);

Actually, looking at the device selector in PCC I notice that the start address of eeprom for your chip is
0x00002100

Open the device selector from the tools menu, find your chip then look at memory.
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