• Aucun résultat trouvé

Séance No. 9 et 10Programmation uC et structure du logiciel(CSYEI)

N/A
N/A
Protected

Academic year: 2022

Partager "Séance No. 9 et 10Programmation uC et structure du logiciel(CSYEI)"

Copied!
15
0
0

Texte intégral

(1)

MTI 29.11.2010 v2.0

iAi institut d’Automatisation industrielle 1

Séance No. 9 et 10 Programmation uC

et structure du logiciel

(CSYEI)

(2)

Programme du jour

1. Structure du logiciel.

2. Partage des variables critiques.

3. Quelques règles pour l’écriture des automates.

(3)

MTI 29.11.2010 v2.0

iAi institut d’Automatisation industrielle 3

Structure principale du logiciel 1/3

Dans notre cas de figure, mais aussi dans les applications industrielles courantes, le logiciel se compose d’un automate qui s'exécute de façon séquentielle ainsi que d’un traitement qui doit s'exécuter à chaque fois que des grandeurs mesurées sont échantillonnées.

Dans le cas d’un système asservi il faut assurer l’échantillonnage des grandeurs d’entrée et de sortie et l'exécution de la routine de calcul dans la période d’échantillonnage.

temps

Interrupt Fin de conversion A/D

Calcul yi(0) = f[xi(0)] Calcul yi(1) = f[xi(1)]

Echantillonnage xi(0) et sortie yi(-1)

Echantillonnage xi(1) et sortie yi(0)

Echantillonnage xi(n) et sortie yi(n-1)

Calcul yi(n) = f[xi(n)]

t = 0

temps

t = Te t = nTe

Période d’échantillonnage Te Période d’échantillonnage Te

Interrupt Fin de conversion A/D

Interrupt Fin de conversion A/D Intervalle entre interrupt ≠ Te Intervalle entre interrupt ≠ Te

exec. automate exec. automate

(4)

Structure principale du logiciel 2/3

Cette séquence est possible que si matériellement on peut déclencher l’échantillonnage à l’aide d’un Timer (HW).

Pour la sortie des grandeurs il faut aussi respecter une période d’échantillonnage (p. ex. les rapports cycliques des PWM sont mis à jour par un Timer).

S&H

A D

Timer 1

CPU PCA

PWM

Timer 2

Int. Fin Conv.

ValConv Di

Int. Fin Cycl.

(5)

MTI 29.11.2010 v2.0

iAi institut d’Automatisation industrielle 5

Structure principale du logiciel 3/3

Si le ou les automates doivent s'exécuter une seule fois entre deux échantillonnages il devient nécessaire d'introduire ne tâche d’attente (IDLE) dans la boucle principale.

Dans les cas où il y a plusieurs routines d’interruption (qui fournissent les variables d’entrée d’un

algorithme) et on veut qu’elles soient les plus courtes possibles. Les calculs et algorithmes se font dans l’automate et doivent se faire une seule fois entre deux échantillonnages.

Les variables écrites ou lues par les routines d’interruption sont des ressources critiques (danger de corruption).

ISR1 ISR n

Exec Automate

Mise à jour IN/OUT Attend temps Boucle

Reset

Initialisation Var 1

Var n

ISR Timer

Clock

Variables statiques

Int1

Intn

Timer Section critique

Boucle infinie

(6)

Exemple de programme principal

void main (void) {

MiniBalance_Init();

while (1) { // Spin forever

WaitRTtic (); // Attend ClearRTtic() sous interrupt ReloadWTD (); // Relance le watchdog

Inputs = Echantillonnage (); // Sauve les grandeurs analogiques

AfficheRT (ERROR); // Fait clignoter la LED et indique l'erreur//

ERROR = ExecAutomate(Inputs); // Automate principal

SetSorties(); // Ecrit les sorties

} }

(7)

MTI 29.11.2010 v2.0

iAi institut d’Automatisation industrielle 7

Partage des variable entre les ISR et le programme principal

Les variables partagées par les interruptions et le programme principal peuvent être corrompues.

L’instant de lecture ou écriture de ces variables par les ISR est imprévisible par le programme principal.

Par exemple: une variable (16 bit) critique est lue par le programme principal, entre la lecture du premier et le deuxième byte l’ ISR s'exécute et modifie la variable 16 bit, lorsque le programme principal reprend il lit le deuxième byte mais ce n’est plus la même variable !!

C’est un phénomène peu probable mais imprévisible et difficile à détecter.

Pour éviter ce problème il suffit d’inhiber l’interruption pendent l’accès à la variable par le prog. principal (la durée d’inhibition doit être la plus courte possible).

Ceci est valable pour n’importe quel type de variable car on ne sait pas à priori combien d’instruction (atomiques) le compilateur utilise pour l’accès.

Pour le compilateur SDCC il existe une primitive de compilation: (ref. SDCC compiler User Guide page42)

Text

Critical Functions and Critical Statements

A special keyword may be associated with a block or a function declaring it as critical. SDCC will generate code to disable all interrupts upon entry to a critical function and restore the interrupt enable to the previous state before returning. Nesting critical functions will need one additional byte on the stack for each call.

int foo () __critical { ... ...

}

The critical attribute maybe used with other attributes like reentrant. The keyword critical may also be used to disable interrupts more locally:

__critical{ i++; }

More than one statement could have been included in the block.

(8)

void main (void) {

MiniBalance_Init();

while (1) // Spin forever {

// Affichage des mesures LCD_start_line_1();

DisableInterrupt();

Courant = Imes;

EnableInterrupt();

printf("PWM %4d I %4d",PWMvalue, Courant);

! SI_DELAY_MS(300);

PMW_B = 1;

LCD_start_line_2();

printf("REF %4d EP%5d",CourantZero,PosErr);

! SI_DELAY_MS(300);

LCD_start_line_3();

DisableInterrupt();

Position = PosMes;

EnableInterrupt();

printf("Zo %4d Z %4d",PositionZero,Position);

! SI_DELAY_MS(300);

....

} }

INTERRUPT(PCA_ISR, INTERRUPT_PCA0) __using 2 {

S16 Correction;

U8 SFRPAGE_save = SFRPAGE;

// PMW_B = 1;

if(AD0INT != 0);

{ // L'ADC a fini une conversion) switch (MesureRegNo)

{

case 0:

Imes = ADC0;// On acquiert

ADC0MX = MUX_Ref1V125; // On lance ...

case 2:

PosMes = ADC0;

ADC0MX = MUX_RefPos; position AD0INT = 0;

MesureRegNo = 3;

break;

...

}

Exemple sur deux variables

section critique

section critique

(9)

MTI 29.11.2010 v2.0

iAi institut d’Automatisation industrielle 9

Quelques règles pratiques pour l’écriture des automates

Les variables d’état définissant l’état interne de l’automate peuvent être modifiés uniquement par l’automate lui même en fonction des variables d’entrée.

Si plusieurs automates s'exécutent dans la même boucle infinie ils doivent modifier que leurs variables internes. Un automate peut lire l’état interne d’un autre automate mais pas le modifier directement.

Un automate ne contient pas de boucle (for while ou autre).

Il est constitué de tests sur les variables d’état et de modifications de celles ci.

Exemple :

void main (void) {

Init();

while (1) { // Spin forever

Inputs = Echantillonnage (); // Sauve les grandeurs analogiques // Automate principal

if (Init) {

Init = !AlimentationsOK(); //Init = 0 si alim OK }else if (CntINIT) {

CntINIT--; // Attends tant que CntINIT == 0 }else if (Tare){ // Met à zéro le poids

SetPoids(Zero);

}else { // demarre la mesure du poids Regulation;

Tare = IsTarePress();

}

SetSorties(); // Ecrit les sorties

} }

(10)

Exercice: Ecriture de l’automate pour la balance.

L’organigramme ci joint a été élaboré par les étudiants master en 2009 (MM. Comte et Gilardoni).

Ecrivez la fonction ExecAutomate() permettant la mise en oeuvre de l’automate ci joint.

La fonction ExecAutomate doit rendre un nombre sur 8 bit (unsigned char) indiquant le no d’erreur, pas d’erreur

= 0.

(11)

MTI 29.11.2010 v2.0

iAi institut d’Automatisation industrielle 11

Réalisation de l’échantillonnage et génération des signaux PWM

PCA0 Module 1

ADC_SYNC

CONVSTR Use 10bits PWM. Auto-Reload register. Interrupt on overflow

PWM mode enable.

Comparator and interrupt enable

Enable ADC0.

Conversion sur flanc montant de CNVSTR

Echantillonnage ADC_SYNC

PWM_A Courant

t [s]

D D/2

ISR_PCA0 PCA0H:L

Diagramme temporel

(12)

Routine ISR_PCA0

INTERRUPT(PCA_ISR, INTERRUPT_PCA0) __using 2 {

S16 Correction;

U8 SFRPAGE_save = SFRPAGE;

if(AD0INT != 0);{ // L'ADC a fini une conversion) switch (MesureRegNo) {

case 0:

Courant = ADC0; // On acquiert le courant de l'actuateur

ADC0MX = MUX_Ref1V125; // On lance l'acquisition de P1.1 : mesure de la tension de référence du courant AD0INT = 0; // Reset du Flag pour autoriser nouvelle aquisition

MesureRegNo = 1;

break;

case 1:

CourantZero = ADC0; // On acquiert la tension de référence du courant

ADC0MX = MUX_MesPos; // On lance l'acquisition deP1.7 : mesure de la position AD0INT = 0; // Reset du Flag pour autoriser nouvelle aquisition

MesureRegNo = 2;

break;

case 2:

Position = ADC0; // On acquiert la position

ADC0MX = MUX_RefPos; // On lance l'acquisition de P1.6 : mesure de la référence position AD0INT = 0; // Reset du Flag pour autoriser nouvelle aquisition

MesureRegNo = 3;

break;

(13)

MTI 29.11.2010 v2.0

iAi institut d’Automatisation industrielle 13

Routine ISR_PCA0

case 3:

PositionZero = ADC0; // On acquiert la tension de référence de la position

ADC0MX = MesureADCcanalNo[MesureAuxNo]; // On lance l'acquisition de la mesure auxilliaire MesureAuxNo AD0INT = 0; // Reset du Flag pour autoriser nouvelle aquisition

MesureRegNo = 4;

break;

case 4:

ADCmesures[MesureAuxNo] = ADC0; // On mémorise la mesure auxilliaire

ADC0MX = MUX_Mes_I; // On lance l'acquisition de P1.0 : mesure du courant dans l'actuateur AD0INT = 0; // Reset du Flag pour autoriser nouvelle aquisition

MesureAuxNo++; //

if (MesureAuxNo >= MSUR_AUX_NBR) MesureAuxNo = 0;

MesureRegNo = 0;

break;

} }

(14)

Exercice: Modification du logiciel existant en appliquant les concepts vu plus haut.

Dans le fichier minibalance.c on trouve une routine d’interruption :

INTERRUPT(PCA_ISR, INTERRUPT_PCA0) __using 2 (pour la syntaxe consulter le fichier

compiler_defs.h)

Cette interruption permet d'acquérir toues les grandeurs physiques du système, à tour de rôle, et les mettre dans les variables globales. D’autres variables auxiliaires sont acqueries à une cadence 5 fois plus faible....

La séquence est montrée ci dessous:

Courant CourantZero Position PositionZero ADCMesures[No_AUX] Courant

1 2 3 4 5 1

1. Définir une structure de données TPhysVal contenant toutes les grandeurs physiques du système, ADCMesures doit rester sous forme d’un tableau dans la structure.

typedef struct {

S16 Courant; // val. du courant [pion]

S16 CourantZero; // Val. du zéro du courant [pion]

S16 Position; // Val. position [pion]

S16 PositionZero; // Val. du zero de la Position [pion]

U16 ADCmesures[MSUR_AUX_NBR] ;// valeur minimum possible } TPhysVal;

(15)

MTI 29.11.2010 v2.0

iAi institut d’Automatisation industrielle 15

2. Introduire une variable SampleDone dans la structure qui permet de dire si la routine d’interruption à été éxecutée avant la lecture des variables échantillonnées ainsi les grandeurs physiques ont été écrites (au moins une) et pas encore lues (SampleDone = 0 si les valeurs ont été lues au moins une fois).

3. Créer deux pointeurs TPhysVal *PhysVal et *PhysValTmp, le premier pointe une zone critique écrite par la routine d’interruption et la deuxième en est une copie tampon non critique.

4. Modifier la routine d’interruption PCA_ISR pour y utiliser la structure de donnée mise en place, la variable

SampleDone doit être settée à 1 dés que l’on sort de la routine d’interruption. Si à l’appel de la routine d’interrupt la variable SampleDone = 1 générer une erreur (erreur doit contenir un numéro, et est aussi une vriable critique).

5. Ecrire une fonction Echantillonnage() avec la primitive --critical permettant de recopier les valeurs en zone critique dans la structure tampon.

6. Ecrire une fonction WaitRTtic() qui attend que la valeur SampleDone soit passée à 1. Cette fonction est aussi doté de la primitive --critical.

7. S’inspirer de la fonction void PWMset (S16 Value) et la modifier pour qu’elle soit utilisée dans le programme principal pour mettre à jour la valeur des PWM.

8. Modifier le programme principal afin d’utiliser les fonctions réalisées et y inclure une procédure vide

regulation() qui aura pour but de réguler le système.

Exercice: Modification du logiciel existant en appliquant les

concepts vu plus haut.

Références

Documents relatifs

Rica critique ouvertement dans ce texte la tyrannie de la mode.. En effet, on trouve le champ lexical l’obligation, la domination et de la soumission : « les architectes ont

Écrivez cette lettre en adoptant le regard d’une personne qui, par son âge, prend de la distance avec le présent et porte un

Le quatrième chapitre est consacré à l’étude et la synthèse de la commande hybride par mode glissant flou pour résoudre le problème de la stabilité et la

Un premier niveau hiérarchique où chaque bloc représente un PCB, les liaisons entre les PCB, les connecteurs externes pour chaque PCB, les protection surtension, filtres

Quel résolution doit avoir le rapport cyclique D pour atteindre la précision voulue sur le courant moyen et donc sur la force. Quelle sera la fréquence du signal PWM en

 pour les systèmes composés de plusieurs appareils, il peut suffire de restreindre son choix aux appareils

Pour améliorer l’efficacité des condensateurs de découplage il faut réduire au minimum l’impédance des connexions, et augmenter du même coup la fréquence de résonance

[r]