AVR EEPROM verliert Daten

Gast #1075385
Lesenswert?

Hallo,

ist irgendwas bekannt, dass ein ATMEGA8 Daten verliert, die im EEPROM 
gespeichert sind?

Ich hab ein Programm, dass schreibt nur ein einziges mal Daten über eine 
Kommandosequenz über RS232, bestehend aus 3 Zeichen. Diverse Tests, ob 
das sinnvoll ist usw sind auch dabei. Nach 2 Wochen hat eine 
Speicherzelle des AVR-Controllers einfach was verloren.

Kann das eventuell mit einem unsauberen Reset zusammenhängen? Ist da 
irgendwas bekannt, dass es mit dem EEPROM Probleme geben kann?

Hier ein Teil aus der Main, der nur bei der Initialisierung einmal 
aufgerufen wird. Die Timer-Funktionen dürfte in diesem Zusammenhang 
uninteressant sein:
1
int main() {
2
        [...]
3
  timer_set(0,eeprom_read(0));
4
  timer_set(1,eeprom_read(1));
5
        [...]
6
}

und die Funktionen für das EEPROM sehen so aus:
1
uint8_t ee_params[] EEMEM = {0xff,0xff};
2

3

4
void eeprom_write(uint8_t adr, uint8_t data)
5
{
6
  if ((adr<0) || adr>sizeof(ee_params))
7
    return;
8

9
  eeprom_write_byte(&ee_params[adr], data); 
10
}
11

12
uint8_t eeprom_read(uint8_t adr)
13
{
14
  if ((adr<0) || adr>sizeof(ee_params))
15
    return;
16

17
  return eeprom_read_byte(&ee_params[adr]);
18
}

Hab ich da was falsch gemacht?

Grüße
Gast
Gast #1075414
Lesenswert?

Ja, ich hatte auch schon den Effekt bei einem Mega8, dass EEPROM Daten 
verfälscht waren oder sogar EEPROM-Zellen zerstört waren(!).
Letztlich zeigte sich, dass eine unsaubere Versorgungsspannung dafür 
verantwortlich war. Die Dinger mögen keine Spannungsspitzen!

Meine Schreibroutine (entspricht dem ATMEL-datenblatt).
Habe aber beim Starten des Schreibvorgangs sicherheitshalber die 
Interrupts deaktiviert.
1
void EEstore(data,address)
2
{
3
  while(EECR & 0x2)
4
  {
5
  }
6
  EEAR = address;
7
  EEDR = data;
8
  SREG = (SREG ^ 128); //Clr Interrupt enable Bit 
9
  EECR |= 0x4; //set EEMWE
10
  EECR |= 0x2; //set EEWE
11
  SREG = (SREG | 128); //Set Interrupt enable Bit 
12
}

Dein Code hilft nicht weiter. Wo z.B. ist "eeprom_write_byte"?

Joachim
(Firma: TravelRec.) Persönliche Seite #1075462
Lesenswert?

>>zur Sicherheit nie die
>>ersten Bytes im EEPROM mit wichtigen Daten belegen.

>Warum?

Weil die EEPROM-Adressregister mit $0000 initialisiert werden, wenn der 
Controller startet. Im Fehlerfall betrifft das Problem also die erste 
Speicherzelle.

>Habe aber beim Starten des Schreibvorgangs sicherheitshalber die
>Interrupts deaktiviert.

Sollte man generell machen, da sonst die atomische Schreiboperation 
unterbrochen werden kann und somit nicht ausgeführt wird.
Gast #1078040
Lesenswert?

>>>zur Sicherheit nie die
>>>ersten Bytes im EEPROM mit wichtigen Daten belegen.

>>Warum?

>Weil die EEPROM-Adressregister mit $0000 initialisiert werden, wenn der
>Controller startet. Im Fehlerfall betrifft das Problem also die erste
>Speicherzelle.

Na ja. Wenn ich das EEPROM lese oder beschreibe und eine falsche (oder 
hier gar keine Adresse, also 0x00) benutze, ist das ja meine Schuld. 
Ansonsten muß man ja alle defaultwerte oder gar Register irgendwie 
berücksichtigen ,da ja standardmäßig auf diese zugegriffen wird.
(Firma: TravelRec.) Persönliche Seite #1078443
Lesenswert?

Nee Lutz, das haste jetzt falsch verstanden. Der Controller 
initialisiert, bevor Dein Programm überhaupt erst startet, seine 
Hardware-Register, somit auch die EEPROM Steuerregister. Startet der 
Controller nun ohne Brown-Out Detektor, kann es aufgrund unzulänglicher 
Spannung passieren, daß die CPU Befehle falsch interpretiert und 
zufälligerweise auf das EEPROM schreibt. Da die Adressregister noch auf 
$0000 stehen, wird also allermeist die unterste EEPROM-Adresse von dem 
fehlerhaften Schreibvorgang betroffen sein. Dieses Problem tritt mit 
aktiviertem BOD nicht auf.
Gast #1078462
Lesenswert?

Das versehentliche überschreiben der EEPROM Daten auf Adresse $0000 war 
ein Problem der ersten Generation der AVRs (AT90Sxxxx), die keine 
Brow-Out Detection hatten. Der Effekt traf meist beim Einschalten (oder 
beim vorhergehenden Ausschalten) auf.
 Die ATmegaxxx sollten das Problem bei aktivierter Brow-Out Detection 
nicht mehr zeigen.

Gruß Norbert
Gast #1078468
Lesenswert?

Vor einigen Jahren hatte ich diese Fehler öfter, trotz brown out 
detector und sauberer VCC. Ich denke, die Teile waren seinerzeit etwas 
"schrottig" in dieser Beziehung. Zur Sicherheit hatte ich die Daten 
immer mehrfach und mit Prüfsumme gespeichert.
Welches Fertigungsdatum hat den Dein Mega8?
#4673043
Lesenswert?

habe auch das Problem, das das EEPROM von meinem Atmega168 nach einer 
Weile Daten verliert. Der resetet sich aber auch schon mal von aleine 
(Proto-bastel-Typ). Ich hatte die Hoffnung dass es an diesen 
"EMV?!"Resets liegt.

Werde sofort checken ob BO aktiviert ist.

Nun eine doofe Frage.
wie vermeide ich das nutzen der ersten EEPROM Adressen?

quick and dirty würde mir jetzt nur einfallen:
a) pointer auf addresse $0000+n*8bit (16/32)
b) a[0] bis a[x] von a[y] leer lassen     | mit 0<x<y

vermutlich beides Unfug ?! ;)

danke und gruß
Gast #4673428
Lesenswert?

> [..] zweitens macht sizeof NICHT das was er denkt, schon garnicht nach
> einem Reset!

..drittens ist das falsch, viertens bitte ggf. einen eigenen Fred 
aufmachen, weil fünftens dieser hier fast acht Jahre alt ist!
Dieser Beitrag ist gesperrt und kann nicht beantwortet werden.