View previous topic :: View next topic |
Author |
Message |
Fabri
Joined: 22 Aug 2005 Posts: 275
|
read_eeprom() after write_eeprom() |
Posted: Thu Nov 16, 2006 2:32 am |
|
|
Hi Everybody,
I have a problem in project where sometimes some location in EEPROM was ereased. I have a routine reading those locations after a routine writing other data in eeprom. I suppose there's a possibility that writing eeprom doesn't end in time to read eeprom and the PIC write location instead of read.
By your experience does it possible ?
Shall I controll the end of writing before read ?
Thanks for help,
Regards, |
|
|
sjbaxter
Joined: 26 Jan 2006 Posts: 141 Location: Cheshire, UK
|
|
Posted: Thu Nov 16, 2006 4:06 am |
|
|
Post an example of your code that shows the problem and we can take a look at it. _________________ Regards,
Simon. |
|
|
Fabri
Joined: 22 Aug 2005 Posts: 275
|
|
Posted: Thu Nov 16, 2006 5:00 am |
|
|
Hi,
This is a code write new data in eeprom if changed in RAM location
Code: |
void aggiorna_dati_eeprom(){
// flag_ciclo
restart_wdt();
if (flag_ciclo!=read_eeprom(ADR_FLAG_CICLO))
write_eeprom(ADR_FLAG_CICLO,flag_ciclo);
// Temperatura Impostata
if (temperatura_impostata!=read_eeprom(ADR_TEMPERATURA_IMPOSTATA))
write_eeprom(ADR_TEMPERATURA_IMPOSTATA,temperatura_impostata);
restart_wdt();
// codice_errore
if (codice_errore!=read_eeprom(ADR_CODICE_ERRORE))
write_eeprom(ADR_CODICE_ERRORE,codice_errore);
restart_wdt();
// Aggiorna potenza stufa
if (potenza_stufa!=read_eeprom(ADR_POTENZA_STUFA))
write_eeprom(ADR_POTENZA_STUFA,potenza_stufa);
// Aggiorna ore lavoro
if (read_eeprom(ADR_CONTATORE_ORE_LAVORO_L)!=make8(ore_lavoro,0))
write_eeprom(ADR_CONTATORE_ORE_LAVORO_L,make8(ore_lavoro,0));
if (read_eeprom(ADR_CONTATORE_ORE_LAVORO_M)!=make8(ore_lavoro,1))
write_eeprom(ADR_CONTATORE_ORE_LAVORO_M,make8(ore_lavoro,1));
if (read_eeprom(ADR_CONTATORE_ORE_LAVORO_H)!=make8(ore_lavoro,2))
write_eeprom(ADR_CONTATORE_ORE_LAVORO_H,make8(ore_lavoro,2));
// Aggiorna ore lavoro assistenza
if (read_eeprom(ADR_CONTATORE_ASSISTENZA_H)!=make8(contaore_da_assistenza,1))
write_eeprom(ADR_CONTATORE_ASSISTENZA_H,make8(contaore_da_assistenza,1));
if (read_eeprom(ADR_CONTATORE_ASSISTENZA_L)!=make8(contaore_da_assistenza,0))
write_eeprom(ADR_CONTATORE_ASSISTENZA_L,make8(contaore_da_assistenza,0));
// Aggiorna parametri modificati direttamente da EEPROM
// Aggiorna modalita termostato
modalita_cronotermostato_gsm=read_eeprom(ADR_MODALITA_TERMOSTATO);
}
|
And this is a code read eeprom location and put data in eeprom for use in software.
Code: |
void carica_variabili_da_eeprom(){
angolo_fase_asp_fumi=99-(read_eeprom(ADR_TON_A_FUMI_VELOCITA_1+(velocita_apiratore_fumi-1-riduzione_potenza)));
angolo_fase_vent_aria=99-(read_eeprom(ADR_TON_V_ARIA_VELOCITA_1+(velocita_vent_aria-1-riduzione_potenza_vent_aria)));
ricetta_selezionata=read_eeprom(ADR_RICETTA_SELEZIONATA);
}
|
In main program, every one second the system call the routines as show.
Code: |
aggiorna_dati_eeprom();
carica_variabili_da_eeprom();
|
|
|
|
sjbaxter
Joined: 26 Jan 2006 Posts: 141 Location: Cheshire, UK
|
|
Posted: Thu Nov 16, 2006 7:26 am |
|
|
What PIC, clock speed and version of CCS compiler are you using ?
Looking at the code you have posted, the number of writes will be confined to the minimum required to store the data. However, do any of these values change often enough that the data gets written every time the function is called ?
Does the problem show up on a new PIC or is this seen on a PIC that has been running the code for a long time ? If this is on your prototype, was the code ever run without the 'read' check before the 'write' ? Basically, what I'm saying is; have you used up the write cycles on these eeeprom addresses ? If this is the case, try chaning the address at which you store the data and see if the problem persists.
If you think that the write may have not completed in time (not sure, but I would have expected the write_eeprom function to return only after the eeprom had been completely written) you could put a small delay between the write and read .... I don't think this will be a problem though.
Edit: unless you have #device WRITE_EEPROM=ASYNC defined in which case the write may not have completed before the read. _________________ Regards,
Simon. |
|
|
Fabri
Joined: 22 Aug 2005 Posts: 275
|
|
Posted: Thu Nov 16, 2006 7:50 am |
|
|
Hi,
PIC is 16F876A, CCS compiler is 3,249.
The problem happend random in very least cases. But I'm working to understand if is possible. The PIC are new and the location don't change very much. Other my equipment work, with the same software solution, from years. In this part of routine I have a dubt.
I can insert a delay between every write function but, in first time, I need to know if the problem happen.
Thanks and Regards, |
|
|
jds-pic
Joined: 17 Sep 2003 Posts: 205
|
Re: read_eeprom() after write_eeprom() |
Posted: Thu Nov 16, 2006 12:53 pm |
|
|
Fabri wrote: | Hi Everybody,
I suppose there's a possibility that writing eeprom doesn't end in time to read eeprom and the PIC write location instead of read.
By your experience does it possible ?
Shall I controll the end of writing before read ? |
this problem is the same whether you are writing/reading from an external EEPROM or an internal-to-PIC EEPROM.
you can do one of two things:
1) read the datasheet for the device to determine the maximum write time (across all temperatures and supply voltages). use this to implement a hard delay (typ. 10 or 20ms) after you write to the EEPROM.
2) read the datasheet to for the device to determine if it is possible to poll for completion of the write to the EEPROM. this allows you to optimize things a bit.
there is a third option but i don't think you are ready for it. it involves using an interrupt timer and a global variable to inhibit/enable writing. this allows your progam to do other things while the write is in progress. it is really a variation on (2) above but without the constant polling overhead. unless you are really pressed for realtime i would suggest simply using (1) above.
jds-pic |
|
|
Fabri
Joined: 22 Aug 2005 Posts: 275
|
|
Posted: Fri Nov 17, 2006 1:03 am |
|
|
Hi,
I thought the same solutions but I call write_eeprom and read_eeprom more then one time in software.
Doesn't write_eeprom() a safed function ?
Bye |
|
|
davekelly
Joined: 04 Oct 2006 Posts: 53 Location: Berkshire, England
|
|
Posted: Fri Nov 17, 2006 2:10 am |
|
|
The write_eeprom() function polls the WR bit to check for completion of the write cycle, so it is unnecessary to use the delay functions as suggested above. |
|
|
SET
Joined: 15 Nov 2005 Posts: 161 Location: Glasgow, UK
|
|
Posted: Fri Nov 17, 2006 9:35 am |
|
|
When you say the EEPROM locations are sometimes erased, do you mean you get a 0xFF back? It might be the case that one of your variables is getting set to this in error, and your code is doing it's job. So if a value is outside it's expected range you should ignore it.
Also, if one or more of your sensor values changed every time you read it (say a temperature that changes from 21 to 22 and back..), then your EEPROM will not last long!
Regards |
|
|
Fabri
Joined: 22 Aug 2005 Posts: 275
|
|
Posted: Fri Nov 17, 2006 9:52 am |
|
|
Hi,
When I say erased I mean 0x00. I save in those 5 locations some system data, writed only by PC with serial link or controll panel. This location doesn't change for all life of system.
Regards, |
|
|
PCM programmer
Joined: 06 Sep 2003 Posts: 21708
|
|
|
Fabri
Joined: 22 Aug 2005 Posts: 275
|
|
Posted: Sat Nov 18, 2006 1:53 am |
|
|
Hi,
No because I write in those eeprom locations just one or two time in all life of micro. Those 5 location was cleared all in the same time and I think is a possible bug of controll pannel that send a write command with all 0x00 but it's so casual and difficult do simulate.
In the thread prayami wrote in eeprom every time he push the button.
Thanks for help,
Regards, |
|
|
SET
Joined: 15 Nov 2005 Posts: 161 Location: Glasgow, UK
|
|
Posted: Sun Nov 19, 2006 3:47 pm |
|
|
Hi Fabri
I agree, I think your software that sets up these 'system' locations must be faulty, rather than a fault in the CCS read/write routines
SET |
|
|
|