Nous ne pouvons pas générer correctement un signal sinusoïdal à l'aide d'un microcontrôleur MC68HC908GP32 . La description du PWM commence à la page 349. La fréquence d'horloge est de 2,4 MHz, tandis que nous avons utilisé le PWM à 7 kHz en utilisant le pré-échelle et en réglant le module de minuterie sur 350 comme suit:
T1SC = 0x60; // Prescaler: Div entre 64
//Counter modulo = 0x015E = 350
T1MODH = 0x01; // High
T1MODL = 0x5E; // Low
La sortie PWM est filtrée par le filtre RLC suivant, puis DC est retiré à l'aide d'un capuchon de 1 uF série. La fréquence de coupure est bien inférieure à 7 kHz de PWM.
Tout d'abord, nous avons essayé d'utiliser une LUT, dont les échantillons ont été générés en utilisant ce site (100 échantillons, amplitude = 250). Cela comprend une seule période.
int seno[100]={ 125, 133, 141, 148, 156, 164, 171, 178, 185, 192, 198, 205, 211, 216, 221, 226, 231, 235, 238, 241, 244, 246, 248, 249, 250, 250, 250, 249, 248, 246, 244, 241, 238, 235, 231, 226, 221, 216, 211, 205, 198, 192, 185, 178, 171, 164, 156, 148, 141, 133, 125, 117, 109, 102, 94, 86, 79, 72, 65, 58, 52, 45, 39, 34, 29, 24, 19, 15, 12, 9, 6, 4, 2, 1, 0, 0, 0, 1, 2, 4, 6, 9, 12, 15, 19, 24, 29, 34, 39, 45, 52, 58, 65, 72, 79, 86, 94, 102, 109, 117};
La largeur de l'impulsion suivante est calculée à chaque cycle PWM:
interrupt 4 void rsi_t1ch0 (void)
{
//-- disable interruption flag
T1SC0&=(~0x80);
//-- pwm to '0'
PTB&=0xFD;
//some sensor measures are done here.... 100 out of the 350 cycles are left for this
}
/************************************************************/
/* TIM1 overflow rutine */
/************************************************************/
interrupt 6 void rsi_ov1 (void)
{
T1SC&=(~0x80);
//-- set PWM to 1
PTB|=0x02;
T1CH0H = ((seno[fase])>>8); // high bits
T1CH0L = (seno[fase])&0xFF; // low bits
fase+=1;
if (fase >= 99)
fase=0;
}
void main(void)
{
float temp;
int i;
CONFIG1|=0x01;
DDRB=0xFF; //-- Port B is set as output
PTB=0x00;
//Timer setup
T1SC = 0x60; // Prescaler: Div by 64
T1MODH = 0x01; //Counter modulo
T1MODL = 0x5E;
T1SC0 = 0x50; //Comparator setup
//-- Initial width
T1CH0H = 0x00;
T1CH0L = 0x53;
EnableInterrupts;
T1SC&=~(0x20); //Run timer forever
for(;;);
}
Lorsque vous le branchez dans la portée, nous obtenons le signal suivant. Nous ne pouvons pas éviter cet étrange pic proche du minimum.
En zoomant autour de ce pic, nous pouvons voir comment la sortie PWM (vers le haut) est en fait incorrecte.
Ainsi, après avoir gâché pendant un certain temps et être incapable de s'en débarrasser, nous avons essayé de calculer le signal sinusoïdal dans le MCU, au lieu de coder en dur la valeur de chaque échantillon. Nous avons ajouté le code suivant dans la fonction principale, juste avant toute la configuration du compteur:
for(i=0;i<99;i++) {
temp=100*(sin(2*3.14159*i/100)+1);
seno[i]=(int)temp;
}
Mais les résultats ne ressemblent même pas à une sinusoïde:
Après des heures de lutte, nous n'avons pas pu trouver notre erreur. Nous apprécierions un conseil.
la source
Réponses:
Au bas de la page 350 de la fiche technique du microcontrôleur, il mentionne que l'écriture d'une petite valeur dans le registre des valeurs du temporisateur pendant l'interruption de débordement peut provoquer le déclenchement de l'interruption suivante uniquement lors de l'itération pwm suivante, car le temporisateur continue de compter pendant que le la routine d'interruption est en cours d'exécution.
Ceci est confirmé par le fait que la valeur pwm est maintenue élevée pendant une période d'horloge pwm entière + ce qui ressemble à la longueur du temporisateur (sur la base des longueurs environnantes). La valeur en cours d'écriture dans le registre de longueur du temporisateur est probablement proche de 0 au moment de l'erreur, il est donc tout à fait viable que le compteur ait dépassé la valeur la plus petite pendant l'interruption et ne se déclenche qu'au cycle suivant.
Cela pourrait être résolu en augmentant le niveau minimum de la sinusoïde à un niveau supérieur au temps nécessaire pour exécuter l'ISR, ou en changeant le mécanisme par lequel le nouveau niveau est défini. Le haut de la page 351 explique comment procéder.
la source