float im EEPROM

Gast #436395
Lesenswert?
• ▲
▼
Ich will ein float im EEPROM ablegen und auslesen. Klappt eigentlich 
auch. Aber ich will feststellen, ob da schon ein Wert abgelegt wurde, 
oder nicht (neuer Chip) und dann einen Standardwert nehmen. Das klappt 
nicht. µC: ATmega32

Ich habe:

float epromwert EEPROM;
float wert=0;
...
eeprom_read_block(&wert, &epromwert, sizeof(float));

Wenn ich wert mit

dtostrf (wert, 6, 3, text);

konvertiere, bekomme ich bei einem leeren EEPROM (FF) "NAN". Ok, so weit 
ja auch brauchbar. Jetzt dachte ich, ich prüfe mit

isnan (wert)

ob das Ergebnis aus dem EEPROM auslesen eine Zahl ist. Aber die Fkt. 
liefert immer 0
:-(

Wie mache ich's denn richtig?
Gast #436428
Lesenswert?
• ▲
▼
Hallo Florian,

eine interessante Fragestellung. Die beiden Funktionen in der avr-libc 
(Version 1.4.4) haben eine unterschiedliche "Meinung" darüber was ein 
NaN ist, ich denke, die richtige Definition müßte sich in IEEE-754 
finden, bei Interesse danach 'googeln' oder auch mal bei 
http://en.wikipedia.org/wiki/NaN vorbeischauen).

bei isnan() findet sich:
  CPI  r25, 0xFF  ; NaN is 0xffc0XXXX
  BRNE  .Lfalse
  CPI  r24, 0xC0
  BRNE  .Lfalse

bei dstrtof():
  cpi  r17, 0xff  ; NAN ?
  brne  1f

Es ist nicht auszuschliessen, dass avr-libc das noch nicht 100 %-ig 
implementiert (siehe auch 
https://savannah.nongnu.org/bugs/?group=avr-libc&func=browse&set=open , 
hier Item # 13330), ich würde das daher in der gegenwärtigen Situation 
'schmutzig' lösen und auf 0xffff (bzw. 2 Worte mit 0xffff) abprüfen. 
Wenn (float)0xfffffffff eine gültige Float-Zahl ist, dann hat man 
natürlich ein Problem... ich hab' gerade kein AVR-System hier, was käme 
denn da raus ?

Ciao
 Hermann-Josef
Gast #436607
Lesenswert?
• ▲
▼
Ah. Dann kann man sich ja totsuchen. Nachzuschauen, wie die Funktionen 
implementiert sind, käme mir nie in den Sinn. Ich gehe (blauäigig, wie 
ich wohl zugeben muß) davon aus, daß die Dinge so funktionieren, wie sie 
sollen.
Ich hatte es noch etwas dreckiger gemacht und in einen String gewandelt 
und dann mit strcmp auf "NAN" geprüft.

Aber der Test auf FF geht auch (in meinem Fall).

for (i=0; i<=6; i+=2)
{
  if (eeprom_read_word((uint16_t *)(&wert+i)) != 0xFFFF)
    is_number = 1;
}

Was mich jetzt nur noch stutzig macht, ist das ein double lediglich 4 
Bytes belegt, wie auch ein float.
Moderator Persönliche Seite #436626
Lesenswert?
• ▲
▼
Naja, davon abgesehen, dass das gesamte Handling der IEEE754-
Sonderfeatures (Inf, NaN, Denormals) in der bestehenden
Implementierung unterbelichtet ist, ist es aber auch recht
blauäugig anzunehmen, dass ein 0xffffffff automatisch eine
gültige NaN wäre.  Den Test auf nicht programmierten EEPROM
solltest du also sinnvollerweise schon explizit gegen 0xffffffff
vornehmen.
Gast #436645
Lesenswert?
• ▲
▼
@ Jörg Wunsch
Ich ging ja nicht davon aus, daß das NaN ist, aber die Funktion isnan 
lieferte halt immer 0, das störte mich. Das die Implementierung nicht OK 
ist, kann man ja nicht unbdeingt wissen finde ich.

@Matthias Weißer
Aha. Wieder was gelernt (und vermutlich dann wieder vergessen, wenn ich 
es das nächste mal brauche :-( ) Ist halt doof, wenn man mehrere 
Sprachen kennt und immer wieder wechselt und dann Wissen transferieren 
will...

Danke.

Antwort schreiben

Bitte melde dich an, um einen Beitrag zu schreiben.

oder

Mit Google-Account einloggen

Die Registrierung ist kostenlos und dauert nur eine Minute.

Jetzt registrieren