Go Down

Topic: Problema con contapezzi (Read 5194 times) previous topic - next topic

leo72

Tempo fa avevo scritto qualcosa di simile.
In pratica facevo così.

Formattavo la EEPROM con una serie di byte standard (esempio $AA).
Ogni blocco di dati iniziava con un byte diverso da $AA, ovviamente. Siccome memorizzavo degli orari e delle letture, era facile avere un byte diverso da $FF dato che un'ora al max arriva a $17 (23d). Ogni volta che scrivevo un blocco di dati, incrementavo il puntatore all'indirizzo del blocco corrente.

In caso di riavvio, controllavo se la prima cella era diversa da $AA, segno che la EEPROM era già stata formattata e che quindi non era il primo avvio. A questo punto partiva un loop che mi "saltava" a blocchi attraverso la EEPROM finché non trovava una cella contenente appunto $AA e quello era l'indirizzo del 1° blocco libero disponibile.

E' ovvio che se io non svuotavo la EEPROM prima di averla riempita, il contatore ripartiva da 0, sovrascrivendomi i dati in fondo. Per ovviare a questo avevo messo un led di avviso per informarmi che i blocchi stavano per terminare.

rocco8383

Con lo sketch di PAOLOP(grazie) ho più cifrea  disposizione ma quando resetto azzera solo la prima cifra.Con lo sketch da te modificato quante volte potrò scrivere l'eeprom?

leo72


Con lo sketch di PAOLOP(grazie) ho più cifrea  disposizione ma quando resetto azzera solo la prima cifra.Con lo sketch da te modificato quante volte potrò scrivere l'eeprom?

Dipende da quante scritture fai e da quanto è grosso il tuo blocco di dati.
Ipotizziamo un blocco di 4 byte e 1 scrittura al secondo.
1K di EEPROM sono 1024 byte, quindi hai 1024/4=256 blocchi.
100.000 scritture per 256 blocchi, sono 256.000.000 blocchi. Scrivendone 1 al secondo bruci la EEPROM in 296 giorni.

PaoloP

#18
Mar 05, 2013, 11:47 am Last Edit: Mar 05, 2013, 11:54 am by PaoloP Reason: 1

Con lo sketch di PAOLOP(grazie) ho più cifre disposizione ma quando resetto azzera solo la prima cifra.


Code: [Select]
#include <LiquidCrystal.h>
#include <EEPROM.h>      

#define PINLED 13
#define INGRESSO1 8
#define INGRESSO2 7

int addr_a = 0; // 0,1,2,3                
int addr_b = 4; // 4,5,6,7              

unsigned long count_a = 0; // Valore massimo 4 miliardi 294...
unsigned long count_b = 0; // Valore massimo 4 miliardi 294...

LiquidCrystal lcd(12, 11, 5, 4, 3, 2);

void setup() {
 pinMode(INGRESSO1,INPUT);
 pinMode(INGRESSO2,INPUT);
 pinMode(PINLED,OUTPUT);
 digitalWrite(PINLED,HIGH);

 lcd.begin(16, 2);
 lcd.print(" xxxxxxxx");
 delay(3000);
 lcd.clear();
 lcd.setCursor(0, 0);
 lcd.print("Valori:");
 lcd.setCursor(0, 1);
 lcd.print("P1=");
 lcd.setCursor(10, 1);
 lcd.print("P2=");

 count_a = EEPROM_readlong(addr_a);          // leggo i valori a salvati nella precedente "sessione di lavoro"
 count_b = EEPROM_readlong(addr_b);          // leggo i valori b salvati nella precedente "sessione di lavoro"
}

void loop() {
 byte c = digitalRead(INGRESSO1);
 byte d = digitalRead(INGRESSO2);
 delay(10); // debounce

 if (c == HIGH){
   count_b++;
   EEPROM_writelong(addr_b, count_b);
   delay(500);
 }

 if (d == HIGH){
   count_a++;
   EEPROM_writelong(addr_a, count_a);
   delay(500);
 }

 if ((c == HIGH) && (d == HIGH)){
   count_a = 0;
   count_b = 0;
   delay(500);
   EEPROM_writelong(addr_b, count_b);
   EEPROM_writelong(addr_a, count_a);

   lcd.setCursor(4, 1);
   lcd.print("  ");
   lcd.setCursor(14, 1);
   lcd.print("  ");
 }

 lcd.setCursor(4, 1);
 lcd.print(count_a);
 lcd.setCursor(14, 1);
 lcd.print(count_b);
}

// read double word from EEPROM, give starting address
unsigned long EEPROM_readlong(int address) {
 //use word read function for reading upper part
 unsigned long dword = EEPROM_readint(address);
 //shift read word up
 dword = dword << 16;
 // read lower word from EEPROM and OR it into double word
 dword = dword | EEPROM_readint(address+2);
 return dword;
}

//write word to EEPROM
void EEPROM_writeint(int address, int value) {
 EEPROM.write(address,highByte(value));
 EEPROM.write(address+1 ,lowByte(value));
}

//write long integer into EEPROM
void EEPROM_writelong(int address, unsigned long value) {
 //truncate upper part and write lower part into EEPROM
 EEPROM_writeint(address+2, word(value));
 //shift upper part down
 value = value >> 16;
 //truncate and write
 EEPROM_writeint(address, word(value));
}

unsigned int EEPROM_readint(int address) {
 unsigned int word = word(EEPROM.read(address), EEPROM.read(address+1));
 return word;
}


Ho aggiunti la scrittura di 2 spazi bianchi quando si resetta.
Se prevedi cifre più lunghe aumenta il numero degli spazi ma attenzione a non andare oltre lo schermo altrimenti i numeri non si capiscono perche taglierebbe le cifre.

Per risolvere il problema protesti prendere una EEPROM i2c (http://www.robot-italy.com/it/24lc256i-i2c-eeprom.html) e quando si esaurisce la cambi.
Naturalmente bisognerebbe rivedere il codice.  :smiley-mr-green:
Però si trova molto materiale
--> http://playground.arduino.cc/Code/I2CEEPROM24LC512
--> http://www.hobbytronics.co.uk/arduino-external-eeprom
--> http://playground.arduino.cc/code/I2CEEPROM
--> https://github.com/mikeneiderhauser/I2C-EEPROM-Arduino

rocco8383

Ma quando la eeprom si esaurirà come si comporterà il contatore?Leggerà sempre l'ultimo valore che è riuscito a scrivere?

rocco8383

Anzi se qualcuno è interessato ne ho 3 stecche di queste eeprom, se si paga la spedizione le spedisco

leo72

Una domanda.... siete tutti a pensare come ottimizzare le scritture sulla EEPROM... ma.. rocco: ha pensato anche che questa EEPROM va svuotata perché con 1024 byte e basta non ci scrivi nulla, se la frequenza è di qualche sscrittura al secondo?

rocco8383

Effettivamente leo72 ha ragione.Dovrei montarlo su una pressa che a seconda del lavoro effettuato conterà o meno...ma non con la fequenza da voi immaginata perchè è azionata da due pulsanti, da una persona fisica che dovra caricare e scaricare il pezzo dallo stampo....

leo72

Riesci a quantificare l'utilizzo di questa pressa, nell'arco di una giornata lavorativa?
Salverai poi solo la data e l'ora dell'azionamento, giusto? Oppure anche il codice dell'operatore?

rocco8383

Può esere che lavori per 5 giorni di fila e che poi rimanga ferma per altrettati.Producendo in 8 ore da 500 a 2500Pz

PaoloP


Una domanda.... siete tutti a pensare come ottimizzare le scritture sulla EEPROM... ma.. rocco: ha pensato anche che questa EEPROM va svuotata perché con 1024 byte e basta non ci scrivi nulla, se la frequenza è di qualche scrittura al secondo?


In che senso svuotata?
Trascriverla su un'altra eeprom per continuare a contare?

Non ho capito perché non dovrebbe scrivere??  :smiley-roll-blue:
La scrittura impiega 3,3 ms a byte e ne deve scrivere 4 per un contatore a 32bit. Ne ha dei tempo tra una scrittura e l'altra.

lesto


Ma quando la eeprom si esaurirà come si comporterà il contatore?Leggerà sempre l'ultimo valore che è riuscito a scrivere?


esatto
sei nuovo? non sai da dove partire? leggi qui: http://playground.arduino.cc/Italiano/Newbie

nid69ita

Ma scrivere su una semplice SD o microSD ?
my name is IGOR, not AIGOR

PaoloP


Ma scrivere su una semplice SD o microSD ?


E poi il divertimento dov'è?  :smiley-mr-green:


Anzi se qualcuno è interessato ne ho 3 stecche di queste eeprom, se si paga la spedizione le spedisco


Quali eeprom? Le 24LC256?

Se le hai già allora butto giù il codice per usarle.  8)

nid69ita

azz, ma se deve usare Arduino per lavoro, forse è meglio un modulino x scrivere su SD, non vi pare?  $)
my name is IGOR, not AIGOR

Go Up