PrettyPrint

sabato 6 gennaio 2024

Stadio di condizionamento per AD590, con unico op-amp 5V

u.r. 28-Gen-2026

In un precedente post, si è visto come usare un sensore AD590, con Arduino UNO R3, senza ricorrere a stadio di condizionamento, ma a un software un po' più complesso. Volendo semplificare il software occorre quindi un hatdware aggiuntivo, uno stadio di condizionamento (in questo caso un amplificatore di tensione) che "scali", quanto più possibile, la piccola dinamica del sensore a quella più ampia dell'ADC di Arduino. Ma anche in questo caso, si vuole semplificare quanto più possibile: non vogliamo alimentazioni aggiuntive, né riferimenti di tensione esterni e si vuole utilizzare componentistica facilmente reperibile (op-amp e resistori)...

L'idea di questo stadio di condizionamento, con op-amp, nasce da due esigenze: la prima, di usare solo l'alimentazione 5V fornita da Arduino e non ricorrere ad un alimentatore duale esterno, anche per lo stadio di condizionamento. La seconda, di volere usare la tensione di riferimento ADC di default da 5V, dello stesso microcontrollore ATmega328.

Problema n.1

Alimentando il sensore AD590 a 5V, con in serie una resistenza da 1kOhm (non è possibile usare a questa tensione una resistenza da 10k),  abbiamo una tensione sulla stessa resistenza di 1mV per ogni grado Kelvin, mentre la risoluzione, teorica, della conversione ADC di Arduino, con Vref=5V, è circa 5mV.

Si rende dunque necessario amplificare questa tensione, per esempio, di un fattore pari a 10 volte, in modo da avere 10mV/K e quindi una risoluzione in temperatura di 0,5K (ovvero 0,5 °C).

Problema n.2

Abbiamo bisogno di un op-amp che possa lavorare ad alimentazione singola, come l'LM358, componente economico, molto reperibile, e dalle buone prestazioni. Bisogna però tenere conto della sua tensione di uscita massima (VSAT+), che è intorno ai 3,5V, quando lo si alimentata a 5V.

Supponendo di volerci limitare alla misura di una temperatura massima di 50°C, abbiamo dunque in corrispondenza una tensione di uscita massima di circa 3,2V (323K->3,23V),

Supponendo, poi, di volerci limitare alla misura di una temperatura minima di -20 °C avremo, quindi, in corrispondenza una tensione di uscita minima di circa 2,5V (250K -> 2,5V)

 

Dimensionamento dello stadio di condizionamento

Per ottenere un guadagno di tensione di 10 con un unico op-amp, in configurazione non invertente, possiamo usare due resistori da 22k e 68k in serie, per il ramo di retroazione, e un resistore da 10K collegato fra il morsetto invertente e massa; infatti abbiamo:




Risultati più accurati si possono ottenere sostituendo R2A con un'ulteriore resistenza serie formata, per esempio, da un resistore da 18k fisso e un trimmer da 5k, in modo da correggere le tolleranze dei resistori e gli effetti dovuti alle correnti di polarizzazione e alla tensione di offset dell'op-amp.


Schematico




Viene usato il primo dei due op-amp dell'LM358. la parte "A". Il resistore da 1K da 0,1% può essere eventualmente sostituito con uno dall'1% oppure da una resistenza serie compresa da un resistore fisso da 820 Ohm e un trimmer da 220 Ohm, che andrà ovviamente regolato in fase di taratura per avere esattamente 1mV/K.  In caso di disturbi, provare a inserire in parallelo alla Rs un condensatore ceramico a disco da 100nF ed, eventualmente, anche in parallelo alla serie R2A+R2B.

RISULTATI LTSPICE:







Software

float tempC;
float tempK;
const float VREF=5.0;
const float C1=0;  // cal.offset, da determinare mediante calibrazione con termometro campione
const float C2=1;  // cal.pendenza, da determinare mediante calibrazione con termometro campione 
float vin;
int N;


void setup() {
  Serial.begin(9600);
}

void loop() {
  N=analogRead(A0);           // si consiglia misura ripetuta 
  vin=N*VREF/1024.0;            
  tempK=100*vin;               // temp in K  
  tempC=(tempK-273.15)*C2+C1;   // temp in °C
  Serial.println(tempC, 1);
  delay(30000);
}

domenica 17 dicembre 2023

Arduino UNO R3: termometro 0/100°C con AD590 e una sola resistenza.

E' possibile usare il solo sensore AD590 con Arduino, senza ricorrere ad op-amp. alimentatori duali, trimmer e altri componenti? La risposta è affermativa, grazie a una tensione di riferimento ADC "segreta" presente in ogni microcontrollore di Arduino; ma occorre un piccolo accorgimento...

L'AD590 è sensore di temperatura a due terminali, che produce in uscita una corrente proporzionale alla temperatura assoluta rilevata. Esso offre ottime prestazioni in termini di accuratezza (± 0,5 °C) e immunità ai disturbi in virtù del funzionamento in corrente e non in tensione. La sua caratteristica è quella di fornire, linearmente, 1
µA per ogni grado Kelvin rilevato.

Il suo range di misura è  molto ampio: −55°C... +150°C . Grazie al fatto che fornisca una corrente proporzionale ai gradi Kelvin, quindi, anche le temperature negative saranno comunque descritte da correnti, e quindi tensioni, di polarità positiva, il che si traduce in una semplificazione dei successivi stadi di condizionamento. 

L'AD590 può essere alimentato da +4 a +30V e richiede una resistenza in serie di polarizzazione, che viene anche sfruttata per la necessaria conversione corrente/tensione.

Per approfondimenti su altre caratteristiche e sulla tecnologia costruttiva, si rimanda al DATASHEET fornito dal Costruttore.

Per una tensione di alimentazione 5V, tipicamente si usa una R=1kΩ, per 12V o 15V, invece, il valore tipico di R è 10kΩ 

Il costruttore consiglia di utilizzare un resistore di precisione (da 0,1% ), preferibilmente in serie a un trimmer, in modo da effettuare una taratura hardware in fase di messa a punto del sistema di misurazione:



Vedremo, più avanti,  che è possibile usare un resistore fisso e raggiungere lo stesso scopo, via software.

Supponiamo di volere misurare una temperatura compresa fra 0°C e 100°C, usando una R=1kΩ avremo che per T=0°C (273K) ai capi della resistenza si avranno 0,273V (1kΩ * 273µA), mentre a T=100°C (327K) si avranno 0,373V (1kΩ*373µA).

La dinamica (differenza fra tensione massima e tensione minima) è quindi di soli 0,1V. Volendo misurare questo range di tensione con Arduino, si rende dunque necessario uno stadio differenziale e amplificatore con op-amp, che porti il range 0,273...0,373V a 0....5V, in quanto la tensione di riferimento dell'ADC interno è, di default, pari a 5V; diversamente, il quanto sarebbe molto elevato.

LA TENSIONE DI RIFERIMENTO INTERNA DI 1,1V DI ARDUINO                         

La soluzione alternativa al condizionamento con amplificatore differenziale è quella di usare una tensione di riferimento più bassa, più "vicina" all'estremo superiore della dinamica del sensore, in modo da ridurre l'errore di quantizzazione e quindi migliorare la risoluzione. Esistono in commercio diversi riferimenti di tensione esterni da 1,2V a 1,25V, ma vorremmo evitarli, sempre in un'ottica di rendere quanto più semplice possibile l'hardware.

Il microcontrollore della scheda UNO R3 (ATmega328) dispone di una tensione di riferimento interna bandgap, pari a 1,1V nominali, che può essere convenientemente usata a tale scopo. 

Utilizzando una Vref=1,1V si avrà 1LSB teorico pari a circa 1mV e quindi una risoluzione di circa 1K/1°C, nel range indicato, che è sicuramente una specifica accettabile. 

HARDWARE

Lo schema è riportato di seguito:


Essendo la resistenza di ingresso del pin dell'ATmega pari a 100 MΩ, la corrente Is del sensore è praticamente la stessa che circola anche nella resistenza da 1KΩ.


MISURA DELLA RESISTENZA R                                                                                        

Avendo usato una resistenza da 1kΩ, 1%  (e non da 0,1% - ovvero un trimmer di regolazione - come suggerito dalla Casa costruttrice) occorrerà misurare il valore attuale della stessa per non introdurre un errore non trascurabile nel calcolo della corrente. Mediante un DMM 3 1/2 cifre e usando una portata di 2kΩ (è molto importante usare questa portata, per avere una misura quanto più possibile accurata), nel nostro caso è stato misurato un valore effettivo R=987 ΩQuesto valore è stato dunque assegnato alla costante R dello sketch; esso servirà per il calcolo della corrente Is (mediante la Legge di Ohm: Vs/R)


MISURA DELLA TENSIONE VS                     

Per misurare la corrente Is, ci serve, dopo la resistenza, ovviamente la tensione Vs, cioè la caduta di tensione che si localizza ai capi della resistenza R di polarizzazione (precedentemente misurata) e che viene quindi applicata all'ingresso analogico di Arduino, per essere misurata. 

Arduino misura la tensione Vs mediante la classica formula di ricostruzione dell'ADC, partendo dal presupposto che Vref sia effettivamente pari al valore nominale 1,1V; ma la tensione di riferimento interno, sebbene molto stabile, ha una tolleranza non trascurabile, cioè il valore effettivo si discosta da quello nominale di 1,1V (secondo il datasheet dell'ATmega il valore può variare, tipicamente, fra 1.0 e 1.2V).  

E' stato, dunque, caricato ed eseguito su Arduino, propedeuticamente, uno sketch che misura l'effettiva tensione di riferimento,  che determina l'effettivo valore e consente dunque di correggere la differenza fra valore nominale e valore effettivo dovuto alla tolleranza di fabbricazione.



SOFTWARE

N.B. Prima di caricare questo sketch occorre caricare - ed eseguire nel monitor seriale - lo sketch di "correzione" della tensione di riferimento interna, reperibile a questo post.

AD590.INO
/* Misura di una temperatura con Arduino Uno e sensore
 * AD590 alimentato a 5V tramite una R=1kOhm,1% => 1mV/K
 * Viene usato il valore della VREF interna memorizzato
 * sulla EEPROM, precedentemente calcolato e salvato.
 */
 
#include <EEPROM.h>

#define STAMPAVS 1         // 1 stampa VS 
#define STAMPATK 1         // 1 stampa T in gradi K

const int EEADD=0;         // ind. EEPROM dove è stato memorizzato il fatt. correttivo
const int AD590 = A0;      // pin analogico a cui è collegato l'AD590
const int R = 987;         // Valore attuale della Resistenza in serie all'AD590
float VREF;                // VREF: verrà letto dalla EEPROM 
const int DELTA_T = 30000;  // intervallo di misurazione in ms

int TC;                    // Temp misurata, in °C
int TK;                    // Temp misurata, in K
float Vs;                  // Tensione misurata (ai capi di R) da Arduino
float Is;                  // Corrente calcolata come Vs/R (in uA)

unsigned long counter=0;    // progressivo misurazioni di temperatura
unsigned long prevMillis;   // marcatore temporale per millis()

void setup() {
  Serial.begin(9600);        // Imposta rtx seriale a 9600bps (monitor seriale, PuTTY ecc)
  analogReference(INTERNAL); // Vref interna =1,1V nominale
  EEPROM.get(EEADD, VREF);    // legge locazione EEADD e assegna valore a VREF
  prevMillis=millis();       // marca istante iniziale 
}

// Effettua una misura ripetuta di Vs: 

float misuraVs() {
  float somma=0;   // somma delle letture singole di V
  float vmedio=0;  // media delle letture singole di V
  float v;         // lettura singola di V
  int n;           // numero restituito dall'ADC
  int nlett=5;     // quante letture effettive
  
  for (int i=0; i<nlett+2; i++) {
     n=analogRead(AD590);
     v=VREF*n/1024;
     if (i>1)  // scarto prime due misure
        somma=somma+v;
     delay(50);
  }
  
  vmedio=somma/nlett;  //calcola valore medio delle misure di tensione
  return (vmedio);     // ritorna la media della misure di I (in uA)
}


void loop() {
  
  /* Misura e stampa periodica della temperatura ogni DELTA_T millisecondi: */
  if(millis()-prevMillis >= DELTA_T) {
     
      Vs=misuraVs();           //misura la Vs ai capi di R e l'assegna alla var. Vs
      Is=1E6*Vs/R;             //calcola Is, con la Legge di Ohm,e la converte in uA
      TK = (int)Is ;           //es. 298.00 diventa 298K
      TC=TK-273;               //es. 298K diventa 25°C   
       
      Serial.print(++counter);         
      #if STAMPAVS
         Serial.print("\t");
         Serial.print(Vs,3);
         Serial.print("V");   
      #endif  
      #if STAMPATK              
         Serial.print("\t");
         Serial.print(TK);
         Serial.print("K");
      #endif
      Serial.print("\t");
      Serial.print(TC);
      Serial.println("°C");
      prevMillis=millis();
  }

  /* altri compiti da eseguire: */
                     
}

VISUALIZZAZIONE STAMPA DATI

Lanciando il monitor seriale, sarà possibile visualizzare la stampa dei dati:





L'informazione su Vs  può essere ovviamente non stampata, settando a 0 nello sketch la costante simbolica STAMPAVS. E' anche possibile non stampare i gradi KELVIN ponendo il simbolo STAMPATK a 0.

Arduino UNO R3: misurare la tensione di riferimento interna

u.r. 17-FEB-2026 

 

L'idea di questa procedura mi è nata quando ho dovuto effettuare la correzione software della tensione di riferimento generata dal bandgap entro contenuto nell'ATmega328P, per l'uso con il sensore AD590 senza stadi attivi di condizionamento. 

La tensione di riferimento del bandgap interno è estremamente stabile, ottima per misurare range fra 0 e 1,1V,  ma ha un'elevata tolleranza di produzione (tipicamente fra 1,0 e 1,2V) che può quindi introdurre errori non trascurabili nel calcolo della tensione misurata dall'ADC.

Il suo utilizzo corretto richiede, quindi, innanzitutto una stima del suo effettivo valore (mediante la procedura di seguito descritta) ma anche lo scarto della prima lettura (che sarebbe non accurato, così come è scritto nel datasheet).

DESCRIZIONE DELLA PROCEDURA

Il pin AREF, se non collegato a nessuna tensione esterna, fornisce in uscita il valore della tensione di riferimento attualmente configurata nel software in esecuzione su Arduino

Si misurerà, quindi, tale tensione con un voltmetro (es un multimetro digitale), che verrà memorizzato nella memoria EEPROM della scheda Arduino e richiamato, all'occorrenza, in ogni software che impieghi la stessa tensione di riferimento interna.

Evidentemente, tale procedura andrà ripetuta ogni volta si cambia la scheda Arduino UNO R3, ovvero il microcontrollore ATmega328, essendo la tolleranza di fabbricazione del bandgap interno piuttosto variabile.

La procedura è stata testata solo su questo microcontrollore, ma dovrebbe funzionare anche per altri micro ATmegax che hanno un bandgap interno da 1,1V

HARDWARE

Occorrerà semplicemente collegare un comune multimetro 3,5 cifre impostato in tensione (se portata manuale selezionare 2V =)  fra il pin AREF e la massa:


Nel mio caso è stata misurata una tensione di 1,078V:





SOFTWARE

1)  BANDGAP_1V1_CAL.INO

Misura della Vref interna e salvataggio su EEPROM

  
  
  
  
 
/****** Problema:
* la tensione di riferimento del bandgap interno 1,1V degli ATmegaX, sebbene molto
* stabile, ha una tolleranza produttiva non trascurabile. Conoscere l'effettivo valore,
* dunque, migliora notevolmente il calcolo delle tensioni misurate via software
* che usano come riferimento questa tensione.
*
****** Risoluzione:
* Mediante un DMM impostato come voltmetro (portata 2V =), si misurerà la d.d.p.
* fra il pin AREF e la GND. Il valore così misurato, verra chiesto dunque
* all'utente (dal monitor seriale) e salvato in una locazione della memoria EEPROM;
* Tale valore verrà richiamato, successivamente, nel software di lettura A/D
* che utilizza come VREF il bandgap interno.
* La procedura va ovviamente ripetuta a ogni cambio di scheda Arduino/microcontrollore.
*
****** Autore:
* Francesco Parisi, 2025-FEB-05
*/
#include <EEPROM.h>

float VREF =1.1; // tensione nominale b/gap int.
const int EEADD=0; // ind. EEPROM dove salvare la VREF misurata con il DMM

void setup() {
Serial.begin(9600);
analogReference(INTERNAL); // impostiamo Vref interna
Serial.print("\nMisura tensione con bandgap interno: ");
Serial.println(F("\n============================================="));
Serial.print("\nInserire misura tensione DMM in Volt (es. 1.078): ") ;
while (Serial.available()==0)
{ } // attende input da monitor seriale
VREF=Serial.parseFloat(); // trasforma input in float
Serial.println(VREF);
EEPROM.put(EEADD, VREF); // scrive il val. VREF all'ind. EEADD
Serial.println(F("============================================="));
Serial.print("Valore della VREF interna salvato all'indirizzo EEPROM: ");
Serial.println(EEADD);
Serial.println(F("============================================="));
Serial.println("Programma terminato con successo!");
}

void loop() {
analogRead(A0); // lettura a vuoto
}


Avviare il monitor seriale e inserire il valore di tensione misurata con il DMM (es. 1.078), battere INVIO:



Il programma procederà nell'esecuzione lo stamperà e lo salverà nella locazione di memoria EEPROM (valore predefinito 0, che può essere cambiato nella sezione dichiarativa: costante EEADD):


2)  BANDGAP_1V1_TEST.INO

Stampa su monitor seriale della variabile VREF salvata su EEPROM
 
 
 
/*
* Test lettura valore VREF memorizzato nella EEPROM
*
*/

#include <EEPROM.h>

const int EEADD=0; // ind. EEPROM dove è stato memorizzato il fatt. correttivo
float VREF; // valore della vref memorizzato all'indirizzo EEADD

void setup() {
Serial.begin(9600);
Serial.print("Indirizzo EEPROM :");
Serial.println(EEADD);
EEPROM.get(EEADD, VREF); // legge locazione EEADD e assegna valore a VREF
Serial.print("VREF = ");
Serial.println(VREF,3);
}

void loop() {

}



Attivando il monitor seriale avremo questo esempio di output:




USARE IL VALORE MEMORIZZATO NELLO SKETCH UTENTE

Nello sketch utente, ovvero lo sketch che impiegherà questo valore occorrerà innanzitutto inserire all'inizio la direttiva di inclusione del file di intestazione della libreria EEPROM:

#include <EEPROM.h>

A seguire, nella sezione globale, si dichiareranno la costante int EEADD e la variabile float VREF

Nel corpo della setup() si richiamerà la seguente funzione di assegnazione del valore letto dalla EEPROM alla variabile VREF:

EEPROM.get(EEADD, VREF);

Per un esempio di impiego , vedere il seguente progetto: https://telparblog.blogspot.com/2023/12/arduino-uno-r3-termometro-0100c-con.html




domenica 29 ottobre 2023

Un altro debounce (non bloccante) per Arduino Uno

Nell'impiego di interruttori, commutatori o pulsanti meccanici, si verifica quasi sempre un inconveniente che, nella maggioranza dei casi, costituisce causa di malfunzionamento nei circuiti digitali: l'elemento mobile che realizza il contatto, quando viene spostato da una posizione all'altra rimbalza (bouncing) diverse volte prima di stabilizzarsi al valore impostato, sia nella fase di pressione che in quella di rilascio.


Questi continui rimbalzi, che avvengono in un tempo brevissimo (generalmente fra 0,1 e 5ms), vengono percepiti dal software in esecuzione  come ripetute pressioni del pulsante e quindi erroneamente conteggiati. Il problema viene aggirato impiegando soluzioni cosiddette di anti-rimbalzo (debouncing) che possono essere circuitali o software. Una delle soluzioni software più semplici è quella di far eseguire un'istruzione di attesa, di un tempo pari, o leggermente superiore, a quello di rimbalzo, in modo che il programma ignori sicuramente queste innumerevoli commutazioni. Al termine di questo periodo, per sicurezza, si torna a leggere lo stato del pulsante: se è corrispondente a quello attivo (es. livello alto) il pulsante è stato dunque "de-rimbalzato" (debounced) e quindi può essere eseguito il codice previsto all'occorrenza della pressione del bottone.


HARDWARE                                  

Il pulsante N.A. è collegato fra il pin di ingresso (2) e la massa; il resistore di pull-up è quello interno dell'ATmegax8: quindi la pressione del pulsante comporta, a regime, la lettura sul pin 2 di un livello logico LOW, mentre il rilascio comporta, a regime,  la lettura di un livello logico HIGH. Sul pin 9 è collegato un LED (attraverso una resistenza da 220..330 Ohm), che, alla pressione del pulsante, commuterà il suo stato da acceso a spento e viceversa. 




SOFTWARE                                 

Lo sketch è imperniato sull'intercettazione della pressione del pulsante (ovvero del rilascio) attraverso un'istruzione di selezione semplice if, che va a "testare" lo stato corrente del pulsante (memorizzato nella variabile statoP1)  e quello della precedente esecuzione del loop (memorizzato nella variabile statoP1prec).  Se i due stati sono diversi vuol dire che c'è stata una variazione (da HIGH a LOW: pressione oppure da LOW a HIGH: rilascio), ma per essere sicuri che sia la prima variazione - ovvero la pressione o il rilascio - e quindi non una successiva variazione dovuta ai rimbalzi, occorre testare una terza variabile di flag che assume valore 0 solo quando non si è ancora verificata la prima variazione.

Se dunque si verifica la condizione logica (stato attuale pulsante NOT EQUAL a quello precedente AND flag=0) dalla pressione (ovvero dal rilascio) , attraverso un marker temporale (variabile t1) viene "segnato" l'istante conteggiato dalla funzione millis() e ovviamente settata a 1 la variabile flag, essendosi verificato l'evento di prima variazione.

Successivamente , a ogni loop, si andrà a leggere il valore  millis() e a confrontarlo con t1, se la differenza è MAGGIORE O UGUALE a 5ms (tempo tipico di attesa per l'esaurirsi del debounce; potrebbe essere necessario aumentarlo, se la qualità dei pulsanti è bassa) si andrà allora a testare lo stato del pulsante: se LOW, allora è una condizione di pressione e quindi si va ad eseguire il codice previsto all'occorrenza della pressione del pulsante.

Diversamente, verrà eseguito il codice restante dello sketch, cioè quello non relativo all'evento della pressione del pulsante, senza alcuna pausa. Infatti l'uso di millis()rende la gestione "non bloccante" dell'intero software, a differenza delle istruzioni di delay(): infatti il "costo" temporale delle istruzioni di check del tempo trascorso sono assolutamente trascurabili rispetto alle decine di millisecondi che avrebbe richiesto una delay.

Ad ogni loop, ovviamente, occorrerà aggiornare lo stato precedente del pulsante per il successivo loop, che ovviamente sarà uguale a quello attuale. Generalmente questa istruzione viene messa come ultima nel corpo della loop().

MIO_DEBOUNCE.INO

/*
 *  Debounce con millis() sulla pressione e sul rilascio
 *  del pulsante.
 *
*/
const int P1=2;   // pulsante 
const int L1=9;   // LED

int statoP1=LOW;       // stato P1 (premuto LOW / rilasciato HIGH)
int statoP1prec=LOW;   // stato precedente P1
int statoL1=LOW;       // stato LED (spento LOW / acceso HIGH)
int flag=0;            // 1: pressione o rilascio
int T=5;               // tempo attesa bouncing (5ms)
unsigned long t1;      // marker temporale di millis()

void setup() {
  pinMode(P1, INPUT_PULLUP);  // attiva la R pull-up interna
  pinMode(L1, OUTPUT);
  digitalWrite(L1, statoL1);
}

void loop() {

  statoP1 = digitalRead(P1);

  // rilevata una pressione o un rilascio
  if (statoP1 != statoP1prec && !flag)
  {
     flag=1;        // flag di avvenuta pressione/rilascio
     t1=millis();   // marca inizio conteggio tempo
  }

  // se si è esaurito il rimbalzo
  if ( millis()-t1 >= T && flag) 
  {
     flag=0;    // azzera flag  (per successive pressioni/rilasci)
// se è una pressione if (statoP1==LOW) { // istruzioni da eseguire alla pressione di P1: statoL1=!statoL1; digitalWrite(L1, statoL1); } } // istruzioni da eseguire al di fuori della pressione di P1: statoP1prec = statoP1; }

lunedì 8 agosto 2022

Installare Packet Tracer 8.2 su Fedora, OpenSUSE, Arch, Manjaro 64-bit

Aggiornamento 08/08/2022: viene attualmente installata la nuova versione 8.2

Come avviene già dalla versione 7.3.0, la Cisco ha deciso di distribuire il suo software Linux solo nel formato Debian (.deb). 

Quindi, nessun problema per chi usa Debian, Ubuntu e le tante distribuzioni derivate, ma per chi, invece, preferisce altre distribuzioni che non usano il formato Debian (es. Fedora, OpenSUSE, Arch, Manjaro ecc) occorre provvedere manualmente a installare i file di installazione e fare delle modifiche di sistema.

Fortunatamente ho trovato in rete uno script di installazione (curato dall'ottimo sviluppatore brasiliano Marcelo Baptista) che automatizza l'intera procedura. Può essere usato anche su Arch/Manjaro, sempre su sistemi operativi a 64-bit e indipendentemente dall'ambiente desktop (Gnome, KDE Plasma, XFCE, Cinnamon ecc).

Va da sé che, volendo, questo script di installazione può essere eseguito anche su sistemi basati su pacchetti .deb (Debian, Ubuntu ecc...)

Vediamo i passi da seguire:

Step #0: avere un account Cisco Netacad

Il software viene eseguito inserendo le proprie credenziali dell'account Cisco Netacad. Nel caso si fosse sprovvisti di tale account, occorrerrà crearne uno (gratuitamente) seguendo la procedura accessibile al seguente link: https://id.cisco.com/signin/register

Step #1 : accettare i termini di licenza

La lettura e l'accettazione dei termini di licenza della Cisco è una procedura prodepeutica all'installazione e all'utilizzo del software.

https://www.netacad.com/portal/resources/packet-tracer

Occorrerà inserire la propria login Netacad, andare nel paragrafo "Download" e cliccare sui link  CISCO END USER LICENSE AGREEMENT (“EULA”) e THE SUPPLEMENTAL END USER LICENSE AGREEMENT

Se si accettano i suddetti termini, passare allo step #2

Step #2: eseguire lo script di installazione

Da terminale non privilegiato:

curl -s https://raw.githubusercontent.com/marcelobaptista/packettracer/master/install_pt.sh | sudo bash

Attendere il termine dello scaricamento e dell'esecuzione dello script. I tempi di download potrebbero essere abbastanza lunghi.

Step #3: lanciare il programma

Il programma può essere lanciato digitando "packet tracer" nella casella di ricerca del proprio DE oppure lanciando lo script "packettracer" in un terminale utente.  In KDE Plasma, inoltre, viene creato un collegamento sotto il menù di avvio "Oggetti smarriti", che può essere ovviamente inviato al desktop per un avvio rapido.

giovedì 14 luglio 2022

Cisco CLI IOS: i comandi utili nell'attività laboratoriale

 

Di seguito verranno descritti alcuni comandi che rendono più produttività l'esperienza di amministrazione di una macchina Cisco, soprattutto nel contesto laboratoriale. Infatti, a differenza del contesto di produzione, nell'attività di laboratorio si tende a privilegiare sicuramente la semplificazione operativa anche se a scapito della sicurezza.

1. Non impostare password

Quando si usa la CLI in ambito laboratoriale (sia reale ma anche con Packet tracer) gli apparati vengono usati da più studenti; una password non conosciuta, impostata da un altro studente, comporta il reset fisico dell'apparato con evidenti ricadute sull'esperienza di laboratorio. Pertanto è buona norma non impostare alcuna password in nessuna modalità utente o privilegiata.

2. Disabilitare il DNS lookup

E' il primo comando EXEC sicuramente da immettere (subito dopo quello dell'assegnazione dell'hostname). Forse è quello più indispensabile. 

Quando si inserisce un comando errato, in alcune circostanze, il sistema prova a interrogare il server DNS impostato di default, nel tentativo di risolvere il nome (ipotizza che la stringa immessa sia il nome di un host al quale ci si vuole collegare). Esempio:

Switch# conifg
Translating "conifg"...domain server (255.255.255.255)
Dopo qualche minuto di blocco della console (non è possibile interrompere in nessun modo da tastiera questa interrogazione DNS...), il sistema risponde con il seguente messaggio, "rilasciando" così l'uso della console:

% Unknown command or computer name, or unable to find computer address

Switch# config terminal

Il problema viene aggirato disabilitando il lookup DNS con il seguente comando EXEC:

Switch(config)# no ip domain-lookup

3. Mitigare i disturbi del syslogging su console 

Il demone syslog del sistema operativo Cisco IOS logga sulla console, in qualsiasi momento, messaggi di sistema, per esempio attivazione/disattivazione di interfaccia, messaggi di protocolli ecc. Se in quel momento si sta, per esempio, usando la console per inserire un comando questo verrà "spezzato" e nel mezzo inserito il messaggio di syslog. Esempio:

R0(config-if)#ip address 192.168.1.10 255.2
%LINEPROTO-5-UPDOWN: Line protocol on Interface GigabitEthernet0/0, changed state to down
55.255.0
La prima soluzione potrebbe essere quella di disabilitare totalmente il logging di syslog attraverso i seguenti comandi:

Switch(config)# line console 0
Switch(config-line)# no logging console

Questa soluzione potrebbe però impedire di leggere messaggi importanti di sistema. Esistono diverse soluzioni alternative che risolvono o mitigano il problema (si rimanda a questo link). 

Il metodo consigliato sui testi Cisco è quello di mantenere abilitato il logging su console, ma in modo "sincrono". In questo modo il comando che si stava inserendo verrà ristampato esattamente dopo la stampa su console dell'evento syslog:

R0(config)#ip address 192.168.1.10 255.2
%LINEPROTO-5-UPDOWN: Line protocol on Interface GigabitEthernet0/0, changed state to up

R0(config)#ip address 192.168.1.10 255.2


ll logging sincrono viene abilitato con i seguenti comandi:

Switch(config)# line console 0
Switch(config-line)# logging synchronous

Se si prevede di usare login SSH/Telnet (VTY terminal) , ripetere i comandi:

Switch(config)# line vty 0 15
Switch(config-line)# logging synchronous

4. Disabilitare il timeout di sessione

Di default dopo 5 minuti di inattività (sia console che SSH/Telnet), il sistema disconnette l'accesso. E' evidente che in un ambiente esercitativo, non di produzione, sarebbe preferibile non disconnettere mai che viene codificato con la coppia 0 ore, 0 min:

Switch(config)# line console 0
Switch(config-line)# exec-timeout 0 0

Se si prevede di usare login SSH/Telnet (Virtual Teletype) , ripetere i comandi:

Switch(config)# line vty 0 15
Switch(config-line)# exec-timeout 0 0

Ovviamente  per salvare sulla memoria di avvio le modifiche fatte  e quindi non perderle con un reboot della macchina,  occorrerà lanciare il comando:

Switch# copy run start

________________

Sitografia/Bibliografia

lunedì 11 luglio 2022

Cisco Catalyst 2960: aggiornamento firmware mediante CLI

Ho comprato mesi fa su eBay uno Switch Cisco Catalyst 2960 ricondizionato, insieme ad altri apparati della stessa casa a un prezzo davvero conveniente, con lo scopo di allestirmi un classico CCNA lab per fare pratica con i comandi CLI di CISCO IOS.

Lo switch 2960 in mio possesso è la versione 24-TT-L non più in produzione e con supporto cessato nel 2019. L'apparato oltre alle 24 porte rame 10/100 ha altre 2 porte rame 10/100/1000 (tutte non PoE) che possono essere usate per i collegamenti di uplink. 


La guida che andrò a descrivere si riferisce all'aggiornamento del firmware dell'apparato usando un computer con sistema operativo Windows 11 (o 7/8/10) versione 64-bit


1. Gli strumenti software/hardware necessari

Oltre ovviamente a un computer con Windows 7/8/10/11 64-bit, dotato di porta RS232 o USB e porta Ethernet (con relativo cavo di rete RJ45/RJ45) occorrono:

Cavo Rollover

Occorrerà un cavo di programmazione rollover DB-9/RJ45 (se avete un computer ancora con la porta RS232 DB9). Se avete, invece, un computer con la sola porta USB la scelta è ovviamente la versione USB/RJ-45 . Se avete già il cavo DB9/RJ45 ma vi serve USB potete ovviamente usare qualsiasi cavo adattatore DB-9/USB

Il cavo andrà collegato, per l'estremità RJ45 nel retro (porta console) dell'apparato, l'estremità USB/DB9 ovviamente al computer:

   



Software emulazione terminale 

Come software di emulazione terminale, per collegarci tramite la porta COM (reale o virtuale USB), il software più usato è senz'altro l'ottimo freeware Putty, che andrà scaricato all'URL:

https://www.chiark.greenend.org.uk/~sgtatham/putty/latest.html

Applicazione server TFTP

Il file binario dell'aggiornamento una volta scaricato sul computer, verrà, a sua volta, scaricato dallo switch mediante una sessione TFTP: quindi lo switch agirà da client e il computer agirà da server. Occorre quindi che sul PC sia in esecuzione un servizio TFTP. A tale scopo i documenti Cisco consigliano un'applicazione server TFTP free, per Windows, molto semplice da configurare e usare; è scaricabile al seguente indirizzo:

https://bitbucket.org/phjounin/tftpd64/downloads/Tftpd64-4.64-setup.exe

Vedremo più avanti come usarlo e configurarlo.

2. Che versione di firmware ho attualmente sulla macchina?


Per interagire con l'apparato abbiamo bisogno dell'emulatore terminale. Lanciamo PuTTY e lo configuriamo per la connessione seriale con lo switch:
  • Serial line
    La porta COM della seriale fisica (RS232) o virtuale (USB), es. COM3. Se non si conosce il numero è possibile individuarla da "Gestione dispositivi" > Porte seriali.
  • Speed
    Va bene anche 9600bps, ma diversi documenti Cisco consigliano 115200bps
  • Connection type
    Serial
Conviene salvare il profilo di connessione con un'etichetta "CISCO" in modo da richiamarlo velocemente per le future sessioni




D'ora in poi si supporà che lo switch si trovi configurato ai valori iniziali di fabbrica:
1) tutte le porte fanno parte della VLAN di default (VLAN ID=1)
2) la VLAN di management è la VLAN ID=1 (default management VLAN)
3) non sono state impostate password utente e/o modalità privilegiata


Aperto il terminale, battere INVIO, e al prompt lanciare il seguente comando EXEC:

Switch>show version

scorrendo il terminale, al termine, verrà visualizzata la versione del firmware attualmente in esecuzione:


3. Scarichiamo sul computer il file dell'aggiormanento


La pagina principale per il download del software Cisco è la seguente:


N.B. Occorre essere forniti di una login Cisco (la registrazione è libera).

Nel form di selezione del prodotto, digiteremo il modello del nostro apparato (nel nostro caso 2960-24TT-L) , quindi apparirà il link (in azzurro) corrispondente:


Successivamente selezioneremo il tipo di software (IOS):


A questo punto si apre la pagina del download del file di aggiornamento


Come si può notare l'ultima release consigliata è la 12.2.55-SE12(MD) a fronte della versione 12.2.55-SE4 attualmente installata.

Quindi procediamo al download cliccando sull'ultima icona sulla destra, salvando nella cartella "Scaricati" dell'utente corrente di Windows.

Nel nostro caso il nome del file è:    c2960-lanbasek9-mz.122-55.SE12.bin

4. Assegniamo allo switch un indirizzo IP

Lo switch si collega al computer anche mediante un cavo ethernet, che andrà collegato fra la porta ethernet del computer e una qualsiasi porta dello switch. 

Il collegamento di rete, come detto in precedenza, serve affinché lo switch possa "scaricare" dal computer il file di aggiornamento, salvato in una cartella dello stesso computer, mediante una connessione client (lo switch) / server (il computer) usando il protocollo TFTP.

Quindi lo switch dovrà avere una configurazione IP (indirizzo IP host, subnet-mask) in accordo con quella della configurazione IP del computer, dovendo le due macchine, ovviamente, far parte della stessa rete per poter comunicare.

Lo switch 2960 è uno switch layer-2, quindi non può avere porte fisiche associate a indirizzi IP. In questo caso, l'interfaccia IP sarà di tipo virtuale (SVI: Switch Virtual Interface) e sarà associata alla VLAN 1  che corrisponde alla default management VLAN. 

Per conoscere la configurazione IP dell'interfaccia ethernet del computer, dal prompt comandi lanciare il seguente comando:

>ipconfig

Scheda Ethernet Ethernet:

   Indirizzo IPv4. . . . . . . . . . . . : 192.168.1.5
   Subnet mask . . . . . . . . . . . . . : 255.255.255.0
   Gateway predefinito . . . . . . . . . : 192.168.1.1

Quindi l'indirizzo IP server (cioè quello dell'interfaccia ethernet del computer) è 192.168.1.5

Assegniamo allo switch un indirizzo IP host compatibile con la subnet mask, e non assegnato già ad altro end device, per esempio l'indirizzo IP 192.168.1.100.

Dal terminale di Putty:

Switch> en
Switch# conf t
Switch(config)# int vlan 1
Switch(config-if)# ip address 192.168.1.100  255.255.255.0
Switch(config-if)# no shut
Switch(config-if)# exit
Switch(config)# ip default-gateway 192.168.1.1

Lo schema definitivo dei collegamenti è quindi il seguente:



N.B. Si ricorda di attendere, ovviamente, che il LED della porta dello switch diventi verde prima di collegarsi all'apparato

5. Avviamo e configuriamo il server TFTP

Una volta lanciata l'applicazione TFTP server, occorrerà prestare attenzione a impostare le seguenti proprietà:

  • Current Directory 
    La cartella dove è stata salvata l'immagine scaricata al precedente punto. Nel nostro caso era la cartella "Scaricati", quindi sarà la s/directory "Downloads" della home dell'utente corrente 

  • Server Interfaces
    Occorre selezionare l'indirizzo IP dell'interfaccia ethernet (cablata), che nel nostro caso è 192.168.1.5 




6. Aggiorniamo il firmware

Da modalità privilegiata (non configurazione), lanceremo il seguente comando:

Switch> en
Switch# copy tftp://192.168.1.5/c2960-lanbasek9-mz.122-55.SE12.bin flash:

Terminata la fase di copia (battere INVIO alle domande), lanciare i comandi:

Switch# show flash:

Directory of flash:/

    2  -rwx     9827106   Mar 1 1993 03:25:11 +00:00  c2960-lanbasek9-mz.122-55.SE12.bin

  617  -rwx         108   Mar 1 1993 00:15:20 +00:00  info

    3  -rwx        1048   Mar 1 1993 00:00:59 +00:00  multiple-fs

  622  drwx         192   Jun 6 2012 10:16:14 +00:00  c2960-lanbasek9-mz.122-55.SE4

Se è andato tutto correttamente, dovrebbe essere visualizzate entrambe le immagini, sia la nuova (SE12) che la precedente (SE4).

Facciamo il boot con la nuova immagine, salviamo la nuova configurazione dalla NVRAM alla memoria flash di avvio e riavviamo il sisteam:

Switch# conf t
Switch(config)# boot system flash:c2960-lanbasek9-mz122-55.SE12.bin
Switch(config)# end
Switch# copy run start
Switch# reload

Riavviato il sistema, verifichiamo con il comando:

Switch> show version

che sia stata caricata la nuova versione del firmwre



7. Conclusioni


La procedura mediante CLI appare la più flessibile e ovviamente portabile su ogni sistema operativo usato per l'aggiornamento. Indipendentemente dal proprio os, occorrerà ovviamente avere un'applicazione TFTP server in esecuzione sul proprio sistema operativo e un'applicazione di emulazione terminale per potersi interfacciare con l'apparato di rete per l'invio dei comandi CLI (comandi EXEC). Applicazioni entrambe reperibili, gratuitamente, per qualunque sistema operativo.

________________

Sitografia: https://www.cisco.com/c/en/us/support/docs/smb/switches/cisco-550x-series-stackable-managed-switches/smb5566-upgrade-firmware-on-a-switch-through-the-command-line-interf.html