Filtrage de signaux num´ eriques
J.-M Friedt, 9 f´ evrier 2015 Objectif de ce TP :
— exploiter les fonctions de traitement du signal de GNU/Octave pour concevoir un filtre
— impl´ ementer ce filtre dans un microcontrˆ oleur avec des calculs sur des entiers uniquement
— valider exp´ erimentalement le fonctionnement du filtre
1 Conception d’un filtre de r´ eponse finie (FIR)
Le sujet de ce TP n’est pas de d´ evelopper la th´ eorie des filtres num´ eriques mais uniquement de rappeler quelques uns des concepts utiles en pratique :
— un filtre de r´ eponse impulsionnelle finie [1] (Finite Impulse Response, FIR) b
mest caract´ eris´ e par une sortie y
n` a un instant donn´ e n qui ne d´ epend que des valeurs actuelle et pass´ ees de la mesure x
m, m ≤ n :
y
n= X
k=0..m
b
kx
n−kL’application du filtre s’obtient pas convolution des coefficients du filtre et des mesures.
— un filtre de r´ eponse impulsionnelle infinie (IIR) a une sortie qui d´ epend non seulement des mesures mais aussi des valeurs pass´ ees du filtre.
— GNU/Octave (et Matlab) proposent des outils de synth` ese des filtres FIR et IIR. Par soucis de stabilit´ e num´ erique et simplicit´ e d’impl´ ementation, nous ne nous int´ eresserons qu’aux FIR. Dans ce cas, les coefficient de r´ ecursion sur les valeurs pass´ ees du filtre (nomm´ ees en g´ en´ eral a
mdans la litt´ erature) seront ´ egaux ` a a = 1.
Le calcul d’un filtre dont la r´ eponse spectrale ressemble ` a une forme impos´ ee par l’utilisateur (suivant un crit` ere des moindres carr´ es) est obtenu par la fonction firls(). Cette fonction prend en argument l’ordre du filtre (nombre de coeffi- cients), la liste des fr´ equences d´ efinissant le gabarit du filtre et les magnitudes associ´ ees. Elle renvoie la liste des coefficients b.
L’application d’un FIR de coefficients b (avec a=1) ou de fa¸ con plus g´ en´ erale d’un IIR de coefficients a et b sur un vecteur de donn´ ees exp´ erimentales x s’obtient par filter(b,a,x);
2800 3000 3200 3400 3600 3800
800 1000 1200 1400 1600 1800 2000
tension ADC (bits)
temps (point)
-50 0 50 100 150 200 250
0 5000 10000 15000 20000
puissance (u.a.)
frequence (GHz)
pas de retard=180 kS/s retard 100=46.6 kS/s
Figure 1 – Gauche : le mˆ eme signal (sinuso¨ıde ` a 440 Hz) ´ echantillon´ e ` a deux fr´ equences diff´ erentes. Droite : les mˆ emes coefficients de filtres appliqu´ es ` a un chirp balayant de 200 ` a 20000 Hz mais pour des fr´ equences d’´ echantillonage diff´ erentes.
Tout filtre se d´ efinit en terme de fr´ equence normalis´ ee : la fr´ equence 1 correspond ` a la demi-fr´ equence d’´ echantillonnage (fr´ equence de Nyquist) lors de la mesure des donn´ ees.
Exercices :
1. en supposant que nous ´ echantillonnons les donn´ ees sur un convertisseur analogique-num´ erique ` a 16000 Hz, identifier les coefficients d’un filtre passe-bande entre 700 et 900 Hz. Combien faut-il de coefficients pour obtenir un r´ esultat satisfaisant ?
2. Quelle est la cons´ equence de choisir trop de coefficients ? Quelle est la cons´ equence de choisir trop peu de coefficients ? 3. ayant obtenu la r´ eponse impulsionnelle du filtre, quelle est sa r´ eponse spectrale ?
4. valider sur des donn´ ees (boucle sur les fr´ equences) simul´ ees la r´ eponse spectrale du filtre
Au lieu de boucler sur des fr´ equences et observer la r´ eponse du filtre appliqu´ e ` a un signal monochromatique, le chirp est un signal dont la fr´ equence instantan´ ee ´ evolue avec le temps. Ainsi, la fonction
chirp([0:1/16000:5],40,5,8000);
g´ en` ere un signal ´ echantillonn´ e ` a 16 kHz, pendant 5 secondes, balayant la gamme de fr´ equences allant de 40 Hz ` a 8 kHz.
Exercices :
1. appliquer le filtre identifi´ e auparavant au chirp, et visualiser le signal issu de cette transformation 2. que se passe-t-il si la fr´ equence de fin du chirp d´ epasse 8 kHz dans cet exemple ?
2 Application pratique du filtre
Exercices : Impl´ ementer sur STM32
1. sachant que les acquisitions se font sur 12 bits, quelle est la plage de valeurs sur laquelle se font les mesures ? 2. comment exploiter les coefficients num´ eriques du filtre pour un calcul sur des entiers sur 16 bits (short) ? sur 32 bits
(long) ?
1. l’´ echantillonnage p´ eriodique de mesures analogiques acquises sur ADC1 2. l’affichage du r´ esultat de ces mesures
3. le filtrage de ces mesures par un FIR synth´ etis´ e selon la m´ ethode vue plus haut 4. l’affichage du r´ esultat de ce filtrage
5. l’affichage de l’amplitude du signal r´ esultant du filtrage
6. appliquer ce programme ` a une mesure sur un chirp g´ en´ er´ e par la carte son du PC au moyen de audacity 7. comparer l’exp´ erience et la simulation.
-400 -200 0 200 400 600
0 500 1000 1500 2000 2500 3000 3500
max. sortie filtre (u.a.)
frequence (Hz)
frequence (Hz)
temps (s) 500
1000
1500
2000
2500
3000
0 0.0005 0.001 0.0015 0.002
-800 -600 -400 -200 0 200 400
sortie du filtre
-1 -0.5 0 0.5 1
0 500 1000 1500 2000 2500 3000 3500 4000
magnitude (u.a.)
magnitude (u.a.) firls(160,[0 600 700 900 1000 fe/2]/fe*2,[0 0 1 1 0 0]);
fe=16000;
ffin=4000;
fdeb=40;
b=firls(160,[0 600 700 900 1000 fe/2]/fe*2,[0 0 1 1 0 0]);
x=chirp([0:1/fe:5],fdeb,5,ffin);
f=linspace(fdeb,ffin,length(x));
plot(f,filter(b,1,x));
freq=[fdeb:150:ffin];
k=1;
for f=freq
x=sin(2*pi*f*[0:1/fe:1]);
y=filter(b,1,x);
sortie(k)=max(y);
k=k+1;
end
hold on;plot(freq,sortie,’r’) xlabel(’frequence (Hz)’) ylabel(’magnitude (u.a.)’)
En haut `a gauche : mesure exp´erimentale de la r´eponse d’un FIR passe bande con¸cu pour ˆetre passant entre 700 et 900 Hz. La mesure est effectu´ee au moyen d’un chirp de 40 `a 4000 Hz en 30 secondes g´en´er´e par une carte son d’ordinateur. En bas `a gauche : mod´elisation de la r´eponse d’un filtre passe bande entre 700 et 900 Hz, en bleu par filtrage d’un chirp, en rouge par calcul de l’effet du filtre sur quelques signaux monochromatiques. Ci- dessus : programme GNU/Octave de la simulation.
Exemple de programme et r´ esultats :
// #d e f i n e pc
#d e f i n e debug
#i f n d e f pc
//# i n c l u d e <s t m 3 2 f 1 / s t m 3 2 f 1 0 x . h> // d e f i n i t i o n u i n t 3 2 t
#i n c l u d e <l i b o p e n c m 3 /cm3/common . h> // BEGIN DECL
#i n c l u d e <l i b o p e n c m 3 / stm32 / f 1 / r c c . h>
#i n c l u d e <l i b o p e n c m 3 / stm32 / f 1 / f l a s h . h>
#i n c l u d e <l i b o p e n c m 3 / stm32 / f 1 / g p i o . h>
#i n c l u d e <l i b o p e n c m 3 / stm32 / f 1 / adc . h>
#i n c l u d e <l i b o p e n c m 3 / stm32 / u s a r t . h>
#i n c l u d e <l i b o p e n c m 3 / stm32 / t i m e r . h>
#i n c l u d e <l i b o p e n c m 3 /cm3/ n v i c . h>
#e l s e
#i n c l u d e<s t d i o . h>
#i n c l u d e<s t d l i b . h>
#i n c l u d e<math . h>
#e n d i f
#d e f i n e NB 128
#d e f i n e NBFIL 61
u n s i g n e d s h o r t t e m p e r a t u r e [NB] ; v o l a t i l e i n t j m f i n d e x =0;
l o n g f i l t r e ( u n s i g n e d s h o r t ∗, l o n g ∗, l o n g , l o n g , l o n g ∗) ;
#i f n d e f pc
s t a t i c v o i d u s a r t s e t u p ( v o i d ) {
r c c p e r i p h e r a l e n a b l e c l o c k (&RCC APB2ENR, RCC APB2ENR USART1EN) ; g p i o s e t m o d e (GPIOA, GPIO MODE OUTPUT 50 MHZ,
GPIO CNF OUTPUT ALTFN PUSHPULL, GPIO USART1 TX) ; u s a r t s e t b a u d r a t e (USART1, 1 1 5 2 0 0 ) ;
u s a r t s e t d a t a b i t s (USART1, 8 ) ;
u s a r t s e t s t o p b i t s (USART1, USART STOPBITS 1 ) ; u s a r t s e t m o d e (USART1, USART MODE TX RX) ; u s a r t s e t p a r i t y (USART1, USART PARITY NONE) ;
u s a r t s e t f l o w c o n t r o l (USART1, USART FLOWCONTROL NONE) ; u s a r t e n a b l e (USART1) ;
}
s t a t i c v o i d g p i o s e t u p ( v o i d )
{ r c c p e r i p h e r a l e n a b l e c l o c k (&RCC APB2ENR, RCC APB2ENR IOPCEN) ; g p i o s e t m o d e (GPIOA, GPIO MODE INPUT, GPIO CNF INPUT ANALOG, GPIO0 ) ; g p i o s e t m o d e (GPIOA, GPIO MODE INPUT, GPIO CNF INPUT ANALOG, GPIO1 ) ;
g p i o s e t m o d e (GPIOC, GPIO MODE OUTPUT 2 MHZ, GPIO CNF OUTPUT PUSHPULL, GPIO8|GPIO9 ) ; }
s t a t i c v o i d t i m e r s e t u p ( v o i d ) { u i n t 3 2 t t i m e r ;
v o l a t i l e u i n t 3 2 t ∗r c c a p b e n r ; u i n t 3 2 t r c c a p b ;
t i m e r = TIM2 ;
r c c a p b e n r = &RCC APB1ENR ; r c c a p b = RCC APB1ENR TIM2EN ;
r c c p e r i p h e r a l e n a b l e c l o c k ( r c c a p b e n r , r c c a p b ) ; t i m e r r e s e t ( t i m e r ) ;
t i m e r s e t m o d e ( t i m e r , TIM CR1 CKD CK INT , TIM CR1 CMS EDGE , TIM CR1 DIR UP ) ; t i m e r s e t p e r i o d ( t i m e r , 0xF∗5 ) ;
t i m e r s e t p r e s c a l e r ( t i m e r , 0 x8 ) ; t i m e r s e t c l o c k d i v i s i o n ( t i m e r , 0 x0 ) ;
t i m e r s e t m a s t e r m o d e ( t i m e r , TIM CR2 MMS UPDATE) ; // G e n e r a t e TRGO on e v e r y u p d a t e t i m e r e n a b l e c o u n t e r ( t i m e r ) ;
}
s t a t i c v o i d i r q s e t u p ( v o i d )
{ n v i c s e t p r i o r i t y ( NVIC ADC1 2 IRQ , 0 ) ; n v i c e n a b l e i r q ( NVIC ADC1 2 IRQ ) ; }
s t a t i c v o i d a d c s e t u p ( v o i d ) { i n t i ;
r c c p e r i p h e r a l e n a b l e c l o c k (&RCC APB2ENR, RCC APB2ENR ADC1EN) ; a d c o f f (ADC1) ;
a d c e n a b l e s c a n m o d e (ADC1) ;
a d c s e t s i n g l e c o n v e r s i o n m o d e (ADC1) ;
a d c e n a b l e e x t e r n a l t r i g g e r i n j e c t e d (ADC1, ADC CR2 JEXTSEL TIM2 TRGO) ; // s t a r t w i t h TIM2 TRGO a d c e n a b l e e o c i n t e r r u p t i n j e c t e d (ADC1) ; // G e n e r a t e t h e ADC1 2 IRQ a d c s e t r i g h t a l i g n e d (ADC1) ;
// a d c e n a b l e t e m p e r a t u r e s e n s o r (ADC1) ;
a d c s e t s a m p l e t i m e o n a l l c h a n n e l s (ADC1, ADC SMPR SMP 28DOT5CYC) ; a d c p o w e r o n (ADC1) ;
f o r ( i = 0 ; i < 8 0 0 0 0 0 ; i ++) a s m ( ” nop ” ) ; a d c r e s e t c a l i b r a t i o n (ADC1) ;
w h i l e ( ( ADC CR2(ADC1) & ADC CR2 RSTCAL) != 0 ) ; a d c c a l i b r a t i o n (ADC1) ;
w h i l e ( ( ADC CR2(ADC1) & ADC CR2 CAL) != 0 ) ; }
v o i d a d c 1 2 i s r ( v o i d )
{ ADC SR(ADC1) &= ˜ADC SR JEOC ; i f ( j m f i n d e x<NB)
{t e m p e r a t u r e [ j m f i n d e x ]= a d c r e a d i n j e c t e d (ADC1, 1 ) ; j m f i n d e x ++;}
}
#e l s e
#d e f i n e f e 3 2 7 6 8 .
#d e f i n e USART1 0
v o l a t i l e f l o a t temps = 0 . ;
v o l a t i l e f l o a t f r e q=f e / ( f l o a t )NB; // g a r a n t i t 1 p e r i o d e v o i d a d c 1 2 i s r ( v o i d )
{t e m p e r a t u r e [ j m f i n d e x ] = ( i n t ) ( 1 2 0 0 . + 1 0 0 0 .∗c o s ( 2∗M PI∗f r e q∗temps ) ) ; j m f i n d e x ++;
temps+=(1/ f e ) ; }
#e n d i f
s t a t i c v o i d m y u s a r t p r i n t i n t ( u n s i g n e d i n t u s a r t , i n t v a l u e ) {
#i f n d e f pc i n t 8 t i ;
u i n t 8 t n r d i g i t s = 0 ; c h a r b u f f e r [ 2 5 ] ;
i f ( v a l u e < 0 ) {u s a r t s e n d b l o c k i n g ( u s a r t , ’−’ ) ; v a l u e=−v a l u e ;}
w h i l e ( v a l u e > 0 ) {b u f f e r [ n r d i g i t s ++] = ” 0 1 2 3 4 5 6 7 8 9 ” [ v a l u e % 1 0 ] ; v a l u e /= 1 0 ;}
f o r ( i = ( n r d i g i t s − 1 ) ; i >= 0 ; i−−) {u s a r t s e n d b l o c k i n g ( u s a r t , b u f f e r [ i ] ) ;}
u s a r t s e n d b l o c k i n g ( u s a r t , ’\r ’ ) ; u s a r t s e n d b l o c k i n g ( u s a r t , ’\n ’ ) ;
#e l s e
p r i n t f (”%d ” , v a l u e ) ;
#e n d i f }
l o n g f i l t r e ( u n s i g n e d s h o r t ∗i n , l o n g ∗f i l , l o n g nin , l o n g n f i l , l o n g ∗s o r t i e ) {u n s i g n e d s h o r t k , j ; l o n g s =0 ,max=−2500;
i f ( nin>n f i l )
{f o r ( k =0; k<nin−n f i l ; k++) {s =0;
f o r ( j =0; j<n f i l ; j ++)
s +=(((( l o n g ) f i l [ j ]∗( l o n g ) i n [ n f i l−1+k−j ] ) ) ) / 2 5 6 ; s=s / 2 5 6 ;
s o r t i e [ k ]= s ;
i f ( max<s ) {max=s ;} }
}
r e t u r n ( ( l o n g ) max ) ; }
i n t main ( v o i d ) {
u n s i g n e d s h o r t k =0;
l o n g s o r t i e [NB] , max ;
u n s i g n e d c h a r c h a n n e l a r r a y [ 1 6 ] ;
// a=( round ( f i r l s ( 6 0 , [ 0 500 700 900 1000 3 2 7 6 8 / 1 6 ] / 3 2 7 6 8∗1 6 , [ 0 0 1 1 0 0 ] )∗6 5 5 3 6 ) ’ ) /∗l o n g f i l 2 0 0 [ NBFIL] ={ −2 8 4 ,−3 4 3 , 1 9 3 , 7 0 0 , 3 6 2 ,−4 5 7 ,−6 6 5 ,−1 6 7 , 1 0 8 , 8 , 3 9 0 , 1 0 9 2 ,\
557 ,−1361 ,−2181 ,−294 ,2040 ,1797 ,−110 ,−628 ,−77 ,−1315 ,−3220 ,−821 ,\
5 5 3 9 , 7 1 7 7 ,−1 1 3 1 ,−1 0 6 2 6 ,−8 0 8 1 , 5 1 9 6 , 1 2 9 3 8 , 5 1 9 6 ,−8 0 8 1 ,−1 0 6 2 6 ,−1 1 3 1 , 7 1 7 7 ,\
5539 ,−821 ,−3220 ,−1315 ,−77 ,−628 ,−110 ,1797 ,2040 ,−294 ,−2181 ,−1361 ,\
5 5 7 , 1 0 9 2 , 3 9 0 , 8 , 1 0 8 ,−1 6 7 ,−6 6 5 ,−4 5 7 , 3 6 2 , 7 0 0 , 1 9 3 ,−3 4 3 ,−2 8 4};
∗/
// a=( round ( f i r l s ( 6 0 , [ 0 500 700 900 1000 3 2 7 6 8 / 2 ] / 3 2 7 6 8∗2 , [ 0 0 1 1 0 0 ] )∗6 5 5 3 6 ) ’ ) l o n g f i l 2 0 0 [ NBFIL]={ −384 ,−543 ,−695 ,−836 ,−964 ,−1074 ,−1164 ,−1229 ,−1270 ,−1283 , \
−1268 ,−1224 ,−1153 ,−1054 ,−930 ,−783 ,−616 ,−433 ,−237 ,−34 ,173 ,379 ,578 ,767 ,941 ,\
1 0 9 6 , 1 2 2 8 , 1 3 3 4 , 1 4 1 1 , 1 4 5 9 , 1 4 7 5 , 1 4 5 9 , 1 4 1 1 , 1 3 3 4 , 1 2 2 8 , 1 0 9 6 , 9 4 1 , 7 6 7 , 5 7 8 , 3 7 9 , 1 7 3 ,\
−34 ,−237 ,−433 ,−616 ,−783 ,−930 ,−1054 ,−1153 ,−1224 ,−1268 ,−1283 ,−1270 ,−1229 ,−1164 ,\
−1074 ,−964 ,−836 ,−695 ,−543 ,−384};
#i f n d e f pc
r c c c l o c k s e t u p i n h s e 8 m h z o u t 2 4 m h z ( ) ; g p i o s e t u p ( ) ;
u s a r t s e t u p ( ) ; t i m e r s e t u p ( ) ; i r q s e t u p ( ) ; a d c s e t u p ( ) ;
g p i o s e t (GPIOC, GPIO8|GPIO9 ) ;
c h a n n e l a r r a y [ 0 ] = 0 ; // c h a n n e l number f o r c o n v e r s i o n a d c s e t i n j e c t e d s e q u e n c e (ADC1, 1 , c h a n n e l a r r a y ) ;
#e n d i f
w h i l e ( 1 ) {
#i f d e f pc
a d c 1 2 i s r ( ) ;
#e n d i f
i f ( j m f i n d e x>=NB) {
#i f d e f debug
f o r ( k =0; k<NB; k++) m y u s a r t p r i n t i n t (USART1, t e m p e r a t u r e [ k ] ) ;
#e n d i f
max= f i l t r e ( t e m p e r a t u r e , f i l 2 0 0 , NB, NBFIL , s o r t i e ) ;
#i f d e f debug
f o r ( k =0; k<NB−NBFIL ; k++) m y u s a r t p r i n t i n t (USART1, s o r t i e [ k ] ) ;
#e n d i f
#i f n d e f pc
m y u s a r t p r i n t i n t (USART1, max ) ;
#e l s e
p r i n t f ( ”\t%f\t%d\n ” , f r e q , max ) ; temps = 0 . ;
f r e q +=10.;
i f ( f r e q>=( f e / 1 0 . ) ) r e t u r n ( 0 ) ;
#e n d i f
j m f i n d e x =0;
}
#i f n d e f pc
g p i o t o g g l e (GPIOC, GPIO8 ) ;
#e n d i f }
r e t u r n 0 ; }
/∗ f r e q = [ 5 0 : 5 0 : 3 0 0 0 ] ; k =1;
f o r f=f r e q
x=s i n ( 2∗p i∗f∗[ 0 : 8 / 3 2 7 6 8 : 0 . 1 ] ) ; y= f i l t e r ( a , 1 , x ) ;
mm( k )=max ( y ( 1 0 0 : 2 0 0 ) ) ; k=k +1;
end
p l o t ( f r e q ,mm)
∗/
On notera en particulier que ce programme est con¸ cu soit pour s’ex´ ecuter sur PC (cas #define pc) soit sur STM32 (cas
#undef pc) : la seule diff´ erence tient dans les fonctions d’initialisation et de communication, tandis que la partie arithm´ etique est commune aux deux impl´ ementations. Il est en effet bien plus ais´ e de valider l’algorithme avec des valeurs synth´ etiques (appel explicite de la fonction de gestion d’interruption dans le main dans le cas de l’ex´ ecution sur PC – fonction qui renvoie dans ce cas des donn´ ees id´ eales de siniso¨ıde ` a fr´ equence variable) que de d´ everminer le programme directement sur microcontrˆ oleur.
3 Conception d’un filtre de r´ eponse infinie (IIR)
Un IIR tient compte non seulement des derni` eres observations mais aussi des valeurs pass´ ees du filtre : y
n= X
k=0..m
b
kx
n−k− X
k=1..m