Forum: Gesperrte Threads Filter schneller berechnen, aber wie?


von Chris c. (chris78)


Lesenswert?

Hallo,
ich beschäftige mich gerade mit der Programmierung von IIR-Filtern. 
Meine ersten Filter habe ich auch sehr zuverlässig auf dem DSP Bord 
TMS320C6713 der Firma Texas Instruments programmiert. Da dieses Bord 
allerdings relativ teuer ist und ich die meisten Funktionen gar nicht 
benötige, habe ich mich nach einer günstigeren Lösung umgesehen. Dabei 
bin ich auf den ATmega32(µC) der Firma Atmel gestoßen, der wirklich 
günstig ist. Zudem ist der A/D-Wandler sogar noch schneller als beim 
Teaxas Instrument Bord. Mir war im Prinzip schon vorher klar, dass ich 
vermutlich Probleme bei der Lösung einer solchen Aufgabe mit einem µC 
bekomme. Schaut man sich allerdings den einfachen C-Code für ein IIR 
2.Ordnung an, kann man vielleicht nachvollziehen, warum ich es dennoch 
versucht habe.
1
// funktionen read_adc und send_dac stehen hier
2
3
void main (void)
4
 {
5
 float a0,a1,a2,b1,b2,u0=0,u1=0,u2=0,u3=0;  //Declare local variables
6
 a0 =  0.2083;     //Zählerkoeffizienten
7
 a1 =  0.4165;
8
 a2 =  0.2083;
9
 b1 =  0.0327;     //Nennerkoeffizienten
10
 b2 = -0.1996;
11
12
 while(1)
13
   {
14
   u0 = read_adc;   //Eingangswert vom AD,  
15
                    //Für Testzwecke Wert direkt zuweisen
16
   
17
   u3 = a0*u0+u2;
18
   u2 = a1*u0-b1*u3+u1;
19
   u1 = a2*u0-b2*u3;
20
21
   send_dac = u3;     //Für Testzwecke löschen
22
   };
23
 }

Zu Testzwecken habe ich den Funktionsaufruf send_dac herausgenommen und 
u0 einen float Wert direkt zugewiesen.
Nun benötigt der ATmega32 mit 14,745 MHz Quarztakt allerdings 160µs für 
einen Durchlauf der "While(1)-Endlosschleife", was für meine späteren 
Anwendungen viel zu langsam ist.
Nun endlich zu meiner Frage: Kennt jemand eine relativ günstige Lösung 
um z.B. die zeitraubenden Multiplikationen durch einen wesentlich 
schnelleren Hardwaremultiplizierer zu berechnen?
Oder einen Prozessor, FPGA o.ä., der einen solchen Durchlauf in ca.0,1µs 
(10MHz) schafft?
Da die maximale Ordnungszahl des Filters 10 betragen wird, würde mir 
auch eine Durchlaufzeit von ca. 3,2 MHZ - 1 MHz für die 10.Ordnung 
ausreichen.

Auch Anregungen und Ideen könnten mir weiterhelfen...

MfG
Chris

von Benedikt K. (benedikt)


Lesenswert?

Als erstes solltest du mal auf Fließkomma verzichten und stattdessen 
Festkommazahlen verwenden. Damit sollte das ganze in wenigen 10µs 
möglich sein. Ansonsten könnten vielleicht die dsPICs für dich 
interessant sein. Diese sollten einen Durchlauf in weniger als 1µs 
schaffen.

von Florian (Gast)


Lesenswert?

Ich würde Deine 'Konstanten' a0-b2 auch als solche abspeichern:
1
const float a0 = 0.2083;

Dann hat der Compiler schon die Möglichkeit zu optimieren. Wenn sich die 
Werte natürlich dynamisch ändern sollen, geht das nicht.

Außerdem würde ich die Direktform I verwenden.

Es wäre auch denkbar, anstatt mit Gleitkommazahlen, mit Festkommazahlen 
zu arbeiten.

von Andreas S. (andreas) (Admin) Benutzerseite


Lesenswert?

Gesperrt wegen Doppelpost.

Dieser Beitrag ist gesperrt und kann nicht beantwortet werden.