Il 0% ha trovato utile questo documento (0 voti)
30 visualizzazioni59 pagine

Corso RP2040

Il documento descrive i servizi di progettazione e realizzazione PCB offerti da Futura Group, evidenziando la scheda FTR2040 basata sul chip RP2040 di Raspberry Pi. Viene fornita una panoramica delle caratteristiche tecniche della scheda e delle procedure per il montaggio e la programmazione, inclusi suggerimenti per l'uso di MicroPython e Arduino. Inoltre, si menziona la disponibilità di un kit di avviamento per facilitare l'apprendimento e l'uso della scheda.
Copyright
© © All Rights Reserved
Per noi i diritti sui contenuti sono una cosa seria. Se sospetti che questo contenuto sia tuo, rivendicalo qui.
Formati disponibili
Scarica in formato PDF, TXT o leggi online su Scribd
Il 0% ha trovato utile questo documento (0 voti)
30 visualizzazioni59 pagine

Corso RP2040

Il documento descrive i servizi di progettazione e realizzazione PCB offerti da Futura Group, evidenziando la scheda FTR2040 basata sul chip RP2040 di Raspberry Pi. Viene fornita una panoramica delle caratteristiche tecniche della scheda e delle procedure per il montaggio e la programmazione, inclusi suggerimenti per l'uso di MicroPython e Arduino. Inoltre, si menziona la disponibilità di un kit di avviamento per facilitare l'apprendimento e l'uso della scheda.
Copyright
© © All Rights Reserved
Per noi i diritti sui contenuti sono una cosa seria. Se sospetti che questo contenuto sia tuo, rivendicalo qui.
Formati disponibili
Scarica in formato PDF, TXT o leggi online su Scribd
Sei sulla pagina 1/ 59

Programmare

con RP2040
SERVIZIO DI SERVIZIO DI
PROGETTAZIONE REALIZZAZIONE PCB
L’area R&D di Futura Grazie al Servizio di
Group studia, progetta realizzazione PCB potrai
e realizza prototipi ricevere i tuoi circuiti
per differenti settori stampati semplicemente
utilizzando tecnologie caricando sul nostro sito
innovative. Il team Futura il tuo Gerber e scegliendo
Group è composto, oltre le dimensioni e le
che dal personale dei nostri caratteristiche preferite.
laboratori tecnici, anche È possibile ordinare
da un numero elevato schede a una singola
di collaboratori esterni, faccia oppure
ciascuno specializzato nel multistrato, scegliendo
proprio settore. anche il colore del solder.

Trasformiamo
le tue idee in realtà!
FUTURA ELETTRONICA È IL TUO PARTNER DI RIFERIMENTO PER MOLTEPLICI SERVIZI.
I NOSTRI TECNICI SONO A TUA DISPOSIZIONE PER FORNIRE TUTTE LE INFORMAZIONI
E UNA VALUTAZIONE PERSONALIZZATA IN BASE ALLE TUE NECESSITÀ.

SERVIZIO SERVIZIO
TAGLIO LASER STAMPA 3D
Futura Elettronica Futura Elettronica mette
offre la possibilità di a disposizione le proprie
realizzare mediante stampanti 3D FDM PROGRAMMARE CON RP2040
taglio laser i tuoi (fused deposition
progetti in plexiglass modeling), per chi
(o metacrilato) con intende realizzare un
spessore massimo di oggetto tridimensionale
10 mm e con dimensioni con dimensioni fino a
massime lavorabili 40x40x40 cm partendo
di 130×90 cm. Carica da un modello 3D
sul nostro sito il digitale. Carica sul
tuo file .DXF, scegli nostro sito il tuo file .STL,
le dimensioni e le scegli le dimensioni e le
caratteristiche preferite. caratteristiche preferite.

Futura Group srl


www.futurashop.it Via Adige, 11 • 21013 Gallarate (VA)
Tel. 0331/799775
Programmare con

RP2040

d i P IE R C
ALDERAN

PUNTATA
N. 1

Conosciamo e impariamo ad usare il nuovo chip RP2040 grazie alla


scheda Raspberry Pi Pico e una board custom perfettamente compatibile
con l’ambiente di programmazione previsto da Raspberry Pi Foundation.

L
e ottime caratteristiche della scheda • 264 kB di SRAM su chip in sei banchi indipendenti;
Raspberry Pi Pico, unite alle dimensioni, • supporto per un massimo di 16 MB di memoria
ridotte come fa presagire il nome, rendono Flash off-chip tramite bus QSPI dedicato;
PROGRAMMARE CON RP2040

tale hardware molto interessante per un • controllore DMA;


vasto pubblico. Per questa ragione abbiamo pensato • architettura AHB (AMBA High-performance Bus);
di dedicare un corso all'utilizzo e alla programmazio- • periferiche con interpolatore e divisore intero;
ne di tale scheda, ma come siamo soliti fare, invece • regolatore LDO (Low Drop Out) programmabile su
di un corso sulla scheda Raspberry Pi Pico, abbia- chip per generare la tensione del core;
mo preferito costruirne una nostra, chiamandola • 2 PLL (Phase-Locked Loop) su chip per generare il
FTR2040. clock USB e core;
Si tratta di una scheda costruita attorno allo stesso • 30 pin GPIO, di cui quattro utilizzabili come in-
microcontrollore RP2040 di Raspberry Pi, ma con gressi analogici;
caratteristiche pensate più per il maker e il progetti- • 2 UART;
sta di hardware personalizzato. • 2 controller SPI;
Le caratteristiche del chip RP2040 sono: • 2 controller I²C;
• Dual ARM Cortex-M0+ a 133MHz; • 16 canali PWM;

1
SCHEMA ELETTRICO
Prima di procedere è opportuno spendere qualche paragrafo
per esporvi come è fatta la nostra board FTR2040, iniziando
con la descrizione dello schema elettrico, il quale è proposto
nella pagina qui accanto. Come potete intuire, il cuore della
scheda è il chip RP2040, siglato U1 nello schema elettrico;
si tratta di un potente microprocessore del quale rendiamo
disponibili sui pad laterali della scheda i GPIO e le linee prin-
cipali, nonché l'USB (pin 39, 40, 41, 42). Il clock che scandisce
il funzionamento dell'U1 è ricavato grazie al quarzo Q1 e ai
condensatori Q5 e Q6, connessi ai piedini di temporizzazio-
 Fig. 1 - La scheda FTR2040. ne 29 e 21, che appartengono all'oscillatore principale e cui
si connettono i componenti esterni. L'alimentazione per il
chip è ricavata dal regolatore a basso drop-out U3, il quale,
• controller USB 1.1 e PHY, con modalità host e device; ricava 3,3V stabilizzati. Grazie ai diodi Schottky (utilizzati per
• 8 PIO state machines. minimizzare la caduta di tensione) D1 e D2, come fonte di ali-
mentazione principale si possono utilizzare i 5V in arrivo dalla
La scheda FTR2040 (la vedete nella Fig. 1) viene fornita in connessione USB o quelli provenienti dal contatto 5V. In altre
versione “decidi-tu-cosa” saldare, ovvero con i pin saldabili parole, il circuito può essere alimentato attraverso la porta
secondo necessità: per esempio, se volete sperimentare USB o il pin 5V, ma è anche possibile connettere la presa USB
inserendo la scheda in una breadboard, potete saldare i pin in (attraverso la specifica breakout board) mentre il circuito è
modo che si vedano le serigrafie sul lato superiore. alimentato dai suoi pad di alimentazione, proprio grazie alla
Attenzione però a saldare i pin in alto e in basso sul lato presenza degli Schottky, che impediscono ad una tensione
opposto perché altrimenti non riuscirete a infilare la scheda di andare sulla linea dell'altra. Completiamo l'analisi dello
nella breadboard. Per contenere le dimensioni della scheda, schema elettrico con l'integrato siglato U2, il quale altro non
viene resa disponibile una piccola breakout board per imple- è che l'indispensabile memoria Flash EPROM da 64Mbit ad
mentare la connettività USB; in pratica, la breakout ospita il accesso seriale, con modalità DUAL e QUAD SPI; come vedete,
connettore USB tipo A e dispone di quattro pad per collegarlo, è interfacciata all'RP2040 attraverso una connessione Serial
mediante altrettanti fili, alla nostra scheda. Così, una volta Peripheral Interface a 4 linee più 2 segnali di controllo. Que-
programmata la scheda per il progetto finale, potete elimina- sta memoria Flash serve a caricare i firmware che scriveremo
re il breakout USB. e a contenere eventuali dati da memorizzare a permanenza,
La scheda nuda e cruda potrà essere comodamente saldata utili alle applicazioni che andremo a realizzare con la nostra
su un PCB di vostra creazione. board, sia durante questo corso, sia in autonomia.

PROGRAMMARE CON RP2040

 Fig. 2 - La confezione e il contenuto di Pico Starter Kit.

2
PROGRAMMARE CON RP2040

| schema ELETTRICO

3
far parte un saldatore a punta molto fine, una stazione ad
aria calda per lavorazione di SMD e BGA (la classica ed econo-
mica hot-air station in versione basic va sempre bene...) delle
pinzette per posizionare i componenti prima della saldatura,
del filo sottilissimo di stagno (diametro non superiore a 0,5
mm) o della pasta-salda per SMD, una lente d'ingrandimento
per verificare il posizionamento del chip RP2040 prima di
saldarlo e tutte le saldature effettuate (alla ricerca di baffi di
stagno che potrebbero costituire cortocircuiti) e della pasta
flussante.
Il montaggio deve iniziare dal chip RP2040, che è il compo-
nente più impegnativo e che va posizionato, rispettando il
verso indicato nel piano di montaggio che vedete nella pagina
accanto, ben centrato sulle rispettive piazzole, preventiva-
mente cosparse di stagno e poi di pasta flussante; fatto ciò,
scaldandolo con la stazione ad aria calda, si salderà quando
avrete visto lo stagno brillare, allorché toglierete il getto
d'aria calda.
La saldatura della Flash dovrà essere fatta similmente. Per il
resto dei componenti, tutti molto più semplici, potrete proce-
dere con il saldatore, sempre dopo aver stagnato e cosparso
di flussante le piazzole.
Terminato il montaggio e verificato, con l'aiuto della lente
d'ingrandimento che sia tutto a posto, la scheda è pronta per
l'uso. Possiamo quindi scordarci l'hardware ed entrare nel
 Fig. 3 - La piedinatura della scheda FTR2040.
vivo della sua programmazione.
Chi, tra voi, non ha l'attrezzatura o non se la sente di costruire
REALIZZAZIONE DELLA BOARD da sè il circuito, non deve disperare perché Futura Elettronica
Il modulo FTR2040 può essere autocostruito seguendo (www.futurashop.it) rende disponibile la scheda FTR2040 già
il piano di montaggio illustrato nella pagina qui accanto montata e collaudata.
e scaricando, per ottenere il relativo PCB, le relative trac-
ce rame dalla sezione Download del nostro sito Internet LO SVILUPPO SOFTWARE
www.elettronicain.it, tra i file di questo corso. Similmente a quanto previsto per la board Raspberry Pi Pico,
Il circuito stampato è un doppia faccia che richiede una per lo sviluppo del software relativo alle applicazioni della
certa competenza per essere realizzato, ma che potete farvi nostra FTR2040, è disponibile l’SDK C/C++ di Raspberry Pi o
preparare da un servizio di circuiti stampati on-line come il MicroPython.
PCBPRODUCTION di Futura Elettronica. In ogni caso, per il La programmazione del caso può essere effettuata utilizzan-
montaggio serve un minimo di attrezzatura, della quale deve do qualsiasi piattaforma, anche se è consigliabile l’uso di una

PROGRAMMARE CON RP2040

 Fig. 5 - La cartella con i due file all’interno della cartella


 Fig. 4 - La finestra per montare l’unità rimovibile.
della scheda.

4
| piano di MONTAGGIO
Elenco Componenti:
R1, R7, R8: 10 kohm (0603)
R2, R4: 1 kohm (0603)
R5, R6: 27 ohm (0603)
R3: -
C1, C3, C4, C10: 100 nF ceramic (0603)
C9: 1 µF ceramic (0603)
C2: 10 µF 6,3 VL tantalum (2012)
C5, C6: 22 pF ceramic (0603)
C7, C8: 10 µF ceramic (0603)
D1, D2: MBR0520LT1G (SOD123)
Q1: Crystal 12MHz (3.2x2.5 mm)
U1: RP2040
U2: W25Q64JVXGIQ TR
U3: MIC5317-3.3YM5-TR

scheda Raspberry Pi, almeno per le prime volte. siasi altra scheda basata su chip RP2040 come Raspberry
In questo corso esploreremo MicroPython, l’ambiente C/C++ pi Pico (Fig. 2). La confezione (kit) in vendita online su
e anche l’ambiente Arduino, giacché è possibile programmare www.futurashop.it con il codice RPICOKIT, comprende una se-
l’RP2040 tramite l’IDE di Arduino. La possibilità di program- rie di componenti elettronici utili a realizzare gli esperimenti
mare la scheda tramite il popolare IDE Arduino, semplice descritti in questo corso, oltre alla scheda Pico.
e molto utilizzato, è un ulteriore punto a favore del nostro
progetto perché lo avvicina anche a chi ha meno dimestichez- PREPARAZIONE DELLA SCHEDA FTR2040
za con gli altri tool. Per utilizzare in pratica la board, bisognerà prepararla in base
a come verrà impiegata; per prima cosa, vi consigliamo di
RP2040 STARTER KIT saldare i pin strip in dotazione nelle piazzole di I/O e alimen-
Per facilitarvi a seguire questo corso in maniera costruttiva tazione, per l'inserimento in una breadboard o su un altro
fin da subito, abbiamo preparato uno speciale Pico Starter circuito stampato. Fatelo stando attenti a saldare sul lato
kit, che può essere utilizzato con la nostra scheda e qual- opposto i pin per la connessione con la breakout USB.
PROGRAMMARE CON RP2040

 Fig. 6 - La finestra principale di Thonny.

5
 Fig. 7 - La scelta dell’interprete MicroPython per Pico.

Per il collegamento USB, vi consigliamo di usare una prolun- Una volta montata l’unità, apparirà una cartella con all'inter-
ga maschio femmina A/A per collegare la scheda al computer. no due file, come mostrato nella Fig. 5:
Anche se è possibile programmare la scheda usando un com-
puter qualsiasi, per comodità abbiamo preferito una scheda • INDEX.HTM
Raspberry Pi 4 connessa in VNC con un PC. • INFO_UF2.TXT
Questo facilita un po’ di cose, soprattutto perché potete
lavorare subito con la scheda usando Thonny, ovvero l’editor Il file INFO_UF2.TXT riporta semplicemente la versione del
per Python e MicroPython preinstallato nel sistema operati- bootloader e il tipo di scheda, mentre il file INDEX.HTM è
vo Raspberry Pi. un link alla documentazione di Raspberry Pi Pico: https://ra-
Se guardate la serigrafia della scheda (Fig. 3) individuate la spberrypi.com/device/RP2?version=E0C9125B0D9B.
scritta “BOOT” che è l’abbreviazione per “boot selector” ovve-
ro selettore di avvio. INSTALLAZIONE DI MICROPYTHON
Prima di collegare la presa USB a Raspberry Pi, dovete Aprite il file INDEX.HTM con Chromium di Raspberry Pi e an-
cortocircuitare il pin BOOT a massa (quindi il pin 5 a un pin date nella pagina della documentazione di Raspberry Pi Pico.
GND qualsiasi). In questo modo la scheda viene abilitata alla Selezionate la scheda “MicroPython” per aprire la sezione
programmazione. specifica di MicroPython. MicroPython è un’implementazione
Dopo aver collegato la scheda FTR2040 alla presa USB completa del linguaggio di programmazione Python 3 che
apparirà un finestra di notifica che vi avverte di montare il viene eseguito direttamente su hardware embedded come
dispositivo come unità rimovibile (Fig. 4). Facendo clic su OK, Raspberry Pi Pico e quindi anche la nostra scheda.
la scheda verrà montata come un’unità rimovibile e a questo Se non avete mai usato MicroPython potete visitare il link
punto potete togliere il corto fra BOOT e GND. MicroPython Wiki nella stessa pagina (https://github.com/mi-
cropython/micropython/wiki).
Nella sezione MicroPython selezionate il link “downloadable
UF2” per scaricare il firmware MicroPython.
Verrà scaricato nella cartella Download un file UF2
(USB Flashing Format) con un nome simile a “rp2-pico-
20220117-v1.18.uf2”. Si tratta di un file che serve a installare
MicroPython per Pico/RP2040.
Aprite un’altra finestra del file manager e recatevi nella car-
tella Download. Trascinate il file con l’estensione “.uf2” nella PROGRAMMARE CON RP2040
finestra dell’unità rimovibile. Una volta rilasciato il file, verrà
installato automaticamente MicroPython e l’unità rimovibile
verrà smontata automaticamente. Dopo alcuni secondi la
cartella scomparirà dal File Manager.

PROGRAMMAZIONE CON MICROPYTHON


Per semplicità di spiegazione e soprattutto per facilitare
l’approccio ai principianti, oggi parleremo solo della program-
mazione con MicroPython e non C/C++.
Dal suo lancio nel 1991, il linguaggio di programmazione
 Fig. 8 - L’installazione dell’interprete MicroPython per Pico. Python è cresciuto fino a diventare uno dei più popolari al
mondo. Il linguaggio Python è stato sviluppato per sistemi

6
tor. Fra le tante c’è anche l’italiano. Da qui in avanti i riferi-
menti e le figure sono relativi all’interfaccia utente in italiano
e la modalità dell’interfaccia utente “Regular”. La scelta della
modalità si trova sotto Strumenti > Opzioni > Generali > Mo-
dalità UI. L’area centrale dell’editor è dedicata agli script, dove
vengono praticamente scritti tutti i programmi in linguaggio
Python e/o MicroPython. La parte inferiore è la cosiddet-
ta Python Shell che consente di digitare singole istruzioni
che vengono eseguite non appena premete il tasto INVIO e
fornisce anche informazioni sugli script in esecuzione, per
esempio, le istruzioni print, gli errori di esecuzione eccetera.
Thonny può essere avviato dal menu Programmazione di
 Fig. 9 - Il LED collegato alla scheda FTR2040. Raspberry Pi. Per impostare Thonny come interprete per
Pico, fate clic nella parte inferiore destra della finestra in
corrispondenza della scritta con il nome dell’interprete e della
informatici di qualsiasi tipo e grandezza, ma i microcontrollori versione, per “Python 3.9.2”.
come RP2040 sono piccoli, più semplici e con una quantità Nell’elenco che appare, selezionate “MicroPython (Raspberry
di memoria notevolmente inferiore, il che significa che non Pi Pico)” (Fig. 7). Questa opzione è presente anche in Stru-
possono eseguire lo stesso codice Python delle controparti menti > Opzioni > Interprete.
più grandi. Fatto questo, si aprirà una finestra (Fig. 8) dalla quale instal-
È qui che entra in gioco MicroPython. Sviluppato origina- lare o aggiornare MicroPython nel Pico.
riamente da Damien George e rilasciato per la prima volta
nel 2014, MicroPython è un linguaggio di programmazione IL PRIMO PROGETTO
compatibile con Python, ma sviluppato specificamente per i Il piccolo microcontrollore RP2040 è stato progettato pen-
microcontrollori, da qui il nome. Include molte delle funziona- sando al calcolo fisico. I suoi numerosi pin di input/output
lità di Python, aggiungendone di nuove progettate specifica- (GPIO) per uso generico consentono di comunicare con una
mente per sfruttare le funzionalità disponibili su RP2040. vasta gamma di componenti, consentendo di creare progetti
Se avete già programmato con Python, troverete MicroPy- anche molto complessi.
thon immediatamente familiare. In caso contrario, è un Non vogliamo soffermarci su print (“Hello World!”) e altre
linguaggio che vi consigliamo di imparare. istruzioni di Python che già dovreste conoscere. Concentria-
moci piuttosto sul primo progetto “fisico” con Pico.
THONNY
Prima di iniziare a programmare Raspberry Pico o l'FTR2040 BLINK DI UN LED
con MicroPython, dovrete configurare un ambiente di svilup- Per capire come funziona il tutto, vi consigliamo di scrivere
po integrato (IDE). nell’editor di Thonny queste poche righe che servono a far
Thonny (Fig. 6) è un popolare ambiente IDE per Python e Mi- lampeggiare a intervalli di un secondo un LED collegato al
croPython ed è precaricato nel sistema operativo Raspberry pin GP25 (che corrisponderebbe al LED interno di una scheda
Pi. Se invece volete utilizzare Pico con una diversa distribu- Pico) (Fig. 9). Ricordatevi di mettere una resistenza da 220 Ω
zione Linux, o usare Windows o macOS, potete scaricare dal in serie al LED. Per chi non lo sapesse, il codice di Python va
sito ufficiale “https://thonny.org” il programma di installazione indentato seguendo l’esempio seguente:
del bundle Thonny e Python per il relativo sistema operativo
PROGRAMMARE CON RP2040

o le istruzioni di installazione per Linux. import machine


Thonny integra tutti gli strumenti necessari per scrivere e import utime
sviluppare software in un’unica interfaccia utente. Anche se
esistono molti altri ambienti IDE per Python, vi consigliamo di led = machine.Pin (25, machine.Pin.OUT)
utilizzare solo Thonny per la programmazione di RP2040.
Nella parte superiore dell’interfaccia utente di Thonny potete while True:
vedere la barra degli strumenti, che offre un sistema di ac- led.value (1)
cesso rapido basato su icone e un menu per l’accesso a varie utime.sleep (1)
funzionalità del programma. Il menu appare solo in moda- led.value (0)
lità “Regular” ed “Expert”, per cui è consigliabile fare clic su utime.sleep (1)
“Switch to regular mode” in alto a destra alla prima apertura
di Thonny. In questo modo potrete accedere al menu Tools e La prima riga di codice import machine è la chiave per
cambiare altre opzioni come, per esempio, la lingua dell’edi- lavorare con MicroPython su RP2040. La libreria “machine”

7
 Fig. 10 - Selezione della scheda Arduino Nano RP2040 Connect.

PROGRAMMARE CON RP2040

 Fig. 11 - Selezione della scheda Raspberry Pi Pico.

8
 Fig. 12 - Il menu parziale del pacchetto non ufficiale con le schede RP2040 compatibili.

contiene tutte le istruzioni necessarie a MicroPython per co- All’interno del ciclo while, l’istruzione led.value (1) accenderà
municare con Pico e altri dispositivi compatibili, estendendo il il LED collegato, mentre l’istruzione led.value (0) lo spegnerà.
linguaggio per il calcolo fisico. L’istruzione utime.sleep (1) imposta il ritardo a 1 secondo fra
Senza questa riga, non sarete in grado di controllare nessuno i due stati.
dei pin GPIO di Pico e, nel nostro caso, non potremo accende-
re il LED collegato al pin GP25. LIBRERIA UTIME INVECE DI TIME
Nella riga successiva del programma potete cambiare il pin a Invece di importare la classica libreria time di Python per cre-
piacere collegandolo a un altro pin: are temporizzazioni e ritardi, qui viene usata la libreria utime
(u sta per la lettera µ = micro).
PROGRAMMARE CON RP2040

led = machine.Pin (25, machine.Pin.OUT) Si fa notare che la libreria utime è una versione progettata
per microcontrollori e anche se si importa la libreria time,
Questa riga definisce un oggetto chiamato led, che è un nome MicroPython utilizzerà automaticamente la libreria utime.
puramente descrittivo. È ovviamente possibile utilizzare
qualsiasi nome, ma è meglio attenersi a nomi che descrivono ESECUZIONE DEL PROGRAMMA
lo scopo della variabile, per rendere il programma più leggibi- Per eseguire il programma basta fare clic sul pulsante Esegui
le e comprensibile. o F5 da tastiera o dal menu Esegui. Vi verrà chiesto di salvare
L’istruzione machine.Pin(25, machine.Pin.OUT) chiama la il programma sul computer locale oppure nella scheda. Salva-
funzione della libreria per gestire i pin GPIO della scheda: te il file nella scheda con il nome “blink_test.py”, per esempio.
• il primo argomento, 25, è il numero del pin che si sta con- Se non avete commesso errori, vedrete il LED lampeggiare a
figurando; intervalli di un secondo. Premete l’icona Stop per fermare il
• il secondo, machine.Pin.OUT, dice al pin deve essere usato programma e il lampeggio del LED.
come output. Se volete che il lampeggio del LED continui, eseguite il pro-

9
 Fig. 13- Casella URL aggiuntivi per il Gestore schede.

gramma senza premere Stop. Potete quindi uscire anche da digitale e commuta semplicemente tra on e off: se il pin è alto,
Thonny. toggle() lo disattiva; se è basso, toggle() lo attiva.
Se volete che il programma venga eseguito in autostart, Basta solo collegare nella breadboard un LED a un pin GPIO
alimentandolo anche da un’altra sorgente, dovete salvarlo qualsiasi.
sempre con il nome “main.py” all’interno della scheda. Per esempio, potete modificare l’istruzione precedente con la
Attenzione che quando si parla dei pin GPIO di RP2040, di seguente per controllare un LED collegato a GP15 scrivendo:
solito vengono indicati con i loro nomi completi: per esempio,
GP25 indica il pin GPIO 25. led_external = machine.Pin (15, machine.Pin.OUT)
In MicroPython, le lettere GP devono essere eliminate, quindi
nel programma bisogna scrivere “25” anziché “GP25”, altri- PROGRAMMARE L’RP2040 CON L’IDE DI ARDUINO
menti non funzionerà. Il modo più semplice per i nuovi utenti è utilizzare MicroPy-
thon. Per gli utenti più esperti, un modo più avanzato è
BLINK CON TOGGLE scrivere codice in C/C++.
C’è anche un altro modo per gestire il lampeggio del LED. C'è un terzo modo in cui possiamo scrivere codice per il
Se si usa la funzione toggle della libreria machine potete nostro RP2040, e cioè tramite l'IDE di Arduino, che molti PROGRAMMARE CON RP2040
ottenere lo stesso risultato con le seguenti righe di codice: conoscono e che trovano senza dubbio più semplice del C++.
Per programmare l’RP2040 con l’IDE di Arduino si può proce-
import machine dere in tre modi, tutti validi, ma con sostanziali differenze:
import utime 1. selezionare la scheda Arduino Nano RP2040 Connect;
2. installare il pacchetto ufficiale RP2040;
led = machine.Pin (25, machine.Pin.OUT) 3. installare il pacchetto non ufficiale RP2040.

while True: Metodo 1


led.toggle() Questo metodo prevede semplicemente la selezione della
utime.sleep (1) scheda Arduino Nano RP2040 Connect dal menu Strumenti
> Scheda > Arduino Mbed OS Nano Boards (Fig. 10). Si tratta
La funzione toggle() è disponibile su tutti i pin di uscita di una scheda Arduino perfettamente compatibile con il chip

10
RP2040, come quello della nostra scheda. IL NOSTRO PRIMO SKETCH PER RP2040
L’unico neo è che gli esempi del menu File sono relativi solo Per vedere se tutto funziona come atteso, vi consigliamo di
alla suddetta scheda Arduino. caricare il solito Blink dal menu esempi dell’IDE di Arduino.
Quando collegate la scheda FTR2040 con il cavo USB, ricor-
Metodo 2 datevi di cortocircuitare momentaneamente il pin BOOT a
Questo metodo prevede l’installazione del pacchetto per massa, come fatto in precedenza. Questo installerà una porta
RP2040 ufficiale ovvero quello reso disponibile da Arduino seriale che sarà disponibile nel menu Strumenti.
(Fig. 11). Dal menu Gestore schede basta cercare Pico e si Selezionate questa porta per caricare lo sketch. In
potrà installare il pacchetto per la scheda Raspberry Pi Pico. un Mac il nome della porta sarà qualcosa di simile a
Anche in questo caso gli esempi sono dedicati alla scheda /dev/cu.usbmodem (Raspberry Pi Pico) mentre, nel caso di
Raspberry Pi Pico, ma la cosa non trascurabile è che questo un computer Windows potrebbe essere ad esempio COM6
pacchetto risulta deprecato. (Raspberry Pi Pico).
Premete il pulsante Carica per compilare e caricare il codice
Metodo 3 nella scheda.
Questo metodo prevede l’installazione del pacchetto per Durante il caricamento sentirete il tipico suono di scollega-
RP2040 non ufficiale. Cosa significa? È un pacchetto svi- mento della porta USB. Se tutto è andato bene vedrete il
luppato da Earle F. Philhower III che ha reso disponibile nel messaggio: “Caricamento completato”.
suo GitHub l’installazione per (praticamente) tutte le schede Dopo il caricamento vedrete il LED collegato al pin 25 della
esistenti, basate sul chip RP2040 (Fig. 12). scheda che inizia a lampeggiare a intervalli di 1 secondo.
Il pacchetto non ufficiale di Earle F. Philhower III è preferibile
rispetto agli altri e sarà quello che useremo in questo corso. CONCLUSIONI
A oggi è quello che fornisce più opzioni di programmazione Bene, per il momento ci fermiamo qui. Con la speranza di
con la gestione di tutte le schede di diverso tipo ma con lo essere stati sufficientemente chiari nell'esporre le varie
stesso microcontrollore RP2040. Da sottolineare il fatto che nozioni di questa prima puntata, vi invitiamo a sperimentare
il menu File è ricco di esempi pronti all’uso. i progetti presentati in queste pagine e vi aspettiamo il mese
prossimo.
Per installare il pacchetto RP2040 non ufficiale dovete segui- Per vostra comodità, abbiamo reso disponibile tutto il codice
re la procedura esposta qui di seguito. degli esempi di questo corso nell'area download del nostro
1. Aprite l’IDE e andate in File > Impostazioni. Copiate e sito www.elettronicain.it, insieme a file del corso.
incollate il seguente link nella casella URL aggiuntivi per il Non ci resta che darvi appuntamento alla prossima puntata,

Gestore schede (riferitevi alla Fig. 13): https://github.com/ augurandovi buon lavoro!
earlephilhower/arduino-pico/releases/download/global/
package_rp2040_index.json.
2. Se avete altri URL, separateli con una virgola.
3. Fate clic su OK per salvare le impostazioni.
4. Andate in Strumenti > Scheda > Gestore schede per apri-
re il Gestore schede.
5. Si aprirà la finestra Gestore schede che caricherà anche il
riferimento URL che avete appena inserito.
6. Cercate nel campo di ricerca “Pico”.
7. Troverete la scheda “Raspberry Pi Pico/RP2040 by Earle
PROGRAMMARE CON RP2040

F. Philhower III”.
8. Selezionate l’ultima versione e fate clic su “Installa”.
9. Dopo che l’installazione del pacchetto non ufficiale è Cosa occorre?
terminata, vedrete la voce INSTALLED di fianco al nome
La board di Futura Elettronica con RP2040
del pacchetto.
(cod. FTR2040) è disponibile a Euro 13,90 e include
i pin strip da saldare.
Adesso nel menù Strumenti > Scheda > Gestore schede Dal sito futurashop.it è possibile acquistare lo starter kit
con Rapsberry Pi Pico (cod. RPICOKIT) a Euro 49,90 o il solo
troverete il nuovo menù: Raspberry Pi RP2040 Boards (2.0.1)
Raspberry Pi Pico (cod. RPI-PICO) a Euro 6,90.
o una versione più aggiornata. Per poter programmare la I prezzi si intendono IVA compresa.
nostra scheda FTR2040 dovrete selezionare la prima voce
di menù: “Raspberry Pi Pico”. Per programmare la scheda Il materiale va richiesto a:

FTR2040 utilizzando l’IDE di Arduino con il pacchetto non Futura Elettronica, Via Adige 11, 21013 Gallarate (VA)
ufficiale, seguite quanto spiegheremo qui di seguito. Tel: 0331-799775 - www.futurashop.it

11
RASPBERRY Pi 400!
La tastiera con il computer integrato

€ 1 6 9 , 00
IVA inclusa
KIT-ITA
Cod. PI400
Prezzo IVA inclusa.

le
Manuano!
a
in itali

Kit completo con computer Raspberry Raspberry Pi 400 è un personal computer completo che
integra nella tastiera (italiana), una scheda Raspberry Pi 4
Pi 400 accessori e manuale in Italiano. da 4Gb con processore quad-core a 64 bit, Wi-Fi, Bluetooth,
doppia uscita video (micro HDMI) con una risoluzione fino
a 4K, Gigabit Ethernet, USB 2.0 e USB 3.0.
Leggero, portatile, semplice da usare. È ideale per navigare sul
web, creare e modificare documenti, guardare video
e imparare a programmare utilizzando l’ambiente desktop del
sistema operativo Raspberry Pi. I pin GPIO di
Raspberry Pi rimangono comunque accessibili, permettendo
di connettere componenti e prototipare progetti.
La confezione di Raspberry Pi 400 contiene tutto il necessario
(ad eccezione di una TV o di un monitor): computer Raspberry
Pi P400, alimentatore da rete, mouse, scheda microSD da 16GB
pre-programmata con Raspberry Pi OS, cavo da Micro HDMI
a HDMI A lungo 1 metro, un manuale illustrato a colori di 247
pagine completamente in Italiano.

Futura Group srl

®
Via Adige, 11 • 21013 Gallarate (VA)
Tel. 0331/799775
Caratteristiche tecniche
e vendita on-line su: www.futurashop.it
Programmare con

RP2040

d i P IE R C
ALDERAN

PUNTATA
N. 2

Continuiamo a sperimentare con semplici dispositivi didattici creati con


la scheda FTR2040 e scriviamone il codice utilizzando l’ambiente
MicroPython, C/C++ e quello Arduino.

N ella puntata introduttiva di questo corso


dedicato alla programmazione di appli-
cazioni basate sulla scheda RP2040 vi
LED E PULSANTI
Oltre a collegare un LED a un qualsiasi contatto
(pin) di I/O della scheda, potete cablare un sem-
PROGRAMMARE CON RP2040

abbiamo spiegato come utilizzare i pin di I/O della plice circuito che accende e spegne il LED stesso
nostra scheda FTR2040 in uscita, ovvero come a seguito della pressione di un pulsante, connes-
output, per applicazioni come ad esempio accen- so ad un pin che imposterete come ingresso. In
dere e spegnere un LED. Ricordiamo che per tutti pratica, al circuito che avete assemblato la volta
gli esempi proposti e che proporremo, faremo rife- scorsa, dovete solo aggiungere un pulsante nella
rimento a una specifica versione della board, che breadboard, come indicato nella Fig. 1.
è quella realizzata e commercializzata da Futura Eseguite queste connessioni:
Elettronica: la FTR2040. 1. collegate nella breadboard l’anodo del LED al
In questa seconda puntata andremo a realizzare pin GP15 con in serie una resistenza da 330 Ω;
qualche circuito applicativo nel quale faremo inte- 2. collegate nella breadboard il catodo del LED al
ragire la scheda con altri componenti, per imple- negativo della breadboard;
mentare vere e proprie applicazioni di complessità 3. collegate un terminale del pulsante al pin GP9 e
crescente. l’altro terminale al positivo della breadboard.

13
 Fig. 1 - Collegamento di un LED e di un pulsante.  Fig. 2 - Lo schema di collegamento di un LED e di un potenziometro.

CODICE PER MICROPYTHON un’uscita analogica dovrebbe essere dotato di un converti-


Seguendo la stessa procedura spiegata la volta scorsa, tore digitale-analogico (DAC, Digital Analog Converter).
collegate la scheda FTR2040 alla vostra board Raspberry Dal momento che il Pico non possiede un DAC ma solo
Pi, quindi lanciate l'ambiente di sviluppo Thonny e scrivete uscite digitali, ovvero con uno stato alto o basso, possiamo
queste poche righe di codice, stando attenti a rispettare usare la tecnologia PWM (Pulse Width Modulation o modu-
l’indentatura: lazione di larghezza di impulso) per “simulare” un segnale
analogico.
import machine In questo modo, potrete collegare un potenziometro a un
import utime ingresso ADC e un LED a un’uscita digitale e trattare questa
come fosse PWM.
led_external = machine.Pin(15, machine.Pin.OUT) Vi ricordiamo che gli ingressi del convertitore analogico-di-
button = machine.Pin(9, machine.Pin.IN, machine.Pin.PULL_UP) gitale della scheda FTR2040 sono disponibili nei seguenti pin:
• GP26: ADC0
while True: • GP27: ADC1
if button.value() == 1: • GP28: ADC2
led_external.value(0)
if button.value() == 0: Noi useremo l’ingresso analogico ADC0 e quindi il pin GP26.
led_external.value(1) Come vedremo, ci sarebbe anche un quarto ingresso ADC,
chiamato ADC_VREF, che però viene utilizzato dal sensore
Come potete vedere: di temperatura incorporato nella scheda.
• con l’istruzione machine.Pin(15, machine.Pin.OUT) si impo- Lo schema di collegamento del potenziometro e del LED è
sta il pin GP15 come uscita; illustrato nella Fig. 2.
• con l’istruzione machine.Pin(9, machine.Pin.IN, machine.Pin.
PULL_UP) si imposta il pin GP9 come ingresso in pull up, CODICE PER MICROPYTHON
cioè sempre alto. Aprite Thonny e scrivete queste poche righe, rispettando
l’indentazione:
Una volta avviato il programma, tenendo premuto il pulsan-
te, il LED si accenderà e, viceversa, si spegnerà. import machine PROGRAMMARE CON RP2040
Questo perché l’ingresso è stato impostato come pull-up, import utime
cioè sempre alto (high o 1), e quando si porta la massa al pin
tramite il pulsante, l’ingresso viene portato basso (low o 0). potentiometer = machine.ADC(26)
La lettura dei due stati del pulsante consente di gestire led = machine.PWM(machine.Pin(15))
l’accensione e lo spegnimento del LED. led.freq(1000)
while True:
USARE LA PWM
Il convertitore analogico-digitale (ADC, Analog Digital reading = potentiometer.read_u16()
Converter) di Pico prende un segnale analogico e lo converte
in un segnale digitale così che il microcontrollore lo possa print(reading)
elaborare. led.duty_u16(reading)
Al contrario, se il microcontrollore digitale dovesse creare utime.sleep(.5)

14
Come potete vedere, con l’istruzione machine lizzato il valore della temperatura in gradi Celsius.
PWM(machine.Pin(15)) il LED viene attivato con la PWM Il modulo machine fornisce la classe ADC() per lavorare con
sull’uscita GP15. L’istruzione led.freq(1000) imposta il duty i pin ADC. Quindi, con l’istruzione machine.ADC(4), si imposta
cycle della PWM a 1000 cicli al microsecondo. la lettura diretta del sensore di temperatura, che abbiamo
L’ingresso analogico ADC0 è collegato al terminale centrale chiamato sensor_temp.
del potenziometro e viene impostato dall’istruzione machine. Alla variabile conversion_factor viene assegnato il fattore di
ADC(26). In questo modo, abilita uno dei quattro ingressi conversione di 3.3 volt su 65535 livelli di lettura.
analogici (GP28, GP25, GP26 e GP35). Con la seguente istruzione…
Una volta avviato il programma, ruotando il potenziome-
tro, vedrete cambiare la luminosità del LED. Notare che la reading = sensor_temp.read_u16() * conversion_factor
risoluzione di lettura dell’ADC è a 16 bit per cui si vedranno
stampati nella shell i valori da 0 a 65535. … la variabile reading legge il valore del sensore di tempera-
tura e lo moltiplica per il fattore di conversione.
SENSORE DI TEMPERATURA Se stampate il valore del valore della temperatura, otterrete
Come abbiamo detto, il sensore di temperatura incorporato un numero intero compreso tra 0 e 65535. Per ottenere i
nel chip RP2040 è collegato all’ingresso 4 dell’ADC. gradi centigradi, dovete eseguire una seconda conversione:
Il pin ADC supporta un intervallo di valori, determinato dalla
tensione di ingresso applicata al pin. temperature = 27 - (reading - 0.706)/0.001721
Nel chip RP2040, i pin ADC supportano 12 bit, il che
significa che il valore può andare da 0 a 4095. Ma il codice Questa è un’operazione matematica specifica per il sen-
MicroPython può ridimensionare i valori ADC in un interval- sore di temperatura del chip RP2040. I valori sono presi
lo di 16 bit. Quindi otteniamo effettivamente l'intervallo da da un documento tecnico disponibile al seguente link:
0 a 65535. https://datasheets.raspberrypi.com.
Il microcontrollore funziona a 3,3 V, il che significa che Questo succede perché il sensore di temperatura funziona
un pin ADC restituirà un valore di 65535 livelli di tensio- fornendo una tensione al pin ADC4 che è proporzionale alla
ne quando gli vengono applicati 3,3 V o 0 quando non c'è temperatura. Dal foglio dati, una temperatura di 27 gradi
tensione. Quindi, possiamo ottenere tutti i valori intermedi Celsius fornisce una tensione di 0,706 V.
quando la tensione applicata al pin è compresa tra 0 e 3,3 V. Con ogni grado aggiuntivo la tensione si riduce di 1,721 mV
I pin ADC nella scheda Pico utilizzano il proprio schema di o 0,001721 V.
numerazione invece di utilizzare il numero pin GPIO. Il primo passaggio nella conversione della temperatura a 16
Come avete visto, i pin sopra sono etichettati ADC0, ADC1, bit è riconvertirla in volt, che viene fatto in base alla tensio-
ADC2 e ADC_VREF (che tecnicamente sarebbe ADC3), e ne massima di 3,3 V utilizzata dalla scheda.
sono i quattro pin ADC accessibili dall'esterno. Con questa conversione, il valore della temperatura viene
Il sensore di temperatura non ha un pin fisico nella scheda stabilito son questa operazione:
ma è accessibile da MicroPython come ADC4. 27 - (valore da 0 a 65535 - 0.706)/0.001721

LETTURA DEL VALORE DELLA TEMPERATURA LA TEMPERATURA SUL DISPLAY LCD I2C
IN MICROPYTHON Nello Starter Kit di Futura Elettronica (cod. RPICOKIT) potete
Ora vediamo il codice del sensore di temperatura in Mi- trovare anche un display LCD compatibile con l’interfaccia
croPython. Scrivete il seguente codice: I2C del chip RP2040 (codice LCD16X2AI2C). Fra le varie
interfacce disponibili, questo display consente un collega-
PROGRAMMARE CON RP2040

import machine mento davvero molto semplice.


import utime Il chip del microcontrollore RP2040 ha due controller I2C.
Potete accedere a entrambi i controller I²C tramite questi
sensor_temp = machine.ADC(4) pin GPIO della scheda FTR2040:
conversion_factor = 3.3 / (65535)

while True: I2C CONTROLLER GPIO


reading = sensor_temp.read_u16() * conversion_factor
I2C0 – SDA GP0/GP4/GP8/GP12/GP16/GP20
temperature = 27 - (reading - 0.706)/0.001721
print(temperature) I2C0 – SCL GP1/GP5/GP9/GP13/GP17/GP21
utime.sleep(2) 2C1 – SDA GP2/GP6/GP10/GP14/GP18/GP26

2C1 – SCL GP3/GP7/GP11/GP15/GP19/GP27


Avviate il programma e vedrete che nella shell verrà visua-

15
 Fig. 3 - Il display LCD collegato a una delle porte I2C.

Ogni connessione del controller può essere configurata temperature = 27 - (reading - 0.706)/0.001721
tramite più pin GPIO, ma prima di utilizzare un controller i2c.writeto(114, '\x7C')
I2C, è necessario configurare nel software quali pin GPIO si i2c.writeto(114, '\x2D')
desiderano utilizzare.
out_string = "Temp: " + str(temperature)
CARATTERISTICHE DEI PIN I²C i2c.writeto(114, out_string)
Il controller I2C del chip RP4020 supporta le seguenti fun- utime.sleep(2)
zionalità:
• modalità Master o Slave (indirizzo Slave predefinito = 0x055) L’istruzione machine I2C(0,sda=sda, scl=scl, freq=400000)
• tre modalità di velocità: Standard (da 0 a 100 Kb/s), Fast imposta i pin GP0 e GP1 come interfaccia I2C in modalità
(minore o uguale a 400 Kb/s) e Fast Plus (minore o ugua- Fast, ovvero alla velocità di 400 Kb/s.
le a 1.000 Kb/s) Nel ciclo while sono state aggiunte le istruzioni i2c.writeto()
• buffer di trasmissione e ricezione per la scrittura nei registri 7C e 2D del display
• può essere utilizzato in modalità di interruzione e DMA La variabile out_string imposta la stringa di output con la
scritta “Temp: ” più il valore di temperatura str(temperature),
Collegando il display a una delle porte I2C e l’alimentazione convertito in stringa.
(Fig. 3), potete aggiungere poche righe allo script preceden- Una volta avviato il programma, potrete vedere la tempera-
te per vedere l’output della temperatura sul display: tura sul display.
PROGRAMMARE CON RP2040
import machine RASPBERRY PI PICO SDK
import utime L'SDK Raspberry Pi Pico (d'ora in poi solo SDK) fornisce le
librerie e il sistema di build necessari per scrivere program-
sda = machine.Pin(0) mi per i dispositivi basati su RP2040 in C, C++ o linguaggio
scl = machine.Pin(1) assembly.
L'SDK è progettato per fornire un'API e un ambiente di pro-
i2c = machine.I2C(0,sda=sda, scl=scl, freq=400000) grammazione agli sviluppatori C.
adc = machine.ADC(4) Un singolo programma viene eseguito su un dispositivo alla
conversion_factor = 3.3 / (65535) volta e viene avviato con un metodo convenzionale main(),
che praticamente contiene tutte le funzioni principali.
while True: Le librerie C/C++ standard sono supportate insieme alle
reading = adc.read_u16() * conversion_factor librerie/API di livello C per l'accesso a tutto l'hardware

16
dell'RP2040, incluso la modalità PIO (Programmed Input esempi dell’SDK dal repository seguente:
Output). Inoltre, l'SDK fornisce librerie di livello superiore
per gestire timer, sincronizzazione, USB (TinyUSB) e pro- git clone https://github.com/raspberrypi/pico-examples
grammazione multi-core insieme a varie utilità.
L'SDK può essere utilizzato per creare qualsiasi cosa, da Per compilare tutti gli esempi, seguite questa procedura.
semplici applicazioni create con MicroPython a software di 1. Entrate nella cartella pico-examples
basso livello in C/C++. 2. Create una cartella di compilazione cmake:
mkdir build
AVVIARE RAPIDAMENTE UN PROGETTO IN C 3. Entrate nella cartella build:
Senza poter entrare nella specifica trattazione del lin- cd build
guaggio C e cercando di facilitare le cose, soprattutto ai 4. Compilate tutti gli esempi (fate attenzione a immettere
principianti, queste istruzioni sono estremamente concise e due punti dopo il comando cmake):
basate solo su Raspberry Pi. cmake ..
Per altre piattaforme come Windows o MacOS, è disponibile 5. Create il target per tutti gli esempi, ovvero gli eseguibili
il documento Raspberry Pi Pico C/C++ SDK a questo indiriz- veri e propri:
zo: https://rptl.io/pico-c-sdk make
Una volta collegata la scheda FTR2040 a un Raspberry Pi,
bisogna verificare che sia installata una versione CMake Abbiate pazienza, perché la compilazione di tutti gli esempi
(almeno la versione 3.12) e il compilatore GCC. può impiegare diverso tempo. Tutti gli eseguibili saranno in
Per fare questo, digitate il comando seguente su un terminale: formato uf2 e si troveranno nelle rispettive cartelle all’inter-
no della cartella build, cioè, per esempio:
sudo apt install cmake gcc-arm-none-eabi libnewlib-arm-none-eabi
libstdc++-arm-none-eabi-newlib /home/pi/pico-examples/build/blink/blink.uf2

Se il sistema operativo di Raspberry Pi è recente, dovreste Per provare l’esempio blink, collegate un LED al pin 25 della
avere già tutto installato e comparirà un messaggio simile scheda (corrispondente al LED di default della scheda di
a questo: Raspberry Pi Pico) seguite questa procedura.
1. Cortocircuitate il pin BOOT a massa e alimentate la sche-
gcc-arm-none-eabi is already the newest version (15:8-2019-q3- da collegandola via USB a Raspberry Pi.
1+b1). 2. Togliete il corto.
libnewlib-arm-none-eabi is already the newest version (3.3.0-1). 3. Apparirà il prompt che vi chiederà di aprire la cartella del
libnewlib-arm-none-eabi set to manually installed. supporto rimovibile (Fig. 4).
libstdc++-arm-none-eabi-newlib is already the newest version 4. Si aprirà una cartella simile alla Fig. 5.
(15:8-2019-q3-1+13).
libstdc++-arm-none-eabi-newlib set to manually installed.
cmake is already the newest version (3.18.4-2+rpt1+rpi1).
0 upgraded, 0 newly installed, 0 to remove and 231 not upgraded.

A questo punto, dovete clonare l'SDK localmente, per esem-


pio, in /home/pi (consigliato):
PROGRAMMARE CON RP2040

git clone https://github.com/raspberrypi/pico-sdk

Verrà creata una cartella pico-sdk. Dopodiché bisognerà


configurare il percorso per utilizzare l'SDK.
Per fare questo, basta impostare il percorso PICO_SDK_
PATH in modo che punti alla cartella dell'SDK.
Se avete clonato l’SDK nella directory di default, dovreste
digitare nel terminale il comando seguente:

export PICO_SDK_PATH=/home/pi/pico-sdk

ESEMPI DELL’SDK  Fig. 4 - Il prompt per aprire supporto rimovibile.


Per vedere se tutto funziona, dovreste clonare tutti gli

17
 Fig. 5 - Il contenuto del supporto rimovibile.

5. Copiate al suo interno il file blink.uf2.


6. La cartella si chiuderà e vedrete il LED lampeggiare.

IL PRIMO PROGRAMMA IN C
Se non avete mai programmato in C, questo è il momen-
to di iniziare, approfittando di questo corso e dell’SDK
Raspberry Pi Pico. La cosa più semplice che potete fare
all’inizio è creare un singolo file di testo, che chiamerete
 Fig. 6 - Il file di testo con estensione .c.
per esempio, “hello_world.c” (Fig. 6). Questo sarà il file
sorgente
Lo potete creare ovunque, ma per dare un po’ di ordine,
vi consigliamo di creare prima una cartella “test” nella
directory /home/pi e poi una sottocartella “hello_world” PROGRAMMARE CON RP2040
all’interno della cartella test, ovvero, da terminale digitate
i comandi seguenti:

mkdir test
cd test
mkdir hello_world

Aprite il file hello_world.c con un buon editor per program-


matori, per esempio, Geany che è già installato nel sistema,
e scrivete queste righe di codice (Fig. 7):
 Fig. 7 - Il codice scritto all’interno dell’editor Geany.
#include <stdio.h>

18
#include "pico/stdlib.h" Per la compilazione del programma è necessario verificare
int main() { che siano incluse tutte le librerie e verificare i loro percorsi.
stdio_init_all(); Proprio per questo motivo, è impossibile avere un Makefile
while (true) { predefinto, per cui bisognerà sempre avere un file CMake-
printf("Hello world!\n"); Lists.txt e creare una cartella di compilazione build. Per la
sleep_ms(1000); generazione del Makefile e la successiva compilazione del
} progetto, è necessario eseguire i seguenti comandi:
return 0;
} mkdir build
cd build
Dopo aver incluso le librerie standard stdio e stdlib, il pro- cmake ..
gramma inizia all’interno della funzione main(). make
Si noti che questo esempio utilizza l’istruzione stdio_init_
all() che inizializza le porte seriali e USB del sistema. I due punti dopo il comando cmake stanno a significare che
Questo per poter leggere i messaggi dagli ingressi seriali il file CMakeLists.txt si trova al livello di cartella esterno a
e visualizzarne il contenuto sul terminale di output (il build.
terminale). Con CMake è possibile annidare anche diversi file
Nel nostro caso, dovremmo vedere stampata sul terminale CMakeLists.txt in modo da rendere tutto estremamente
la stringa Hello, world! mandata dalla scheda collegata via facile. Vediamo come fare.
USB. Tramite l’istruzione printf infatti possiamo accedere
alla periferica UART o USB. Il primo file CMakeLists.txt
Tecnicamente, printf scrive la stringa C a cui punta il Create nella cartella hello_world un nuovo file, chiamatelo
formato della stringa nello standard output (stdout). Se CMakeLists.txt, apritelo con Geany e scrivete al suo interno
il formato include identificatori, gli argomenti aggiuntivi queste righe (notare i commenti con anteposto il simbolo
che seguono il formato vengono formattati e inseriti nella #):
stringa risultante.
Nel nostro caso, abbiamo questo: # se il target è inizializzato come usb…
if (TARGET tinyusb_device)
printf("Hello world!\n");
# … aggiunge l’eseguibile
Il formato della stringa è “Hello world!” più il carattere add_executable (hello_world hello_world.c)
\n di a capo. Quello che apparirà sarà il messaggio Hello
world! e un a capo. # estrae le dipendenze comuni
Gli intervalli sono impostati a 1000 ms (un secondo) dalla target_link_libraries (hello_world pico_stdlib)
funzione sleep_ms.
Tenete presente che il loop viene creato dall’istruzione # abilita l'uscita USB e disabilita l'uscita uart
while (true), esattamente come in MicroPython e tanti altri pico_enable_stdio_usb (hello_world 1)
linguaggi. pico_enable_stdio_uart (hello_world 0)

CMAKE # crea file map/bin/hex/uf2 ecc.


Per la compilazione dei file scritti C di solito si usa gcc pico_add_extra_outputs (hello_world)
PROGRAMMARE CON RP2040

(GNU Compiler Collection), sito ufficiale https://gcc.gnu.org.


Si tratta di un compilatore C creato inizialmente per GNU/ # aggiunge l'URL tramite pico_set_program_url
Linux e poi diffuso su tutte le piattaforme, Windows example_auto_set_url (hello_world)
compreso.
La compilazione avviene a riga di comando e può essere # altrimenti se il target non è inizializzato come USB, appare
poco agevole, soprattutto per i principianti. il messaggio seguente
Per semplificare le cose, possiamo usare CMake, un elseif (PICO_ON_DEVICE)
software libero multipiattaforma per l'automazione della message (" hello_world non viene compilato perché TinyUSB
compilazione in C. non è inizializzato nell'SDK")
CMake permette con poche istruzioni di generare Makefile endif ()
che possono venire eseguiti dall’utility make. CMake ha
una particolare sintassi con moltissime macro che vengo- Il secondo file CMakeLists.txt
no immesse in un apposito file chiamato CMakeLists.txt. Tornate nella cartella test e copiate al suo interno i

19
 Fig. 8 - Il contenuto della cartella test.

seguenti file che trovate nella cartella pico-examples che project(pico_examples C CXX ASM)
avete clonato in precedenza (Fig. 8): set(CMAKE_C_STANDARD 11)
set(CMAKE_CXX_STANDARD 17)
example_auto_set_url.cmake
pico_sdk_import.cmake set(PICO_EXAMPLES_PATH ${PROJECT_SOURCE_DIR})

Create un nuovo file CMakeLists.txt e scrivete al suo interno # Inizializza l'SDK


(notate i commenti con anteposto il simbolo #): pico_sdk_init()

cmake_minimum_required (VERSION 3.12) include(example_auto_set_url.cmake)

# Inserisce l’SDK (deve essere prima del progetto) # Aggiunge l’esempio hello_world ovvero la cartella sua cartella
include(pico_sdk_import.cmake) che contiene il CMakeLists.txt creato in precedenza

PROGRAMMARE CON RP2040

 Fig. 9 - Il contenuto della cartella build /hello_world.

20
guibile hello_world.elf assieme al file hello_world.uf2 (Fig. 9).
Basta solo copiare il file hello_world.uf2 nella scheda
FTR2040, seguendo la consueta procedura per il bootsel.
Quando si aprirà l’unità removibile, trascinate il file hel-
lo_world.uf2 al suo interno.
Per vedere l’output sul terminale digitate il comando seguen-
te che apre l’applicazione minicom, che dovrebbe già essere
installata nel sistema:

minicom -b 115200 -o -D /dev/ttyACM0

Nel terminale vedrete apparire il messaggio Hello World! a


intervalli di un secondo (Fig. 10).

 Fig. 10 - L’output del programma nel terminale. CODICE IN C DEL PULSANTE PIÙ UN LED
Adesso che tutto sembra più chiaro, dovreste essere in grado
di rifare i programmi scritti in MicroPython con l’SDK in C.
All’interno della cartella test, create una cartella, per esempio
add_sottodirectory (hello_world) button. Quindi create un file, per esempio, button.c, apritelo
con Geany e scrivere le righe di codice riportate nel Listato 1
# Aggiunge le opzioni di compilazione al suo interno.
add_compile_options(-Wall -Wno-format -Wno-unused-function Come potete vedere, oltre all’output su terminale, abbiamo
-Wno-maybe-uninitialized) aggiunto la libreria gpio che gestisce l’hardware della scheda.
Una volta definito un pulsante con BUTTON_PIN, bastano
COMPILARE CON CMAKE solo le istruzioni della libreria gpio per impostare il pulsante
A questo punto avete un CMakeLists.txt nella cartella test che
fornisce tutte le istruzioni per includere librerie cmake e per
aggiungere la sottodirectory hello_world.
Portatevi nella cartella test e create una directory build di
compilazione CMake.  Listato 1
#include <stdio.h>
mkdir build #include "pico/stdlib.h"
cd build #include "hardware/gpio.h"

cmake .. #define BUTTON_PIN 9


#define LED_PIN 15
Se non avete fatto errori, dovreste vedere nell’output del int main()
terminale i seguenti messaggi: {
stdio_init_all();

-- Configuring done gpio_init(LED_PIN);


-- Generating done gpio_set_dir(LED_PIN, GPIO_OUT);

-- Build files have been written to: /home/pi/test/build gpio_init (BUTTON_PIN);


PROGRAMMARE CON RP2040

gpio_set_dir (BUTTON_PIN, GPIO_IN);


gpio_pull_up(BUTTON_PIN);
A questo punto create il target dalla directory della build
creata con il comando seguente: while (true)
{
if (!gpio_get (BUTTON_PIN))
make {
printf ("Pulsante premuto\n");
gpio_put(LED_PIN, 1);
Se non ci sono errori di compilazione, dovreste vedere alla
fine dei messaggi qualcosa di simile a questo: sleep_ms(250);
}
else
[ 17%] Linking CXX executable hello_world.elf gpio_put(LED_PIN, 0);
[100%] Built target hello_world }
}

Significa che nella cartella build/hello_world troverete l’ese-

21
if (TARGET tinyusb_device)
add_executable (button button.c)
target_link_libraries (button pico_stdlib)
pico_enable_stdio_usb (button 1)
pico_enable_stdio_uart (button 0)
pico_add_extra_outputs (button)
example_auto_set_url (button)

elseif (PICO_ON_DEVICE)
message(WARNING "not building button because TinyUSB submo-
dule is not initialized in the SDK")
endif ()

 Fig. 11 - L’output del programma sul terminale Entrate nella cartella test e modificate il file CMakeLists.txt
quando viene premuto il pulsante. aggiungendo solo questa riga:

add_subdirectory (hello_world)
come ingresso (pin 9) e il led come uscita (15). Nel ciclo while, add_subdirectory (button)
se (!gpio_get (BUTTON_PIN), ovvero se il pulsante viene por-
tato a massa apparirà il messaggio “Pulsante premuto” e si In pratica, verrà aggiunta la cartella button alla compila-
accenderà il led. Altrimenti il led rimarrà spento. Create il file zione. Se volete compilare i due programmi hello_world e
CMakeLists.txt copiando il precedente scritto per hello_world e button digitate il comando seguente:
sostituite tutte le occorrenze hello_world con button.
make

Se volete compilare solo button o solo hello_world, digitate


 Listato 2 uno dei seguenti comandi:

// le costanti sono usate qui per impostare i pin:


make button
const int buttonPin = 9; // pin del pulsante
const int ledPin = 15; // pin del LED make hello_world

// le variabili di stato cambieranno in base alla pressione


del pulsante: Una volta compilato senza errori il file button, troverete il
int buttonState = 0; // variabile per la lettura dello stato file eseguibile button.uf2 nella cartella build/button.
del pulsante
Copiatelo nella scheda come al solito, avviate minicom
void setup() { e premete il pulsante. Vedrete nel terminale qualcosa di
// inizializza il pin del LED come output:
pinMode(ledPin, OUTPUT);
simile alla Fig. 11, mentre il led si accenderà e si spegnerà
alla pressione del pulsante.
// inizializza il pin del pulsante come input pullup (sempre
alto):
pinMode(buttonPin, INPUT_PULLUP); IL CODICE PER ARDUINO IDE
} Abbiamo spiegato nella scorsa puntata come usare l’IDE di
void loop () { Arduino per programmare la scheda FTR2040.
// legge lo stato del valore del pulsante:
buttonState = digitalRead(buttonPin);
Lasciando inalterati i circuiti assemblati finora, basta col- PROGRAMMARE CON RP2040
legare la scheda a una porta USB di un PC e avviare l’IDE di
// controlla se il pulsante è premuto. Arduino.
if (buttonState == HIGH) { Selezionate la scheda Raspberry Pico dal menu Strumenti
// tiene spento il LED > Schede > Raspberry Pi RP2040 Boards (2.0.1) e la porta
digitalWrite(ledPin, LOW); seriale a cui è collegata la scheda.
// altrimenti, se lo è, lo stato del pulsante è LOW…
} else { CODICE PER ARDUINO
// accende il LED:
digitalWrite(ledPin, HIGH); Sketch pulsante/LED
} Fate riferimento al codice riportato nel Listato 2 e caricate
}
lo sketch nella scheda per vedere accendersi il LED ad ogni
pressione del pulsante.

22
 Listato 3
// seleziona il pin di ingresso per il potenziometro
int sensorPin = A0;

// seleziona il pin per il LED


int ledPin = 15;

// variabile per memorizzare il valore proveniente dal sensore


int sensorValue = 0;

void setup() {
// dichiara il ledPin come OUTPUT:
pinMode(ledPin, OUTPUT);

// apre la seriale
Serial.begin(57600);
}

void loop() {
// legge il valore dal sensore:
sensorValue = analogRead(sensorPin);

// scrive il valore analogico su ledPin


analogWrite(ledPin, sensorValue);
 Fig. 12 - L’output del programma sul terminale
// stampa il valore analogico sul monitor seriale quando viene premuto il pulsante.
Serial.println(sensorValue);
delay(10);
}
lo sketch nella scheda per leggere e stampare l’output del
sensore di temperatura interno al chip RP2040.
Vi facciamo notare che viene usata solamente la funzione
Sketch potenziometro/LED analogReadTemp(), già inclusa nella libreria Raspberry Pico e
Fate riferimento al codice riportato nel Listato 3 e caricate che fa tutto.
lo sketch nella scheda per mandare il valore analogico letto Una volta caricato lo sketch, vedrete sul monitor seriale i
dal potenziometro all’uscita PWM del LED. valori di temperatura in gradi Celsius (Fig. 12).
Facciamo notare che il numero del pin A0, quello che di so-
lito si usa con le schede Arduino, viene convertito automati- CONCLUSIONI
camente come numero del pin ADC0 del chip RP2040. Con la speranza di essere stati sufficientemente chiari, vi
Una volta caricato lo sketch, vedrete variare la luminosità invitiamo a sperimentare i progetti presentati in queste
del LED in base alla rotazione del potenziometro e i valori da pagine e vi diamo appuntamento alla prossima puntata.
0 a 1023 stampati sul monitor seriale. Per vostra comodità, ricordiamo che tutto il codice degli
esempi qui proposti è disponibile nell'area di download del
Sketch temperatura nostro sito Internet www.elettronicain.it, insieme ai file di
Fate riferimento al codice riportato nel Listato 4 e caricate questo numero di Elettronica In.

PROGRAMMARE CON RP2040

 Listato 4
Cosa occorre?
void setup() {
La board di Futura Elettronica con RP2040
Serial.begin(57600); (cod. FTR2040) è disponibile a Euro 13,90 e include
delay(1000); i pin strip da saldare.
Dal sito futuranet.it è possibile acquistare lo starter kit con
} Rapsberry Pi Pico (cod. RPICOKIT) a Euro 49,90 o il solo
Raspberry Pi Pico (cod. RPI-PICO) a Euro 6,90.
void loop() { I prezzi si intendono IVA compresa.
Serial.printf("Ambient temperature: %2.1fC\n",
analogReadTemp());
delay(1000); Il materiale va richiesto a:
}
Futura Elettronica, Via Adige 11, 21013 Gallarate (VA)
Tel: 0331-799775 - www.futurashop.it

23
Piastre
Piastre sperimentali
Ideali per creare velocemente un circuito sperimentale per effettuare test,
senza dover necessariamente realizzare un PCB.

MILLEFORI
CODICE MISURA (mm) FACCIA DISTANZA PREZZO
Piastra Millefori 150×90 mm PIAZZOLE (€)
(mm)
doppia faccia
cod. YK653

€ 4,50
YK604 150×90 singola 2,54 3,80

YK647 100×50 singola 2,54 2,60

YK009 70×30 doppia 2,54 1,50


Distanza tra
piazzole: 2,54 mm HR2570 120×80 doppia - 4,50

BREADBOARD
Breadbord 170 contatti Breadbord con base Breadboard 1660 contatti
colore bianco autoadesiva 400 contatti con base in metallo
45x35 mm 82x55 mm e boccole
ROSSO Misura piastra:
cod. BBMINIW 164x109x9,5 mm
cod. BBMINIR
€ 2,50
cod. BB400 cod. YJ319
Misura base:
€4 ,00
€ 14,00
NERO 215x131x1 mm
cod. BBMININ

BLU
cod. BBMINIB COD. MISURA N. PREZZO COD. MISURA MISURA N. PREZZO
(mm) CONT. (€) PIASTRA BASE CONT. (€)
VERDE (mm) (mm)
cod. BBMINIV BB830 165x55 830 5,50 BB3220 188x182x9,5 240x210 3220 21,00

RAMATE PRESENSIBILIZZATE
Piastra Ramata 160×100 mm Piastra Presensibilizzata PROGRAMMARE CON RP2040
singola faccia 160×100 mm singola faccia
cod. P-951 cod. 4062

€2 ,50
€ 6,00

CODICE MISURA (mm) FACCIA PREZZO (€) CODICE MISURA (mm) FACCIA PREZZO (€)
Prezzi IVA inclusa.

P-952 200×150 singola 4,20 4072 160×100 doppia 7,80

P-956 160×100 doppia 5,40 P-995 233×160 singola 13,50

P-957 200×150 doppia 6,20 P-997 233×160 doppia 17,00

Futura Group srl


Caratteristiche tecniche di questi prodotti
www.futurashop.it Via Adige, 11 • 21013 Gallarate (VA)
e acquisti on-line su www.futurashop.it
Tel. 0331/799775
Programmare con

RP2040

d i P IE R C
ALDERAN

PUNTATA
N. 3

Configuriamo la scheda FTR2040 di Futura Elettronica come end device


della rete LoRaWAN e scopriamo come collegarla a The Things Network.

P robabilmente il vincitore della guerra tra


gli standard sui protocolli di rete WAN
per l'Internet delle cose è LoRaWAN, un
Ora vi mostreremo come questo piccolo controller
possa essere in grado di comunicare con un chip
Semtech SX1276, ovvero quello che viene comu-
PROGRAMMARE CON RP2040

protocollo a bassa potenza, larghezza di banda nemente impiegato nelle breakout board HopeRF
ridotta e lungo raggio. Destinato a collegare ad In- RFM95W (Fig. 1) e disponibile per l’acquisto on-li-
ternet i sensori remoti alimentati a batteria tramite ne sul sito di Futura Elettronica www.futurashop.it
un gateway, con un'antenna adeguata permette di con il codice prodotto RFM95-868.
ottenere fino a 15 km di portata nella connessione
di un end device LoRa. L’unico limite è la larghezza
di banda disponibile, quantificabile in pochi byte al LA LIBRERIA LORAWAN
secondo, ma siccome i dispositivi IoT richiedono la Il supporto per la connettività LoRaWAN per
trasmissione periodica di piccole quantità di dati, Raspberry Pi Pico è stato messo a disposizione
LoRa è la tecnologia ideale e soddisfa i requisiti. da Sandeep Mistry, l’autore della libreria Ardui-
Nelle prime due puntate di questo corso avete avu- no LoRa, che più recentemente ha fornito anche
to modo di saggiare le potenzialità del chip RP2040 il supporto LoRa per Pico e altre schede basate
di Raspberry Pi. su RP2040 utilizzando il modulo radio Semtech

25
eseguito il comando seguente (senza spazi prima e dopo il
segno di uguale):

export PICO_SDK_PATH=/home/pi/pico/pico-sdk

Prima di compilare gli esempi, bisogna fare altre due cose:


• configurare l'infrastruttura cloud di The Things Network;
• creare un end device LoRaWAN con la scheda RP2040.

REGISTRAZIONE DEL GATEWAY SULLA RETE TTN


The Things Network (da ora in poi solo TTN) consente di regi-
 Fig. 1 - La breakout board HopeRF RFM95W. strare un gateway LoRaWAN in pochissimo tempo con pochi
e semplici passaggi. Consente inoltre di creare applicazioni
per la decodifica dei payload (carichi utili) e l’integrazione
con servizi di terze parti per elaborare ulteriormente i dati.
SX1276. Ciò significa che le breakout board come la scheda
RFM95W sono completamente supportate. Creazione di un account
Se non avete già configurato la toolchain C/C++ di Raspber- Per prima cosa dovete iscrivervi recandovi all’indirizzo web
ry Pi Pico nella vostra Raspberry Pi, fatelo prima di proce- www.thethingsnetwork.org e fare clic sul pulsante Sign Up
dere. Vi consigliamo di seguire le istruzioni riportate nella nell’angolo in alto a destra della pagina (Fig. 2).
seconda puntata del corso. Nella pagina Create an account, digitate un nome utente,
Se invece avete già configurato la toolchain C/C++, come un indirizzo e-mail valido e una password con almeno sei
spiegato nella scorsa lezione, clonate il repository con il caratteri, quindi fate clic sul pulsante “Create account”.
comando: Dopo qualche minuto, nella Posta in arrivo riceverete una e-
mail di convalida dell’account TTN, nella quale dovrete fare
git clone --recurse-submodules https://github.com/sandeepmistry/ clic sul pulsante Activate account.
pico-lorawan.git Dopo aver attivato l’account, dalla pagina di benvenuto, fate
clic sul pulsante Login nella parte superiore della pagina e
Prima di procedere, assicuratevi di avere il percorso PICO_ inserite le credenziali per effettuare l’accesso.
SDK_PATH impostato. Una volta riconosciuti, potrete modificare i dati del vostro
Per esempio, se state compilando su una Raspberry Pi profilo, uscire da TTN oppure accedere alla propria Console;
e avete seguito la seconda puntata, dovreste avere già da qui potrete scegliere un cloud in Europa, dopodiché, ve-

PROGRAMMARE CON RP2040

 Fig. 2 - La home page di TTN.

26
 Fig. 3 - La console personale.

 Fig. 4 - L’elenco dei gateway.

drete la vostra console diventare come nella Fig. 3. le. Per saperne di più sui gateway multicanale, fate riferi-
La console consente di registrare gateway e dispositivi, mento all’apposito riquadro in queste pagine (“Canali LoRa,
creare applicazioni, creare integrazioni e gestire collaboratori gateway multicanale e a canale singolo”). Per registrare un
e varie impostazioni. Se permettete di memorizzare i cookies nuovo gateway o per aggiungerne uno a quelli già esistenti,
PROGRAMMARE CON RP2040

di accesso nel browser, dopo aver selezionato Europe 1 come basta fare clic su Register gateway. Nella casella che appare,
cloud, potrete accedervi direttamente da questo link: digitate il cosiddetto EUI, per esempio B827EBFFFFA16ABB.
Questo è un identificatore unico per il gateway. Se usate un
eu1.cloud.thethings.network/console gateway iC880A che utilizza il Semtech UDP Packet Forwar-
der, copiatelo dal file global_conf.json. Per esempio, l’ID di
La pagina della console si presenta con due grosse icone con default AA555A0000000000, può diventare semplicemente
le scritte Go to applications e Go to gateways. BB555A0000000000 e deve essere unico. Quindi è possibile
A questo punto, se è la prima volta che accedete, dovete scegliere qualsiasi numero. Una volta modificato, bisogna
registrare almeno un gateway. Se avete registrato già altri riportare lo stesso ID anche nel file local_conf.json nella
gateway in precedenza verranno elencati (Fig. 4). stessa cartella. Il Semtech UDP Packet Forwarder (con file
Prestate attenzione al fatto che nel nuovo stack V3 di TTN, global_conf.json) è disponile a questo link:
i gateway a singolo canale non sono più supportati, quindi
dovrete acquistare o costruirvi da soli un gateway multicana- https://github.com/Lora-net/packet_forwarder

27
Canali LoRa, gateway multicanale e a canale singolo
La tecnologia LoRa/LoRaWAN consente di trasmettere e Tutti gli 8 canali sono separati da 0,3 MHz rispetto ai canali
ricevere su uno o più canali adiacenti, sempre rimanendo adiacenti. Va da sé quindi che un gateway multicanale è in grado
all’interno di una banda di frequenza. di ricevere e trasmettere su più canali e più frequenze, mentre un
Per la rete LoRaWAN esistono diverse bande definite per gateway a canale singolo può ricevere e trasmettere su un solo
USA, UE e Cina. canale e una frequenza fissa.
Per esempio la Tabella 1 elenca i canali LoRa nella banda Il gateway iC880A della tedesca Wireless solutions è in grado di
868 MHz (per UE) e riporta, per ciascun numero di canale, la ricevere pacchetti di diversi end device inviati con diversi fattori di
rispettiva frequenza. diffusione su un massimo di 8 canali in parallelo.
La banda va da 863 a 870 MHz. Grazie alla combinazione di fattori di diffusione e larghezze di ban-
da del segnale si possono ottenere diverse velocità di trasmissione
dati. Questo diventa possibile con l’utilizzo della tecnologia “Dyna-
NUMERO DEL CANALE FREQUENZA CENTRALE mic Data-Rate Adaption”. Ciò significa che i nodi LoRa distanti
dal concentratore devono utilizzare fattori di spread più elevati e
CH_10_868 865.20 MHz quindi avere una velocità di trasmissione dati inferiore.
CH_11_868 865.50 MHz
CH_12_868 865.80 MHz

CH_13_868 866,10 MHz

CH_14_868 866,40 MHz

CH_15_868 866,70 MHz

CH_16_868 867 MHz

CH_17_868 868 MHz

 Tabella 1 - Assegnazione delle frequenze nella banda


863÷870 MHz.

Cliccate quindi su “confirm” e poco dopo a video apparirà


una schermata (Fig. 5) in cui occorre inserire i seguenti dati:
• Gateway name: un nome qualsiasi, ma, una volta asse-
gnato non lo si può più riutilizzare neanche dopo aver
eliminato il gateway;
• Frequency plan: il piano europeo della frequenza, che è
stato stabilito nella banda 868 MHz.
Nel nostro caso deve essere selezionato Europe PROGRAMMARE CON RP2040
863 - 870 MHz (SF9 for RX2 -recommended).

Tutto il resto può rimanere così com’è. Cliccate quindi su


Register gateway e facendo ciò, accanto al nome del gateway
dovreste vedere la dicitura Connected.
Una volta avviato il gateway si vedrà qualcosa di simile a
quello mostrato nella Fig. 6 con l’indicazione Last activity e
il tempo trascorso dall’ultimo accesso del gateway (nor-
malmente ogni 15 secondi). Alla voce Live data si possono
leggere i pacchetti ricevuti. Facendo clic su Live data si apre
una pagina con tutti i pacchetti ricevuti (Fig. 7) e facendo clic
 Fig. 5 - Pagina di registrazione del gateway.
su un pacchetto se ne può visualizzare il contenuto decodifi-

28
I nodi LoRa più vicini al concentratore possono utilizzare fattori di
spread inferiori e pertanto possono aumentare la velocità dei dati.
Ciò consente di costruire reti a stella o a stella multiple facili da
gestire senza la necessità di router o ripetitori. Per chi ama la pro-
gettazione fai da te, è possibile realizzare facilmente un gateway
LoRaWAN completo nelle sue funzionalità, in combinazione con
una scheda Raspberry Pi e con il software HAL; quest’ultimo può
essere scaricato gratuitamente dal repository https://github.com/
Lora-net. Per eventuali approfondimenti a riguardo vi consiglia-
mo di visitare il sito web del produttore, https://www.wireless-
solutions.de. Vi rimandiamo altresì al corso LoRa, che abbiamo
pubblicato nei fascicoli di Elettronica In dal numero 246 al 251.
Il LIG16 ha bande di frequenza LoRaWAN standard preconfigurate
Dragino LIG16 Indoor LoRaWAN Gateway da utilizzare per diversi paesi. L'utente può anche personalizzare le
Fra le decine di gateway commerciali, il LIG16 dell’azienda cinese bande di frequenza da utilizzare nella propria rete LoRaWAN.
Dragino (https://www.dragino.com) è un gateway LoRaWAN per Il LIG16 può comunicare con il nodo finale ABP LoRaWAN senza
interni preconfigurato e anche open source. Consente di collegare la server LoRaWAN. L'integratore di sistema può utilizzarlo per
rete wireless LoRa a una rete IP tramite WiFi, rete Ethernet. Il wire- integrarsi con il proprio servizio IoT esistente senza configurare il
less LoRa consente agli utenti di inviare dati e raggiungere distanze proprio server LoRaWAN o utilizzare il servizio LoRaWAN di terze
estremamente lunghe a basse velocità di trasmissione dati. parti.
Il LIG16 utilizza il packet forwarder Semtech e la connessione
LoRaWAN Station, è completamente compatibile con il protocollo Gateway a canale singolo
LoRaWAN. Include un concentratore LoRa SX1302 , che è il chip LoRa Benché ormai non siano più supportati dai cloud come TTN e altri,
in banda base di nuova generazione per gateway con un consumo è possibile acquistare o autocostruirsi un gateway a canale singolo
di corrente inferiore e una maggiore quantità di traffico rispetto ai a solo scopo didattico. Per la costruzione di un gateway a canale
dispositivi precedenti. singolo si veda il nostro corso LoRa su accennato.

cato in formato JSON. Facendo clic sul Location, si accede • Application ID: in questo campo dovete inserire un iden-
alla pagina per impostare la location del gateway. tificativo univoco della applicazione sulla rete. Nel nostro
caso abbiamo scelto: my-rp2040. Tutti i caratteri devono
CREAZIONE DI UN’APPLICAZIONE essere minuscoli, con eventuali trattini e senza spazi.
Fino a questo momento il gateway TTN riceve pacchetti di • Application name: scrivete un nome qualsiasi, a piaci-
dati “grezzi” dal gateway fisico, ovvero pacchetti di dati mento, come per esempio “my-rp2040”.
che includono informazioni del payload e altre informazioni • Description: scrivete una descrizione a piacere.
PROGRAMMARE CON RP2040

relative al trasmettitore e non dell’end device.


In pratica, non siamo ancora in grado di visualizzare e A questo punto dovete fare clic sul pulsante Create applica-
decodificare il messaggio vero e proprio. Per questo motivo, tion per creare l’applicazione, allorché verrete indirizzati alla
dobbiamo necessariamente creare almeno un’applicazione pagina di anteprima che riassume tutti i dati dell’applicazio-
che decodifichi i payload per estrarre i dati dai pacchetti. ne (Fig. 10).
Da questa pagina si può accedere alla sezione End devices,
Pagina Applications così da poter poi andare alla pagina Register end devices.
Facendo clic sul pulsante Applications della console, pos-
siamo vedere tutte le applicazioni attive al momento o Pagina Register end devices
aggiungerne una nuova; nell’esempio proposto nella Fig. 8 è Nella sezione End devices delle Applications non ci sarà an-
presente già un’applicazione. Facendo clic su Add application cora alcun dispositivo registrato, quindi dovete registrarne
si aprirà la relativa pagina (Fig. 9). Nella pagina Add Applica- uno e allo scopo fate clic sul collegamento Add end device,
tion dovete compilare tutti i campi del modulo come segue. che aprirà la pagina Register end device.

29
 Fig. 6 - La pagina del gateway attivo.

 Fig. 7 - La pagina Live data.

PROGRAMMARE CON RP2040

 Fig. 8 - Pagina Applications.

30
Impostati tutti questi campi, cliccate sul pulsante Register
end device per registrare il dispositivo.

COSTRUIAMO L’END DEVICE


Ora che avete configurato il cloud TTN con un gateway
e un’applicazione e che avete aggiunto un end device, la
prossima cosa che dovete fare è creare materialmente il
vostro end device, ovvero connettere la scheda FTR2040
alla breakout board RFM95W; l’ideale sarebbe utilizzare
l’immancabile e pratica breadboard, ma sfortunatamente
abbiamo constatato che la breakout board RFM95W non è
molto adatta alla breadboard, cioè la sua piedinatura non è
compatibile con la spaziatura della breadboard e pertanto
dovete accedere ai pin del breakout con dei fili volanti saldati
 Fig. 9 - Pagina Add Application. direttamente (Fig. 13). La mappatura, vale a dire la corri-
spondenza tra i pin della nostra scheda FTR2040 e quelli
della breakout board dovrà essere quella proposta nella
Qui potrete registrare il vostro dispositivo, nella fattispecie Tabella 2.
il nostro end device FTR2040.
Nella pagina Register end device (Fig. 11), si può scegliere
una marca di dispositivo commerciale dal menu a tendina FTR2040 MODULO RFM95W
Brand... ma non è il nostro caso. 3V3 VCC
Ovviamente per il nostro dispositivo auto costruito, dovete
scegliere l’opzione Manually per compilare manualmente i GND GND
campi come segue (Fig. 12): GP7 DIO0
• Frequency plan: Europe 863-870 MHz (SF9 for RX2 –
GP8 NSS
recommended);
• LoRaWAN version: selezionare 1.0.2; GP9 RST
• Regional Parameters version: RP001 Regional Parame- GP10 DIO1
ters 1.0.2;
• Activation mode: lasciare selezionato OTAA; GP16 MISO
• DevEUI: un ID generato automaticamente; GP18 SCK
• AppEUI: riempire l’ID con tutti 0 (zero);
GP19 MOSI
• AppKey: una chiave generata automaticamente;
• End device name: va scritto un nome qualsiasi, come ad  Tabella 2 - Corrispondenza tra i pad delle due schede
componenti il progetto end point.
esempio rp2040-otaa.
PROGRAMMARE CON RP2040

 Fig. 10 - Pagina Application.

31
 Fig. 11 - Pagina Register end device.

Fate attenzione che i numeri dei pad riportati nella tabella


corrispondono all’impostazione predefinita della libreria e
possono comunque essere modificati nel software, tuttavia  Fig. 12 - Pagina Manually Register end device.

è sconsigliato fare ciò: meglio lasciarli come sono.

IL CODICE DI ESEMPIO lo_otaa, contenente questi tre file:


Nella stessa cartella della libreria che avete già clonato, • CmakeLists.txt;
troverete una cartella examples. • Config.h;
Al suo interno troverete una sottocartella di nome hel- • Main.c;

PROGRAMMARE CON RP2040

 Fig. 13 - Cablaggio della scheda FTR2040 e del modulo RFM95W.

32
Aprite per prima cosa il file config.h e modificatelo in
questo modo:

#define LORAWAN_REGION LORAMAC_REGION_EU868


#define LORAWAN_DEVICE_EUI "70B3D57ED0054DEF"
#define LORAWAN_APP_EUI "0000000000000000"
#define LORAWAN_APP_KEY "9CABA5322B
2630BE471F0C769B81A977"

Resta inteso che dovete sostituire le stringhe con


quelle dell’end device che avete creato in precedenza
su TTN.
Quindi, dopo aver modificato il file config.h, potete
andare avanti e creare l’applicazione di esempio per il
vostro end device.
Per fare questo, entrate nella cartella pico-lorawan,
create una cartella di nome build, entrate nella cartella
build ed eseguite prima il comando cmake e successi-  Fig. 14 - Il debug del dispositivo sul terminale.
vamente il comando make. La compilazione così avviata
potrebbe richiedere qualche minuto. La sequenza di
comandi è quella proposta qui di seguito:
sending unconfirmed message 'hello world!' ... success!
cd home/pi/pico-lorawan. (significa che il messaggio è stato inviato con successo a TTN)
mkdir build
cd build Essendo l’esempio hello_otaa un collegamento di tipo OTAA
cmake .. -DPICO_BOARD=pico (Over The Air Activation) bisognerà aspettare TTN per il JOIN,
make cioè la connessione all’applicazione.
Quando apparirà “success”, significa che il dispositivo è col-
Se tutto va bene, a procedura completata dovreste avere legato all’applicazione e dovreste vedere arrivare i dati nella
il file pico_lorawan_hello_otaa.uf2 nella cartella build/ pagina dell’applicazione e del device (Fig. 15).
examples/hello_otaa. Attenzione! L’esempio hello_otaa prevede di mandare i
A questo punto, potete caricare questo file UF2 nella dati della stringa “hello world!” ogni 5 secondi. Dato che
scheda nel modo consueto, ovvero mettendo a massa il pin TTN pone delle limitazioni nella Community Edition, ovvero
BOOT e inserendo il breakout nella presa USB. alla versione gratuita, vi consigliamo di portare l’invio ad
In questo modo, si aprirà la cartella del dispositivo. almeno 60 secondi.
Trascinate al suo interno il file UF2 e riavviate la scheda Per fare questo, andate alla riga seguente del file main.c
togliendo il corto a massa e ricollegando il dispositivo alla nella cartella dell’esempio, e cambiate il valore dei millise-
presa USB. condi fra un messaggio e l’altro portandolo a 60000:
Dal terminale potete quindi lanciare il comando seguente
per vedere il debug della porta seriale USB: if ((now - last_message_time) > 60000)
PROGRAMMARE CON RP2040

minicom -D /dev/ttyACM0 DECODIFICA DEI MESSAGGI


I messaggi inviati dal dispositivo sono ovviamente una serie
Se il collegamento ha successo, potrete vedere i messaggi di byte incomprensibili all’occhio umano. Se andate nella
seguenti (Fig. 14): pagina Live data del device e fate clic su un messaggio, do-
vreste vedere la stringa hello world! esattamente in questo
success! modo:
(significa che l’inizializzazione del dispositivo ha avuto
successo) 68 65 6c 6c 6f 20 77 6f 72 6c 64 21

Joining LoRaWAN network ... joined successfully! Tale stringa è sostanzialmente la serie di numeri esadeci-
(significa che il collegamento con l’applicazione su TTN ha mali corrispondenti ai valori ASCII della stringa hello world!.
avuto successo) Spiegheremo in seguito come decodificare in maniera au-

33
 Fig. 15 - I dati in arrivo nell’applicazione TTN.

 Fig. 16 - Il messaggio hello world! decodificato.

PROGRAMMARE CON RP2040


tomatica i messaggi, per il momento potete decodificare il
messaggio manualmente, copiandolo e andando in uno dei Cosa occorre?
tanti siti dedicati alla conversione hex to string, come per
La board di Futura Elettronica con RP2040
esempio https://codebeautify.org/hex-string-converter.
(cod. FTR2040) è disponibile a Euro 13,90 e include
Compiendo questa operazione dovreste vedere il messaggio i pin strip da saldare.
decodificato come nell’esempio proposto nella Fig. 16. Dal sito futurashop.it è possibile acquistare lo starter kit
con Rapsberry Pi Pico (cod. RPICOKIT) a Euro 49,90 o il solo
Raspberry Pi Pico (cod. RPI-PICO) a Euro 6,90.
CONCLUSIONI I prezzi si intendono IVA compresa.
Con la speranza di essere stati sufficientemente chiari, vi
invitiamo a sperimentare il progetto presentato in queste Il materiale va richiesto a:
pagine, basato sull’End Point e vi aspettiamo il mese prossi- Futura Elettronica, Via Adige 11, 21013 Gallarate (VA)

mo per la seconda parte del progetto pratico LoRaWAN. Tel: 0331-799775 - www.futurashop.it

34
Programmare con

RP2040

d i P IE R C
ALDERAN

PUNTATA
N. 4

In questa puntata continuiamo a parlare di LoRa/LoRaWAN.


Imparerete a sfruttare il cloud TTN per creare un dispositivo IoT
con visualizzazione dei dati su Node-RED.

N ella scorsa puntata vi abbiamo spiegato


come collegare la nostra scheda FTR2040
a un breakout LoRa/LoRaWAN della
HopeRF RFM95W e come connetterla a The Things
PAYLOAD FORMATTER
Se avete già creato un’applicazione su TTN, con
almeno un end device registrato, potete procedere
nella lettura. In caso contrario rileggete la scorsa
PROGRAMMARE CON RP2040

Network (Fig.1). Se siete riusciti a connettere il puntata che vi spiega come farlo nei dettagli.
vostro end device a un gateway di TTN avrete Accedendo all’applicazione e al vostro end device,
sicuramente visto la stringa “Hello world!”, arrivata dovreste vedere sul menu a sinistra della pagi-
sotto forma di dati grezzi, ovvero una serie di nu- na del device una serie di voci, fra cui Payload
meri esadecimali corrispondenti ai caratteri ASCII formatters (Fig.2). Qui potete trovare una serie
della stringa. Ovviamente, avete avuto bisogno di di cosiddetti “formattatori di payload” di diverso
ricorrere a un convertitore da hex a string per veri- tipo. Quello che useremo come Payload formatter
ficare il tutto. On-line esistono diversi decoder, ad è all’interno del menu Uplink e si chiama Custom Ja-
esempio https://codebeautify.org/hex-string-converter vascript formatter, selezionabile dal menu a tendina.
ma ricorrere a questi servizi, per quanto molto utili, Questo Payload formatter è molto facile da usare
è anche parecchio scomodo. e consente di scrivere direttamente nell’editor una
Vediamo quindi come far compiere questa conver- funzione Javascript che servirà, appunto, a format-
sione in modo automatico all’applicazione TTN. tare il Payload.

35
 Fig. 1 - Cablaggio della scheda FTR2040 e del modulo RFM95W.

All’interno dell’editor, dovreste vedere una funzione prede- bytes: input.bytes


finita simile a questa: },
warnings: [],
function decodeUplink(input) { errors: []
return { };
data: { }

PROGRAMMARE CON RP2040

 Fig. 2 - La pagina Payload formatters.

36
I valori letterali dell'oggetto JSON contengono coppie chia-
 Listato 1
ve/valore separate da due punti.
function Decoder(bytes, port) { Pertanto, con decoded.t1 = bytes[0] assegniamo il valore del
var decoded = {};
decoded.t1 = bytes[0]; // assegnazione del byte di byte in ingresso alla chiave t1 dell’oggetto.
// temperatura alla variabile Quindi avremo un output tipo t1:28 dove t1 è la chiave e 28
return decoded;
il valore dell’oggetto JSON.
}
Ovviamente il valore cambierà in base alla temperatura
function decodeUplink(input) { letta dal sensore.
var data = input.bytes;
var valid = true;
IL CODICE DI ESEMPIO
if (typeof Decoder === "function") {
data = Decoder(data, input.fPort); Il codice di esempio si trova nella stessa cartella examples
} che avete clonato nella scorsa puntata dal repository Gi-
tHub di Sandeep Mistry.
if (typeof Converter === "function") {
data = Converter(data, input.fPort); Se non lo avete ancora fatto, eseguite il seguente comando:
}

if (typeof Validator === "function") { git clone --recurse-submodules https://github.com/sandeepmistry/


valid = Validator(data, input.fPort); pico-lorawan.git
}

if (valid) { Fra le diverse sottocartelle, trovate otaa_temperature_led


return {
che contiene tre file:
data: data
}; • CMakeLists.txt
} else { • Config.h
return {
data: {}, • Main.c
errors: ["Invalid data received"]
};
} Aprite il file config.h e modificatelo in questo modo:
}
#define LORAWAN_REGION LORAMAC_REGION_EU868
#define LORAWAN_DEVICE_EUI "70B3D57ED0054DEF"
#define LORAWAN_APP_EUI "0000000000000000"
Come potete intuire, la funzione non fa nulla di speciale e #define LORAWAN_APP_KEY "9CABA5322B2630BE471F0C769B81A977"
bisognerà scrivere del codice che abbia senso.
Per esempio, supponiamo di voler formattare il valore di Ovviamente, questo è solamente un esempio; dovete sosti-
temperatura inviato dal nostro end device. tuire le stringhe con quelle dell’end device che avete creato
Come già dovreste sapere dalla puntata 2 del corso, il chip in precedenza su TTN. Quindi, dopo aver modificato il file
RP2040 è dotato di un sensore di temperatura incorporato config.h, potete proseguire e compilare il codice per il vostro
e più avanti spiegheremo come scrivere il codice per leggere end device.
i dati da questo e mandarli a TTN tramite l’end device. Per fare questo, entrate nella cartella pico-lorawan, create
La funzione che dovreste scrivere all’interno dell’editor una cartella build (se non l’avete già fatto), entrate nella
potrebbe essere simile a quella che illustriamo nel Listato 1. cartella ed eseguite prima cmake e quindi make.
Una volta scritta la funzione fate clic sul pulsante Save
PROGRAMMARE CON RP2040

change. Come potete vedere nel listato, abbiamo commen-


tato solo la parte che ci interessa di più all’interno della
funzione Decoder:

function Decoder(bytes, port) {


var decoded = {};
decoded.t1 = bytes[0]; // assegnazione della temp alla var
return decoded;
}

La variabile decoded è un oggetto JSON vuoto.


Per chi non lo sapesse, i valori letterali degli oggetti JSON  Fig. 3 - Il debug del dispositivo sul terminale.
sono racchiusi tra parentesi graffe {}.

37
 Fig. 4 - I dati di temperatura in arrivo nel device su TTN.

La compilazione potrebbe richiedere qualche minuto: Dal terminale potete lanciare il comando seguente per
vedere il debug della porta seriale USB:
cd home/pi/pico-lorawan.
mkdir build minicom -D /dev/ttyACM0
cd build
cmake .. -DPICO_BOARD=pico Se il collegamento ha successo, avrete (Fig. 3):
make
success!
Se tutto va bene dovreste avere il file pico_lorawan_otaa_ Joining LoRaWAN network ............ joined successfully!
temperature_led.uf2 nella cartella build/examples/otaa_tem- sending internal temperature: 27 °C (0x1b)... success!
perature_led. A questo punto, potete caricare questo file UF2 sending internal temperature: 28 °C (0x1c)... success!
nella scheda nel modo consueto, ovvero mettendo a massa
il pin BOOT e inserendo il breakout nella presa USB. success! significa che l’inizializzazione del dispositivo ha
In questo modo, si aprirà la cartella del dispositivo. avuto successo.
Trascinate al suo interno il file UF2 e riavviate la scheda Joining LoRaWAN network ... joined successfully! significa che
togliendo il corto a massa e ricollegando il dispositivo alla il collegamento (join) con l’applicazione su TTN ha avuto
presa USB. successo.
sending internal temperature: 28 °C (0x1b)... success! significa
che il messaggio è stato inviato con successo a TTN sotto
forma di numero esadecimale.
Essendo l’esempio otaa_temperature_led basato su una con-
nessione di tipo OTAA (Over-The-Air-Activation) bisognerà
aspettare TTN per il JOIN, cioè l’unione fisica all’applicazio- PROGRAMMARE CON RP2040
ne: i dispositivi eseguono una procedura di unione con la
rete (join), durante la quale viene assegnato un indirizzo di
dispositivo dinamico e le chiavi di sicurezza vengono nego-
ziate con il dispositivo (vedi il BOX OTAA e ABP).
Quando apparirà “success”, significa che il dispositivo è uni-
to (joned) all’applicazione e dovreste vedere arrivare i dati
nella pagina dell’applicazione e del device (Fig. 4).
Il dato di temperatura viene formattato esattamente come
previsto dal Payload formatter. Infatti invece di un solo
numero esadecimale, dovreste vedere la stringa t1 seguita
 Fig. 5 - Pagina Integrations per l’integrazione MQTT di TTN dal valore di temperatura già in gradi Celsius.
Per esempio t1:28.

38
OTAA e ABP
Ogni end device deve essere registrato con una rete prima di ABP
inviare e ricevere messaggi. Questa procedura è nota come Activation By Personalization (ABP) richiede l'hardcoding
attivazione. Sono disponibili due metodi di attivazione. dell'indirizzo del dispositivo e delle chiavi di sicurezza nel
dispositivo. ABP è meno sicuro di OTAA e presenta anche lo
OTAA svantaggio che i dispositivi non possono cambiare provider di
Over-The-Air-Activation (OTAA) è il metodo di attivazione rete senza cambiare manualmente le chiavi nel dispositivo.
più sicuro e consigliato (soprattutto da TTN) per gli end
device. I dispositivi eseguono una procedura di unione con Potete trovare ulteriori informazioni sui metodi attivazione
la rete (join), durante la quale viene assegnato un indirizzo a questo link:
di dispositivo dinamico e le chiavi di sicurezza vengono https://www.thethingsnetwork.org/docs/lorawan/end-device-
negoziate con il dispositivo. activation

ATTENZIONE! L’esempio otaa_temperature_led prevede di su un nostro server Node-RED.


mandare i dati la stringa del sensore ogni 30 secondi. TTN mette a disposizione diversi tipi di integrazione.
Dato che TTN pone delle limitazioni nella Community Edi- Per scoprire quelle previste da TTN è sufficiente aprire il
tion, ovvero alla versione gratuita, vi consigliamo di portare menu a sinistra alla voce Integrations e troverete queste
l’invio ad almeno 60 secondi. possibilità:
Per fare questo, andate nella cartella dell’esempio e aprite il
file main.c. Andate alla riga seguente e cambiate il valore dei MQTT
millisecondi fra un messaggio e l’altro portandolo a 60000: Webhooks
Storage integrations
if (lorawan_process_timeout_ms (60000) == 0) AWS IoT
Azure IoT
INTEGRAZIONE MQTT E NODE-RED LoRa Cloud
MQTT (Message Queue Telemetry Transport ) è un protocol-
lo di messaggistica di pubblicazione/sottoscrizione proget- Facendo clic su MQTT, si aprirà una pagina simile alla Fig. 5.
tato appositamente per l'IoT e per questo motivo scegliere- Qui troverete tutte le informazioni da inserire in seguito in
mo questo tipo di integrazione per poter visualizzare i dati Node-RED per l’integrazione MQTT di TTN.
PROGRAMMARE CON RP2040

 Fig. 6 - Il nodo MQTT.  Fig. 7 - Il tab Connection del nodo MQTT

39
 Listato 2
var obj =
{
"temp":msg.payload.uplink_message.decoded_payload.t1
}

var res_temp = obj["temp"]


var msg1 = { payload:res_temp };

return [msg1]

 Fig. 8 - Il tab Security del nodo MQTT.

tramite il pulsante Generate new API key.


Dovrete copiare queste informazioni dopo aver creato un
flow su Node-RED, come spieghiamo nel prossimo paragrafo.

MQTT E NODE-RED
Fra i framework più utilizzati per la visualizzazione di dati
IoT su un’interfaccia grafica web-based, crediamo che
 Fig. 9 - Il nodo MQTT In connesso a TTN. Node-RED sia sicuramente ai primi posti.
Per approfondire l’uso di Node-RED vi consigliamo il corso
Node-RED pubblicato su Elettronica In dal numero 258 al
numero 265. Per la connessione con TTN, dovete innanzi-
MQTT server host tutto creare un nodo MQTT In, cioè un nodo che rimarrà in
Public address eu1.cloud.thethings.network:1883 ascolto dei dati del broker MQTT di TTN.
Public TLS address eu1.cloud.thethings.network:8883 In un flow di Node-RED trascinate il nodo MQTT In dalla
barra laterale sinistra ed editate il contenuto in questo
Connection credentials modo (Fig. 6):
Username: my-rp2040@ttn
Password: Generate new API key Server: Add new mqtt-broker…
Action: Subscribe to single topic
Oltre all’indirizzo del server MQTT e la porta di connessione, Topic: # (significa la sottoscrizione a qualsiasi topic)
vengono date le credenziali di accesso, che sono relative al QoS: 2
nome utente, ovvero il nome dell’applicazione che state uti- Output: auto-detect (string or buffer)
lizzando seguito da @ttn, e la password che viene generata Name: mqtt TTN (o qualsiasi altro nome)

PROGRAMMARE CON RP2040

 Fig. 10 - Il debug di Node-RED.

40
 Fig. 11 - Il debug di Node-RED con solo il valore di temperatura.

Facendo clic sull’icona matita del menu Add new mqtt-bro-


ker… si aprirà una finestra in cui dovete inserire le informa-
zioni dell’integrazione MQTT di TTN, viste prima.
Nel tab Connection inserite l’indirizzo del broker TTN e un
nome qualsiasi (Fig. 7):

Name: ttn broker


Server: eu1.cloud.thethings.network:1883 Port 1883

Nel tab Security inserite Username e password generati da


TTN (Fig. 8).
Username: my-rp2040@ttn
Password: ****************** (l’API key generata da TTN)

Fate clic su Update e Done per chiudere l’editor e quindi su


Deploy per distribuire il nodo. Dovreste vedere la connes-
 Fig. 12 - Il debug di Node-RED con solo il valore
sione attivarsi, ovvero visualizzare connected in corrispon- di temperatura.
denza del nodo MQTT In (Fig. 9). Senza entrare nei dettagli,
possiamo solo dirvi che i dati del nodo vanno convertiti in un
oggetto JSON da un nodo json collegato all’uscita del nodo dirizzo della dashboard (solitamente 127.0.0.1:1880/ui)
MQTT In. Collegando un nodo debug all’uscita del nodo json dovreste vedere qualcosa di simile alla Fig. 12.
dovreste vedere nella finestra di debug qualcosa di simile Ogni qualvolta il valore di temperatura del vostro end device
alla Fig. 10. Appariranno tutti i dati provenienti dall’end cambierà, vedrete l’ago del gauge muoversi e indicare la
device, compreso la coppia chiave:valore che abbiamo deco- temperatura esattamente come è stata rilevata.
dificato con il Payload formatter: {"t1":28}
A questo punto possiamo collegare un nodo function e CONCLUSIONI
scrivere una funzione che “isoli” solo il dato che ci inte- Con la speranza di essere stati sufficientemente chiari, vi
ressa, ovvero il valore di temperatura. Per fare questo, invitiamo a sperimentare il progetto presentato in queste
all’interno del nodo function scriviamo una funzione che pagine e vi aspettiamo il mese prossimo per continuare la
trovate nel Listato 2. Nella variabile obj creiamo una coppia sperimentazione con la nostra scheda FTR2040. 
PROGRAMMARE CON RP2040

chiave:valore composta dalla chiave “temp” e dal valore


msg.payload.uplink_message.decoded_payload.t1, ovvero dal
valore di t1, che corrisponde alla chiave di temperatura.
Con la variabile var res_temp = obj["temp"] assegniamo il
valore decodificato della temperatura e con var msg1 = { Cosa occorre?
payload:res_temp } creiamo l’oggetto da restituire con return La board di Futura Elettronica con RP2040
[msg1]. Collegando un nodo debug all’uscita del nodo fun- (cod. FTR2040) è disponibile a Euro 13,90 e include
ction dovreste vedere solo il valore di temperatura (Fig. 11). i pin strip da saldare, il modulo LoRa (cod RFM95-868) è in
vendit a Euro 13,50 . I prezzi si intendono IVA compresa.
A questo punto, per visualizzare il valore di temperatura
nella dashboard di Node-RED, basta aggiungere un nodo
Il materiale va richiesto a:
gauge e collegarlo all’uscita del nodo function.
Ovviamente dovrete creare anche un gruppo e tab per Futura Elettronica, Via Adige 11, 21013 Gallarate (VA)
visualizzare il nodo gauge nella dashboard. Andando all’in- Tel: 0331-799775 - www.futurashop.it

41
INDISPENSABILI
IN LABORATORIO!

MICROINVERTER SOLARE WIFI


AD IMMISSIONE DIRETTA IN RETE

Tappeto in silicone Tappetino


per saldatura 550×350 mm antistatico

ANTISTATICO
550×300×2 mm
Tappeto in silicone antistatico multifunzione
PER SALDARE

per saldatura resistente al calore fino a una


temperatura di 500°C. Estremamante flessibile, Tappetino antistatico particolarmente indicato per
anche dopo piegato ritorna sempre posizionare e manipolare componenti o schede
alla sua forma originale. elettroniche. Viene fornito completo di cavo
Dispone di 3 piccoli di collegamento messa terra. Resistività
contenitori superficiale: 10^7 ~ 10^10 ohm/m²,
e di 5 aree tempo decadimento carica
magnetiche. statica: <0,03 secondi.
cod. AS13

cod. AS12 € 13,50


€ 35,00
cod. CUTMAT30X22

€ 9,00
Tappetino da taglio
300×220×2,8 mm
PER TAGLIARE

Tappetino da taglio realizzato in PVC (Polivi-


nile-cloruro) ideale come piano di lavoro per
tagliare carta, cartoncino, cartone pressato, fogli
Prezzi IVA inclusa.

di vinile, ecc. Dispone di griglia di misurazione


1×1 cm e goniometro che consente all’utente di
eseguire segni e tagli precisi.

Scopri la gamma completa su www.futurashop.it


Futura Group
Futura
srl Group srl
Caratteristiche tecniche di questi
questoprodotti
prodotto
® www.futurashop.it Via
ViaAdige,
Adige,11
11• •21013
21013Gallarate
Gallarate(VA)
(VA)
e acquisti on-line su www.futurashop.it
® Tel. 0331/799775
Tel. 0331/799775
• Fax. 0331/792287
Programmare con

RP2040

d i P IE R C
ALDERAN

PUNTATA
N. 5

In questa puntata spieghiamo come usare la porta seriale


della nostra scheda FTR2040 per interfacciarla con Raspberry Pi
e per gestirla in ambiente Node-RED.

N ella progettazione di dispositivi IoT di


qualunque tipo, spesso c'è bisogno di vi-
sualizzare i dati dei sensori su un browser
Internet o di controllarli da remoto, sempre da una
Poiché Raspberry Pi RP2040 è ancora relativamen-
te giovane, la scelta di operare con MicroPython
influenza quale di queste connessioni può essere
utilizzata meglio. Se scegliete la prima opzione,
pagina web. potete passare agli esempi qui sotto per la spiega-
PROGRAMMARE CON RP2040

In questo corso trovate spesso dei riferimenti a zione di come le due schede possono comunicare
Node-RED, perché riteniamo che sia il framework più direttamente via USB. Se scegliete la seconda, è
semplice da usare per la gestione di dispositivi IoT. necessario abilitare i pin TX/RX con i passaggi
In questa puntata imparerete a collegare la nostra descritti nella sezione successiva.
scheda FTR2040 a una scheda Raspberry Pi trami-
te una comunicazione seriale via USB e attraverso CONFIGURARE LA PORTA SERIALE
i collegamenti UART delle rispettive porte GPIO. Per prima cosa vi consigliamo di configurare Ra-
Infine, vedrete anche come visualizzare i dati della spberry Pi in modo che abbia la porta seriale UART
scheda FTR2040 su una pagina web di Node-RED. attivata e la console seriale disattivata. Per fare ciò
Iniziamo precisando che esistono due opzioni per dovete configurare la porta seriale dal pannello di
connettersi da Raspberry Pi al modulo FTR2040: configurazione del menu Preferenze.
• da USB a USB; Nella Fig. 1 potete vedere un fac-simile di configu-
• tramite i pin TX/RX delle rispettive schede. razione delle interfacce in cui si vede chiaramente

43
stesso cavetto USB che utilizzate per la programmazione
della scheda RP2040. Il codice del Listato 1 illustra l’invio di
dati tramite USB dalla scheda RP2040 e quello del Listato 2
per la ricezione di questi dati su Raspberry Pi.
Il primo script è in MicroPython e va caricato nella scheda
FTR2040 come già dovreste sapere dalla prima puntata.
Caricate il file pico_usb_sender.py in Thonny e analizziamo-
lo. Ricordate che nel chip RP2040, i pin ADC supportano 12
bit ma il codice MicroPython può ridimensionare i valori ADC
in un intervallo di 16 bit. Quindi otteniamo effettivamente
l'intervallo da 0 a 65535. Il microcontrollore funziona a
3,3V, il che significa che un pin ADC restituirà un valore su
65.535 livelli di tensione quando gli vengono applicati 3,3V
o zero quando non c'è tensione. Quindi, possiamo ottenere
 Fig. 1 - Il pannello di configurazione di Raspberry Pi tutti i valori intermedi quando la tensione applicata al pin
è compresa tra 0 e 3,3 V. Come avete visto, i pin ADC sono
etichettati ADC0, ADC1, ADC2 e ADC_VREF (che tecnica-
che la porta seriale è attivata e la console seriale disattivata. mente sarebbe ADC3), e sono i quattro pin ADC accessibili
Questo evita di mandare comandi dalla console alla porta dall'esterno. Il sensore di temperatura non ha un pin fisico
seriale. nella scheda ma è accessibile da MicroPython come ADC4.
Vi ricordiamo che il valore del sensore di temperatu-
COMUNICAZIONE SERIALE VIA USB ra necessita di una conversione particolare. Si tratta di
L'invio e la ricezione di dati da e verso Raspberry Pi tramite una semplice operazione matematica esposta nel da-
la porta USB è davvero molto semplice; potete usare lo tasheet di Raspberry Pi, consultabile dalla pagina web

PROGRAMMARE CON RP2040

 Fig. 2 - L’output di Thonny.

44
https://datasheets.raspberrypi.com; da essa si evince che
una temperatura di 27 gradi Celsius fornisce una tensione  Listato 1
di 0,706 V e che ogni grado aggiuntivo riduce la tensione di import sys
1,721 mV (0,001721 V, se preferite). import machine
Il primo passaggio nella conversione della temperatura a 16 import utime

bit è riconvertirla in volt. Questo viene fatto in base alla ten- usb = sys.stdout
sione massima di 3,3V utilizzata dalla scheda. Con questa sensor_temp = machine.ADC(4)
conversion_factor = 3.3 / (65535)
conversione, il valore della temperatura viene stabilito con
questa operazione: while True:
reading = sensor_temp.read_u16() * conversion_factor
temperature = int(27 - (reading - 0.706)/0.001721)
27 - (valore da 0 a 65535 - 0.706)/0.001721 usb.write(str(temperature))
utime.sleep(2)

Per comodità commentiamo il Listato 1 riga per riga:

import sys # importa la libreria sys di sistema


import machine # importa la libreria machine di MicroPython  Listato 2
import utime #importa la libreria utime (microtime) di MicroPython
import serial #importa la libreria seriale
ser = serial.Serial('/dev/ttyACM0', 115200)
sensor_temp=machine.ADC(4) #crea l’oggetto per il sensore di temperatura #imposta l’oggetto seriale come dispositivo
#sulla porta ACM0 creata per la comunicazione USB
conversion_factor=3.3/(65535) #variabile per il fattore di conversione
while True: #ciclo while
reading_usb = ser.readline()
while True: #ciclo while
#lettura del messaggio dalla porta USB
reading = sensor_temp.read_u16() * conversion_factor print(reading_usb.decode('ascii')[0:-2])
#variabile di lettura del sensore di temperatura #decodifica del messaggio ricevuto

temperature = int(27 - (reading - 0.706)/0.001721)


#operazione di conversione della temperatura float
#in numeri interi
print(str(temperature)) Vedrete quindi sul terminale qualcosa simile alla Fig. 3.
#scrive il valore di temperatura sull’output standard Notate che quando attivate l’output standard sul termi-
utime.sleep(2) # ritardo di 2 secondi nale, se collegate Thonny alla stessa porta USB utilizzata
per l’output standard, ciò comporterà la disconnessione da
Se mandate in esecuzione il codice, vedrete nella shell di Thonny: vedrete apparire nella shell di Thonny un messag-
Thonny qualcosa simile alla Fig. 2. gio di questo tipo: “Connection lost (device reports readi-
Ora esaminiamo il Listato 2, relativo al lato ricevitore di Ra- ness to read but returned no data (device disconnected or
spberry Pi. Aprite Thonny e caricate il file rpi_usb_receiver.py. multiple access on port?)). Use Stop/Restart to reconnect”,
Come potete vedere, bastano poche righe per visualizzare ovvero, “Connessione persa (il dispositivo segnala la dispo-
sul terminale il messaggio inviato sull’output standard del nibilità alla lettura ma non ha restituito dati (dispositivo
dispositivo ACM0, corrispondente alla porta USB: disconnesso o accesso multiplo sulla porta?)).
Utilizzare Stop/Restart per riconnettersi.
import serial #importa la libreria seriale
ser = serial.Serial('/dev/ttyACM0', 115200)
PROGRAMMARE CON RP2040

#imposta l’oggetto seriale come dispositivo


#sulla porta ACM0 creata per la comunicazione USB

while True: #ciclo while


reading_usb = ser.readline() #lettura del messaggio dalla porta USB
print(reading_usb.decode('ascii')[0:-2])
#decodifica del messaggio ricevuto

Attenzione: eseguite lo script in Python da terminale e non


da Thonny; allo scopo, andate nella cartella dove risiede il
file e digitate:
 Fig. 3 - L’output sul terminale.
python rpi_usb_receiver.py

45
come slave. Se osservate il Listato 3, abbiamo creato una
sorta di protocollo di comando per poter gestire la scelta del
 Listato 3
canale ADC, tramite l’input dell’utente.
import serial #importa la libreria seriale Aprite il file rpi_usb_adc_sender.py e osservate che nel ci-
ser = serial.Serial('/dev/ttyACM0', 115200)
clo while, tramite l’istruzione input, viene chiesto all’utente
#imposta l’oggetto seriale come dispositivo sulla porta ACM0
#creata per la comunicazione USB di scegliere un canale ADC:
while True: #ciclo while
command = string(result) + \n #input dell’utente result= input("Inserisci un canale ADC: ")
command = string(result) + \n #input dell’utente
ser.write(bytes(command.encode('ascii')))
La risposta dell’utente viene convertita in una stringa a cui
viene aggiunto un carattere di “a capo”:

command = string(result) + \n

 Listato 4
Con l’istruzione successiva viene inviata alla porta seriale la
import select risposta dell’utente codificata ASCII:
import sys
import machine
import utime ser.write(bytes(command.encode('ascii')))

sensor_temp = machine.ADC(4)
adc0 = machine.ADC(0) Ora guardate il Listato 4 che illustra il codice da scrivere con
adc1 = machine.ADC(1) MicroPython e caricare nella scheda FTR2040. Aprite il file
adc2 = machine.ADC(2)
adc3 = machine.ADC(3) pico_usb_receiver.py e osservate che sono stati assegnati
conversion_factor = 3.3 / (65535) tutti i canali ADC a 5 variabili:
while True:
sensor_temp = machine.ADC(4)
if select.select([sys.stdin],[],[],0)[0]:
adc0 = machine.ADC(0)
ch = sys.stdin.readline()
if ch[0]== "0": adc1 = machine.ADC(1)
print("adc ch: " + str(ch[0]) + " : " + adc2 = machine.ADC(2)
str(adc0.read_u16()))
if ch[0]== "1": adc3 = machine.ADC(3)
print("adc ch: " + str(ch[0]) + " : " +
str(adc1.read_u16()))
if ch[0]== "2": Nel ciclo while viene effettuata la selezione del canale ADC
print("adc ch: " + str(ch[0]) + " : " + attraverso la lettura del valore corrispondente dalla porta
str(adc2.read_u16()))
if ch[0]== "3":
seriale:
print("adc ch: " + str(ch[0]) + " : " +
str(adc3.read_u16())) if select.select([sys.stdin],[],[],0)[0]:
if ch[0]== "4":
reading = sensor_temp.read_u16() * ch = sys.stdin.readline()
conversion_factor
temperature = 27 - (reading - 0.706)/0.001721
print("Temp: " + str(temperature)) A questo punto, dopo la lettura del canale selezionato, il va-
lore viene assegnato all’istruzione per la lettura del canale
else:
print ("NO data")
ADC e quindi stampato il valore del sensore collegato a quel
utime.sleep(2) canale. Per esempio, nel caso di ADC0, ADC1, ADC2, ADC3,
verranno stampati valori compresi da 0 a 4095. Nel caso di PROGRAMMARE CON RP2040
ADC4 verrà stampato il valore del sensore di temperatura,
rilevata come già spiegato in precedenza:
Questo significa che se volete usare nuovamente Thonny
con la scheda FTR2040, dovete prima fermare lo script if ch[0]== "0":
Python da terminale (CTRL+C) e premere il tasto Stop di print("adc ch: " + str(ch[0]) + " : " + str(adc0.read_u16()))
Thonny. if ch[0]== "1":
print("adc ch: " + str(ch[0]) + " : " + str(adc1.read_u16()))
ACCEDERE ALLE PORTE ADC VIA USB if ch[0]== "2":
Visto che il chip RP2040, oltre al sensore di temperatura, è print("adc ch: " + str(ch[0]) + " : " + str(adc2.read_u16()))
dotato di 4 porte ADC per il collegamento di sensori ana- if ch[0]== "3":
logici, potrebbe essere interessante gestire queste porte print("adc ch: " + str(ch[0]) + " : " + str(adc3.read_u16()))
utilizzando Raspberry Pi come master e la scheda FTR2040 if ch[0]== "4":

46
reading = sensor_temp.read_u16() * conversion_factor
temperature = 27 - (reading - 0.706)/0.001721
print("Temp: " + str(temperature))

In assenza di input dell’utente non verrà assegnato nessun  Fig. 4 - L’input dell'utente da terminale.
canale e quindi verrà stampato “No data”.
Dopodiché, mandate in esecuzione il codice python da ter-
minale e vedrete qualcosa di simile alla Fig. 4. Supponendo porta UART di Raspberry Pi con quelli della porta UART della
di aver scelto il canale ADC4 corrispondente al sensore di scheda FTR2040, seguendo lo schema riportato in Tabella 1.
temperatura, vedrete il valore del sensore di temperatura A complemento di ciò, la Fig. 6 illustra il collegamento fisico
nella shell di Thonny. Se inserite valori da 0 a 3, otterrete i delle due porte UART (ricordate anche di collegare una
valori dei canali ADC da 0 a 3 e vedrete apparire nella shell massa comune). Qui di seguito vedete il codice relativo a
di Thonny qualcosa simile alla Fig. 5, con il valore dei senso- MicroPython per la scheda FTR2040.
ri corrispondenti all’input dell’utente.
import os
COLLEGAMENTO DIRETTO TRA I PIN TX/RX import machine
Per poter gestire la comunicazione seriale senza conflitti di from time import sleep
sistema, ovvero l’utilizzo contemporaneo della porta USB, è uart = machine.UART(0, 115200)
necessario collegare le due schede fisicamente tramite una sensor_temp = machine.ADC(4)
porta UART. conversion_factor = 3.3 / (65535)
La porta UART predefinita di Raspberry Pi corrisponde ai b = None
pin GPIO 14 (TX) e GPIO 15 (RX). Una delle porte UART della msg = ""
scheda FTR2040 corrisponde ai pin GP0 (TX) e GP1 (RX) while True:
Sapendo questo, dovete semplicemente collegare i pin della reading = sensor_temp.read_u16() * conversion_factor
PROGRAMMARE CON RP2040

 Fig. 5 - L’output di Thonny

47
temperature = int(27 - (reading - 0.706)/0.001721)
uart.write(str(temperature))
sleep(2)

Caricate il file pico_uart_sender.py in Thonny e osservate


che, con l’istruzione

uart = machine.UART(0, 115200)

viene creato l’oggetto uart sulla porta UART 0, corrispon-


dente proprio ai suddetti pin GP0 e GP1.
Il codice per la lettura del sensore della temperatu-
 Fig. 6 - Collegamento fisico delle porte UART.
ra rimane pressoché invariato e con l’istruzione uart.
write(str(temperature)) viene scritto il valore int della tem-
peratura, visto che non ci servono i decimali del valore float.

PUBBLICAZIONE DEI DATI SU NODE-RED


Per poter visualizzare i dati in modo più efficiente e anche
più gradevole, abbiamo creato un codice di lettura dei dati
 Fig. 7 - Il broker MQTT in esecuzione.
seriali di temperatura e la pubblicazione di questi su un
broker MQTT.
A nostro avviso, diventa davvero molto semplice collegarsi
al broker MQTT da remoto e creare una pagina web con
Node-RED per la visualizzazione dei dati ricevuti dal broker
MQTT. Vediamo come fare.
Per prima cosa, installate su Raspberry Pi un broker MQTT
come ad esempio Mosquitto (https://mosquitto.org); aprite il
terminale e digitate:

sudo apt update


sudo apt install -y mosquitto mosquitto-clients
sudo systemctl enable mosquitto.service

Potete modificare il file di configurazione in questo modo:

sudo nano /etc/mosquitto/mosquitto.conf

Dopo aver impartito tale comando ed aperto il file suddetto,


andate ad aggiungere le righe seguenti:
 Fig. 8 - L’editor del nodo MQTT in di Node-RED.

listener 1883
allow_anonymous true PROGRAMMARE CON RP2040
Fatto ciò salvate il file e riavviate mosquitto con questo
comando:

sudo systemctl restart mosquitto

Infine, eseguite mosquitto in background come demone:

mosquitto -d

 Fig. 9 - Il flow completo di Node-RED.


Il Listato 5 illustra il codice per la ricezione dalla porta UART
predefinita di Raspberry Pi (AMA0).

48
L’insieme delle istruzioni per inizializzare la porta è:
 Listato 5
ser = serial.Serial ('/dev/ttyAMA0', import time
baudrate = 115200, import serial
from paho.mqtt import client as mqtt_client
parity=serial.PARITY_NONE,
stopbits=serial.STOPBITS_ONE, ser = serial.Serial('/dev/ttyAMA0', baudrate = 115200,
parity=serial.PARITY_NONE, stopbits=serial.STOPBITS_ONE,
bytesize=serial.EIGHTBITS,
bytesize=serial.EIGHTBITS, timeout=1)
timeout=1
broker = 'localhost'
port = 1883
Segue tutto il codice per la pubblicazione sul broker MQTT topic = "temp"
che è in esecuzione come demone all’indirizzo “localhost” client_id = "control"

di Raspberry Pi, ovvero con l’IP 127.0.0.1, sulla porta def connect_mqtt():
di default 1883. A questo punto, è sufficiente creare una def on_connect(client, userdata, flags, rc):
if rc == 0:
connessione MQTT da un server Node-RED in esecuzione su print("Connected to MQTT Broker!")
un computer remoto. Per semplicità, il computer utilizzato è else:
nella stessa rete di casa e quindi può connettersi al broker print("Failed to connect, return code %d\n", rc)

MQTT di Raspberry Pi attraverso un IP assegnato dal router, client = mqtt_client.Client(client_id)


per esempio, 192.168.1.100 o qualcosa di simile. Per i client.on_connect = on_connect
client.connect(broker, port)
collegamenti da DNS esterni, bisognerà impostare il router return client
di casa come port forwarding.
def publish(client):
Senza entrare nei dettagli del codice MQTT, guardate le msg_count = 0
righe del Listato 5 che riportano il seguente codice: while True:
temp=ser.readline()
result = client.publish(topic, temp)
while True:
temp=ser.readline() def run():
client = connect_mqtt()
result = client.publish(topic, temp) client.loop_start()
publish(client)
Come potete vedere, ogni volta che viene ricevuto un dato if __name__ == '__main__':
di temperatura dalla porta seriale, questo viene pubblicato run()
nel broker MQTT nel topic stabilito in precedenza. Il topic
che abbiamo impostato l’abbiamo chiamato “temp”.
Mandate in esecuzione da terminale il file mqtt_rpi_serial_ nodo di debug al nodo mqtt in e fate il deploy del flow. Nella
receive.py e vedrete qualcosa di simile alla Fig. 7. finestra di debug vedrete arrivare i dati di temperatura della
A questo punto, avviate il server Node-RED su un PC remoto scheda FTR2040 (Fig. 9). Per rendere tutto più gradevole,
e recatevi nella home di Node-RED al consueto indirizzo lo- aggiungete un nodo gauge di tipo “ago” e configuratelo in
cale 127.0.0.1:1880. Nell’editor di Node-RED, trascinate in un tab e un gruppo della dashboard. Dopo il deploy vedrete
un flow un nodo mqtt in e configuratelo in modo da connet- nella dashboard di Node-RED qualcosa di simile alla Fig. 10.
terlo al broker MQTT di Raspberry Pi, usando l’indirizzo as- Per comodità, potete importare in Node-RED il nostro file
segnato dal router, per esempio, 192.168.1.100, e alla porta pronto all’uso che si chiama flow_pico_mqtt.json.
predefinita 1883 (Fig. 8). Se non avete fatto errori vedrete Con questo abbiamo concluso; vi invitiamo a sperimentare
comparire “connected” sotto al nodo mqtt in. Collegate un

il progetto e vi rimandiamo alla prossima puntata.
PROGRAMMARE CON RP2040

Cosa occorre?
La board di Futura Elettronica con RP2040
(cod. FTR2040) è disponibile a Euro 13,90 e include
i pin strip da saldare, il modulo LoRa (cod RFM95-868)
è in vendita Euro 13,50. I prezzi si intendono IVA compresa.

Il materiale va richiesto a:

 Fig. 10 - Il gauge ad ago con il valore di temperatura


Futura Elettronica, Via Adige 11, 21013 Gallarate (VA)
nella dashboard di Node-RED.
Tel: 0331-799775 - www.futurashop.it

49
Lampade da tavolo per ogni esigenza!
A LED, con lente, con ricarica wireless...

Lampada da tavolo
Lampada a LED da tavolo a LED con lente
dimmerabile con fissaggio a clip d’ingrandimento

Lampada LED
touch con orologio
 Alimentazione: 5 Vdc – 1 A
 Consumo: 3 W e termometro
 Flusso luminoso: 60 -110 lm
 Temperatura colore: 3000 – 6500 K  Lente d’ingrandimento:  Temperatura colore:
 Dimensioni (mm): 66 x 53 x 123 3 + 12 diottrie 3000K-6000K
x 390 (braccio)  Ingrandimento: 1,75 x + 4 x  Flusso luminoso:
 Alimentazione: max. 300 lumen dimmerabile

€34,00
230 VAC / 50 Hz – 5,5 W  Alimentazione: 5 VDC / 1 A –
 Flusso luminoso: 400 lumen tramite adattatore di rete: 220
 Temperatura colore: VAC (incluso)
6000-7000 K  Consumo: 6 W
Cod. VTLLAMP15  Diametro lente: 85 mm
 Lunghezza braccio

€39,00
di supporto: 250 mm
Lampada da tavolo a LED
con lente d’ingrandimento
 Lente d’ingrandimento: 3 + 12 diottrie
Cod. TP206 €42,00
Cod. TP231
 Ingrandimento: 1,75 x + 4 x
 Alimentazione:
230 VAC / 50 Hz – 6,5 W
 Flusso luminoso:
Lampada LED touch dimmerabile
520 lumen con ricarica wireless
 Temperatura colore:
per smartphone
6500 K
 Diametro lente: 90 mm
Lampada LED professionale
 Lunghezza braccio con lente d’ingrandimento
di supporto: 290 mm
 Lente d’ingrandimento:

€49,50
3 diottrie
 Flusso luminoso: 850 lumen
 Temperatura colore: 6500 K
 Temperatura colore:  Fissaggio: morsetto da tavolo
Cod. TP248 2800 K – 3400 K –  Lunghezza del braccio: 790 mm
4500 K – 5600 K  Consumo: da 0,5 a 12 W
 Flusso luminoso: 250 lumen  Alimentazione: 230 VAC / 50 Hz – 5,5 W
Lampada professionale  Alimentazione: 5 VDC / 2,5 A
– a corredo cavo USB e adattatore
a LED dimmerabile - 880 da rete 220 VAC (opzionale)
lumen  Consumo: 5 watt
 Ricarica wireless: 5 V / 1 A

€98,00
 Dimensioni (mm): 126x45x440

€34,00
Prezzi IVA inclusa.

 Alimentazione:
Cod. TP233
220 VAC – 240 VAC / 50 Hz
 Consumo: da 1,5 a 14,5 W Cod. EFL60
(dipende dalla luminosità)
 Flusso luminoso: 880 lumen

€134,00
 Temperatura colore: 6000-7000 K
 Montaggio: morsetto metallico
per il fissaggio al banco
 Dimensioni (mm): 450 x 80 x 400 (braccio) Cod. TP243

Futura Group
Futura
srl Group srl
Caratteristiche tecniche di questi prodotti
® www.futurashop.it Via
ViaAdige,
Adige,11
11• •21013
21013Gallarate
Gallarate(VA)
(VA)
e acquisti on-line su www.futurashop.it
Tel. 0331/799775
Tel. 0331/799775
• Fax. 0331/792287
Programmare con

RP2040

d i P IE R C
ALDERAN

PUNTATA
N. 6

In questa puntata spieghiamo come usare la nostra scheda FTR2040


come controller per LED NeoPixel.

I n questo corso abbiamo illustrato le molte


potenzialità della scheda FTR2040, ovvero del
processore Raspberry Pi RP2040 e di tutti i
modelli compatibili. Potremmo proseguire all’infinito,
tamente dalla scheda un anello a 12 o 24 LED non ci
sono problemi, ma per strisce di LED molto lunghe
dovete procurarvi un’alimentazione esterna.
Per fare funzionare l’anello o la striscia NeoPixel,
ma come per ogni cosa, anche questo corso deve dovete saldare sul retro dell’anello tre dei quattro
PROGRAMMARE CON RP2040

terminare e vogliamo lasciarvi con un progetto facile terminali:


e divertente. • GND: massa
• 5 o 3.3 volt: alimentazione positiva
LED NEOPIXEL • DI: ingresso digitale
Nel kit di Futura Elettronica per Raspberry Pi Pico,
fra le molte cose disponibili, c’è anche un anello con Se volete collegare in cascata più anelli (o più strisce)
12 LED RGB con driver integrato WS2812B. di LED, dovete saldare il terminale DO (digital output)
Per semplicità di spiegazione, d’ora in poi chiame- al corrispondente terminale DI del successivo anello
remo questo dispositivo con il termine NeoPixel, (o striscia).
amichevolmente chiamato così da Adafruit (Fig. 1).
Si fa notare che questo progetto può essere applica- CABLAGGIO DELL’ANELLO NEOPIXEL
to anche a strisce di LED NeoPixel indirizzabili con lo Il primo passo è quello di collegare l’anello NeoPixel
stesso driver. Fate attenzione! Per alimentare diret- alla scheda FTR2040, come mostrato in Fig. 2.

51
Dopo aver saldato i tre terminali all’anello, inserite nella
breadboard i cavetti in questo modo:

SCHEDA FTR2040 NEOPIXEL

GND GND
VBUS 3.3V
GP28 DI

PROGRAMMAZIONE DEI LED NEOPIXEL


Prima di poter programmare l’anello, dovete installare la
libreria NeoPixel nella scheda FTR2040. Fra le tante librerie
 Fig. 1 - L'anello NeoPixel a 12 LED. disponibili abbiamo scelto quella che ci sembra più facile da
usare rispetto a quello fornita da Adafruit.
Il repository GitHub della libreria NeoPixel è il seguente:
https://github.com/blaz-r/pi_pico_neopixel
Si ricorda che la scheda può alimentare un numero limitato Una volta clonato il repository sul vostro Raspberry Pi, trove-
di LED NeoPixel a causa della corrente ridotta che può essere rete all’interno della cartella la libreria “neopixel.py”.
assorbita dal pin 5V sulla scheda. Aprite il file con Thonny e, con il comando salva con nome,
Gli esempi seguenti presuppongono l’uso di un anello o stri- salvatelo all’interno della scheda (Fig. 3).
scia NeoPixel con al massimo 24 LED. All’interno della cartella examples, troverete vari esempi.

PROGRAMMARE CON RP2040

 Fig. 2 - Il cablaggio dell'anello NeoPixel e la scheda FTR2040.

52
vengono stabiliti dalle variabili seguenti:

red = (255, 0, 0)
green = (0, 255, 0)
blue = (0, 0, 255)

L’istruzione seguente imposta il primo valore di K sul rosso, il


successivo valore di K sul verde, il successivo valore di K sul
blu e il resto a R, G, B, R, G, B ecc…
K = min (K, (numpix-1) // 3) # notare il doppio simbolo di divi-
 Fig. 3 - Il salvataggio della libreria neopixel.py
sione per ottenere un risultato intero e non float
all’interno della scheda.
Per impostare la luminosità si usa l’istruzione seguente con
valori da 1 a 255:
Per vedere se tutto funziona, aprite il file di esempio set_ran-
ge.py e modificate le righe seguenti, come evidenziato nel strip.brightness (255)
Listato 1:
Quindi si impostano i colori di partenza:
strip = Neopixel(numpix, 0, 0, "GRB")
numpix = 60 # numero di LED strip[:] = blue # tutto blu
time.sleep (5.0) # tempo di attesa con tutti i LED accesi
time.sleep (0.5) # tempo della velocità di rotazione dei LED poi vengono alternati i colori red e green con delle operazioni
sulla costante K.
… in questo modo:

strip = Neopixel(numpix, 0, 24, "RGB")


numpix = 12
 Listato 1
time.sleep (1.0)
time.sleep (0.1) import time
from neopixel import Neopixel

In pratica, abbiamo impostato a 12 il numero di LED dell’anel-


numpix = 12
lo e ridotto il tempo di attesa per i LED tutti accesi e il tempo di K = 3
rotazione dei LED. Lasciate tutto il resto inalterato.
strip = Neopixel(numpix, 0, 28, "GRB")
Analizzando le parti salienti dell’esempio, potete notare che red = (255, 0, 0)
all’inizio viene importata la libreria neopixel, ovvero quella che green = (0, 255, 0)
blue = (0, 0, 255)
avete salvato nella scheda con l’operazione descritta prima.
# imposta la prima K sul rosso, la successiva K sul verde,
# la successiva K sul blu;# e il resto in R,G,B,R,B ..
from neopixel import Neopixel # e poi inizia la rotazione .

# riduce K, se numpix è < K*3+1K = min(K,(numpix-1)//3)


Quindi, la variabile numpix = 12 imposta il numero di LED
strip.brightness(80)
dell’anello e va commisurata al numero di LED dell’anello o
PROGRAMMARE CON RP2040

della striscia NeoPixel. strip[:] = blue # prima tutto in blu...


# ora riempie il rosso e il verde...
Subito dopo l’oggetto strip viene impostato dalla classe Neo- strip[:K] = red
pixel con i seguenti parametri: strip[K:2*K] = green
strip[3*K::3] = red
strip[3*K+1::3] = green
strip = Neopixel (numpix, 0, 24, "RGB")
strip.show()

In pratica, l’oggetto strip viene impostato a 12 LED con il # appaiono i LED per 2 secondi...
time.sleep(2.0)
collegamento al pin GP24 della scheda. Il tipo di colorazione
è RGB, ma potrebbe anche essere RGBW, se esiste anche il # rotazione...

canale White. Notare che si possono ordinare i colori con varie while(True):
combinazioni, per esempio, GRB, BRG ecc. a seconda di come strip.rotate_right()
strip.show()
si vogliono accendere nell’ordine i LED in rosso, in verde o blu. time.sleep(0.1)
La variabile K = 3 imposta la posizione dei tre colori RGB che

53
rappresenta il colore iniziale.
 Listato 2 Parametro right_rgb_w: tupla di forma (r, g, b) o (r, g, b, w)
from machine import ADC, Pin che rappresenta il colore finale.
from time import sleep Parametro how_bright: [predefinito: Nessuno] Imposta la lu-
photoPIN = 27 minosità dell'intervallo corrente. Se how_bright è None, viene
usato il valore di luminosità globale.
def readLight(photoGP):
photoRes = ADC(Pin(27))
light = photoRes.read_u16() Il metodo crea un gradiente di colore, ovvero una transizione
light = round(light/65535*100,2)
return light di colore da left_rgb_w a right_rgb_w tra i led con indice
pixel1 e indice pixel2 (inclusi).
while True:
print ("luninosità: " + str(readLight(photoPIN)) +"%") Esempio per un anello di 12 LED RGB:
sleep (1)
rgbw1 = (0, 0, 50)
rgbw2 = (50, 0, 0)
strip.set_pixel_line_gradient(0, 11, rgbw1, rgbw2) # crea un
gradiente da blu a verde per tutti i LED da 0 a 11
strip[:K] = red
strip[K:2*K] = green set_pixel_line(pixel1, pixel2, rgb_w, how_bright = None)
strip[3*K::3] = red Parametro pixel1: indice del pixel iniziale (incluso).
strip[3*K+1::3] = green Parametro pixel2: indice del pixel finale (incluso).
Parametro rgb_w: tupla di forma (r, g, b) o (r, g, b, w) che
Il comando seguente fa apparire il tutto: rappresenta il colore da utilizzare.
Parametro how_bright: [predefinito: Nessuno] La luminosità
strip.show () dell'intervallo corrente. Se how_bright è None, viene usato il
valore di luminosità globale.
… viene introdotta un’attesa di 2 secondi: Il metodo riempie i led dal led con l'indice pixel1 all'indice
pixel2 (inclusi) con il colore rgb_w.
time.sleep (2.0) Esempio:
rgb = (0, 50, 0)
… e poi inizia la rotazione a destra di tutti i LED con un tempo strip.set_pixel_line(0, 5, rgb) #accende 6 LED in rosso da 0 a 5.
di 0.1 secondi fra le accensioni. In questo modo si ottiene una
rotazione abbastanza gradevole. Per cambiare la velocità di rgb = (0, 0, 50)
rotazione, basta variare il tempo di time.sleep. strip.set_pixel_line(6, 8, rgb) #accende 3 LED in blu da 7 a 9.

While (True): set_pixel(pixel_num, rgb_w, how_bright=None)


strip.rotate_right() Parametro pixel_num: indice del pixel da impostare o oggetto
strip.show() slice che rappresenta più led.
time.sleep(0.1) Parametro rgb_w: tupla di forma (r, g, b) o (r, g, b, w) che
rappresenta il colore da utilizzare.
I METODI DELLA LIBRERIA NEOPIXEL Parametro how_bright: [predefinito: Nessuno] La luminosità
Per vostra comodità riportiamo alcuni metodi della libreria dell'intervallo corrente. Se how_bright è None, viene usato il
neopixel da usare per svariati effetti. Tutti gli esempi seguenti valore di luminosità globale.
sono riportati nel nostro codice “esempi_neopixel.py”. PROGRAMMARE CON RP2040
Il metodo imposta il pixel sull'indice pixel_num sul colore
brightness(brightness=None) rgb_w. Se pixel_num è un oggetto slice, l'operazione viene
Parametro luminosità: [predefinito: Nessuno] applicata a tutti i pixel inclusi nella slice.
Valore di luminosità nell'intervallo da 1 a 255. Esempio:
Esempio: strip.set_pixel(5, (0, 0, 92)) # accende il LED numero 6 di blu
strip.brightness (42) #imposta la luminosità a 42 con intensità 92

set_pixel_line_gradient(pixel1, pixel2, left_rgb_w, right_ setitem (idx, rgb_w)


rgb_w, how_bright=None) Parametro idx: l'indice può essere un numero di indicizzazione
Parametro pixel1: indice del pixel iniziale (incluso). o uno slice (vedere sotto).
Parametro pixel2: indice del pixel finale (incluso). Parametro rgb_w: tupla di forma (r, g, b) o (r, g, b, w) che
Parametro left_rgb_w: tupla di forma (r, g, b) o (r, g, b, w) che rappresenta il colore da utilizzare.

54
Imposta il pixel o i pixel rappresentati da idx al colore rgb_w. da accendere attraverso l’uso di un sensore di luce. Per prima
Esempi con anello da 12 LED: cosa procuratevi un fotoresistore, comunemente chiamato
strip[2] = (0,255,0) # imposta il LED 2 in verde LDR (Light Dependent Resistor), e collegatelo alla scheda
strip[3:6] = (255,0,0) # imposta i LED da 3 fino a 6 in rosso come illustrato in Fig. 4. Usate un resistore da 10 kΩ come
strip[7:9:11] = (0,0,255) # imposta i LED 7, 9, 11 in blu pulldown per l’ingresso GP27 della scheda.
strip[1::2] = (0,0,0) # imposta tutti i LED dispari su 'off' Aprite il codice di esempio ldr_test.py e vedrete quanto è
semplice impostare la lettura del fotoresistore su un pin con
rotate_left(num_of_pixels=None) caratteristiche ADC. Ricordiamo che i pin ADC dell’RP2040
Parametro: [predefinito: Nessuno] Imposta il numero di pixel sono GP26 (ADC0), GP27 (ADC1) e GP28 (ADC2).
da spostare a sinistra. Se num_of_pixels è None, si sposta di Tenendo d’occhio il Listato 2, potete vedere come funziona
1. Attenzione! Dovete mettere il metodo all’interno di un ciclo la lettura del pin ADC della scheda. Tutto è demandato alla
While. seguente istruzione:
Il metodo sposta tutti i pixel in modo circolare a sinistra con
un passo definito da num_of_pixels. photoRes = ADC(Pin(27))
Esempio:
while True: Quindi, basta impostare la lettura a 16 bit:
strip.rotate_left(1) # [1, 2, 3] diventa [2, 3, 1]
time.sleep (.1) light = photoRes.read_u16()

rotate_right(num_of_pixels=None) … e applicare l’operazione seguente per ottenere una percen-


Parametro: [predefinito: Nessuno] Imposta il numero di pixel tuale di luminosità, con due decimali di precisione:
da spostare a destra. Se num_of_pixels è None, si sposta di
1. Attenzione! Dovete mettere il metodo all’interno di un ciclo light = round (light/65535 * 100 , 2)
while.
Il metodo sposta tutti i pixel in modo circolare a destra con un Nel ciclo while si stamperà il valore in stringa della percentua-
passo definito da num_of_pixels. le della luminosità a intervalli di un secondo:
Esempio:
while True: while True:
strip.rotate_right(1) # [1, 2, 3] diventa [2, 3, 1] print ("luminosità: " + str (readLight(photoPIN)) +"%")
time.sleep (.1) sleep(1)

show() Il risultato è visibile in Fig. 5.


Il metodo invia i dati in uscita, facendo in modo che tutte le A questo punto non ci resta che collegare l’anello NeoPixel e il
modifiche sui LED abbiano effetto. Questo metodo dovrebbe fotoresistore alla scheda. In questo modo creerete una specie
essere utilizzato dopo ogni metodo che modifica lo stato dei di “monitor ottico” della percentuale di luminosità oppure un
LED o dopo una serie di modifiche. semplice gadget di divertimento (Fig. 6).
Esempio:
strip.rotate_right(1)
strip.set_pixel(0, (0, 50, 0))
strip.show()
PROGRAMMARE CON RP2040

clear()
Cancella l'intera striscia di LED, cioè imposta ogni colore su 0.
Esempio :
strip.clear()

Potete trovare ulteriori informazioni su tutti i metodi della


libreria neopixel a questo link:
https://github.com/blaz-r/pi_pico_neopixel/wiki/Library-methods-
documentation

CONTROLLARE LA LUCE CON… LA LUCE


Abbiamo pensato di arricchire il progetto NeoPixel con qual-  Fig. 4 - L’LDR collegato alla scheda.
cosa di utile e divertente, ovvero controllare il numero di LED

55
Per fare questo, dovete lasciare intatti i due circuiti sulla
breadboard e caricare lo script ldr_neopixel.py, che riportiamo
nel Listato 3.
In pratica, abbiamo unito i due script precedenti con l’unica
differenza sostanziale nel ciclo while, in cui abbiamo aggiunto
alcune istruzioni. Il valore della variabile K, invece di essere un
valore fisso, viene determinato dalla lettura del pin ADC che,
come detto poc’anzi è il GP27.

K = readLight (photoPIN)

Quindi, avendo un anello di 12 Led abbiamo imposto un valore


minimo e un valore massimo della variabile K, che non deve
essere maggiore di 12 o inferiore a 1.

if K > 11: K = 12
if K < 1: K = 1

Nel primo ciclo for abbiamo usato il metodo strip.set_pixel per


accendere tutti i LED in blu.

for x in range (12):


strip.set_pixel (x, blue)
Nel secondo ciclo for abbiamo usato il metodo strip.set_pixel
 Fig. 5 - I dati di luminosità in percentuale. per accendere i LED in rosso in base al valore determinato dal-

PROGRAMMARE CON RP2040

 Fig. 6 - L’anello NeoPixel e il fotoresistore collegati alla scheda.

56
 Listato 3
from neopixel import Neopixel
from machine import ADC, Pin
import time
photoPIN = 27
numpix = 12
K = 1
strip = Neopixel(numpix, 0, 28, "GRB")
red = (255, 0, 0)
blue = (0, 0, 255)
strip.brightness(255)
strip[:] = blue
strip[:K] = red
strip.show()
time.sleep(2.0)
def readLight(photoGP):
photoRes = ADC(Pin(27))
light = photoRes.read_u16()
light = int (round (light/65535*10,0))  Fig. 8 - I led accesi proporzionalmente alla luce.
return light
while True:
print ("light: " + str (readLight(photoPIN)))
K=readLight (photoPIN)
if K > 11: K = 12
if K < 1: K = 1
la variabile K, ovvero del valore di luminosità letto dal pin ADC.
for x in range(12):
strip.set_pixel(x, blue) for x in range(K):
for x in range(K):
strip.set_pixel(x,red)
time.sleep (0.1) strip.set_pixel (x,red)
strip.show()
time.sleep (0.3) time.sleep(0.1)

Abbiamo effettuato anche una piccola modifica alla percen-


tuale che deve essere arrotondata da 1 a 12, cioè come il
numero di LED, dividendo il valore per 10, anziché 100 (Fig. 7).

light = int (round (light/65535*10,0))

Se non avete commesso errori, vedrete accendersi in rosso i


LED in modo proporzionale alla luce raccolta dal fotorestistore,
come illustrato in Fig. 8.

CONCLUSIONI
Con questa puntata si conclude questo corso e, nella speranza
che vi sia stato utile, vi diamo appuntamento su queste pagi-
ne per future sperimentazioni.

PROGRAMMARE CON RP2040

Cosa occorre?
La board di Futura Elettronica con RP2040
(cod. FTR2040) è disponibile a Euro 13,90 e include
i pin strip da saldare, lo starter kit per Raspberry Pi Pico
(cod. RPICOKIT) è in vendita Euro 56,00.
I prezzi si intendono IVA compresa.

Il materiale va richiesto a:
 Fig. 7 - Il valore arrotondato da 1 a 12
della percentuale. Futura Elettronica, Via Adige 11, 21013 Gallarate (VA)
Tel: 0331-799775 - www.futurashop.it

57

Potrebbero piacerti anche