Yahoo refuse tous les emails du site. Si vous avez une adresse chez un autre prestataire, c'est le moment de l'utiliser
En cas de soucis, n'hésitez pas à aller faire un tour sur la page de contact en bas de page.
Exemple d'utilisation de structure avec EEPROM.put(), avec CRC et versionnage
par skywodd | | Langue : C++ | Licence : GPLv3
Description :
Exemple d'utilisation de structure avec EEPROM.put()
.
Variante avec versionnage et détection de première utilisation.
Utilise une somme de contrôle 16 bits pour détecter les erreurs de lecture.
Code source :
Voir le code source brut | Télécharger eeprom_struct_crc.ino | Télécharger eeprom_struct_crc.ino.zip
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 | /**
* Exemple d'utilisation de structure avec EEPROM.put().
* Variante avec versionnage et détection de première utilisation.
* Utilise une somme de contrôle 16 bits pour détecter les erreurs de lecture.
*/
#include <EEPROM.h>
/** Le nombre magique et le numéro de version actuelle */
static const unsigned long STRUCT_MAGIC = 123456789;
static const byte STRUCT_VERSION = 2;
/** La structure qui contient les données */
struct MaStructure {
unsigned long magic;
byte struct_version;
uint16_t checksum;
int valeur_1; // Depuis la struct_version = 0
float valeur_2; // Depuis la struct_version = 1
char valeur_3[16]; // Depuis la struct_version = 2
};
/** L'instance de la structure, globale car utilisé dans plusieurs endroits du programme */
MaStructure ms;
void setup() {
Serial.begin(9600);
// Charge le contenu de la mémoire
chargeEEPROM();
// Affiche les données dans la structure
Serial.print("Valeur 1 = ");
Serial.println(ms.valeur_1);
Serial.print("Valeur 2 = ");
Serial.println(ms.valeur_2);
Serial.print("Valeur 3 = ");
Serial.println(ms.valeur_3);
}
void loop() {
}
/** Sauvegarde en mémoire EEPROM le contenu actuel de la structure */
void sauvegardeEEPROM() {
// Met à jour le nombre magic, le numéro de version et la checksum avant l'écriture
ms.magic = STRUCT_MAGIC;
ms.struct_version = STRUCT_VERSION;
ms.checksum = 0; // Calcul la checksum sans prendre en compte la valeur actuelle
ms.checksum = crc16_ccitt((byte*) &ms, sizeof(ms));
EEPROM.put(0, ms);
}
/** Charge le contenu de la mémoire EEPROM dans la structure */
void chargeEEPROM() {
// Lit la mémoire EEPROM
EEPROM.get(0, ms);
// Calcul de la checksum
uint16_t current_checksum = ms.checksum;
ms.checksum = 0; // Calcul la checksum sans prendre en compte la valeur actuelle
uint16_t real_checksum = crc16_ccitt((byte*) &ms, sizeof(ms));
// Détection d'une mémoire non initialisée ou corrompue
byte erreur = ms.magic != STRUCT_MAGIC || current_checksum != real_checksum;
// Valeurs par défaut struct_version == 0
if (erreur) {
// Valeurs par défaut pour les variables de la version 0
ms.valeur_1 = 42;
}
// Valeurs par défaut struct_version == 1
if (ms.struct_version < 1 || erreur) {
// Valeurs par défaut pour les variables de la version 1
ms.valeur_2 = 13.37;
}
// Valeurs par défaut pour struct_version == 2
if (ms.struct_version < 2 || erreur) {
// Valeurs par défaut pour les variables de la version 2
strcpy(ms.valeur_3, "Hello World!");
}
// Sauvegarde les nouvelles données
sauvegardeEEPROM();
}
/** Fonction de calcul d'une somme de contrôle CRC-16 CCITT 0xFFFF */
uint16_t crc16_ccitt(unsigned char* data, unsigned int data_len) {
uint16_t crc = 0xFFFF;
if (data_len == 0)
return 0;
for (unsigned int i = 0; i < data_len; ++i) {
uint16_t dbyte = data[i];
crc ^= dbyte << 8;
for (unsigned char j = 0; j < 8; ++j) {
uint16_t mix = crc & 0x8000;
crc = (crc << 1);
if (mix)
crc = crc ^ 0x1021;
}
}
return crc;
}
|