Outils pour utilisateurs

Outils du site


tns_nucleo_tp1

Différences

Ci-dessous, les différences entre deux révisions de la page.

Lien vers cette vue comparative

Les deux révisions précédentes Révision précédente
Prochaine révision
Révision précédente
tns_nucleo_tp1 [2018/04/04 20:15]
bvandepo
tns_nucleo_tp1 [2019/04/03 14:01] (Version actuelle)
bvandepo
Ligne 44: Ligne 44:
 Ensuite:  ​ Ensuite:  ​
   - lancer eclipse via la console en tapant: ​  /​opt/​STM32/​SystemWorkbench/​eclipse  ​   - lancer eclipse via la console en tapant: ​  /​opt/​STM32/​SystemWorkbench/​eclipse  ​
 +  - Si une fenêtre "​Select a workspace"​ apparaît, saisir le nom de dossier: /​home/​IUT/<​login étudiant>/​workspace_ac6/​ et cocher "Use this as the default..."​
 +  - fermer l'​onglet "​Welcome"​ en cliquant sur la croix.
   - cliquer à gauche sur l'​icone C/C++   - cliquer à gauche sur l'​icone C/C++
   - cliquer droit dans project Explorer->​Import,​ puis General->​Existing Projects into Workspace   - cliquer droit dans project Explorer->​Import,​ puis General->​Existing Projects into Workspace
Ligne 51: Ligne 53:
   - cliquer sur Finish   - cliquer sur Finish
  
-===Initialisation système de gestion de version=== +===Activation de la sauvegarde automatique des fichiers à chaque compilation=== 
-Seulement après avoir importé le projet depuis l'​archive dans eclipse, saisir dans une console:+  - Cliquer sur  Window->​Preferences. 
 +  - Dans la colonne de gauche, cliquer sur la petite flèche à gauche de "​General"​ puis sur "​Workspace"​ dans la liste qui apparaît. 
 +  - A droite, cocher "Save automatically before build"​. 
 +  - Cliquer sur OK. 
 + 
 + 
 +===Initialisation ​du système de gestion de version=== 
 +Seulement après avoir importé le projet depuis l'​archive dans eclipse, saisir ​**dans une nouvelle ​console**: 
 +  echo commence
   cd ~/​workspace_ac6/​   cd ~/​workspace_ac6/​
   rm  nucleo_tns_etu2018.zip   rm  nucleo_tns_etu2018.zip
Ligne 60: Ligne 70:
   git commit -m'​initial version'​   git commit -m'​initial version'​
   gitk    gitk 
-  ​ +  ​echo fini
  
 ------------------------------------------------------------------------------------ ------------------------------------------------------------------------------------
Ligne 72: Ligne 81:
 Vous devrez affecter une bonne valeur à **htim1.Init.Period** pour obtenir la fréquence demandée. Il s'agit de la valeur correspondant au nombre de cycle -1 de décomptage du timer (chargée dans le registre nommé ARR lors du TD précédent),​ le prédiviseur étant réglé sur un facteur 1. Vous avez effectué un tel calcul lors du TD précédent. Vous devrez affecter une bonne valeur à **htim1.Init.Period** pour obtenir la fréquence demandée. Il s'agit de la valeur correspondant au nombre de cycle -1 de décomptage du timer (chargée dans le registre nommé ARR lors du TD précédent),​ le prédiviseur étant réglé sur un facteur 1. Vous avez effectué un tel calcul lors du TD précédent.
  
-Il faut ensuite compléter la fonction d'​interruption dans le fichier Src/main.c +Il faut ensuite compléter la fonction d'​interruption dans le fichier ​**Src/main.cpp**: 
 +<file cpp main.cpp>​
   void HAL_TIM_PeriodElapsedCallback(TIM_HandleTypeDef *htim){   void HAL_TIM_PeriodElapsedCallback(TIM_HandleTypeDef *htim){
-     //Code executé ​à la fréquence d'​interruption+     //Ecrire ici votre code exécuté ​à la fréquence d'​interruption
   }   }
-  ​+</​file>  ​
 ===Génération du signal sur la broche===  ​ ===Génération du signal sur la broche===  ​
  
Ligne 84: Ligne 93:
 {{https://​homepages.laas.fr/​bvandepo/​files/​iut/​tp_tns/​tns_line_in.jpg}} {{https://​homepages.laas.fr/​bvandepo/​files/​iut/​tp_tns/​tns_line_in.jpg}}
   ​   ​
 +
 +Au verso de la carte, les signaux en sortie directe du DAC sont accessibles sur la broches PA6 (et éventuellement PA5 pour un second signal dans le TP suivant):
 +
 +{{https://​homepages.laas.fr/​bvandepo/​files/​iut/​tp_tns/​image_verso.jpg}}
   ​   ​
-Les autres broches des connecteurs sont organisées tel que le montre le schéma suivant:+Les autres broches des connecteurs sont organisées tel que le montre le schéma suivant ​(la carte étant vue depuis le haut, composants face à vous):
 {{ ::​nucleo-f334_pinout.png?​800 |}} {{ ::​nucleo-f334_pinout.png?​800 |}}
 +
  
   ​   ​
 Pour générer le signal demandé, vous utiliserez la fonction **void HAL_GPIO_WritePin(GPIO_TypeDef* GPIOx, uint16_t GPIO_Pin, GPIO_PinState PinState)**. La valeur pour l'​argument **GPIOx** est **GPIOB**, et pour l'​argument **GPIO_Pin**,​ la valeur est **GPIO_PIN_11**. Le troisième argument peut prendre la valeur **GPIO_PIN_SET** ou **GPIO_PIN_RESET** selon que l'on souhaite activer ou désactiver la sortie. Pour générer le signal demandé, vous utiliserez la fonction **void HAL_GPIO_WritePin(GPIO_TypeDef* GPIOx, uint16_t GPIO_Pin, GPIO_PinState PinState)**. La valeur pour l'​argument **GPIOx** est **GPIOB**, et pour l'​argument **GPIO_Pin**,​ la valeur est **GPIO_PIN_11**. Le troisième argument peut prendre la valeur **GPIO_PIN_SET** ou **GPIO_PIN_RESET** selon que l'on souhaite activer ou désactiver la sortie.
  
-Une fois le code mis en place et compilé, il vous faut mesurer la fréquence et la durée à l'​état haut du signal généré à l'​oscilloscope pour valider le bon fonctionnement. **ATTENTION :le signal généré est haute fréquence (par rapport à la fréquence analogique max de l'​oscilloscope),​ il faut donc désactiver le filtrage HF dans le menu Mode/​Coupling.**+ 
 + 
 +=== Compilation et téléchargement sur la cible en mode Debug === 
 +Après l'​ouverture du projet, il est nécessaire de le compiler une première fois avant de pouvoir le debbuguer. Pour cela, cliquez sur le bouton: ​ {{ ::​build.png?​64 |}} 
 + 
 + 
 +Brancher la carte Nucleo au port USB du PC. 
 + 
 +Pour activer le mode Debug : 
 +  - Clique-droit sur le nom du projet  
 +  - Choisir Debug As -> Ac6 STM32  
 +Par la suite, pour exécuter votre application,​ il suffit de cliquer sur Run->​Debug (ou raccourci touche F11). 
 + 
 +<color red> 
 +Important: Il faut quitter le mode debug avant de pouvoir recompiler et tester à nouveau votre programme, pour cela, cliquer sur Run->​Terminate (ou raccourci CTRL+F2). 
 +</​color>​ 
 + 
 + 
 +Le logiciel va vous proposer d'​ouvrir la "​perspective"​ de Debug (agencement des fenêtres facilitant le Debug), répondre "​ok"​. Par défaut le programme est arrêté sur la première ligne de la fonction **main()**, vous pouvez ensuite lancer l'​exécution en appuyant sur F8 ou faire du pas à pas en utilisant F5 et F6. Pour positionner un point d'​arrêt sur une ligne, il suffit de double cliquer sur son numéro. 
 + 
 + 
 +===Mesure des signaux à l'​oscilloscope=== 
 + 
 + 
 +Une fois le code mis en place et compilé, il vous faut mesurer la fréquence et la durée à l'​état haut du signal généré à l'​oscilloscope pour valider le bon fonctionnement. Reporter ces valeurs sur le compte rendu. **ATTENTION :le signal généré est haute fréquence (par rapport à la fréquence analogique max de l'​oscilloscope),​ il faut donc désactiver le filtrage HF dans le menu Mode/​Coupling.**
  
  
Ligne 108: Ligne 146:
 {{http://​homepages.laas.fr/​bvandepo/​files/​iut/​tp_tns/​BONUS.jpg}} ​ Vous devez maintenant faire clignoter la LED rouge présente sur la carte de sortie. Pour cela, à chaque 24000 exécutions de la fonction d'​interruption,​ changer l'​état de la broche pilotant la LED. Vous pourrez utiliser la fonction **void HAL_GPIO_TogglePin(GPIO_TypeDef* GPIOx, uint16_t GPIO_Pin)**. La valeur pour l'​argument **GPIOx** est **GPIOB**, et pour l'​argument **GPIO_Pin**,​ la valeur est **GPIO_PIN_13**. {{http://​homepages.laas.fr/​bvandepo/​files/​iut/​tp_tns/​BONUS.jpg}} ​ Vous devez maintenant faire clignoter la LED rouge présente sur la carte de sortie. Pour cela, à chaque 24000 exécutions de la fonction d'​interruption,​ changer l'​état de la broche pilotant la LED. Vous pourrez utiliser la fonction **void HAL_GPIO_TogglePin(GPIO_TypeDef* GPIOx, uint16_t GPIO_Pin)**. La valeur pour l'​argument **GPIOx** est **GPIOB**, et pour l'​argument **GPIO_Pin**,​ la valeur est **GPIO_PIN_13**.
   ​   ​
 +
 +Conseil: Implémenter un compteur à l'aide d'une variable **static** définie dans la fonction **void HAL_TIM_PeriodElapsedCallback(TIM_HandleTypeDef *htim)**.
 +
  
 Vérifier que la LED s'​allume bien une fois par seconde. Vérifier que la LED s'​allume bien une fois par seconde.
Ligne 122: Ligne 163:
   ​   ​
  
 +<ifauth @prof> 
 +Solution: 
 +régler dans Src/tim.c 
 +   ​htim1.Init.Period = 1332; 
 +et 
 +<file cpp soluce.cpp>​ 
 + void HAL_TIM_PeriodElapsedCallback(TIM_HandleTypeDef *htim) 
 + { 
 + static uint32_t cpt = 0; 
 +//pour accès plus rapide aux broches 
 +       //​GPIOB->​ODR|=GPIO_PIN_11;​ 
 +       //​GPIOB->​ODR&​=~GPIO_PIN_11;​ 
 +//pour accès plus lent au broches, en passant par les registres de demande de mise à 1/0 
 + HAL_GPIO_WritePin(GPIOB,​ GPIO_PIN_11,​ GPIO_PIN_SET);​ 
 + if (cpt == 24000) 
 +
 + cpt = 0; 
 + HAL_GPIO_TogglePin(GPIOB,​ GPIO_PIN_13);​ 
 +
 + else 
 + cpt++; 
 + HAL_GPIO_WritePin(GPIOB,​ GPIO_PIN_11,​ GPIO_PIN_RESET);​ 
 + } 
 +</​file>​ 
 +</​ifauth>​ 
 + 
 ------------------------------------------------------------------------------------ ------------------------------------------------------------------------------------
  
Ligne 128: Ligne 194:
 ===== Exercice 2: Test du DAC ===== ===== Exercice 2: Test du DAC =====
  
-Pour observer ​le comportement du DAC, nous allons l'​utiliser ​pour générer un signal sinusoïdal (480Hz). ​Pour cela il vous faut compléter la fonction d'​interruption pour :+Nous allons utiliser ​le DAC pour générer un signal sinusoïdal (480Hz). ​
  
-  * Piloter ​la sortie connectée à la broche PB11 et à la LED (déjà mis en place dans l'​exercice précédent) +===Précalcul des échantillons pour la fonction sinus=== 
-  * Déterminer ​la valeur ​de l'échantillon actuel ​du signal sinusoïdal à 480Hz +Les fonctions de la librairies math (sin, cos, tan ...) ne sont pas utilisables ​dans la fonction ​de gestion d'interruption timer du fait de leur lenteur. Il faut donc définir un tableau contenant les échantillons précalculés d'une période de la fonction sinus pour la fréquence demandée. ​
-  * Ecrire l'échantillon sur le DAC +
-  * Piloter ​la sortie connectée à la broche PB11 (déjà mis en place dans l'​exercice précédent)+
  
-Les fonctions de la librairies math (sincos, tan ...) ne sont pas utilisables ​dans la fonction de gestion d'​interruption timer du fait de leur lenteurIl faut donc définir un tableau contenant les échantillons précalculés d'une période de la fonction sinus pour la fréquence demandée. Pour cela, compléter le code suivant ​(à coller où il faut ...). Les échantillons ainsi générés doivent couvrir la dynamique du convertisseur DAC (0 < = échantillon < = 4095). Vous pourrez vous inspirer du code écrit lors du TP4 de TNS qui est rappelé ici : +Pour celacopier ​dans le fichier main.cpp et compléter le code suivant:
- +
-  Ecrivez d'​abord l'​expression mathématique de chaque signal +
-   Ex : signal(t)=A.sin(2Π.fo.t) + Vmoy +
-  Déterminez alors la valeur du signal aux instants d'​échantillonnages. +
-   Ex : signal(k.Tech)=A.sin(2Π.fo.k.Tech) + Vmoy +
-  Créez ensuite un tableau de taille nbEch (qui dépend de la durée voulue. Ex : tmax=duree=kmax.Tech d’où +
-   ​kmax=duree.Fech) par signal et remplissez-le avec les valeurs pour chaque k +
-  Ex :  nbEch = kmax+1 +
-        double signal[nbEch] +
-        for(int k=0; k<nbEch; k++) signal[k]= ..................;​+
  
  
Ligne 152: Ligne 206:
  #​define SAMPLING_RATE ​ ( 48000.0f)  #​define SAMPLING_RATE ​ ( 48000.0f)
  #​define SIN_FREQ ​ ( 480.0f)  #​define SIN_FREQ ​ ( 480.0f)
- #​define SIN_AMP ​2000.0f + #​define SIN_AMP ​1024.0f 
- #​define ​SIN_TAB_LENGTH ​((unsigned int) (SAMPLING_RATE / SIN_FREQ)) //Taille du tableau pour une période du signal sinus + #​define ​SIN_TAB_SAMPLES_PER_PERIOD ​((unsigned int) (SAMPLING_RATE / SIN_FREQ)) //Taille du tableau pour une période du signal sinus 
-  uint32_t sin_tabbed[SIN_TAB_LENGTH];+  uint32_t sin_tabbed[SIN_TAB_SAMPLES_PER_PERIOD];
   void init_sin_tabbed(){   void init_sin_tabbed(){
  unsigned int k ;  unsigned int k ;
- for(k = 0 ; k < SAMPLING_RATE/​SIN_FREQ; k ++ ){+ for(k = 0 ; k < SIN_TAB_SAMPLES_PER_PERIOD; k ++ ){
  sin_tabbed[k] = ???; //​Compléter ici par le calcul de la valeur des échantillons  sin_tabbed[k] = ???; //​Compléter ici par le calcul de la valeur des échantillons
  }  }
Ligne 163: Ligne 217:
 </​file>​ </​file>​
  
-Cette fonction est à appeler **une fois** au bon endroit dans le code de la fonction main, avant le lancement du timer, afin d'​éviter qu'une interruption timer ne survienne avant que le tableau soit initialisé:​ 
  
 +Pour déterminer la valeur des différents échantillons,​ vous pouvez vous inspirer du code écrit lors du TP4 de TNS qui est rappelé ci-dessous. Les échantillons ainsi générés doivent être compris dans la dynamique du convertisseur DAC (0 < = échantillon < = 4095) et leur valeur moyenne doit être réglée au milieu cette plage. La constante $\pi$ est définie sous le nom **M_PI**. Dans la formule suivante, **Tech** est obtenue en inversant **SAMPLING_RATE**.
 +
 +
 +<file txt aide.txt>​
 +  Ecrivez d'​abord l'​expression mathématique du signal:
 +   Ex : signal(t)=A.sin(2Π.fo.t) + Vmoy
 +  Déterminez alors la valeur du signal aux instants d'​échantillonnages:​
 +   Ex : signal(k.Tech)=A.sin(2Π.fo.k.Tech) + Vmoy
 +  Créez ensuite un tableau de taille nbEch (qui dépend de la durée voulue. Ex : tmax=duree=kmax.Tech d’où
 +   ​kmax=duree.Fech) par signal et remplissez-le avec les valeurs pour chaque k
 +  Ex :  nbEch = kmax+1
 +        double signal[nbEch]
 +        for(int k=0; k<nbEch; k++) signal[k]= ..................;​
 +</​file>​
 +
 +
 +La fonction **void init_sin_tabbed()** est à appeler **une seule fois** au bon endroit dans le code de la fonction **main()**, avant le lancement du timer, afin d'​éviter qu'une interruption timer ne survienne avant que le tableau soit initialisé:​
 +<file c call_sin_tabbed.c>​
   //Insérez ici l'​appel de votre fonction **init_sin_tabbed**   //Insérez ici l'​appel de votre fonction **init_sin_tabbed**
   HAL_TIM_Base_Start_IT(&​htim1);​ //Déjà mis en place   HAL_TIM_Base_Start_IT(&​htim1);​ //Déjà mis en place
   HAL_DAC_Start(&​hdac2,​ DAC2_CHANNEL_1);​ //Déjà mis en place   HAL_DAC_Start(&​hdac2,​ DAC2_CHANNEL_1);​ //Déjà mis en place
 +</​file>​
  
 +Ainsi, le tableau **sin_tabbed** contient les échantillons à utiliser dans la fonction d'​interruption.
  
-Ainsi, le tableau "​sin_tabbed"​ contient les échantillons ​à utiliser ​dans la fonction d'​interruption.+===Exploitation des échantillons dans la fonction d'​interruption ​Timer===
  
-La fonction à utiliser pour écrire sur la sortie du DAC est: **HAL_StatusTypeDef HAL_DAC_SetValue(DAC_HandleTypeDef* hdac, uint32_t Channel, uint32_t Alignment, uint32_t Data);**. Cette fonction ​écrit une valeur "​Data"​ sur canal "​Channel"​ du DAC "​hdac"​ avec l'alignement "​Alignement"​. Utiliser comme valeur de premier argument **DAC_HandleTypeDef* hdac** configuré à **&​hdac2**. Pour le  canal du DAC utiliser **DAC2_CHANNEL_1** et pour l'​alignement **0**.+Complétez ​la fonction ​d'interruption ​pour :
  
-Une fois le code complet, valider par la mesure ​à l'oscilloscope ​du signal ​généré. La mesure se fait sur la broche PA6 de la carte pour la sortie du DAC. +  - Piloter ​la sortie connectée à la broche PB11 à l'état haut (déjà mis en place dans l'​exercice précédent) 
-{{ ::nucleo-f334_pinout.png?​800 |}}+  - Déterminer la valeur de l'​échantillon actuel ​du signal ​sinusoïdal à 480Hz 
 +  - Mettre à jour le numéro ​de l'​échantillon ​pour l'​interruption suivante (en veillant à rester dans les bornes autorisées) 
 +  - Ecrire l'​échantillon sur le DAC 
 +  Piloter la sortie connectée à la broche PB11 à l'​état bas (déjà mis en place dans l'​exercice précédent)
  
-Mesurez aussi le nouveau temps d'​exécution de la fonction d'​interruption sur la boche PB11.+ 
 +La fonction à utiliser pour écrire sur la sortie du DAC est: **HAL_StatusTypeDef HAL_DAC_SetValue(DAC_HandleTypeDef* hdac, uint32_t Channel, uint32_t Alignment, uint32_t Data);**. Cette fonction écrit une valeur "​Data"​ sur canal "​Channel"​ du DAC "​hdac"​ avec l'​alignement "​Alignement"​. Utiliser comme valeur de premier argument **DAC_HandleTypeDef* hdac** configuré à **&​hdac2**. Pour le  canal du DAC utiliser **DAC2_CHANNEL_1** et pour l'​alignement **0**. 
 + 
 +Une fois le code complet, observez le signal généré à l'​oscilloscope sur la broche PA6 (indiquée par une étiquette sous la carte Nucléo). Mesurez la valeur moyenne, la fréquence et l'​amplitude crête à crête du signal sinusoïdal généré. ​Mesurez aussi le nouveau temps d'​exécution de la fonction d'​interruption sur la boche PB11 et reportez ces valeurs sur votre compte rendu.  
 +Mesurer la valeur moyenne, la fréquence et l'​amplitude crête à crête du signal en sortie du circuit de mise en forme sur la broche A1 de la carte LINE_OUT et en déduire le facteur d'​atténuation.
  
  
Ligne 191: Ligne 271:
   ​   ​
  
 +
 +<ifauth @prof>
 +Solution:
 +<file cpp soluce.cpp>​
 +
 +#include <​math.h>​
 +#define SAMPLING_RATE ​ ( 48000.0f)
 +#define SIN_FREQ ​ ( 480.0f)
 +#define SIN_AMP 2000.0f
 +#define SIN_TAB_SAMPLES_PER_PERIOD ((unsigned int) (SAMPLING_RATE / SIN_FREQ)) //Taille du tableau pour une période du signal sinus
 + ​uint32_t sin_tabbed[SIN_TAB_SAMPLES_PER_PERIOD];​
 + void init_sin_tabbed(){
 + unsigned int k ;
 + for(k = 0 ; k < SIN_TAB_SAMPLES_PER_PERIOD;​ k ++ ){
 + sin_tabbed[k] = SIN_AMP*sin( 2*M_PI *SIN_FREQ*k/​SAMPLING_RATE)+ 2048; //​Compléter ici par le calcul de la valeur des échantillons
 + //​signal(k.Tech)=A.sin(2Π.fo.k.Tech) + Vmoy
 + }
 + }
 +void HAL_TIM_PeriodElapsedCallback(TIM_HandleTypeDef *htim)
 + {
 + static uint32_t k = 0;
 + HAL_StatusTypeDef ret= HAL_DAC_SetValue(&​hdac2,​DAC2_CHANNEL_1,​0,​sin_tabbed[k]);​
 + if (k>= SIN_TAB_SAMPLES_PER_PERIOD -1)
 + k=0;
 + else
 + k++;
 +//....
 + }
 +</​file>​
 +</​ifauth>​
  
 ------------------------------------------------------------------------------------ ------------------------------------------------------------------------------------
Ligne 196: Ligne 306:
  
 ===== Exercice 3: Utilisation de l'ADC ===== ===== Exercice 3: Utilisation de l'ADC =====
 +
 +Nous allons utiliser l'ADC pour échantillonner un signal d'​entrée analogique. Pour vérifier le bon fonctionnement de l'ADC, les échantillons acquis seront recopiés sur le DAC. La broche PB11 est utilisée pour mesurer le temps total passé dans l'​interruption tandis que PB12 est maintenant utilisé pour mesurer la durée de la conversion numérique->​analogique.
 +
 +
 +Complétez la fonction d'​interruption **void HAL_TIM_PeriodElapsedCallback(TIM_HandleTypeDef *htim)** pour :
 +
 +  - Piloter la sortie connectée à la broche PB11 à l'​état haut (déjà mis en place dans l'​exercice précédent)
 +  - Piloter la sortie connectée à la broche PB12 à l'​état haut
 +  - Lancer une conversion sur l'ADC
 +  - Attendre la fin de la conversion (HAL_ADC_PollForConversion doit retourner HAL_OK)
 +  - Récupérer le résultat de la conversion
 +  - Stopper le convertisseur
 +  - Piloter la sortie connectée à la broche PB12 à l'​état bas
 +  - Ecrire l'​échantillon converti sur le DAC (recopie le signal d'​entrée sur la sortie) ​
 +  - Piloter la sortie connectée à la broche PB11  à l'​état bas (déjà mis en place dans l'​exercice précédent)
 +
 +
  
  
Ligne 203: Ligne 330:
   HAL_StatusTypeDef HAL_ADC_Start(ADC_HandleTypeDef* hadc); // Lance la conversion ​   HAL_StatusTypeDef HAL_ADC_Start(ADC_HandleTypeDef* hadc); // Lance la conversion ​
   HAL_StatusTypeDef HAL_ADC_Stop(ADC_HandleTypeDef* hadc); // Stoppe la conversion ​   HAL_StatusTypeDef HAL_ADC_Stop(ADC_HandleTypeDef* hadc); // Stoppe la conversion ​
-  HAL_StatusTypeDef HAL_ADC_PollForConversion(ADC_HandleTypeDef* hadc, uint32_t Timeout); //Attend le résultat de la conversion, le deuxième paramètre permet de limiter le temps d'​attente. +  HAL_StatusTypeDef HAL_ADC_PollForConversion(ADC_HandleTypeDef* hadc, uint32_t Timeout); ​ 
-  uint32_t HAL_ADC_GetValue(ADC_HandleTypeDef* ​had) //Lit le résultat de la conversion+  ​//Attend le résultat de la conversion, le deuxième paramètre permet de limiter le temps d'​attente. 
 +  //Vous pouvez le régler à 10 
 +  uint32_t HAL_ADC_GetValue(ADC_HandleTypeDef* ​hadc) //Lit le résultat de la conversion
   ​   ​
 Les valeurs possibles du paramètre de retour **HAL_StatusTypeDef** sont :  **HAL_OK** , **HAL_ERROR** , **HAL_BUSY** et **HAL_TIMEOUT**. Les valeurs possibles du paramètre de retour **HAL_StatusTypeDef** sont :  **HAL_OK** , **HAL_ERROR** , **HAL_BUSY** et **HAL_TIMEOUT**.
  
-A l'aide de ces fonctions, complétez la fonction appelée périodiquement : **void HAL_TIM_PeriodElapsedCallback(TIM_HandleTypeDef *htim)** pour : 
- 
-  * Piloter la sortie connectée à la broche PB11 et à la LED (déjà mis en place dans l'​exercice précédent) 
-  * Piloter la sortie connectée à la broche PB12 à l'​état haut 
-  * Lancer une conversion sur l'ADC 
-  * Attendre la fin de la conversion (HAL_ADC_PollForConversion doit retourner HAL_OK) 
-  * Récupérer le résultat de la conversion 
-  * Stopper le convertisseur 
-  * Piloter la sortie connectée à la broche PB12 à l'​état bas 
-  * Ecrire l'​échantillon converti sur le DAC (recopie le signal d'​entrée sur la sortie) ​ 
-  * Piloter la sortie connectée à la broche PB11 (déjà mis en place dans l'​exercice précédent) 
  
 Pour la valeur effective de l'​argument **ADC_HandleTypeDef* hadc** des fonctions ADC, vous utiliserez la valeur **&​hadc1**,​ par exemple : **HAL_ADC_Start(&​hadc1);​** Pour la valeur effective de l'​argument **ADC_HandleTypeDef* hadc** des fonctions ADC, vous utiliserez la valeur **&​hadc1**,​ par exemple : **HAL_ADC_Start(&​hadc1);​**
   ​   ​
-La broche PB12 qui est maintenant pilotée permet de visualiser le temps nécessaire à la conversion analogique/​numérique des échantillons d'​entrée.+
  
 Une fois le code  mis en place il vous faut le tester. Pour ce test, la carte Nucléo est associée à deux cartes : LINE_IN, LINE_OUT pour adapter les niveaux et protéger l'​entrée ADC du micro-controleur. L'​adaptation en entrée applique un gain de 4.54 sur le signal mis en entrée et le centre sur 1.65v. Une fois le code  mis en place il vous faut le tester. Pour ce test, la carte Nucléo est associée à deux cartes : LINE_IN, LINE_OUT pour adapter les niveaux et protéger l'​entrée ADC du micro-controleur. L'​adaptation en entrée applique un gain de 4.54 sur le signal mis en entrée et le centre sur 1.65v.
Ligne 230: Ligne 348:
   - vérifiez les caractéristiques du signal avec l'​oscilloscope   - vérifiez les caractéristiques du signal avec l'​oscilloscope
   - branchez la sortie du générateur de signaux sur l'​entrée A0 de la carte d'​adaptation LINE_IN   - branchez la sortie du générateur de signaux sur l'​entrée A0 de la carte d'​adaptation LINE_IN
-  - branchez l'​entrée de l'​oscilloscope sur la sortie A1 de la carte d'​adaptation LINE_OUT +  - branchez l'​entrée de l'​oscilloscope sur la sortie A1 de la carte d'​adaptation LINE_OUT. Il s'agit d'une version mise en forme du signal présent sur PA6.
 {{:​img_20170327_130651.jpg?​0x500}} ​ {{:​img_20170327_130710.jpg?​0x500}} {{:​img_20170327_130651.jpg?​0x500}} ​ {{:​img_20170327_130710.jpg?​0x500}}
  
-Vérifiez:  +  - Vérifiez la recopie ​correcte ​du signal d'​entrée sur la sortie ​(au facteur d'​amplification/​atténuation près). 
-  - la recopie du signal d'​entrée sur la sortie +  ​- Mesurez ensuite et reportez sur le compte rendu : 
-  - sur la broche PB12, mesurez le temps temps nécessaire à l'ADC pour effectuer une conversion. +      ​- sur la broche PB12, mesurez le temps temps nécessaire à l'ADC pour effectuer une conversion. 
-  - sur la broche PB11, mesurez le temps total d'​exécution de la fonction d'​interruption.+      - sur la broche PB11, mesurez le temps total d'​exécution de la fonction d'​interruption
 +  - Conclure sur le temps disponible pour effectuer le calcul de l'​équation de récurrence.
  
  
Ligne 250: Ligne 368:
   echo fini   echo fini
   ​   ​
 +
 +<ifauth @prof>
 +Solution:
 +<file cpp soluce.cpp>​
 + HAL_GPIO_WritePin(GPIOB,​ GPIO_PIN_12,​ GPIO_PIN_SET);​
 + uint32_t ech;
 + HAL_ADC_Start(&​hadc1);​ // Lance la conversion
 + HAL_ADC_PollForConversion(&​hadc1,​ 10); //Attend le résultat de la conversion, le deuxième paramètre permet de limiter le temps d'​attente.
 + HAL_ADC_Stop(&​hadc1);​ // Stoppe la conversion
 + ech= HAL_ADC_GetValue(&​hadc1);​ //Lit le résultat de la conversion
 + HAL_GPIO_WritePin(GPIOB,​ GPIO_PIN_12,​ GPIO_PIN_RESET);​
 + HAL_StatusTypeDef ret= HAL_DAC_SetValue(&​hdac2,​DAC2_CHANNEL_1,​0,​ech);​
 +//​ HAL_StatusTypeDef ret= HAL_DAC_SetValue(&​hdac2,​DAC2_CHANNEL_1,​0,​sin_tabbed[k]);​
 +</​file>​
 +</​ifauth>​
 +
  
  
Ligne 256: Ligne 390:
 Vous pouvez maintenant passer au TP suivant dans lequel vous allez insérer le filtre dans le programme du microcontroleur:​ [[tns_nucleo_filtre]] Vous pouvez maintenant passer au TP suivant dans lequel vous allez insérer le filtre dans le programme du microcontroleur:​ [[tns_nucleo_filtre]]
  
 +
 +------------------------------------------------------------------------------------
 +
 +=====En cas de plantage du debuggueur=====
 +
 +<ifauth @prof>
 +si l'​étudiant relance le debuggueur alors qu'il est déjà en route, le processus est détaché d'​Eclipse et il ne peut plus être fermé. ​
 +Pour lister les processus utilisant le fichier .elf:
 +  lsof |grep nucleo_tns.elf
 +Pour tuer le processus à partir de son PID:
 +  kill -9 3942
 +  ​
 +  il faut aussi tuer tous les process dont le nom commence par  arm-none-
 +</​ifauth>​
 +
 +Pour tuer le processus du debugguer au cas où vous n'​auriez pas arreté le mode Debug avant de le relancer, copier coller dans une console: ​
 +  kill -9 $(lsof -t  ~/​workspace_ac6/​nucleo_tns/​Debug/​nucleo_tns.elf)
 +  kill -9 $(lsof -t  -c arm-none-)
 +  ​
 +
 +<ifauth @prof>
 +Pour gestion fine de la fréquence d'​interruption:​
 +
 + cpt_it++;
 + if (cpt_it>​=3) {
 + htim1.Init.Period = 1333;
 + cpt_it=0;
 + }else{
 +   htim1.Init.Period = 1332;
 + }
 +
 +</​ifauth>​
tns_nucleo_tp1.1522865752.txt.gz · Dernière modification: 2018/04/04 20:15 par bvandepo