|
|
View previous topic :: View next topic |
Author |
Message |
cerr
Joined: 10 Feb 2011 Posts: 241 Location: Vancouver, BC
|
weird eeprom issue |
Posted: Fri Feb 18, 2011 2:58 pm |
|
|
Hi There,
I posted the other day already with eeprom issues but then thought i got them resolved and it all seemed to work fine but now I have yet another issue I can't explain
It seems as if my read algorithm would only read 0xff out but only if i didn't write before. If I write before I read I read 0x00 out of every cell.. :(
I have no clue what's going on here, my read algoithm looks like this:
Code: | for (i=OFFSET;i<VARNUM+OFFSET;i++){
int16 lobyte=read_eeprom(i*2);
printf("lobyte:%Ld\r\n",lobyte);
int16 hibyte=read_eeprom(i*2+1);
printf("hibyte:%Ld\r\n",hibyte);
read[i].value=lobyte|(hibyte<<8);
printf("value%Ld\r\n",read[i].value);
} |
where VERNUM is 16 and OFFSET 2
and my store algorithm looks like this:
Code: | for(i=OFFSET;i<VARNUM+OFFSET;i++){
write_eeprom(i*2,store[i].value & 0xFF);
write_eeprom(i*2+1,(store[i].value >> 8) & 0xFF);
} |
What's going on here? Can someone give me a hint or a suggestion? I'm stuck :( - not necessarily a nice way to end the work week... |
|
|
temtronic
Joined: 01 Jul 2010 Posts: 9221 Location: Greensville,Ontario
|
|
Posted: Fri Feb 18, 2011 3:15 pm |
|
|
I'd add some 'printf'...statements so that you can verify your writing to eeprom addresses and data are correct.
Also, make a table of known 'test' data and try that.
Always a lot easier to debug when you know what it's supposed to be....! |
|
|
Ttelmah
Joined: 11 Mar 2010 Posts: 19497
|
|
Posted: Fri Feb 18, 2011 3:36 pm |
|
|
First, in C, variables can _only_ be declared at the start of a program section. 'lobyte', is technically declared legally, but hibyte is not.
Historically, variables could only be declared right at the start of a function (not just a program section), and CCS still prefers this, so though lobyte's declaration location is technically 'legal', far safer to declare all variables at the start of the function.
Second, don't try to assign from a function, inside the declaration. The values assigned to a variable in it's declaration, is only allowed to be a _constant_ in traditional C (which CCS basically is). Initialisation, is done _before the code actually runs...
Best Wishes |
|
|
cerr
Joined: 10 Feb 2011 Posts: 241 Location: Vancouver, BC
|
|
Posted: Fri Feb 18, 2011 4:32 pm |
|
|
temtronic wrote: | I'd add some 'printf'...statements so that you can verify your writing to eeprom addresses and data are correct.
Also, make a table of known 'test' data and try that.
Always a lot easier to debug when you know what it's supposed to be....! |
I know exactly what I'm writing in there, my store structure is filled with 16 default values that I want to safe to the eeprom the first time the software boots up. I wanna read them back but am not reading anything... :( |
|
|
cerr
Joined: 10 Feb 2011 Posts: 241 Location: Vancouver, BC
|
|
Posted: Fri Feb 18, 2011 5:16 pm |
|
|
Ttelmah wrote: | First, in C, variables can _only_ be declared at the start of a program section. 'lobyte', is technically declared legally, but hibyte is not.
Historically, variables could only be declared right at the start of a function (not just a program section), and CCS still prefers this, so though lobyte's declaration location is technically 'legal', far safer to declare all variables at the start of the function.
Second, don't try to assign from a function, inside the declaration. The values assigned to a variable in it's declaration, is only allowed to be a _constant_ in traditional C (which CCS basically is). Initialisation, is done _before the code actually runs...
Best Wishes |
These issues in fact were ones that bugged me along the whole way. Coming from a gcc environment, it's very different as gcc allows all kinds of things that may not be "real C" after definition and it also has better pointer and double pointer tracking and feedback... CCS seems to not care if you use a . or a -> even though choosing the wrong identifier, of course causes your project to not work. WATCH YOUR CODE I'm telling myself ;)
Thanks for that! |
|
|
temtronic
Joined: 01 Jul 2010 Posts: 9221 Location: Greensville,Ontario
|
|
Posted: Fri Feb 18, 2011 5:49 pm |
|
|
cerr
Please do not criticize, condemn and complain about CCSs product until YOU can create and sell us a better product for the same price.
Every 'language' has it's quirks and it is very important to read the manual, forums like this, etc.
Not having been shown your entire code, I would not assume that the data you say you wrote to the eeprom was correct. A previous pointer could have overlapped ram, some 'offset' from some other function, heck your power supply could have dipped. A hundred different valid reasons for why your code fragment doesn't work.
After 20+ years of programming PICs my crystal ball is getting cloudy but the more info you show us, the better we can help. |
|
|
Ttelmah
Joined: 11 Mar 2010 Posts: 19497
|
|
Posted: Sat Feb 19, 2011 3:26 am |
|
|
Problem here is that C, is not a 'strongly typed' language.
Now 'strong typing', implies that if (for instance), you use a int, where a char is expected, the compiler will complain. Plus of this, is it makes it harder to make 'type' mistakes. However 'downside', is that it prevents you from deliberately cross-using types 'on the fly'.
Originally, C, was aimed at being able to perform a lot of the jobs that otherwise needed assembler, allowing you (for example), to happily manipulate an array of characters, as an array, but also as a string, without too much extra overhead over the assembler version. CCS keeps very close to the original K&R usage, and definitions, and this is one reason why everyone programming in C, really should have a copy of "The C programming language", and if in doubt refer to this along with the CCS manual.
The way to avoid lack of typing causing problems is to become a better disciplined programmer:
1) Use the explicitly 'sized' types. So int8, int16, int32, rather than 'int', or 'long'. This way your declarations show the size of variable you are declaring.
2) Use names that reflect the type. So for defines, use capitals. For a type declared as a pointer to an int16 array, called 'fred' inside a routine, give it a name like 'lpfred'. Done with some logic, it makes your code self documenting, so if you use a -> construct, it should always have a variable in front of it starting with 'p' or 'lp' to say this variable is a pointer. One problem here is that the type checking on 'higher level' languages, can make people lazy, and careless about this sort of thing, relying on the checks to report stuff, which (not being perfect), they sometimes don't. Then finding a type fault, on a 50000+ line program, without any of these little hints in the names, becomes a real exercise. So, approaches like this, are _better_, whatever language you are using, and will help to make your programs more likely to compile 'right' first time.
Best Wishes |
|
|
|
|
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
|