Salta la barra di navigazione [1] - Vai alla barra di navigazione [3] - Scrivimi una mail [4]

Usare l'ADC con MCC - Le basi

PIC18 in C - Sommario - Novità - Tutorial - Progetti - Risorse - Non solo elettronica

PIC18LF26K42

In questa pagina è descritto come usare il Convertitore Analogico Digitale (ADC) interno al PIC18 insieme a MPLAB Code Configurator. Se non sapete cosa è un ADC potete andare a questa pagina: il convertitore analogico digitale.

Il processore utilizzato è il PIC18F2xK42 il cui ADC (nota 1) è caratterizzato di una risoluzione di 12 bit ed un tempo di conversione minimo teorico di circa 15 µs.

Il circuito di riferimento

Il circuito utilizzato negli esempi può essere realizzato su breadboard oppure è possibile utilizzare PICdemo oppure PICdemo R2, pagine a cui si rimanda per lo schema completo.

Lo schema elettrico

In sintesi:

Misura raziometrica

L'uso di MCC semplifica di molto la configurazione del convertitore. Le immagini seguente mostrano le impostazioni utilizzate.

Il convertitore AD verrà utilizzato scegliendo la prima delle due risorse ADCC, visibile qua sotto:

Scelta della periferica

La configurazione qui mostrata è indicata come Basic_mode e utilizza come clock lo stesso utilizzato dal processore, opportunamente diviso per ottenere un valore di TAD conforme al contenuto della tabella 36.1 ADC CLOCK PERIOD (TAD ) VS DEVICE OPERATING FREQUENCIES, presente nel manuale; in pratica TAD deve essere un valore compreso tra 1 µs (valore in figura) e 9 µs.

Il tempo di acquisizione deve essere calcolato in base al paragrafo 36.3 ADC Acquisition Requirements del manuale. Nel caso specifico non è rilevante in quanto è utilizzato un solo ingresso analogico; è stato impostato 2 µs a solo scopo dimostrativo.

Si noti che sono state scelte come tensioni di riferimento massa (VSS) ed alimentazione (VDD) in relazione al fatto che la tensione da misurare è, in questo caso, linearmente dipendente da VDD (è un partitore di tensione che realizza un trasduttore raziometrico). Il risultato della conversione sarà un numero compreso tra 0 (tensione A0 pari a massa) e 4095 (tensione A0 pari all'alimentazione positiva VDD).

Impostazione di base del convertitore

Occorre infine selezionare quale o quali canali analogici potranno essere utilizzati in aggiunta ai canali interni. In figura è selezionato come unico ingresso analogico A0. evidenziato da un lucchetto verde. Anche selezionando più di un ingresso, all'ingresso dell'ADC sarà collegato solo uno di questi alla volta.

La porta C ha tutti i pin configurati come uscite digitali e ad essa potranno essere collegati fino ad otto LED.

Configurazione dei pin

Il codice è particolarmente semplice:

Gran parte del codice è generato da MCC. Di seguito il codice completo del main():

void main(void) {
  uint16_t ADCvoltage; // Voltage from ADC (unsigned integer, 16 bit)
  SYSTEM_Initialize(); // Configure ADC (and other system devices)
  while (1) {
     ADCvoltage = ADCC_GetSingleConversion(A0); // Get voltage fron A0 pin
     // LATC = ADCvoltage >> 4; // Display 8 bits on LEDs - Optional
     // NOP(); // Place here breakpoint for debug - Optional
     }
  }

Con i valori mostrati, il tempo di conversione è di circa 16 + 2 µs (nota 4). Per la misura è stata utilizzata la tecnica qui descritta.

Misure assolute

A volte potrebbe essere utile conoscere il valore assoluto di una tensione. In questi casi è possibile utilizzare il modulo Fixed Voltage Reference (FVR) che genera una tensione fissa indipendente dall'alimentazione, nominalmente pari a 1 024 mV. Tale tensione può essere opzionalmente amplificata per 2 o per 4 (nota 2).

Dopo aver installato la risorsa FVR di MCC, l'impostazione è banale:

Impostazione di FVR

Occorre inoltre aver impostato il riferimento positivo dell'ADC a VFR anziché VDD.

Il codice è identico al precedente. L'unica avvertenza è relativa all'interpretazione dei dati numerici, che in questo caso sono una misura di tensione assoluta e nel precedente una frazione della tensione di alimentazione. Per esempio la lettura del numero 1000 indica rispettivamente:

Il valore di FVR

Il valore del riferimento di tensione è solo nominalmente 1,024 V. In alcuni PIC, per esempio nel PIC18LF2xK42, tale valore viene misurato in fabbrica durante il collaudo di ciascun esemplare, scrivendolo in un'apposita area di memoria non modificabile (Device Information Area, DIA).

Tale valore può essere per esempio letto con la funzione seguente (nota 3) ed utilizzato per la calibrazione dell'ADC:

uint16_t GetFVRA2X(void) {
  uint16_t FVRA2X;
  FVRA2X = FLASH_ReadWord(0x003F0032); // Read calibrated data from Device Information Area
  TBLPTRU = 0; // Restore TBLPTR for 64k code (workaround required after FLASH_ReadWord() )
  return (FVRA2X);
}

Misurare VDD

Spesso è necessario misurare la tensione di alimentazione del PIC18; il caso tipico è la misura della tensione della batteria che alimenta il PIC per la classica segnalazione LOW BATT.

Per fare ciò è possibile misurare FVR (valore noto) usando come tensione di riferimento per l'ADC VDD (valore ignoto); si applica quindi la formula inversa:

uint16_t ADCvoltage; // Voltage from ADC (unsigned integer, 16 bit)
uint16_t ReferenceVoltage; // Value of calibrated reference voltage (nominal: 2 048) [mV]
uint16_t Vdd; // VDD [mV]]

[...]
ReferenceVoltage = GetFVRA2X(); // Get FVR from calibration data
ADCvoltage = ADCC_GetSingleConversion(channel_FVR_Buffer1); // Get FVR from ADC using VDD as reference
Vdd = (((uint24_t) ReferenceVoltage) << 12) / ADCvoltage; // Inverse formula calculation

Misurare la temperatura

All'interno del PIC18F2xK42 è presente un sensore di temperatura che fornisce una tensione legata alla temperatura del chip. Il sensore è calibrato durante il processo di produzione alla temperatura di 90 °C e tale valore è salvato nella DIA.

La formula fornita per il calcolo della temperatura in gradi centigradi è:

 TemperatureTIM = 90 + (ADCmeas - ADCdia) * FVRA2X / (4095 * MV);

dove:

Due avvertenze:

Osservazioni

  1. Tale componente viene indicato come ADC2 o ADCC; la seconda C sta per Computation in quanto questo componente è in grado di eseguire una serie di operazioni indipendentemente dal processore
  2. Ovviamente non è possibile superare la tensione di alimentazione, Per esempio se l'alimentazione è di 3,3 V, non è possibile usare l'impostazione 4x
  3. La funzione FLASH_ReadWord() è contenuta nel modulo MCC Memory. L'azzeramento di TBLPTRU è richiesto per evitare che il valore assegnato da FLASH_ReadWord possa interferire con l'uso di puntatori a funzioni. Penso sia un bug del compilatore
  4. Il valore indicato in MCC non è conforme alla TABLE 44-15: ANALOG-TO-DIGITAL CONVERTER (ADC) CONVERSION TIMING SPECIFICATIONS dei fogli tecnici
  5.  Questa informazione è da prendere con le pinze e da verificare in un circuito reale non collegato ad un debugger


Data di creazione di questa pagina: luglio 2019
Ultima modifica: 26 luglio 2019


PIC18 in C

Appendici:

Qualche utile informazione integrativa: C per sistemi embedded

Licenza Creative Commons Attribuzione 4.0 Internazionale


EN - Pagina principale - Sommario - Accessibilità - Note legali e privacy policy - Posta elettronica

XHTML 1.0 Strict - CSS 3