Scuola Politecnica e delle Scienze di Base
Corso di Laurea in Ingegneria Informatica
Elaborato finale in Misure per l’Automazione e la Produzione Industriale
Programmazione di microcontrollori
STM32: Protocollo SPI e comunicazione
con sensore
Anno Accademico 2014/2015
Candidato:
Antonio Pagano
matr. N46001239
“ Alla nonna Lucia e alla zia
Carolina, le quali hanno sempre
creduto nelle mie capacità ”
Indice
Indice .................................................................................................................................................. III
Introduzione ......................................................................................................................................... 4
Capitolo 1: Serial Peripheral Interface (SPI) ....................................................................................... 5
1.1 Interfaccia................................................................................................................................... 6
1.2 Configurazione master-slave...................................................................................................... 7
1.3 Struttura interna.......................................................................................................................... 8
1.4 Comunicazione sul bus ............................................................................................................ 10
1.5 Modalità Half-duplex ................................................................................................................... 12
Capitolo 2: SPI (STM32F4xx) ........................................................................................................... 13
2.1 Caratteristiche principali .......................................................................................................... 13
2.2 Registri SPI .............................................................................................................................. 15
2.3 Gestione della trasmissione e della ricezione .............................................................................. 22
Capitolo 3: Comunicazione con il sensore (il Giroscopio) ................................................................ 23
3.1 Attivazione PIN e settaggio della modalità.............................................................................. 24
3.2 Trasmissione tra SPI1 e sensore di Giroscopio ........................................................................ 25
Capitolo 4: Esempio di utilizzo del protocollo SPI e comunicazione con il sensore sul
microcontrollore STM32F4xx ........................................................................................................... 27
Bibliografia ........................................................................................................................................ 33
III
Introduzione
L’utilizzo di microcontrollori è sempre più consistente nella società moderna. Tale
successo lo si deve principalmente all’enorme utilizzo che tale componente prevede in
molti dispositivi, anche di uso comune, come ad esempio una lavatrice o un caricabatterie.
I microcontrollori della famiglia STM32 sono tra i più diffusi e utilizzati sul mercato. Tali
dispositivi sono prodotti dalla STMicroelectronics, una società franco-italiana, tra i più
grandi produttori di componenti elettronici al mondo.
In questo elaborato verrà adoperato proprio un microcontrollore STM32 per studiare e
mostrare l’utilizzo di uno dei principali protocolli di comunicazione tra dispositivi: il
protocollo Serial Peripheral Interface (SPI).
In particolare, la trattazione sarà suddivisa in livelli: si mostreranno le caratteristiche
tecniche e teoriche riguardanti il protocollo SPI, per giungere successivamente alla sua
applicazione nei microcontrollori STM32. In particolar modo sarà poi mostrata come
effettuare la comunicazione tra il microcontrollore e il sensore interno di giroscopio
digitale. Viene infine fornito il codice sorgente da caricare sul microcontrollore che
consente di ottenere i valori degli assi di rotazione x, y e z.
4
Capitolo 1: Serial Peripherl Interface (SPI)
SPI (Serial Peripheral Interface) è un bus di comunicazione seriale sincrono sviluppato da
Motorola e utilizzato per comunicazioni tra dispositivi a brevi distanze: tra un
microcontrollore e altri circuiti integrati tra più microcontrollori.
La trasmissione avviene tra un dispositivo detto master e uno o più slave (letteralmente
dall’inglese padrone e schiavo). Il master controlla il bus, cioè ne prende possesso così da
evitare che altri dispositivi possano utilizzarlo mentre questo è occupato. Di seguito,
emette il segnale di clock e decide quando iniziare e terminare la comunicazione, inviando
frames di scrittura/lettura al dispositivo slave. Il protocollo SPI prevede un’architettura
single-master multi-slave.
Per quanto riguarda la velocità di scambio dei dati, essa dipende fortemente dalla scelta
della frequenza di clock, cioè dal numero di impulsi che il segnale di clock genera in un
secondo. Ad ogni impulso generato, si effettua la trasmissione di un bit. Risulta evidente
quindi che tanto più questi impulsi sono frequenti, tanto più velocemente sarà passato il
dato. La frequenza di clock viene settata dal dispositivo master. Non vi è un limite di
velocità minimo, in quanto i dispositivi sono statici: se alimentati possono mantenere uno
stato logico per un tempo indefinito. Vi è tuttavia un limite massimo che va determinato
dai datasheet [1] dei singoli dispositivi connessi.
Il bus SPI di definisce full-duplex in quanto il “colloquio” può avvenire
contemporaneamente sia in trasmissione che in ricezione.
1
Documentazione che riassume le caratteristiche di un componente, un apparato, un software o anche un composto
chimico. Di solito si presenta in formato PDF.
5
1.1 Interfaccia
Il generico dispositivo SPI prevede 4 canali:

SCLK (SCK): Serial Clock;

MOSI: Master Output Slave Input;

MISO: Master Input Slave Output;

CS (SS): Chip Select (Slave Select);
Essendo a 4 canali, il sistema è genericamente detto a 4 fili. Va però tenuto conto che
deve esserci una connessione di riferimento (Vref) e che quindi fisicamente i fili sono
cinque.
Figura 1.1
Nel dettaglio:

SCLK (SCK) è il canale del clock, il quale scandisce gli istanti in cui master e
slave possono trasmettere e ricevere i bit sul bus. Tale canale è gestito dal master,
il quale dunque richiede la trasmissione, di volta in volta, di una “parola”;

MOSI è il canale adoperato per trasmettere il dato dal dispositivo master a quello
slave;

MISO è il canale adoperato per trasmettere il dato dal dispositivo slave a quello
master;

CS (SS) è il canale attraverso cui il master sceglie con quale dispositivo slave
comunicare. Per abilitare la comunicazione è necessario settare il pin SS ad un
livello logico basso (come si nota dalla Figura 1.1, il pin SS è negato, dunque nel
caso sia settato al livello logico alto esso diventa di livello logico basso,
disabilitando la comunicazione).
6
1.2 Configurazioni master-slave
Si mostrano di seguito due configurazioni possibili per il collegamento tra master e slave:
Dispositivi slave controllati singolarmente
Ogni
dispositivo
slave
è
collegato ad un pin con il
segnale SS del dispositivo
master. Il dispositivo master
dovrà avere un numero di pin
SS
pari
al
numero
dispositivi
slaves
Dunque
abilitando
di
collegati.
un
determinato pin SSi, verrà
attivato lo slave corrispondente a tale pin.
Figura 1.2
In definitiva ogni slave si collega al dispositivo master indipendentemente dagli altri
slaves.
Il numero di dispositivi slaves che si possono connettere al bus è limitato esclusivamente
dal numero massimo di linee gestibili dal master.
Il vantaggio di tale soluzione è la velocità di comunicazione tra il master e i singoli slave.
Di contro, lo svantaggio è l’eccessivo numero di pin SS richiesti per tale architettura.
7
Dispositivi slaves connessi in catena (daisy chain)
Il dispositivo master possiede un unico pin SS in uscita ed il segnale che esso pilota è
inviato a tutti i dispositivi slave
sui relativi pin SS. I dispositivi
slave vengono quindi attivati tutti
contemporaneamente,
ma
lavorano in catena: il dispositivo
master invia il dato effettivamente
solo al primo dispositivo slave,
attraverso
il
canale
MOSI.
Figura 1.3
Successivamente,
i
dispositivi
slave comunicano tra loro in cascata, utilizzando i canali MISO e MOSI: lo slave i-1 invia
il dato attraverso il suo canale MISO, mentre lo slave i riceve il dato sul suo canale MOSI.
Tale catena si ripete fino all’ultimo slave, il quale avrà il proprio canale MISO collegato a
quello del master.
Il vantaggio di tale soluzione è l’abolizione di un numero elevato di pin SS a favore di un
unico pin SS che gestisce tutti gli slave. Di contro lo svantaggio è la minore velocità di
aggiornamento dei singoli slaves.
1.3 Struttura interna
Figura 1.4
Ogni dispositivo SPI possiede un registro a scorrimento utilizzato per inviare e ricevere i
dati serializzati. Un registro a scorrimento è un componente molto utilizzato in elettronica
8
digitale: esso è costituito da una serie di flip-flop[2] di tipo D, collegati tra loro in modo
tale che l’uscita del precedente sia l’ingresso del successivo. Un flip-flop di tipo D è
dotato di un ingresso per il dato (D), di un ingresso per la sincronizzazione (clock) e di
un’uscita (Q). Quando riceve il segnale di clock, trasferisce l’ingresso in uscita e lo
mantiene finché non cambia l’ingresso.
Nella sua versione più semplice il registro a scorrimento ha il seguente funzionamento: ad
ogni colpo di clock, ogni flip-flop passa il proprio valore al successivo ed il primo flipflop della catena assume il valore del segnale di ingresso al registro. Il valore
precedentemente memorizzato nell'ultimo flip-flop viene assegnato al segnale di uscita del
registro a scorrimento. Lo scorrimento può avvenire dal bit più significativo verso quello
meno significativo, o viceversa.
In SPI, usualmente tale registro ha una dimensione di 8 bit, ma in generale potrebbe avere
dimensione arbitraria, a patto che siano di uguali dimensioni il registro del dispositivo
master e quello slave. Se si suppone un trasferimento da parte del master verso lo slave, il
dato contenuto nell'ultimo flip-flop verrà trasmesso sul canale MOSI. Nel dispositivo
slave, a sua volta, il canale MOSI sarà collegato al primo flip-flop del suo registro a
scorrimento. I dati avanzano nei due registri a scorrimento utilizzando la sincronizzazione
del segnale SCLK inviato dal dispositivo master. L'ultimo flip-flop del registro a
scorrimento del dispositivo slave, a sua volta, è collegato al segnale in uscita MISO. I dati
pervenuti nel dispositivo master e provenienti dal dispositivo slave, sul segnale MISO,
saranno caricati a loro volta nel primo flip-flop del registro a scorrimento del master.
L'architettura interna composta dai registri a scorrimento, unita alla configurazione delle
interconnessioni dei segnali MISO e MOSI, consentono di realizzare un anello chiuso.
2
Circuito elettronico sequenziale utilizzato in elettronica digitale come cella di memoria elementare
9
Proprio tale architettura ad anello permette ai dispositivi SPI di effettuare una
comunicazione di tipo full-duplex.
Nei dispositivi commerciali è possibile configurare la direzione dei dati trasmessi dal
registro a scorrimento: in un caso si ha che il primo bit ad essere trasmesso è quello più
significativo, viceversa si ha quello meno significativo.
1.4 Comunicazione sul bus
La comunicazione tra master e slave avviene seguendo nell’ordine le seguenti operazioni:
1. Il dispositivo master, nel caso in cui il dispositivo slave sia controllato
singolarmente, seleziona lo slave con cui comunicare settando il segnale SS
corrispondente al livello logico basso (logica 0-Attiva). Nel caso di un’architettura
di tipo slaves in catena, il master setta il suo unico segnale SS al livello logico
basso;
2. Il master invia il segnale di clock, configurandolo ad una frequenza tale che tutti i
dispositivi possano supportarlo;
3. Ad ogni ciclo di clock avviene la comunicazione: il master invia il primo bit del
dato attraverso il canale MOSI, insieme al segnale di clock;
4. Il dispositivo slave riceverà il segnale di clock e il primo bit sul canale MOSI,
interpretandolo come l’inizio della comunicazione. In contemporanea invierà un
altro dato sul canale MISO.
Notiamo come la comunicazione tra i due dispositivi sia effettivamente seriale, in quanto
sia sul canale MISO che su quello MOSI sarà trasmesso un solo bit alla volta. Tuttavia, i
dispositivi compiono effettivamente un tipo di comunicazione in parallelo, in quanto
verranno passati due bit in contemporanea: uno sul canale MOSI, uno sul canale MISO.
Questo implica che ogni dispositivo invierà il suo bit più significativo (o meno
significativo in base alla direzione dello scorrimento del registro) e riceverà in
contemporanea un bit che verrà posto come bit meno significativo (o più significativo) sul
registro.
10
Si è detto che il dispositivo master setta la frequenza del segnale di clock. Esso deve
inoltre configurare la sua polarità, ovvero il valore logico su cui si porta il segnale di
clock quando questo è inattivo, e la sua fase, ovvero il fronte di clock in cui il ricevente
campiona il segnale in ingresso. Tali attributi sono settabili attraverso due parametri:
CPOL per la polarità, CPHA per la fase.
Le possibili combinazioni sono le seguenti:
1. CPOL = 0, CPHA = 0: Il dato è catturato sul fronte di salita e propagato sul fronte
di discesa del clock
2. CPOL = 0, CPHA = 1: Il dato è catturato sul fronte di discesa e propagato sul
fronte di salita del clock
3. CPOL = 1, CPHA = 0: Il dato è catturato sul fronte di discesa e propagato sul
fronte di salita del clock
4. CPOL = 1, CPHA = 1: Il dato è catturato sul fronte di salita e propagato sul fronte
di discesa del clock
Figura 1.5
11
1.5 Modalità Half-duplex
Come si è detto, il protocollo SPI implementa implicitamente la modalità full-duplex.
Tuttavia alcune implementazioni dei dispositivi supportano la modalità half-duplex: il
dispositivo master e il dispositivo slave comunicano tra loro su un unico canale detto SISO
(Slave input Slave output), il quale può essere bidirezionale in presenza di un dispositivo
slave che trasmette dati verso il master oppure no.
12
Capitolo 2: SPI (STM32F4xx)
I SoC[3] della famiglia STM32F4xx, prodotti da ST Microelectronics, supportano e
implementano il bus SPI. Essi posseggono 3 periferiche per l’utilizzo di SPI: SPI1, SPI2,
SPI3. Il dispositivo indicato con SPI1 è connesso al bus APB2 a 84MHz, mentre gli altri
due (SPI2 e SPI3) sono connessi al bus APB1 a 42MHz. Tramite l’interfaccia di tali
dispositivi è possibile la trasmissione seriale sincrona dei dati verso i dispositivi esterni al
System-on-a-Chip. Oltre alla modalità full-duplex, è supportata anche la modalità halfduplex.
2.1 Caratteristiche principali
Attraverso l’interfaccia SPI dei dispositivi forniti dalla famiglia STM32F4xx, è possibile
settare le seguenti caratteristiche:

Modalità full-duplex per la trasmissione dei dati utilizzando tre canali (SCK,
MISO e MOSI);

Modalità half-duplex per la trasmissione monodirezionale o bidirezionale su due
canali;
3

Lunghezza delle frame di 8-bit o 16-bit;

Modalità operative master o slave;

8 prescaler per la regolazione del baud rate (fPCLK/2 max);

Selezione del dispositivo slave in hardware o software (NSS);

Configurazione in software dei parametri CPOL e CPHA;
System-on-a-chip (sistema su circuito integrato), è un circuito integrato in cui un solo chip contiene un intero sistema.
13

Configurazione in software della direzione di trasferimenti dei dati (prima il bit più
significativo, o prima quello meno significativo);

Flag nei registri di stati dedicati alle interruzioni;

Generazione e controllo in hardware del CRC[4];

Controllo degli errori con flag e interruzioni (master mode fault, overrun e CRC).
L'interfaccia possiede 4 canali principali:
1. MOSI: Linea dati per la trasmissione dei dati dal dispositivo master a quello slave;
2. MISO: Linea dati per la trasmissione dei dati dal dispositivo slave a quello master;
3. SCK: Serial clock inviato dal dispositivo master a quello slave;
4. NSS: Linea di controllo utilizzata per la selezione del dispositivo slave.
La struttura di SPI su STM32F4xx è fornito dal seguente diagramma a blocchi:
Figura 2.1
4
Cyclic redundancy check (controllo a ridondanza ciclica), metodo per il calcolo delle somme di controllo (checksum).
Utilizzato per il controllo sulla trasmissione dei dati.
14
2.2 Registri SPI
Nel seguito saranno mostrati come settare i registri del microcontrollore STM32F4xx
riguardanti SPI, per configurare le varie caratteristiche.
In particolare verranno utilizzati i seguenti registri:

SPI_CR1

SPI_CR2

SPI_SR
Selezione del dispositivo in modalità master o slave
Il dispositivo seleziona la sua modalità di master o di slave attraverso la configurazione
del bit MSTR del registro SPI_CR1. Settando tale bit al livello logico 1, il dispositivo
opererà in modalità master; settato al livello logico 0, il dispositivo sarà configurato in
modalità slave.
Gestione della selezione dello slave (NSS)
La selezione del dispositivo slave può avvenire sia in hardware che in software. Tale scelta
si effettua configurando il bit SSM (Software Slave Management) nel registro SPI_CR1:
se il bit viene settato al valore logico 1, la selezione dello slave è fatta in software, se
settato a 0, la selezione è fatta in hardware. Se la selezione è fatta in software, il valore del
bit SSI (Internal Slave Select) viene forzato sul pin NSS, ignorando il valore che
quest’ultimo possedeva: in questo modo, dunque, il dispositivo (che opererà in modalità
15
slave) verrà selezionato in base alla configurazione software presente nel bit SSI.
Ricordiamo che per essere attivo, lo slave deve avere livello logico basso su SS, per cui il
bit SSI deve essere settato a 0 per attivarlo. Il valore del bit SSI viene ignorato nel caso in
cui il bit SSM non sia stato settato.
Se la selezione è fatta in hardware, invece, il pin NSS può essere configurato come input o
output, a seconda che si tratti rispettivamente di un dispositivo slave o master. Se
configurato come output (dunque per la modalità master), la periferica piloterà
opportunamente questo segnale al livello logico basso (logica 0-attiva) quando è
necessario selezionare il dispositivo slave a cui è collegato. A questo punto il dispositivo
master è pronto per il trasferimento dei dati e il dispositivo slave agirà da tale, a valle della
rilevazione del passaggio del livello logico alto -> basso del segnale NSS. Il segnale NSS
dovrà essere al livello logico basso durante tutta la durata della trasmissione della frame.
Configurazione baud rate
E’ prevista la possibilità di selezionare 8 possibili configurazioni di baud rate attraverso
l’interfaccia SPI. Tanto più alto sarà il baud rate, cioè la velocità con cui viaggiano i dati,
tanto meno tempo sarà impiegato per la comunicazione.
Il baud rate è definito come: fPCLK / 2 max
dove fPCLK è la frequenza del segnale di clock (SCK), e max equivale a 2i, con i che varia
nell’intervallo [1, 8].
Sono messi a disposizione 3 bit, corrispondenti a BR[2:0], del registro SPI_CR1 (i bit 3, 4
e 5), per selezionare il baud rate desiderato. Le possibili configurazioni sono:
16
Configurazione parametri CPOL e CPHA (clock polarity e clock phase)
Al fine di determinare gli istanti temporali di propagazione e cattura del dato sui canali
MISO e MOSI, è possibile configurare la polarità e la fase del clock dando luogo a quattro
possibili modalità operative differenti, così come visto precedentemente. I due parametri
CPOL e CPHA sono configurabili nel registro SPI_CR1, attraverso i bit CPOL e CPHA.
Dal settaggio di tali bit, si determinano, dunque, se la lettura del dato deve avvenire sul
fronte di salita o discesa e se il livello logico idle del segnale di clock deve essere quello
basso oppure alto.
Si noti inoltre che siccome il segnale SCK è mappato su un pin in uscita per il master
(entrata nel caso dello slave) mediante GPIO, è necessario configurare una resistenza di
pull-up nel caso in cui CPOL=1 o una resistenza di pull-down nel caso in cui CPOL=0. Il
dispositivo master e quello slave devono configurare questi due parametri allo stesso
modo.
Lunghezza della frame e direzione
L'interfaccia può lavorare con frame di dimensione differenti. È possibile configurare la
lunghezza del frame (singola trasmissione) usando il bit DFF del registro SPI_CR1: se
impostato a 0, la frame di trasmissione/ricezione sarà di 8-bit, viceversa di 16-bit. La
direzione di trasferimento (prima il bit più significativo o prima quello meno significativo)
è configurabile, invece, utilizzando il bit LSBFIRST nel registro SPI_CR1: se settato a 0
la trasmissione inizia dal bit più significativo, se settato a 1 dal bit meno significativo.
Modalità half-duplex
L’interfaccia SPI in STM32F4xx prevede la possibilità di utilizzare la modalità halfduplex. Con tale modalità è possibile utilizzare un unico canale per la trasmissione delle
informazioni. Tale trasmissione può essere bidirezionale, cioè i dati possono essere
17
trasferiti dal master allo slave e viceversa, o monodirezionale, ovvero i dati possono essere
trasferiti esclusivamente dal master allo slave.
Nella modalità half-duplex, inoltre, i canali vengono ridotti da 4 a 3, in quanto si userà un
unico canale per la trasmissione: il MOSI se si tratta del dispositivo master, il MISO se si
tratta di quello slave. L’interfaccia sarà costituita allora dai canali SCK, MOSI/MISO,
NSS.
Si mostrano quindi i bit da configurare per la modalità half-duplex di tipo:

Bidirezionale: si setta a 1 il bit BIDIMODE del registro SPI_CR1. Si può inoltre
configurare la direzione del trasferimento attraverso il bit BIDIOE, sempre del
registro SPI_CR1; se posto a 1, la direzione sarà di output per quella periferica
(uscente), se posto a 0 sarà di input (entrante).

Monodirezionale: si setta il bit BIDIMODE a 0. La direzione del trasferimento
viene impostata dal bit RXONLY del registro SPI_CR1; se posto a 0, la
trasmissione sarà dal master allo slave, se posto a 1, la trasmissione sarà di sola
ricezione, quindi il master sarà in grado esclusivamente di ricevere i dati dallo
slave. Si noti che, anche nel caso in cui il master sia in modalità di sola ricezione,
lo slave, prima di cominciare la trasmissione, dovrà comunque attendere la
selezione sul segnale NSS e rilevare il cambiamento di fronte sul segnale SCK.
Data Register (DR)
Il registro SPI_DR mantiene i dati ricevuti o da trasmettere durante la comunicazione
attraverso SPI. Tale registro è suddiviso in due buffer: uno dedicato alla trasmissione,
Trasmission buffer (Tx buffer), e uno dedicato alla ricezione, Receive buffer (Rx buffer).
In caso di scrittura su SPI_DR, il dato sarà scritto sul Tx buffer; in caso di lettura su
SPI_DR, sarà letto il dato tenuto sul Rx buffer.
18
Tale struttura è chiarita dal particolare dello schema a blocchi di figura 2.1:
Figura 2.2
Si ricordi inoltre che SPI prevede la selezione di due formati diversi di frame: 8-bit o 16bit. Nel caso in cui la lunghezza della frame sia di 8-bit, i buffers saranno di soli 8-bit,
corrispondenti agli 8 bit meno significativi del registro SPI_DR, e solo tali bit saranno
utilizzati per la ricezione/trasmissione.
Generazione e controllo del CRC
Per
garantire
trasferimenti
affidabili,
l'interfaccia
SPI
nei
SoC
della
famiglia STM32F4xx implementa in hardware il calcolo e la verifica del CRC.
Il calcolo avviene serialmente su ogni bit, attraverso l’utilizzo di un polinomio di grado n1, dove n è il numero di bit della frame da verificare. E’ possibile settare il polinomio
generatore del codice CRC nel registro SPI_CRCPR. Ricordiamo che le frames possono
essere di 8 o 16 bit, dunque il polinomio sarà al massimo di grado 15.
La generazione e il controllo del CRC è abilitata settando il bit CRCEN nel registro
SPI_CR1. Durante una trasmissione, il codice CRC viene calcolato serialmente e riposto
19
nel registro SPI_TXCRCR. Quindi ad ogni bit trasmesso, si calcolerà il corrispettivo CRC,
il quale verrà memorizzato nell’apposita locazione del registro SPI_TXCRCR.
Quando si è in procinto di trasferire l'ultimo byte della sequenza dei dati, se i trasferimenti
sono gestiti dalla CPU e non da un dispositivo DMA, il software dovrà settare il bit
CRCNEXT sul registro SPI_CR1 e, in hardware, verrà caricato lo shift-register (registro a
scorrimento) con il codice CRC calcolato fino ad allora e riposto nel registro
SPI_TXCRCR. In questo modo, dunque, il codice CRC viene trasmesso come ultimo byte
(se il formato della frame è su 8-bit) dopo aver trasmesso i dati. In maniera del tutto
analoga avviene la fase di ricezione e controllo del CRC: alla ricezione dell'ultimo byte, se
la ricezione è gestita dalla CPU e non da un dispositivo DMA, sarà necessario settare in
software il bit CRCNEXT. Dopodiché l'hardware controllerà se il codice CRC ricevuto
come ultimo byte è uguale a quello generato in ricezione e riposto nel registro
SPI_RXCRCR.
Eventuali errori scaturiti dal fallimento del controllo, ricezioni o trasferimenti errati del
CRC verranno indicati dall'hardware attraverso il flag CRCERR del registro SPI_SR.
Opzionalmente è possibile abilitare un'interruzione nel caso si manifestino errori settando
il bit ERRIE nel registro SPI_CR2.
20
Interruzioni
L'interfaccia SPI presenta sette eventi interrompenti, ognuno indicato da appositi flag del
registro SPI_SR. Gli eventi interrompenti sono i seguenti:

TXE: il buffer in trasmissione (Tx buffer) è stato svuotato ed è possibile caricare
altri dati;

RXNE: il buffer in ricezione (Rx buffer) è stato caricato con un nuovo dato e può
essere letto;

MODF: master mode fault event. Può accadere quando il dispositivo è impostato
come master e il segnale NSS viene settato a 0 (in modalità di selezione dello slave
in hardware) o quando il bit SSI è settato a 0 (in modalità di selezione dello slave
in software);

OVR: errore di overrun. Può accadere quando sono stati ricevuti nuovi dati e il flag
RXNE è ancora alto, ovvero il buffer in ricezione non è stato ancora letto dal
software mediante il registro SPI_DR;

CRCERR: errore di controllo o ricezione/trasferimento errato del codice CRC;

BSY: busy flag. Si verifica quando il bus SPI è occupato oppure se il buffer Tx
(buffer di trasmissione) non è vuoto;

FRE: frame format error. Errore scatenato da un formato di frame non supportato.
Si noti che i bit UDR e CHSIDE del registro SPI_SR non sono utilizzati dal SPI.
21
2.3 Gestione della trasmissione e della ricezione
Di seguito si mostrano gli eventi caratterizzanti la trasmissione e la ricezione attraverso
SPI.

Trasmissione:
1. Il dato è caricato (in parallelo) dal bus APB al Tx buffer interno;
2. Il bit più significativo del Tx buffer (o quello meno significativo) è posto
sul segnale in uscita;
3. La trasmissione comincia appena il dispositivo slave ha ricevuto la
variazione del segnale SCK;
4. I restanti 7 bits (se la frame è impostata su 8-bit) o 15 bits (se la frame è
impostata su 16-bit) vengono caricati nello shift-register e inviati uno per
volta sul segnale in uscita;
5. Quando i dati dal Tx buffer vengono caricati nello shift-register, viene
settato il flag TXE nel registro SPI_SR ad indicare che il buffer è vuoto ed
è possibile caricare altri bit nel buffer per la trasmissione successiva;
6. Opzionalmente, se settato il bit TXEIE nel registro SPI_CR2, verrà lanciata
la relativa interruzione

Ricezione:
1. Quando il trasferimento è completo, i dati vengono trasferiti dallo shift-
register al Rx buffer;
2.
Dopo
l'ultimo
bit
ricevuto,
viene
settato
il
flag
RXNE
nel
registro SPI_SR ad indicare che il buffer in ricezione non è vuoto;
3. Opzionalmente, se settato il bit RXNEIE nel registro SPI_CR2, verrà
lanciata la relativa interruzione;
4. I dati ricevuti possono essere letti dalla periferica con un'operazione di
lettura sul registro SPI_DR. Ciò provocherà, in hardware, il reset del flag
RXNE.
22
Capitolo 3: Comunicazione con il sensore (il Giroscopio)
Un giroscopio è un dispositivo che usa la gravità terrestre per determinare l’orientamento.
Esso è costituito da un disco a forma toroidale, chiamato rotore, libero di ruotare intorno
ad un asse di simmetria che lo attraversa
centralmente e che termina con due punte che
fungono da perni di rotazione. Tali perni sono
inseriti in due fori presenti in un giunto
cardanico[5]. Tramite un sistema di giunti
cardanici, vengono collegati all’asse di rotazione
3 anelli metallici, disposti perpendicolarmente tra
loro. Tali giunti permettono al giroscopio di
effettuare qualsiasi movimento, mantenendo però
fisso il baricentro.
Il principio su cui si basa il funzionamento di un giroscopio è quello secondo il quale, in
assenza di momenti di forze esterne, il vettore momento angolare[6] si conserva[7] e ciò
comporta che l’orientamento nello spazio dell’asse di rotazione rimanga invariato. Tale
comportamento prende nome di inerzia giroscopica.
Se il dispositivo è messo in rapida rotazione con una cordicella, avvolta lungo l’asse di
rotazione, si osserva che tale asse mantiene invariata la direzione per la notevole inerzia
5
Il giunto cardanico o giunto di Cardano è un quadrilatero articolato spaziale. Esso permette di trasmettere il moto tra
due assi in rotazione i cui prolungamenti sono incidenti in un punto.
6
Grandezza di tipo vettoriale, legata alle rotazioni spaziali.
7
Principio fisico che afferma che il momento angolare è costante nel tempo se è nullo il momento delle forze esterne
che agiscono su esso.
23
del giroscopio. Inoltre, se si sollecita un giroscopio in rotazione con una forza, il suo asse
non si muove nella direzione della forza, ma tende a muoversi in una direzione ad essa
perpendicolare.
Per tali motivi, il giroscopio è utilizzato per misurare e mantenere l’orientamento.
Applicazioni tecnologiche del giroscopio si riscontrano nelle bussole giroscopiche
(girobussole) presenti a bordo di aerei o di navi, attraverso le quali si riescono a
stabilizzare i mezzi sui quali si trovano quando questi cambiano direzione. Sono alla base
inoltre dei modellini radiocomandati (ad esempio droni), in cui prevedono l’uso di un
giroscopio montato nella ruota motrice, così da poter mantenere l’equilibrio. Inoltre è
spesso presente negli smartphone, i quali sfruttano la sua capacità di captare ogni minimo
movimento del dispositivo per svariate applicazioni (sicurezza, giochi, etc…).
I microcontrollori della famiglia STM32F4xx, prevedono un sensore interno di giroscopio
digitale, capace di fornire le misurazioni delle rotazioni rispetto all’asse x, y e z. La
comunicazione tra il microcontrollore del SoC con tale sensore viene effettuata attraverso
il protocollo SPI.
3.1 Attivazione PIN e settaggio della modalità
Si è detto che i microcontrollori STM32F4xx prevedono 3 bus SPI: SPI1, SPI2, SPI3.
Supponiamo da ora in poi di utilizzare SPI1.
In generale SPI necessita la configurazione di 4 PIN, uno per ogni canale (SCK, MISO,
MOSI, NSS). Nel caso specifico in cui la comunicazione deve avvenire tra il
microcontrollore e il sensore di giroscopio, si setta come master il microcontrollore
stesso, mentre si setta come slave il sensore. La comunicazione tra microcontrollore e
sensore avverrà attraverso il PIN PE3, settato in modalità di output. Tale PIN fungerà da
NSS: infatti settandolo a 0 si abiliterà la trasmissione (logica 0-attiva), settandolo a 1 si
disabiliterà.
Inoltre, è necessario settare i PIN di SPI1 così da avere un canale MISO, un canale MOSI
e un canale SCK.
24
In particolare è necessario settare i PIN PA5, PA6, PA7 nella modalità alternativa AF05,
così come mostrato nella seguente tabella:
Figura 3.1
3.2 Trasmissione tra SPI1 e sensore di Giroscopio
La trasmissione tra SPI1 e Giroscopio funziona nel seguente modo:
1- Abilito il canale di comunicazione attraverso il pin P3 per avviare la trasmissione;
2- SPI1 aspetta che possa mandare la richiesta. Invia quindi la richiesta del registro del
Giroscopio da cui vuole ricevere i dati;
3- Il giroscopio invia un messaggio di conferma;
4- SPI1 riceve tale messaggio e risponde con un altro messaggio di conferma;
5- Il giroscopio manda il dato effettivo;
6- SPI1 riceve il dato, il quale viene salvato in un’apposita variabile;
7- Si termina la comunicazione bloccando il canale di comunicazione.
Tale processo deve essere effettuato due volte per ogni asse. Il sensore del giroscopio,
infatti, memorizza ogni asse in due registri: ad esempio la rotazione sull’asse x è
memorizzata nei registri OUT_X_L e OUT_X_H. Questo implica che per ottenere i valori
degli assi x, y e z sarà necessario effettuare i passi da 1 a 7 per sei volte.
25
I registri a cui accedere per ottenere i valori degli assi sono mostrati nella seguente tabella:
Figura 3.2
Si noti inoltre che la modalità con cui si deve accedere ai registri deve essere in lettura; per
ottenere ciò è necessario effettuare una or tra il registro a cui si accedere e il valore
esadecimale 0x80.
26
Capitolo 4: Esempio di utilizzo del protocollo SPI e
comunicazione con il sensore sul microcontrollore STM32F4xx
Di seguito è mostrato il codice sorgente riguardante la programmazione del
microcontrollore STM32F4xx con il quale si utilizza il protocollo SPI per ottenere i valori
degli assi di rotazione x, y e z, attraverso la comunicazione con il sensore del giroscopio.
#include "stm32f4xx.h"
short int data;
short int cont = 8;
short x;
short y;
short z;
#define N 1000
#define CS_LO (uint16_t) 0x8
//Definizione abilitazioni
#define GPIOACKEN (uint32_t) 0x1
#define GPIOECKEN (uint32_t) (1<<4)
#define SPI1CKEN (uint32_t) (1<<12)
// Definizione porte GPIOA
#define PA7_AF (uint32_t) (1<<15)
#define PA6_AF (uint32_t) (1<<13)
#define PA5_AF (uint32_t) (1<<11)
27
#define PA5_SCK (uint32_t) (5<<20)
#define PA6_MOSI (uint32_t) (5<<24)
#define PA7_MISO (uint32_t) (5<<28)
#define PA5_50MHZ (uint32_t) (1<<15)
#define PA6_50MHZ (uint32_t) (1<<13)
#define PA7_50MHZ (uint32_t) (1<<11)
#define PA5_PD (uint32_t) (1<<15)
#define PA6_PD (uint32_t) (1<<13)
#define PA7_PD (uint32_t) (1<<11)
// Definizione porte GPIOE
#define PE3_DO (uint32_t) (1<<6)
int main (void){
// Abilitazione periferiche
RCC->AHB1ENR |= (GPIOACKEN|GPIOECKEN); //attiva porta A e porta E
RCC->APB2RSTR |= SPI1CKEN;
//il registro APB2RSTR è un registro di
reset. Si setta a 1 il bit di SPI1 per resettarlo
RCC->APB2RSTR &= !((uint32_t)SPI1CKEN);
//abbassa il bit dell'SPI1 a 0 così
non avverrà più il reset
RCC->APB2ENR |= SPI1CKEN;
//attiva l'ISP1
// Configurazione GPIOA
GPIOA->MODER |= (PA5_AF|PA6_AF|PA7_AF); //setta i PIN PA5 PA6 PA7 in
modalità alternata
GPIOA->AFR[0] |= (PA5_SCK|PA6_MOSI|PA7_MISO); //setta la configurazione
delle funzioni alternate. AFR[0] corrisponde al registro AFRL. Setta per ogni PIN i
corrispondenti bit a 0101, impostando la configurazione AF05. Importando la
configurazione AF05 per ogni PIN si imposta la modalità da usare sull'SPI, come si
può verificare dal DataSheet
GPIOA->OSPEEDR |= (PA5_50MHZ|PA6_50MHZ|PA7_50MHZ);
//setta la
velocità di ogni PIN a 50MH
28
GPIOA->PUPDR |= (PA5_PD|PA6_PD|PA7_PD);
//setta i PIN in Pull-
Down
// Configurazione GPIOE
GPIOE->MODER |= PE3_DO;
//seleziona il PIN PE3 come
output
// Configurazione SPI1
SPI1->CR1 |=1<<9;
//SSM=1; si abilita la selezione dello slave via
software
SPI1->CR1 |=1<<8;
//setta a 1 il bit SSI (se si imposta SSM=1, SSI deve
essere settato a 1)
SPI1->CR1 |= 0x18;
//si imposta il baud rate a 1/16 (più è alto il baud rate
più velocemente riceve/trasmette)
SPI1->CR1 |=1<<2;
//si abilita il bit MSTR, in pratica si imposta il
microcontrollore in modalità master
SPI1->CR1 |= 1<<6;
//SPI attivo
while(1){
//lettura di X
GPIOE->ODR &= !(CS_LO); // setta a 0 il CH SELECT
while(((SPI1->SR)&0x2)==0);
//attende che il buffer di
trasmissione sia vuoto
SPI1->DR = (uint16_t) (0x80|0x28);
//"punta"
il
registro
OUT_X_L del giroscopio in modalità lettura;
while(((SPI1->SR)&0x1)==0);
//attende che il buffer di
ricezione sia vuoto
data = SPI1->DR;
//legge il dato ricevuto. Il dato letto non ha
rilevanza, ma è necessario eseguire tale istruzione altrimenti il buffer
di
ricezione non si libera
while(((SPI1->SR)&0x2)==0);
//attende che il buffer di
trasmissione sia vuoto
29
SPI1->DR = (uint16_t) 0x1;
//invia un dummy
while(((SPI1->SR)&0x1)==0);
//attende che il buffer di ricezione sia
vuoto
data = SPI1->DR;
//riceve il valore X_L
GPIOE->ODR |= CS_LO;
//setta a 1 il CH SELECT
x =( uint16_t)data;
//copia il dato letto da X_L sui bit da 0
a 7 della variabile x
GPIOE->ODR &= !(CS_LO);
while(((SPI1->SR)&0x2)==0);
SPI1->DR = (uint16_t) (0x80|0x29);
//"punta"
il
registro
OUT_X_H del giroscopio in modalità lettura;
while(((SPI1->SR)&0x1)==0);
data = SPI1->DR;
while(((SPI1->SR)&0x2)==0);
SPI1->DR = (uint16_t) 0x1;
while(((SPI1->SR)&0x1)==0);
data = SPI1->DR;
//riceve il valore X_H
GPIOE->ODR |= CS_LO;
x|=(uint16_t)data<<8;
//copia il dato letto da X_H sui bit da 8 a 15
della variabile x
//lettura di Y
GPIOE->ODR &= !(CS_LO);
while(((SPI1->SR)&0x2)==0);
SPI1->DR = (uint16_t) (0x80|0x2A);
//"punta" il registro
OUT_Y_L del giroscopio in modalità lettura;
while(((SPI1->SR)&0x1)==0);
30
data = SPI1->DR;
while(((SPI1->SR)&0x2)==0);
SPI1->DR = (uint16_t) 0x1;
while(((SPI1->SR)&0x1)==0);
data = SPI1->DR;
//riceve il valore Y_L
GPIOE->ODR |= CS_LO;
y=(uint16_t)data;
GPIOE->ODR &= !(CS_LO);
while(((SPI1->SR)&0x2)==0);
SPI1->DR = (uint16_t) (0x80|0x2B);
//"punta" il registro
OUT_Y_H del giroscopio in modalità lettura;
while(((SPI1->SR)&0x1)==0);
data = SPI1->DR;
while(((SPI1->SR)&0x2)==0);
SPI1->DR = (uint16_t) 0x1;
while(((SPI1->SR)&0x1)==0);
data = SPI1->DR;
//riceve il valore Y_H
GPIOE->ODR |= CS_LO;
y|=(uint16_t)data<<8;
//lettura di Z
GPIOE->ODR &= !(CS_LO);
while(((SPI1->SR)&0x2)==0);
SPI1->DR = (uint16_t) (0x80|0x2C);
//"punta" il registro OUT_Z_L
del giroscopio in modalità lettura;
while(((SPI1->SR)&0x1)==0);
data = SPI1->DR;
31
while(((SPI1->SR)&0x2)==0);
SPI1->DR = (uint16_t) 0x1;
while(((SPI1->SR)&0x1)==0);
data = SPI1->DR;
//riceve il valore Z_L
GPIOE->ODR |= CS_LO;
z=(uint16_t)data;
GPIOE->ODR &= !(CS_LO);
while(((SPI1->SR)&0x2)==0);
SPI1->DR = (uint16_t) (0x80|0x2D);
//"punta" il registro OUT_Z_H
del giroscopio in modalità lettura;
while(((SPI1->SR)&0x1)==0);
data = SPI1->DR;
while(((SPI1->SR)&0x2)==0);
SPI1->DR = (uint16_t) 0x1;
while(((SPI1->SR)&0x1)==0);
data = SPI1->DR;
//riceve il valore Z_H
GPIOE->ODR |= CS_LO;
z|=(uint16_t)data<<8;
}
}
32
Bibliografia
[1]
STMicroelectronics group, RM0368 Reference manual, 835, 2014
[2]
STMicroelectronics group, PM0214 Programming manual, 245, 2014
[3]
STMicroelectronics group, MEMS motion sensor: three-axis digital output
gyroscope, 44, 2012
33
Scarica

Elaborato Pagano Antonio N46001239