Ich entwerfe ein Gerät, das seine physische Position automatisch anpasst, wenn sich die Temperatur ändert. Wenn das Gerät ausgeschaltet oder die Stromversorgung unterbrochen wird, muss sich das Gerät an die letzte Temperatur und Position erinnern. Ich habe die Möglichkeit, diese Werte im EEPROM zu speichern, aber das Problem ist, dass sich Position und Temperatur sehr schnell ändern können. Wenn ich die Temperatur und die Position nach jeder Änderung in das EEPROM schreiben würde, würde dies (1) die Firmware etwas verlangsamen und (2) das EEPROM wahrscheinlich nach ein oder zwei Jahren beenden. So wie ich es sehe, sind meine Optionen wie folgt ...
1) Verwenden Sie einen Kondensator / eine Batterie, um das Gerät nach Stromausfall für kurze Zeit mit Strom zu versorgen, damit ich die Werte nur zu diesem Zeitpunkt in das EEPROM schreiben kann. Ich mag das nicht, weil das Board ein bisschen machtgierig ist und dies eine große Kappe erfordern würde. Und ich habe nicht viel freien Speicherplatz. Und ich möchte nicht die zusätzlichen Kosten für eine Batterie und einen Batteriehalter / oder eine große Kappe.
2) Verwenden Sie F-RAM anstelle von EEPROM, damit ich Billionen Mal darauf schreiben kann, ohne es zu verschleißen. Ich mag diese Option nicht, weil FRAM ziemlich viel teurer als EEPROM ist und dies für ein Produktionsprodukt ist (nicht nur für eines).
3) Schreiben Sie die Position und Temperatur nur etwa alle 5 Minuten auf. Auf diese Weise habe ich immer eine relativ neue Position / Temperatur aufgezeichnet, aber ich schreibe nicht jede Sekunde, damit mein Programm nicht verlangsamt wird und das EEPROM nicht so schnell stirbt. Dies scheint meine beste Option zu sein.
Hat jemand andere Vorschläge, an die ich nicht denke?
quelle
Antworten:
Was Sie brauchen, ist eine Technik namens Verschleißnivellierung . Es schreibt Ihre Daten nicht jedes Mal an derselben Stelle im EEPROM, sondern verwendet einen Algorithmus, um verschiedene Stellen zu verwenden. Ich habe über komplexe Verschleißausgleichsalgorithmen gelesen, aber ich würde nicht wissen, warum die folgende einfache Methode nicht funktionieren würde.
Fügen Sie Ihren Daten einen 24-Bit-Zähler hinzu, sodass Ihr Datenblock beispielsweise 8 Byte lang ist. Seiten auf einem 24AA64 sind 32 Byte lang, sodass ein 64-KB-EEPROM 256 Seiten enthält. Aus dem Datenblatt:
Daher ist es nicht sinnvoll, Datenblöcke zu verwenden, die kleiner als eine 32-Byte-Seite sind.
Schauen Sie sich den Zähler der ersten Seite an. Wenn es Null ist, haben Sie die maximale Anzahl von Schreibzyklen für diese Seite verwendet. Fahren Sie also mit der nächsten Seite fort und überprüfen Sie diesen Zähler. Wiederholen, bis Sie einen Zähler> Null finden. Das ist die Seite, die Sie gerade verwenden. Die EEPROMs von Microchip haben eine Lebensdauer von 1 Million Zyklen, die Sie mit dem angegebenen Beispiel von maximal 32 Bytes pro Block in einem 64-KB-EEPROM auf 256 Millionen erhöhen können. Das sollte ausreichen, um Ihr Produkt zu überdauern: 40 Jahre, wenn Sie alle 5 Sekunden (!) Einmal schreiben.
Sie möchten Ihr EEPROM bei der ersten Verwendung initialisieren. Woher weißt du, wann das ist? Verwenden Sie die letzte Seite, um bei der Initialisierung eine eindeutige Signatur zu schreiben. Überprüfen Sie bei jedem Einschalten, ob die Signatur vorhanden ist. Ist dies nicht der Fall, muss das Gerät initialisiert werden. Sie können den Zähler auf jeder Seite mit 0xF4240 (für 1 Million) voreingestellt oder alles auf 0xFF löschen und den 0xF4240 schreiben, wenn Sie die Seite zum ersten Mal verwenden.
Das Initialisieren eines EEPROM ist erforderlich, da manchmal im Produktions- / Testprozess ein bestimmtes Muster darauf geschrieben wird.
edit
Die Verschleißnivellierung sollte Ihre Probleme lösen, aber ich möchte trotzdem die Kondensatorlösung kommentieren. Sie sagen, die Karte ist ziemlich leistungshungrig, aber vielleicht können Sie die Leistung des Mikrocontrollers / EEPROMs mit einer Diode vom Rest der Karte trennen. Sie benötigen also wahrscheinlich nur wenige mA, wenn die Hauptstromversorgung unterbrochen ist. Der 24AA64 schreibt eine Seite in weniger als 5 ms, dann bei 10 mA und einem zulässigen Spannungsabfall von 100 mV, den Sie benötigen
Einfach mit einer kleinen Superkappe.
Lesen
Sie weiter das Datenblatt 24AA64
EEPROM Endurance Tutorial
quelle
1) Sobald Sie den Schreibvorgang gestartet haben, müssen Sie nur noch die MCU / das EEPROM mit Strom versorgen und sicherstellen, dass die Steuerleitungen nicht fehlerhaft sind - I2C ist wahrscheinlich SPI vorzuziehen. Benötigen Sie nur ein paar mA für ein paar Millisekunden, damit dies keine große Kappe ist, und Sie können die MCU in den Ruhezustand versetzen, sobald der Schreibvorgang gestartet wird. 3) Sie können wahrscheinlich etwas Intelligenz anwenden, z. B. einen Holdoff - einmal geschrieben, hält es immer eine bestimmte Zeit, bevor ein weiterer Schreibvorgang stattfinden kann. Oder warten Sie eine Weile, bis der Wert stabil ist, bevor Sie schreiben.
Sie können die Ausdauer auch erhöhen, indem Sie die Daten auf mehrere Standorte verteilen. Microchip verfügt über einige Tools und Appnotes, mit denen die Lebensdauer der Eeproms berechnet werden kann. Dies kann hilfreich sein.
quelle
Ich würde vorschlagen, ein blockorientiertes Flash-Gerät zu verwenden und ein Byte von jedem Block als Modus-Flag zu verwenden. Behalten Sie als Invariante bei, dass fast alle Modusflags programmiert werden. Es gibt nur einen Block, in dem das Modus-Flag nicht programmiert ist, aber der vorherige Block (ggf. umbrechen). Dieser Block ist derjenige mit den neuesten Daten. Wenn dieser Block voll ist, löschen Sie den folgenden Block (beachten Sie, dass der zu löschende Block während des Löschzyklus eine beliebige Kombination von Daten enthalten kann und die Invariante weiterhin gültig ist). Wenn das Löschen abgeschlossen ist, programmieren Sie das Modus-Flag auf das, was früher verwendet wurde sei der letzte Block.
Es ist notwendig, die Versorgung des Flashs gut genug zu schützen, um sicherzustellen, dass jeder Versuch, ein Byte zu programmieren, entweder erfolgreich ist oder vollständig fehlschlägt. Es spielt jedoch keine Rolle, ob ein Löschzyklus unterbrochen wird und ein Block voller beliebiger Daten übrig bleibt. da der nächste Versuch, einen Dateneintrag zu schreiben, diesen Block erneut löscht.
Wenn Ihre Daten 16 Bit groß sind, enthält ein 64Kx8-Chip über 32.000 Einträge. Das Schreiben eines Eintrags pro Sekunde würde den Chip ungefähr 2,7-mal füllen. Selbst ein Chip mit einer Lebensdauer von "nur" 10K-Löschzyklen würde über 10 Jahre halten. Die Verwendung eines größeren Chips oder eines Chips mit einer Lebensdauer von 100.000 würde die Lebensdauer proportional verlängern.
quelle
1) Möglicherweise die einfachste Option, obwohl möglicherweise Hardwareänderungen erforderlich sind. Ich habe dies zuvor ohne PBC-Modifikationen erreicht, indem ich nur die Entkopplungskappen vergrößert und das Brown-Out unterbrochen habe.
2) Wie Sie bereits betont haben, ist das Problem mit FRAM der Preis!
3) Abhängig von der Flüchtigkeit Ihrer Temperatur- und Positionsdaten erhöhen Sie die Ausdauer, indem Sie nur schreiben, wenn sich der Wert geändert hat. Möglicherweise messen Sie die Temperatur einmal pro Sekunde, aber wenn sie sich nur alle 5 Minuten ändert, ist das Problem behoben.
quelle
So habe ich dieses Problem in meinem Projekt gelöst:
Reservieren Sie 1 Flash-Sektor, um eine Bitmaske nicht verwendeter Steckplätze und eine Anzahl von Steckplätzen für den Wert aufzunehmen.
Die Bitmaske, die ich verwendet habe, war 16 Byte lang, also hatte ich 128 Steckplätze, um Werte zu setzen.
Die Bitmaske wird für alle initialisiert, was in Flash-Begriffen der gelöschte Zustand ist.
Wenn Sie einen neuen Wert schreiben möchten, lesen Sie die Bitmaske ein und suchen Sie das erste Bit, das eins ist. Dies ist die Steckplatznummer, in die Sie den Wert schreiben. Ändern Sie dieses Bit auf Null, um es als verwendet zu markieren, und schreiben Sie die Bitmaske zurück, um zu blinken, ohne sie zuvor zu löschen. Schreiben Sie als nächstes den Wert in den Steckplatz nach der Bitmaske, ohne den Blitz zu löschen.
Auf diese Weise verlängern Sie die Flash-Schreibzyklen um das 128-fache, indem Sie die neue Bitmaske nur mit einer Änderung von eins auf null schreiben.
Wenn die gesamte Bitmaske 0 ist, löschen Sie den Flash-Sektor und starten Sie neu.
quelle