Il modulo Master Synchronous Serial Port di Microchip è utilizzato, nel nostro caso, per implementare due protocolli seriali utilizzati nella maggior parte delle applicazioni di tipo embedded: I2C bus e Serial Peripheral Interface, meglio conosciuto come SPI. In questo articolo, vediamo nei dettagli come il primo di questi diffusissimi protocolli sia stato integrato nella nuova famiglia di micro, l’Enhanced-Mi. L'articolo, tratto dal numero 107 di Firmware, anno 2014, rientra tra i contenuti della Rubrica Firmware Reload contenente approfondimenti e articoli tecnici della passata rivista cartacea Firmware.
LE PERIFERICHE MICROCHIP
Un processore, in modo particolare un microcontrollore, è costruito per essere impiegato nei campi più disparati utilizzando le differenti periferiche per interagire con l’ambiente, ecco perché ogni costruttore cerca di integrare diversi tipi di dispositivi di I/O. Infatti, possiamo trovare le periferiche più svariate quali, ad esempio, un CAN (è un protocollo di comunicazione seriale), un PWM (è un generatore d’impulsi a frequenza costante con duty-cycle variabile), un Pulse Accumulator (è un particolare registro che si incrementa all’occorrenza di ogni impulso in ingresso), un Input Capture (è un misuratore di frequenze esterne, o di intervalli di tempo). In particolare, Microchip ha sempre garantito la presenza di un’interfaccia SPI (Serial Peripheral Interface) e un’I2C bus. Un’interfaccia SPI è, in buona sostanza, una porta seriale sincrona introdotta a suo tempo da Motorola, mentre I2Cbus, o Inter-Integrated Circuit bus, è una semplice interfaccia seriale a 2 fili sviluppata per applicazioni a 8 bit e largamente usata per interfacciare dispositivi esterni. In effetti, un processore come il PIC16F876 di Microchip, dispone di due moduli per le comunicazioni seriali, il MSSP e l’USART, che a loro volta possono funzionare in diverse modalità. Il modulo MSSP, o Master Synchronous Serial Port, è impiegato per le comunicazioni seriali ogni qualvolta abbiamo la necessità di utilizzare dispositivi quali EEPROM, shift-register, convertitori A/D e altri, o con altri MCU. Infatti, è possibile gestire le periferiche ricorrendo a una delle due modalità utilizzate, I2C o SPI, impostando in modo opportuno i diversi registri. Da una parte è possibile ricorrere alla modalità SPI (Serial Peripheral Interface) quando abbiamo l’esigenza di gestire la trasmissione e la ricezione simultanea di 8 bit di dati in modo sincrono ed è configurabile sia in modalità master che slave. Dall’altra, con l’I2C (Inter-Integrated Circuit) è possibile implementare tutte le funzionalità tipiche sia di un modulo master che slave, poiché può operare in entrambi i modi, e gestisce in hardware gli interrupt per determinare se il bus è libero per la comunicazione.
SPECIFICA I2C BUS
Con questo particolare bus è possibile collegare diversi dispositivi esterni attraverso due linee: un clock e una linea dati (in realtà ci potrebbero essere presenti anche alcune linee di abilitazione). Grazie a questo standard, ogni periferica è direttamente indirizzabile perché attraverso un particolare codice d’indirizzo non è necessario utilizzare un decodificatore dedicato: ogni costruttore, al fine di sfruttare le potenzialità di un bus di questo tipo, deve premunirsi del relativo codice. L’architettura di questo bus si basa sul paradigma master/slave: solo il master può fare una richiesta (trasmissione/ricezione) e gestire, di conseguenza, la comunicazione insieme al suo segnale di clock poiché questa tecnica è sincrona.
Non esistono particolari limiti; infatti, in un’architettura di questo tipo possono essere presenti uno o più master insieme a differenti slave opportunamente configurati avendo cura di rispettare la capacità massima del bus. Attraverso questa tecnica è possibile trasmettere dati a una velocità, su un frame da 8 bit, che spazia da 100 Kbit/s fino all’ordine dei Mbit/s, per via della possibilità di sfruttare la modalità High Speed. Non solo, un progettista hardware o firmware può sfruttare l’enorme flessibilità del bus: è possibile inserire o togliere componenti indirizzati senza per nulla modificare il design, per via dell’assenza di periferiche di controllo. Ogni componente che intende sfruttare questo bus deve offrire due pin: SCL (Serial Clock) e SDA (Serial Data). Il primo è utilizzato per offrire il segnale di clock impiegato per la comunicazione sincrona, mentre il secondo è impiegato per trasmettere/ricevere i dati in connessione half-duplex. In effetti, in ambito I2C bus le linee coinvolte nello standard sono, per l’appunto, bidirezionali e devono essere collegate al positivo di alimentazione attraverso resistenze opportunamente dimensionate. In assenza di comunicazione (idle bus), le due linee devono trovarsi ad un livello logico alto: questo indica che il bus non è occupato in trasmissioni/ricezioni in corso ed è così disponibile per iniziare una sessione di lavoro. I dati sulla linea SDA devono essere stabili durante il periodo alto del clock, livello logico 1, mentre può cambiare di valore nel periodo basso (livello logico 0).
Nello standard I2C bus, un componente, sia esso master o slave, deve trovarsi in uno dei seguenti stati: start, stop e restart (anche se da qualcuno è chiamata sequenza di start ripetuto). Qualunque master che intenda iniziare una comunicazione deve trovarsi in una condizione di start: si è in start quando si ha una transizione della linea SDA dal livello logico 1 al livello logico 0, mentre la linea SCL si trova a livello logico 1 (a questo proposito si veda la Figura 2). In seguito, il bus è considerato occupato e non più direttamente impiegabile. Successivamente, al termine del trasferimento dei dati su bus, il master ha la necessità di porre fine all’uso del bus: questo si verifica quando si ha una transizione della linea SDA dal livello logico 0 al livello logico 1, mentre la linea SCL si trova a livello logico 1, sempre Figura 1.

Figura 1: Timing tra le condizioni di start e stop
La condizione di re-start rappresenta un caso particolare, Figura 2. Infatti, a volte può succedere che un master intende tenere occupato il bus per diversi motivi più o meno pressanti e, allo stesso tempo, non intende liberare la risorsa: per fare questo è necessario inviare uno start senza aver generato una condizione di stop.

Figura 2: Condizione di restart
È chiaro che un comportamento di questo tipo è squisitamente software perché, da un punto di vista hardware, questo si realizza inviando uno stop subito successivo ad uno start. I dati, come abbiamo già fatto notare, transitano a richiesta del master sulla linea SDA: un frame dati è composto da 8 bit ed è corretto quando transita il bit più significativo per primo. Non esiste un limite di byte da trasferire/ricevere, ma se eccede il frame è necessario inviare un segnale di acknowledge. Tipicamente in un’architettura sincrona, il segnale di riconoscimento è di fondamentale importanza perché, in caso di scambio dati tra due dispositivi, la mancanza dell’acknowledge ne determina un errore di comunicazione. Il master genera il clock legato al segnale e si aspetta che il trasmettitore, sia esso master o slave, rilasci la linea dati ad un valore logico alto. Allo stesso modo, il ricevitore deve portare a livello logico 0 la linea dati SDA durante l’impulso di clock dell’acknowledge in modo da avere tale condizione stabile durante il suo campionamento sul fronte di salita. È possibile che un dispositivo slave possa non riconoscere l’indirizzo inviato dal master, in questo caso la linea dati deve essere posta a livello alto. In questo modo, il master ha la possibilità di inviare uno stop per interrompere la sessione e generare una condizione di re-start al fine di tentare di instaurare una nuova sessione di lavoro. Può accadere, poi, che un dispositivo slave non riconosca i dati inviati da un master, allora in questo caso lo stesso master deve porsi nella condizione di stop, allo stesso modo se lo slave non risponde con il segnale di acknowledge dopo il primo byte.

Figura 3: Tipica trasmissione Slave

Figura 4: Tipica ricezione Slave
Leggi anche la puntata precedente: I2C Bus con Master Synchronous Serial Port – Parte 1 | Elettronica Open Source



