Lettura contemporanea di tutti pin digitali inpostati a INPUT

Salve a tutti del forum,
sto facendo un sw con arduino.

Il progetto consiste nella lettura contemporanea di 8 bit (1byte binario) di una periferica e registrarlo in un file, per iniziare va bene anche il Monitor.

Come collegamenti: Arduino ha i primi 8 pin digitali (0 a 7) connessi con la periferica (con massa in comune). In più c’è un’altro pin digitale (pin 8) connesso al pin enable della periferica.

La periferica in un tempo passato si connetteva ad un PC tramite porta parallela.

Praticamente, quando il pin enable si porta allo stato logico 1, Arduino ha l’intero byte stabile da acquisire e memorizzare/monitorare.

Ritornando alla programmazione, nella funzione setup() ho impostato i PIN interessati (da 0 a 8) come: pinMode(0, INPUT_PULLUP);

pinMode(8, INPUT_PULLUP);

Nella funzione Loop() eseguo un controllo sulla lettura del pin digitale 8. Se la lettura restituisce 1 Arduino deve leggere l’intero byte (0 a 7) e stamparlo/memorizzarlo.

Da tutti gli esempi che ho visto, esiste la funzione “digitalRead(pin);” che opera su un singolo pin.

Domanda: esiste una funzione per ottenere il byte intero in un unico ciclo? (anche se restituisce un char va bene lo stesso).

Chiedo questo perchè potrei avere un treno di byte (con una frequenza inferiore a quella di Arduino da memorizzare. Usare ‘n’ digitalRead(pin) per poi costruire il byte di output, temo che potrei perdere qualche byte.

Ovviamente, nei prossimi giorni, il pin enable della periferica sarà connesso al pin digitale di Arduino che è utilizzabile come interrupt con la apposita funzione.

Vi ringrazio per ever letto, ancor di più se mi date un feedback.

NI …
… ovvero, non esiste una funzione del framework “wiring” di Arduino, ma, se i pin che usi, fanno tutti parte dello stesso PORT fisico della MCU (ogni MCU ha una serie di PORT che corrispondono a gruppi di PIN), allora, lavorando a basso livello con i comandi PORT e PIN la cosa è fattibile.

Ovviamente occorre studiarsi come è fatta la MCU, quali PORT contiene, ogni PORT quali PIN mette a disposizione, come sono chiamati in Arduino, collegare gli otto fili agli otto PIN dello stesso PORT ed allora, con una sola istruzione si possono sia leggere che scrivere contemporaneamente tutti e otto.

Ti allego un documento da studiare …

Guglielmo

Manipoliamo direttamente le porte logiche di una MCU.pdf (226 KB)

… ti allego anche un altro documento con le varie corrispondenze dei pin sul ATmega328P.

Guglielmo

atmega328v3_0.pdf (341 KB)

Per Arduino Uno (ATmega328p), da 0 a 7 sono PD0...PD7 e li leggi con un semplice PIN:

byte lettura=PIND;

N.B.: PIN viene dichiarato di sola lettura; in realtà, però, può anche essere usato per invertire lo stato di uno o più pin di uscita.

Per rimanere in tema, un pinmode in blocco puoi farlo con
DDRD=0x00;
e puoi attivare le resistenze di pull-up con
PORTD=0xFF;
All'accensione, comunque, le porte sono impostate di default come ingressi.

>Datman: ... magari, lasciare la gente "ragionare" e "capire" i documenti che gli si è forniti, prima di dare la "pappa fatta" sarebbe meglio. Cortesemente tienne conto per il futuro (... o dovrò cominciare a cancellare i post, REGOLAMENTO, punto 16.13) ... Grazie !

Guglielmo

Beh... Gli ho solo esplicitato le basi, ma ancora c'è molto altro da sapere sul tema, eh! :slight_smile:
Mi ricordo le difficoltà che ho avuto io all'inizio, non sapendo nemmeno che cosa c'era da sapere, perché purtroppo è impossibile trovare un testo completo! Ci sono da conoscere

  • i comandi di Arduino
  • i comandi AVR
  • il datasheet
  • il C (++)
    Non esiste un testo che raccolga tutto e spieghi tutto dall'inizio alla fine. È come dover frequentare 4 o 5 corsi per arrivare alla laurea.
    Ciò è dimostrato dalla mole di programmi scritti in maniera molto approssimativa che si trovano in rete.

Datman:
... Mi ricordo le difficoltà che ho avuto io all'inizio, non sapendo nemmeno che cosa c'era da sapere, perché purtroppo è impossibile trovare un testo completo! Ci sono da conoscere ...

Guada che bastava che studiasse quanto gli ho allegato per capire come fare ... magari leggili i documenti allegati prima di rispondere. :wink:

Guglielmo

Ok, grazie a tutti per le risposte e mi sto leggendo i documenti (non si finisce mai di imparare).

Ho a disposizione sia Arduino Uno e sia Arduino Mega 2560.

Ma ho anche due bordine che utilizzano MCP23017 (vecchia conoscenza in quanto le ho utilizzate con il Raspberry). Gli MCP utilizzano due interrupt INTA e INTB quando qualche pin di un bus cambiano di stato.

Comunque i documenti passati sono molto importanti e non avendo precedenti con Arduino (qualche giorno), nella programmazione posso fare affidamento alla conoscenza del ANSI C e dei libri di arduino acquistati.

Quindi ringrazio gbp01 in quanto ha capito che mi servono documentazione più che soluzione, ma ringrazio anche Datman per le risposte pratiche.

Grazie e a presto.

Io in questo caso specifico andrei anzi su PORTB (se non si usa l’SPI) o su PORTC poiché su PORTD ci sono due pin connessi a qualcosa di indispensabile in base a quanto dichiarato nel primo messaggio :wink:

8 bit insieme sono solo su D. Per l'interrupt, se veramente è indispensabile, mi sembra che ci sia modo di usare anche altri pin.

Hai parzialmente ragione sul 328 il C espone solo 7 bit, ma il B ne espone otto e il problema di D non è l'interrupt ma il fatto che lui vuole usare il monitor seriale

gpb01:
Ti allego un documento da studiare ...

Interessante, grazie

Federico

fabpolli:
La porta B espone otto bit

PB6 e PB7 nel formato DIL28 sono usati per il quarzo, quindi per averli disponibili dovrebbe usare l'oscillatore RC interno.

Già hai ragione mi era sfuggito, allora stando così le cose non ha possibilità se non rinuncia alla comunicazione seriale

Se proprio serve, può usare softwareSerial.

Vero ma abbisogna di un adattatore e non della connessione che utilizza per caricare il programma sulla UNO, è bene precisarlo onde evitare fraintendimenti