Microcontrôleurs II - Séquence 7 Filière IESE 3ième Année
TD 7 : Utilisation du Convertisseur analogique-numérique
Exercices à préparer avant le TD : (à rendre au début de la séance)
Exercice 1 :On suppose la tension de référence du convertisseur ADCx fixée à VDDA=3.3V.
Donner la précision de conversion en bits et en Volts en fonction de la valeur des bits de configuration RES.
Valeur des bits RES Précision en nombre de bits Précision relative (%) Précision absolue (Volts)
(ADCx->CR1)
0b00
0b01
0b10
0b11
Exercice 2 : Remplir le tableau suivant en indiquant les plages de bits concernées :
Fonction Séquence normale Séquence injectée
Déclencheur de mesure
Indicateur de mesure en cours
Indicateur de fin de mesures
Registre de séquence de mesure
Nombre de mesures par séquence
Registre(s) de résultats de mesures
Exercices traités en TD :
Exercice 3 : Écrire une routine qui paramètre le temps d'échantillonage d'un canal du convertisseur ADC.
void ADC1_temps_echantillonnage(uint8_t canal,uint8_t SMPR);
Où SMPR est la valeur binaire sur 3bits qui code le temps d'échantillonnage.
Exercice 4 : Écrire une routine qui utilise le mode injecté du convertisseur ADC1 pour mesurer les valeurs des
4 canaux passés en paramètres :
void mesure_injectee_ADC1(uint8_t canal1,uint8_t canal2,
uint8_t canal3,uint8_t canal4);
La routine devra attendre la fin de la mesure avant de se terminer.
1/4
Microcontrôleurs II - Séquence 7 Filière IESE 3ième Année
Exercice 5 : Après une séquence de mesures, on arrête le programme et avec GDB, on obtient le contenu des
registres du convertisseur analogique-numérique. Décodez les paramètres pour expliciter ce qui a été mesuré
(canaux et temps d'échantillonnage) et les résultats obtenus.
(gdb) print /x ADC1
$1 = {SR = 0xc, CR1 = 0x100, CR2 = 0x1, SMPR1 = 0x7e00000, SMPR2 = 0x0,
JOFR1 = 0x0, JOFR2 = 0x0, JOFR3 = 0x0, JOFR4 = 0x0, HTR = 0xfff, LTR =
0x0, SQR1 = 0x0, SQR2 = 0x0, SQR3 = 0x0, JSQR = 0x38ca52, JDR1 = 0x39d,
JDR2 = 0x39d, JDR3 = 0x39b, JDR4 = 0x5d8, DR = 0x0}
(gdb) print /x ADC_common
$2 = {CSR = 0xc, CCR = 0x830000, CDR = 0x0}
Exercice 6 :
On donne l'ensemble de valeurs suivantes :
Nom Description Valeur hexa
VREFIN_CAL (valeur d'usine) mesure de la tension fixe pour 0x5e1
VDDA=3.3v
VREFIN mesure de la tension fixe (VDDA actuel) 0x5db
TS_CAL1 (ou ValC1) mesure de la température pour 0x3b5
VDDA=3.3v et TC1=30°C
TS_CAL2 (ou ValC2) mesure de la température pour 0x4b0
VDDA=3.3v et TC2=110°C
ValTS mesure actuelle de la température pour 0x3b9
VDDA et T inconnues
1) Donner la formule et calculer la valeur actuelle de VDDA.
2) Donner la formule et calculer la valeur de la température mesurée sachant que la tension du capteur est
indépendante de VDDA et évolue linéairement par rapport à la température. On pourra s'aider de la figure
fournie à l'exercice 4 du TP.
2/4
Microcontrôleurs II - Séquence 7 Filière IESE 3ième Année
TP 7 : Utilisation du Convertisseur analogique-numérique
Potentiomètre, Capteur de température
Le répertoire /home/iese-2019/Partage/microC/TP7/adc_project contient un projet prêt à compiler
avec la bibliothèque de fonctions permettant d'utiliser le convertisseur analogique-numérique.
L’apéritif (le B-A, Ba)
Exercice 1 : Mesure du potentiomètre
Voici les connections des entrées analogiques de la carte shield.
Patte STM32 Patte connecteur Utilisation Nucleo Utilisation Shield
PB0 A3 ADC12_IN8 Potentiomètre
PC0 A5 ADC123_IN10 Diodes protection
PC1 A4 ADC123_IN11 Diodes protection
a) Écrire une routine void configuration_potentiometre() qui configure la patte PB0 du port
GPIOB et le convertisseur ADC1 pour mesurer la valeur du canal 8. On utilisera un temps d'échantillonage
long.
b) Écrire une routine uint32_t mesure_potentiometre() qui lance une mesure et renvoie le résultat
de la mesure.
c) À l'aide d'une boucle, afficher en continu le résultat de la mesure.
Le plat de résistance (l’incontournable)
Exercice 2 : On veut maintenant écrire un programme plus économe en rafraichissant moins souvent l'affichage
de la valeur du potentiomètre.
Pour cela on va utiliser une variable globale volatile uint32_t flag=0;
- On va utiliser le SysTick (période=1ms) pour lever l'indicateur flag (0->1) toutes les 500ms.
- Dans le programme main, on attendra que flag passe à 1 pour l'abaisser (1->0) et lancer une mesure du
potentiomètre puis afficher le résultat.
- pour attendre intelligemment que l'indicateur flag passe à 1, on peut utiliser __WFI()pour arrêter le CPU
jusqu'à la prochaine interruption : while (flag==0) __WFI();
Mettre en place cette stratégie pour afficher la valeur du potentiomètre (Rafraîchissement toutes les 500ms).
Exercice 3 : Maintenant, utiliser la valeur du potentiomètre pour afficher un motif tournant avec les 4 LEDs :
Quand on tourne le bouton du potentiomètre, les LEDs doivent afficher un motif tournant dans le même sens
que le bouton.
Le motif des leds doit faire 12 tours sur toute la course du bouton du potentiomètre.
On pourra passer la période de rafraîchissement à 20 ms et supprimer l'affichage.
3/4
Microcontrôleurs II - Séquence 7 Filière IESE 3ième Année
La cerise sur le gâteau (le défi de la semaine !) :
On veut écrire un programme qui affiche la température toutes les 500ms. Pour cela on doit alimenter le capteur
de température : enable_Vrefint();
Ensuite, il faut mesurer la tension de référence (ADC1 canal 17) et celle du capteur (ADC1 canal 18).
a) Faire mesurer, calculer et afficher la valeur actuelle de Vdda. (voir exercice 6 du TD)
b) Ajouter la mesure, le calcule et l'affichage des tensions du capteur (mesure et calibrage à 30°C et 110°C).
c) Ajouter le calcul et l'affichage de la température.
On utilisera les constantes globales VREFIN_CAL, TS_CAL1 et TS_CAL2 pour normaliser les valeurs
mesurées.
Indication : On utilisera le type float pour les calculs en flottants et la fonction ftod(f) pour l'affichage
comme dans l'exemple ci-dessous :
printf("Vdda=%5.3fV\tTs=%4.1fC\r",ftod(voltage_sensor()),ftod(temp_sensor()));
4/4