Programmatore EEPROM

Il prossimo progetto che vorrei realizzare con Arduino è un programmatore economico per EEPROM tipo W27E512. Ci sono molte cose che non mi sono chiare, ma il primo problema che non so come risolvere è che devo avere la possibilità di switchare liberamente su un pin 5/12/14V, per gestire la lettura/programmazione/cancellazione.

Supponendo di alimentare il tutto a 12V, come genero i 14? E come li switcho?

Puoi benissimo alimentare a 5V, da USB o altra sorgente, e usare uno stepup per ottenere 16V e da qui ricavare i 12V e 14V tramite due piccoli regolatori lineari, bastano 50 mA per la programmazione delle EEPROM, poi li commuti tramite dei mos per piccoli segnali, ottimi gli FDN338 per questo scopo, sono dei canale P dato che devi commutare il positivo.
In alternativa puoi usare uno stepup a tensione variabile che regoli tramite un potenziometro digitale, così non ti servono nemmeno i mos visto che se prendi un ic con enable quando non ti serve la tensione lo spegni.
Semmai vedo il problema del numero pin, le EEPROM con bus parallelo ne richiedono tanti tra data, address e control bus, mi sa che ti tocca andare su un Atmega a 40 pin se vuoi averne a sufficienza anche per pulsanti, led e un eventuale display, molto utile se lo vuoi fare stand alone con lettura dei dati da caricare da SD.

I pin non sono un grosso problema. Ho già fatto un lettore di (((E)E)P)ROM, e ho usato due 595 per pilotare il bus indirizzi, funziona alla grande. Ora si tratta più che altro di capire come pilotare i chip durante la cancellazione/programmazione e come generare queste tensioni.

Mi faresti un esempio pratico dello step-up variabile? Tieni conto che vorrei usare componenti comuni.

Questa è la sezione di alimentazione del mio programmatore di EPROM annata 1990. Ho optato per volgari microrelé 5V con interblocco elettronico.

Per la tua applicazione direi che l'ideale sia l'MCP1661 di Microchip, facilmente reperibile presso tutti i grandi distributori di componente a circa 1E, p.e. da RS,.
LìMCP1661, case SOT23 5 pin quindi facilmente saldabile, ti permette di realizzare un switching step up in grado di fornire più di 100 mA a 12 e 14 V partendo da una tensione in ingresso di 5V, è pensato per lavorare con varie tipologie di batterie quindi può esserti utile anche per altri progetti visto che gli basta una singola cella LiPo o due batterie classiche, 3V input, per generare una tensione out compresa tra 3 e 24 V, fino a 200 Ma per tensioni out minori di 12V.
La tensione in uscita dipende da un partitore resistivo che determina la tensione sul pin Vfb, questa tensione deve essere di 1.227V, il regolatore aggiusta la tensione in uscita in modo da tenere costante questo valore, calcolando opportunamente il partitore è possibile ottenere le varie tensioni in uscita.
Il pin En permette di accendere/spegnere il regolatore, se non ti serve la tensione per la programmazione o per l'erase conviene spegnerlo, in tutti i casi metterei comunque un FDN338 in serie per dare/togliere la Vpp alla EEPROM, il regolatore non cambia tensione in modo istantaneo quindi è meglio prima modificare il valore del partitore, attivare il regolatore da Enable, attendere qualche ms e dare tensione a Vpp tramite il mos.
Lo schema che trovi sul datasheet va bene, però in ingresso e uscita metti condensatori da 100 uF, preferibilmente low esr, con in parallelo il solito condensatore da 100 nF ceramico, per il partitore metti un potenziometro digitale da 50k in serie a 10k fissi su Rbot e una R fissa su Rtop da 680k, in questo modo puoi regolare la tensione in uscita tra ~ 9 e 16 V (ho fatto i conti al volo a mente, sono da confermare facendoli nel giusto modo).

Aggiungo solo una cosa, se non trovi il potenziometro digitale adatto, puoi usare un partitore variabile fatto con resistenze e piccoli mosfet (o transistor, alla peggio) ... nel senso che chiudi la resistenza (o meglio, il trimmer per la taratura) verso massa del partitore con un mosfet, per ottenere il valore che ti serve di volta in volta :wink: ... tanto a te in fondo servono solo due valori, oltre ai 5V che hai gia ... quindi, partitore fisso per i 12V, piu un mos che aggiunge al ramo in parallelo una seconda resistenza, per i 14V ...

Ottimo il consiglio di Astro di usare un mos anche per interrompere la tensione verso la eeprom, alcuni modelli reagiscono male a tensioni che variano, anche se velocemente ...

Per il potenziometro digitale Microchip offre una infinità di modelli, sia I2C che SPI o semplicemente up/down, con valori compresi tra 1k e 50k, tutti a basso costo e facilmente reperibili.

Finite le vacanze, vediamo di prendere in mano questa cosa. Vediamo se ho capito come fare la parte di switching, tanto per incominciare:

Quindi: con A0/A1 (intendo i pin di Arduino) LOW, posso pilotare il pin A0 della EEPROM normalmente tramite il pin 7 di Arduino. Altrimenti metto quest'ultimo in INPUT e mandando A0 o A1 (mai entrambi!) a HIGH posso mettere una tensione più alta sul pin in questione.

Immagino ci vogliano dei pullup sui gate dei MOSFET, ma dove li collego? A 5V o alla tensione che switchano?

Ho idea che sia una tavanata galattica :cold_sweat:.

SukkoPera:
Ho idea che sia una tavanata galattica :cold_sweat:

Solo mezza.
I p-mos conducono quando la tensione di gate è qualche volt più bassa di quella di source, quindi è corretto mettere delle pull-up che collegano il gate al source.

Se fossero messe a 5V la tensione sarebbe troppo bassa e i mos condurrebbero sempre.

Ma... così arriverebbero i 12..14V ai pin di Arduino E il livello alto 5V delle uscite di Arduino vanificherebbe le pull-up, i mos sarebbero ancora sempre accesi.

Basta pilotare i gate dei p-mos con dei transistor NPN con emettitore a massa (o n-mos con source a massa), o con un ULN2003 (lasciando scollegato il terminale comune dei diodi interni).

Tra parentesi, i p-mos potrebbero anche essere accesi contemporaneamente, alla EEPROM arriverebbe la tensione più alta tra le due, e questa tensione non ritornerebbe indietro verso le altre più basse perché ci sono i diodi.

Grazie dei consigli. E se invece dei transistor/ULN mettessi dei diodi tra pin Arduino e gate?

Dico questo per avere il minor numero possibile di componenti diversi.

E aggiungo: deduco che il MOSFET dei 3.75V vada gestito diversamente, ma come?

SukkoPera:
se invece dei transistor/ULN mettessi dei diodi tra pin Arduino e gate?

Se li metti col catodo verso i gate non conducono mai (e i p-mos restano sempre spenti).
Se li metti col catodo verso Arduino arrivano i 12..14V ad Arduino (e i p-mos restano sempre accesi)

Dico questo per avere il minor numero possibile di componenti diversi.

Per questo ho nominato l'ULN, è un solo componente e non servono neppure resistenze su ingressi e uscite.

deduco che il MOSFET dei 3.75V vada gestito diversamente

Per questo si, oltre la pull-up gate/source, basta un diodo con il catodo verso Arduino, i 5V di arduino non raggiungono il gate mentre un livello basso lo porta a 0.6V.

Capito. Version 2:

Ricapitolando (prima avevo sbagliato qualche connessione):

  • A0 mi basta pilotarlo a 0 o 5V.
  • A9 deve poter switchare tra 0/5/14V.
  • /OE deve poter switchare tra 0/5/12/14V.
  • Lasciamo un attimo da parte i 3.75V.

Torna tutto?

Per avere anche il livello zero su A9 e /OE, su questi terminali servono due resistenze di pull-down. Il resto direi che è a posto.

Per compensare le cadute sui p-mos e sui diodi, le tensioni di alimentazione le alzerei a 12.6 e 14.6V (non so da dove provengono e se è fattibile). Se invece i diodi sono schottky allora non serve.

Credo userò degli Schottky (1N5817?), ma in ogni caso otterrò le varie tensioni con step-up regolabili, quindi non sarà un problema ottenere i valori corretti al punto giusto.

Version 3:

Questa dovrebbe essere completa, a meno del quarzo e di un convertitore USB/Seriale.

Considerando che una shiftOut "standard" richiede circa 140µs, ogni indirizzo richiederebbe come minimo 280µs, cioè 18 secondi per passarli tutti.

Gli indirizzi potrebbero invece essere generati con due contatori binari CD4040 in cascata, così basterebbero due comandi (reset e avanzamento) e soprattutto l'avanzamento degli indirizzi sarebbe circa venti volte più veloce.

Se poi gli impulsi di avanzamento si generano con la scrittura diretta dei bit sulle porte, e non usando la normale digitalWrite, si dovrebbe migliorare di altre 20..30 volte (a questo punto sarebbero tutte le altre operazioni ad occupare più tempo).

Alternativa: mantenere comunque gli shift register ma usare la scrittura diretta sulle porte scrivendo una shiftOut ottimizzata, anche in questo caso miglioriamo di almeno venti volte rispetto alla shiftOut standard.

Qualcosa come questa:

#define cbi(sfr, bit) (_SFR_BYTE(sfr) &= ~_BV(bit))
#define sbi(sfr, bit) (_SFR_BYTE(sfr) |= _BV(bit))

//--------------------------------------------------------------------
// Trasmissione MSBFIRST, D3=dati, D4=clock
//--------------------------------------------------------------------
void shiftOut_(byte n){
    for (byte c=0; c<8; c++){
        if ((n & 128) != 0) sbi(PORTD, 3); else cbi(PORTD, 3);
        sbi(PORTD, 4);   // shift clock = 1
        cbi(PORTD, 4);   // shift clock = 0
        n <<= 1;
    }
}

Sì, di questo sono cosciente, ma almeno il primo prototipo sarà così, per alcuni motivi:

  1. Ho una breadboard già cablata così per il mio dumper, e sono un sacco di fili che non ho voglia di spostare :D.
  2. Il dumper di cui sopra ha già anche il codice pronto e debuggato per sparare gli indirizzi in quel modo (vabbeh, saran 5 righe...)
  3. Almeno per il momento, non programmerò ROM più grandi di 64KB, per cui il tempo richiesto è comunque ragionevole.
  4. Al momento non ho CD4040 per le mani.

Comunque se la cosa si dimostra ben funzionante, probabilmente vorrò fare un PCB e sicuramente questa cosa andrà cambiata.

Una domanda: invece di usare transistor per pilotare i MOSFET, non potrei usare direttamente transistor per switchare le "alte" tensioni? In questo modo non risparmierei qualche componente?

I transistor PNP si dovrebbero collegare esattamente come i p-mos e i più servirebbero le resistenze sulla base di tutti.

Una domanda.....
ma vuoi programmare solo le W27E512 ?

Sostanzialmente sì, c'è qualcosa di non troppo incasinato che posso fare per supportare anche altre EEPROM?

Forse restando nella stessa famiglia. Amatorialmente una volta si realizzava un hardware base (dati indirizzi qualche segnale di controllo) e si ponticellavano di volta in volta i pin diversi regolando le tensioni. A far bene c'erano anche kit con "chiavi hardware" specifiche per ogni modello che contenevano i collegamenti necessari/diversi.

Sicuramente a ponticelli è flessibile ma è anche matematico che al momento non ci si ricorda più cosa collegare.

Converrebbe trovare i datasheet delle memorie potenzialmente usabili e confrontare i pin (dovrebbero seguire lo standard jedec), le tensioni, e le modalità di lettura/scrittura (nelle poche memorie che ho provato la verifica non so perché non mi ha mai funzionato anche se i dati erano scritti correttamente).

I programmatori universali hanno molti terminali rinconfigurabili in hardware per generare le tensioni necessarie.