Taula de continguts:

Microcontrolador AVR. LED intermitents mitjançant el temporitzador. Interruptors temporitzadors. Mode temporitzador CTC: 6 passos
Microcontrolador AVR. LED intermitents mitjançant el temporitzador. Interruptors temporitzadors. Mode temporitzador CTC: 6 passos

Vídeo: Microcontrolador AVR. LED intermitents mitjançant el temporitzador. Interruptors temporitzadors. Mode temporitzador CTC: 6 passos

Vídeo: Microcontrolador AVR. LED intermitents mitjançant el temporitzador. Interruptors temporitzadors. Mode temporitzador CTC: 6 passos
Vídeo: Efecte amb 8 LEDS mitjançant mini-AVR. 2024, Desembre
Anonim
Image
Image

Hola a tothom!

Els temporitzadors són un concepte important en el camp de l’electrònica. Tots els components electrònics funcionen en una base de temps. Aquesta base de temps ajuda a mantenir tot el treball sincronitzat. Tots els microcontroladors funcionen a una freqüència de rellotge predefinida, tots tenen una disposició per configurar temporitzadors. AVR presumeix de tenir un temporitzador molt precís, precís i fiable. Ofereix un munt de funcions, cosa que el converteix en un tema extens. La millor part és que el temporitzador és totalment independent de la CPU. Per tant, funciona paral·lel a la CPU i no hi ha cap intervenció de la CPU, cosa que fa que el temporitzador sigui bastant precís. En aquesta secció explico els conceptes bàsics dels temporitzadors AVR. Estic escrivint un programa senzill en codi C per controlar els intermitents LED, mitjançant temporitzadors.

Pas 1: descripció

Declaració del problema 1: llampem primer LED (verd) cada 50 ms
Declaració del problema 1: llampem primer LED (verd) cada 50 ms

A ATMega328 hi ha tres tipus de temporitzadors:

Timer / Counter0 (TC0): és un mòdul de temporitzador / comptador de 8 bits per a usos generals, amb dues unitats OutputCompare independents i suport PWM;

Temporitzador / comptador1 (TC1): la unitat de temporitzador / comptador de 16 bits permet una sincronització precisa de l’execució del programa (gestió d’esdeveniments), generació d’ones i mesurament de la sincronització del senyal;

Temporitzador / comptador2 (TC2): és un mòdul de temporitzador / comptador de 8 bits, de propòsit general, amb funcionament asincrònic i PWM;

Pas 2: declaració del problema 1: llampem primer LED (verd) cada 50 ms

Declaració del problema 1: llampem primer LED (verd) cada 50 ms
Declaració del problema 1: llampem primer LED (verd) cada 50 ms
Declaració del problema 1: llampem primer LED (verd) cada 50 ms
Declaració del problema 1: llampem primer LED (verd) cada 50 ms

Metodologia:

- utilitzar un precalificador Timer0 per reduir un senyal elèctric d'alta freqüència a una freqüència inferior per divisió sencera;

- utilitzar una interrupció cada vegada que el Timer0 es desborda;

Temporitzador0 (8 bits) compta de 0 a 255 després, es desborden, aquest valor canvia a cada pols del rellotge.

F_CPU = 16 MHz: període de temps de rellotge = 1000 ms / 16000000 Hz = 0,0000625 ms

Recompte de temporitzador = (Retard obligatori / període de temps de rellotge) -1 = (50 ms / 0,0000625 ms) = 799999

El rellotge ja ha marcat 799999 vegades per donar un retard de només 50 ms.

Podem utilitzar una tècnica de divisió de freqüències que s’anomena prescaling per disminuir el recompte del temporitzador. L'AVR ens ofereix els següents valors de prescaler per triar: 8, 64, 256 i 1024. Vegeu la taula que resumeix els resultats de l'ús de diferents prescalers.

El valor del comptador sempre ha de ser un nombre enter. Escollim un prescaler 256.

A la majoria de microcontroladors, hi ha una cosa anomenada Interrupció. Aquesta interrupció es pot activar sempre que es compleixin determinades condicions. Ara, cada vegada que s’activa una interrupció, l’AVR s’atura i desa l’execució de la rutina principal, atén la trucada d’interrupció (executant una rutina especial, anomenada ISR) i un cop finalitzada, torna a la rutina principal i continua executant-la.

Com que el retard necessari (50 ms) és superior al màxim possible: 4, 096 ms = 1000 ms / 62500Hz * 256, òbviament el temporitzador es desbordarà. I sempre que el temporitzador es desborda, es dispara una interrupció.

Quantes vegades s'hauria de disparar la interrupció?

50ms / 4.096ms = 3125/256 = 12.207 Si el temporitzador s'ha desbordat 12 vegades, haurien passat 12 * 4.096ms = 49.152ms. A la 13a iteració, necessitem un retard de 50 ms a 49.152 ms = 0,848 ms.

A una freqüència de 62500Hz (prescaler = 256), cada tick dura 0,016 ms. Per tant, per aconseguir un retard de 0,848 ms, caldria 0,848 ms / 0,016 ms = 53 paparres. Per tant, a la 13a iteració, només permetem que el temporitzador compti fins a 53 i, després, el restableixi.

Inicialitzeu el temporitzador 0 / comptador (vegeu la imatge):

TCCR0B | = (1 << CS02) // configura el temporitzador amb prescaler = 256 TCNT0 = 0 // inicialitza el comptador TIMSK0 | = (1 << TOIE0) // activa interrupció de desbordament sei () // activa interrupcions globals tot_overflow = 0 // inicialitzar la variable de comptador de desbordament

Pas 3: declaració del problema 2: llampem segon LED (blau) cada 1 s

Declaració del problema 2: llampem el segon LED (blau) cada 1 s
Declaració del problema 2: llampem el segon LED (blau) cada 1 s
Declaració del problema 2: llampem el segon LED (blau) cada 1 s
Declaració del problema 2: llampem el segon LED (blau) cada 1 s
Declaració del problema 2: llampem el segon LED (blau) cada 1 s
Declaració del problema 2: llampem el segon LED (blau) cada 1 s

Metodologia:

- utilitzar un precalificador Timer1 per reduir un senyal elèctric d'alta freqüència a una freqüència inferior per divisió sencera;

- utilitzant Clear Timer en mode Comparació (CTC);

- utilitzar interrupcions amb mode CTC;

El temporitzador1 (16 bits) compta de 0 a 65534 després d'això, es desborden. Aquest valor canvia a cada pols del rellotge.

F_CPU = 16 MHz: període de temps de rellotge = 1000 ms / 16000000 Hz = 0,0000625 ms Recompte de temporitzador = (Retard / període de temps de rellotge obligatori) -1 = (1000 ms / 0,0000625 ms) = 15999999

El rellotge ja ha marcat 15999999 vegades per donar un retard d'1 s.

Podem utilitzar una tècnica de divisió de freqüències que s’anomena prescaling per disminuir el recompte del temporitzador. L'AVR ens ofereix els següents valors de prescaler per triar: 8, 64, 256 i 1024. Vegeu la taula que resumeix els resultats de l'ús de diferents prescalers. El valor del comptador sempre ha de ser un nombre enter. Escollim un prescaler 256.

En el mode Temporitzador net en comparació (CTC), s’utilitza el registre OCR1A o ICR1 per manipular la resolució del comptador. En mode CTC, el comptador s'esborra a zero quan el valor del comptador (TCNT1) coincideix amb l'OCR1A o l'ICR1. L’OCR1A o l’ICR1 defineixen el valor màxim del comptador, d’aquí també la seva resolució. Aquest mode permet un major control de la freqüència de sortida de la comparació de comparació. També simplifica el funcionament del recompte d'esdeveniments externs. Hem de dir a l'AVR que restableixi el temporitzador1 / comptador tan aviat com el seu valor assoleixi el valor 62500, per aconseguir així un retard d'1 s.

Inicialitzeu el temporitzador1 / comptador (vegeu la imatge):

TCCR1B | = (1 << WGM12) | (1 << CS12) // configurar temporitzador amb prescaler = 256 i mode CTC TCNT1 = 0 // inicialitzar comptador TIMSK1 | = (1 << OCIE1A) // habilitar comparar interrupció OCR1A = 62500 // inicialitza el valor de comparació

Pas 4: declaració del problema 3: llampem el tercer LED (vermell) cada 16 ms

Declaració del problema 3: llampem el tercer LED (vermell) cada 16 ms
Declaració del problema 3: llampem el tercer LED (vermell) cada 16 ms
Declaració del problema 3: llampem el tercer LED (vermell) cada 16 ms
Declaració del problema 3: llampem el tercer LED (vermell) cada 16 ms
Declaració del problema 3: llampem el tercer LED (vermell) cada 16 ms
Declaració del problema 3: llampem el tercer LED (vermell) cada 16 ms
Declaració del problema 3: llampem el tercer LED (vermell) cada 16 ms
Declaració del problema 3: llampem el tercer LED (vermell) cada 16 ms

Metodologia:

- utilitzar un precalificador Timer2 per reduir un senyal elèctric d'alta freqüència a una freqüència inferior per divisió sencera;

- utilitzant Clear Timer en mode Comparació (CTC);

- utilitzar el mode CTC de maquinari sense interrupcions;

Timer2 (8 bits) compta de 0 a 255 després, es desborden. Aquest valor canvia a cada pols del rellotge.

F_CPU = 16 MHz: període de temps de rellotge = 1000 ms / 16000000 Hz = 0,0000625 ms

Recompte de temporitzador = (Retard obligatori / període de temps de rellotge) -1 = (16 ms / 0,0000625 ms) = 255999

El rellotge ja ha marcat 255999 vegades per donar un retard de 16 ms.

Vegeu la taula que resumeix els resultats de l’ús de diferents prescaladors. El valor del comptador sempre ha de ser un nombre enter. Escollim un prescaler 1024!

En mode CTC, el comptador s'esborra a zero quan el valor del comptador (TCNT2) coincideix amb l'OCR2A o l'ICR2. El pin PB3 també és el pin de comparació de sortida de TIMER2 - OC2A (vegeu el diagrama).

Registre de control del temporitzador / comptador2 A - TCCR2A Bit 7: 6 - COM2A1: 0 - Comparació del mode de sortida per a la unitat de comparació A. Com que hem de commutar el LED, escollim l’opció: Activa OC2A a la comparació de comparació Sempre que es produeix una coincidència de comparació, El pin OC2A es commuta automàticament. No cal comprovar cap bit de bandera, ni cal atendre cap interrupció.

Inicialitzar Timer2 / Counter

TCCR2A | = (1 << COM2A0) | (1 << WGM21) // configura el pin OC2A del temporitzador en mode alternat i en mode CTC TCCR2B | = (1 << CS22) | (1 << CS21) | (1 << CS20) // configurar el temporitzador amb prescaler = 1024 TCNT2 = 0 // inicialitzar el comptador OCR2A = 250 // inicialitzar el valor de comparació

Pas 5: Escriure codi per a un programa a C. Penjar fitxers HEX a la memòria flash del microcontrolador

Escriptura de codi per a un programa a C. Penjar fitxers HEX a la memòria flash del microcontrolador
Escriptura de codi per a un programa a C. Penjar fitxers HEX a la memòria flash del microcontrolador
Escriptura de codi per a un programa a C. Penjar fitxers HEX a la memòria flash del microcontrolador
Escriptura de codi per a un programa a C. Penjar fitxers HEX a la memòria flash del microcontrolador

Escriptura i creació de l'aplicació de microcontrolador AVR en codi C mitjançant la plataforma de desenvolupament integrat - Atmel Studio.

F_CPU defineix la freqüència de rellotge en Hz i és comú en els programes que utilitzen la biblioteca avr-libc. En aquest cas, les rutines de retard l’utilitzen per determinar com calcular els retards.

#ifndef F_CPU

#define F_CPU 16000000UL // indicador de freqüència de cristall (16 MHz AVR ATMega328P) #endif

#include // header per habilitar el control de flux de dades sobre pins. Defineix pins, ports, etc.

El primer fitxer d’inclusió forma part d’avr-libc i s’utilitzarà en pràcticament qualsevol projecte AVR en què treballeu. io.h determinarà la CPU que utilitzeu (és per això que especifiqueu la peça en compilar-la) i, al seu torn, inclourà la capçalera de definició IO adequada per al xip que estem utilitzant. Simplement defineix les constants de tots els pins, ports, registres especials, etc.

#include // header per habilitar la interrupció

volàtil uint8_t tot_overflow; // variable global per comptar el nombre de desbordaments

Metodologia de l'enunciat del problema: LED de primer flaix (verd) cada 50 ms

- utilitzar un precalificador Timer0 per reduir un senyal elèctric d'alta freqüència a una freqüència inferior per divisió sencera;

- utilitzar una interrupció cada vegada que el Timer0 es desborda;

void timer0_init () // inicialitza el temporitzador0, la interrupció i la variable

{TCCR0B | = (1 << CS02); // configurar el temporitzador amb prescaler = 256 TCNT0 = 0; // inicialitzar el comptador TIMSK0 | = (1 << TOIE0); // active overflow nterrupt sei (); // habilita les interrupcions globals tot_overflow = 0; // inicialitzar la variable de comptador de desbordament}

Metodologia de l'enunciat del problema: Flash segon LED (blau) cada 1 s

- utilitzar un precalificador Timer1 per reduir un senyal elèctric d'alta freqüència a una freqüència inferior per divisió sencera;

- utilitzant Clear Timer en mode Comparació (CTC);

- utilitzar interrupcions amb mode CTC;

void timer1_init () // inicialitza el temporitzador1, la interrupció i la variable {TCCR1B | = (1 << WGM12) | (1 << CS12); // configurar el temporitzador amb prescaler = 256 i el mode CTC TCNT1 = 0; // inicialitzar el comptador OCR1A = 62500; // inicialitzar el valor de comparació TIMSK1 | = (1 << OCIE1A); // habilita la interrupció de comparació}

Metodologia de l'enunciat del problema: Flash tercer LED (vermell) cada 16 ms

- utilitzar un precalificador Timer2 per reduir un senyal elèctric d'alta freqüència a una freqüència inferior per divisió sencera;

- utilitzant Clear Timer en mode Comparació (CTC);

- utilitzar el mode CTC de maquinari sense interrupcions;

void timer2_init () // inicialitzar temporitzador2 {TCCR2A | = (1 << COM2A0) | (1 << WGM21); // configureu el pin OC2A del temporitzador en mode de commutació i mode CTC TCCR2B | = (1 << CS22) | (1 << CS21) | (1 << CS20); // configurar el temporitzador amb prescaler = 1024 TCNT2 = 0; // inicialitzar el comptador OCR2A = 250; // inicialitzar el valor de comparació}

La rutina de servei d'interrupció de desbordament TIMER0 es diu cada vegada que desborda TCNT0:

ISR (TIMER0_OVF_vect)

{tot_overflow ++; // fer un seguiment del nombre de desbordaments}

Aquest ISR s'activa sempre que es produeix una coincidència, per tant, canvia el led aquí mateix:

ISR (TIMER1_COMPA_vect) {PORTC ^ = (1 << 1); // commuta aquí}

int main (buit)

{DDRB | = (1 << 0); // connecteu 1 (verd) al pin PB0 DDRC | = (1 << 1); // connecteu 2 (blau) al pin PC1 DDRB | = (1 << 3); // connectar 3 (vermell) al pin PB3 (OC2A) pin timer0_init (); // inicialitzar timer0 timer1_init (); // inicialitzar timer1 timer2_init (); // inicialitzeu el temporitzador2 mentre (1) // bucle per sempre {

Si el temporitzador 0 ha sobrevolat 12 vegades, haurien passat 12 * 4.096ms = 49.152ms. A la 13a iteració, necessitem un retard de 50 ms a 49.152 ms = 0,848 ms. Per tant, a la 13a iteració, només permetem que el temporitzador compti fins a 53 i, després, el restableixi.

if (tot_overflow> = 12) // comprova si no. de desbordaments = 12 NOTA: s’utilitza '> ='

{if (TCNT0> = 53) // comproveu si el recompte del temporitzador arriba a 53 {PORTB ^ = (1 << 0); // commuta el led TCNT0 = 0; // restabliment del comptador tot_overflow = 0; // restablir el comptador de desbordament}}}}

Càrrega del fitxer HEX a la memòria flash del microcontrolador:

escriviu l'ordre a la finestra de l'indicador DOS:

avrdude –c [nom del programador] –p m328p –u –U flash: w: [nom del fitxer hexadecimal] En el meu cas és: avrdude –c ISPProgv1 –p m328p –u –U flash: w: Timers.hex

Aquesta ordre escriu un fitxer hexadecimal a la memòria del microcontrolador. Mireu el vídeo amb una descripció detallada de la gravació de memòria flash del microcontrolador:

La memòria flash del microcontrolador està gravant …

D'acord! Ara, el microcontrolador funciona d’acord amb les instruccions del nostre programa. Ho comprovem!

Pas 6: Realització del circuit elèctric

Realització del circuit elèctric
Realització del circuit elèctric
Realització del circuit elèctric
Realització del circuit elèctric
Realització del circuit elèctric
Realització del circuit elèctric

Connecteu els components segons el diagrama esquemàtic.

Recomanat: