Les ports parallèles d'E/S

Caractéristiques générales

  • L'Arduino UNO dispose de 23 broches d'E/S, organisées en 3 ports parallèles numériques

    • ce sont les ports B, C et D
    • port B : broches numériques 8 à 13
    • port C : broches analogiques (0 à 5)
    • port D : broches numériques 0 à 7
  • Ils sont tous bidirectionnels

  • le port C peut aussi être utilisé comme « port d'entrée analogique » (CAN)
  • Leurs lignes peuvent être configurées/utilisées individuellement

Registres de contrôle des ports

  • Chaque port x (pour B, C ou D) est contrôlé par 3 registres
    • DDRx : le registre de direction (sens de transfert) du port
    • PORTx : le registre de donnée du port
    • PINx : le registre d'entrée du port
  • Chacun de leur bit contrôle une ligne particulière du port
    • exemple : le port B regroupe les broches numériques 8 à 13
    • le bit 0 de ses registres est donc associé à la broche numérique 8

Registres du port D


Fonction des registres

  • Seuls PORTx et DDRx se comportent vraiment comme des variables mémoires
    • un composant mémoire leur ait associé, qui joue le rôle de verrou (=latch)
    • les écritures dans ces registres sont donc persistentes
  • PINx n'est pas un composant mémoire

    • il est directement connecté aux lignes du port x, et traduit donc leur tension
  • DDRx : détermine la direction de chaque broche du port x

    • 0 pour une Entrée, 1 pour une Sortie (« 0/1 » pour « E/S »)
  • PORTx
    • pour les broches en sortie : 0 pour tension basse, 1 pour tension haute
    • pour les broches en entrée : 1 pour activer la résistance « pull-up », 0 sinon
  • PINx
    • indique la tension des broches : 0 pour tension basse, 1 pour tension haute

Les timers

Qu'est-ce que c'est ?

Définition

Définition : Timer

  • C'est un périphérique matériel destiné à compter :
    • soit des évènements extérieurs, potentiellement non-périodiques : c'est sa fonction de compteur ;
    • soit des évènements internes périodiques (tops d'horloge) : c'est sa fonction de temporisateur, de mesure le temps.
  • Tant qu'il est « activé », un timer compte. C'est sa fonction : il s'incrémente chaque fois qu'il détecte un nouvel évènement.
    En cas de débordement, il reprend à 0 (sauf mode de fonctionnement particulier), comme n'importe quelle variable C de type entier non-signé.
  • Un timer sert généralement à :
    • mesurer des durées
    • déclencher périodiquement des routines d'interruptions
    • générer des signaux MLI

Composition d'un timer type
  • des broches :
    • d'entrée : pour compter ses changements d'états ; ce sont les « évènements externes » que le timer peut compter ;
    • de sortie : pour signaler que le compteur a atteint une valeur particulière ;
  • un sélecteur : sélectionne l'entrée dont les changements d'états (évènements) seront comptés, en général :
    • l'horloge interne
    • ou une broche externe ;
  • un prédiviseur :
    • dans le cas ou le compteur est connecté à l'horloge, il est possible de ralentir le comptage en ne comptant qu'1 top d'horloge sur n ;
    • n : c'est le prédiviseur. Il est généralement choisi parmi un ensemble de puissances de 2, par exemple : {1, 16, 64, 256} ;
  • un registre de comptage : c'est lui qui stocke la valeur de comptage ;
  • des unités de comparaison, chacune munie d'un registre de comparaison : ces registres contiennent une valeur destinée à être comparée à celle du compteur ; dans le but de changer l'état d'une broche de sortie de l'unité de comparaison, ou de déclencher une interruption ;
  • des registres de contrôle : pour configurer son mode de fonctionnement.

Le timer 0 de l'ATmega328

Schéma du timer 0 de l'ATmega328

Schéma du timer 0


Deux principaux modes de fonctionnement
Mode normal
  • le timer compte tout le temps, c'est-à-dire qu'il s'incrémente à chaque « évènement » détecté, qui peuvent être au choix :
    • les tops d'horloge prédivisés, en mode temporisateur,
    • les changements d'état de sa broche d'entrée, en mode compteur ;
  • il revient naturellement à 0 après un débordement (overflow).
  • il peut déclencher une interruption de débordement :

Mode normal du timer 0

  • Lorsque le timer compte les tops d'horloge prédivisés (fonction temporisateur), la durée (période) de ses cycles est définie par :
            T_cycle_normal = prédiviseur/fcpu * 256

Mode remise à zéro sur comparaison
  • C'est le mode CTC : Clear Timer on Compare match
  • Le domaine de comptage est raccourci : le timer évolue de 0 à la valeur du registre de comparaison A, puis revient à 0
  • le test de comparaison peut aussi déclencher (outre le reset du compteur) :
    • une interruption de comparaison A (différente de celle de débordement ! et de celle de comparaison B)
    • un changement d'état de la broche de sortie OC0A

Mode CTC du timer 0

  • Dans ce mode, + fonction temporisateur, la durée du cycle est :
   T_cycle_CTC = préd./fcpu * (OCR0A+1)

Génération de signal carré en mode CTC
  • La broche de sortie OC0A (= broche du timer 0 associée à la comparaison A) peut s'inverser à chaque comparaison :

Génération de signal carré en mode CTC

  • Cela permet la génération d'un signal carré de période double de celle du cycle de comptage :
   T_signal_sortie_CTC = 2*préd./fcpu * (OCR0A+1)

Les registres du timer 0
Registre de comptage du timer 0 : TCNT0

Registre de comptage du timer 0

  • C'est un registre 8 bits : le timer 0 est donc un timer 8 bits.
  • on veillera à l'initialiser à 0 si l'on souhaite que son premier cycle soit complet.

Registre de comparaison A du timer 0 : OCR0A

Registre de comparaison A du timer 0

  • C'est aussi un registre 8 bits (son domaine de valeurs est identique à celui du registre de comptage)
  • en cas d'égalité avec le contenu du registre de comptage, une interruption peut être demandée, et l'état de la broche de sortie OC0A peut être inversée.
  • il existe une seconde unité de comparaison, appelée B, construite sur le même modèle ; elle dispose donc aussi :
    • d'un registre de comparaison : OCR0B, qui permet de définir une seconde valeur de comparaison ;
    • d'une source d'interruption propre (l'interruption de comparaison B) ;
    • d'une broche de sortie propre : OC0B.

Registre de contrôle A du timer 0 : TCCR0A

Registre de contrôle A du timer 0

  • Les 2 bits de poids faibles sont utilisés - avec le bit WGM02 de l'autre registre de contrôle - pour définir le mode de fonctionnement du timer (dont son sens de comptage) :

Tableau de sélection du mode de fonctionnement du timer 0


Registre de contrôle A du timer 0 (suite) : TCCR0A

Registre de contrôle A du timer 0

  • Les 2 bits de poids forts - COM0A1 et COM0A0 - sont utilisés pour émettre un signal sur la broche de sortie associée à la comparaison A - OC0A - dont la forme évolue lorsque le compteur prend la valeur du registre de comparaison A

  • En mode normal ou CTC, ces 2 bits peuvent être réglés ainsi :

Tableau de sélection de la forme du signal généré sur la broche OC0A

  • L'inversion (toggle) permet de généré le signal carré illustré plus haut

  • Les 2 bits suivants concernent la comparaison avec le second registre de comparaison - B - et ne sont pas décrits ici


Registre de contrôle B du timer 0 : TCCR0B

Registre de contrôle B du timer 0

Il complète le registre précédent :

  • pour la définition du mode de fonctionnement, cf. tableau ci-dessus.
  • pour la sélection du signal « pris en compte »
    • soit un signal d'entrée sur la broche T0 (fonction compteur)
    • soit un signal d'horloge, avec son prédiviseur (temporisateur)

Tableau de sélection du prédiviseur du timer 0


Registre d'interruption du timer 0 : TIMSK0

Registre d'interruption du timer 0

Il permet d'activer/désactiver individuellement les 3 sources d'interruption du timer 0 :

  • TOIE0 : autorisation de l'interruption de débordement
  • OCIE0A : autorisation de l'interruption de comparaison A
  • OCIE0B : autorisation de l'interruption de comparaison B

Programmation du timer 0 : procédure à suivre
  1. Spécifier le mode de fonctionnement du timer (cf. TCCR0A, TCCR0B), parmi ceux vus ici :
    • mode normal
    • mode remise à zéro sur comparaison (CTC)
  2. Spécifier le mode temporisateur, avec la période d'interruption souhaitée :
    1. choix du prédiviseur (cf. TCCR0B)
    2. calcul de la valeur de comparaison, si mode CTC(cf. OCR0A )
  3. Autoriser l'interruption souhaitée (cf. TIMSK0)
    • soit celle de débordement, si mode normal
    • soit celle de comparaison, si mode CTC
  4. Reset du registre de comptage (TCNT0 = 0)
    • si l'on souhaite un 1er cycle complet (sachant qu'après la 1ère comparaison/débordement, le registre est forcément remis à zéro)

Le timer 2 de l'ATmega328

Un timer proche du timer 0

Schéma du timer 2


Des fonctions similaires, mais avec qqs différences
  • Tous les registres du timer 0 existent pour le timer 2, avec un fonctionnement globalement identique.

  • Leurs noms sont les mêmes, en dehors du numéro du timer. Par exemple, le registre de comparaison A s'appelle OCR0A dans le timer 0, et OCR2A dans le timer 2.

  • Nous voyons ici les différences qui nous importent (c.-à-d. pour les modes de fonctionnements normaux et CTC).


Registre de contrôle A du timer 2 : TCCR2A

Registre de contrôle A du timer 2

Il ne se paramètre pas exactement comme le registre TCCR0A :

Tableau de sélection du mode de fonctionnement du timer 2


Registre de contrôle B du timer 2 : TCCR2B

Registre de contrôle B du timer 2

Là encore, il y a des différences, sur les prédiviseurs disponibles :

Tableau de sélection du prédiviseur du timer 2