Forum: Mikrocontroller und Digitale Elektronik erzeugen eines sinus mit variabler frequenz


von Kervin K. (kernel)


Lesenswert?

Hi.
Ich bin gerade ein bisschen am Testen mit nem ATmega32 und wollte jetzt 
mal nen Sinus mit variabler Frequenz erzeugen, um schöne Töne ausgeben 
zu können und später vielleicht auch mehrere Töne gleichzeitig ausgeben 
zu können (Überlagerung).

Ich hab mir beim Programmstart ne Sinus-Tabelle mit 64 Einträgen 
angelegt:
for (i = 0; i < 64; i++)
        sintab[i] = (127. * sin(2  PI  i /64)) + 127.;

Im weiteren Verlauf des Programms nehm ich immer einen Wert davon, geb 
ihn über eine 8-Bit-PWM (Timer 2) aus und erhöhe den Zähler, der auf 
eine Stelle in der Tabelle zeigt.
Über nen Tiefpass am Ausgangs-Pin ergibt sich dann auch ein schöner 
Sinus mit ca. 1 Hz bei Taktfrequenz 1 MHz.

Wie kann ich diese Frequenz jetzt zur Laufzeit ändern?

Danke schon mal.

von johnny.m (Gast)


Lesenswert?

> Wie kann ich diese Frequenz jetzt zur Laufzeit ändern?
Vielleicht durch Ändern der PWM-Frequenz?

> Danke schon mal.
Keine Ursache...

von Einhart (Gast)


Lesenswert?

Moin,

mach z.B. das Holen des nächsten Tabellenwertes in der Interruptroutine 
eines anderen Timers. Die Änderung des Interruptzyklus dieses Timers 
ändert dann die Frequenz des Sinus.

von Markus 8. (markus_8051)


Lesenswert?

@johnny.m: Eben nicht!

@kernel: Du mußt die Frequenz ändern, mit der Du die Schleife aufrufst, 
die einen Wert aus der Tabelle holt, ihn ins PWM-Register schreibt und 
den Zähler erhöht. Dabei solltest Du daran denken, daß die maximale 
Frequenz, die Du über einen PWM-Ausgang ausgeben kannst um ein 
vielfaches unter der PWM-Frequenz liegt. Schließlich ist der PWM ein 
Tiefpass nachgeschaltet, daß die Aufgabe hat, die eigentlich 
PWM-Frequenz rauszufiltern. Je nachdem wie steil Dein Filter ist und wie 
sauber Du das Signal haben möchtest, mußt Du den Abstand von 
PWM-Frequenz und maximaler Ausgabefrequenz wählen.

Mit welcher Frequenz arbeitet denn Deine PWM?

Allgemein kann man aber sagen, daß PWM eine schlechte Methode ist, ein 
Audiosignal mit einem µC zu erzeugen. Da würde ich eher so einen ganz 
simplen D/A-Wandler, bestehend aus ein paar Widerständen an einem 
acht-bit-Port verwenden - mal vorausgesetzt, Du hast noch sowas frei.

Markus_8051

von Christoph Kessler (db1uq) (Gast)


Lesenswert?

Das ist eine normale "DDS"-Sinuserzeugung. Um die Frequenz zu ändern 
variiert man die Sprungweite in der Tabelle, die Zeit zwischen den 
Tabellenwertausgaben bleibt konstant.

von johnny.m (Gast)


Lesenswert?

> Eben nicht!
Stimmt natürlich. Man müsste dann ja auch die Tabellenwerte entsprechend 
skalieren. Und dabei ginge die ganze Auflösung den Bach runter...

von Lupin (Gast)


Lesenswert?

Christoph damit verlierst du aber an auflösung, wenn möglich ist es 
besser die timer frequenz mit der die neuen werte geladen werden zu 
erhöhen.

von Christoph Kessler (db1uq) (Gast)


Lesenswert?

Ja sicher, jeder DDS hat Jitter. Je höher die Frequenz desto schlimmer, 
die Stufen sind ja ab der niedrigsten Frequenz gleich. Die Sinustabelle 
muß möglichst groß sein, so dass die niedrigste Frequenz gerade jeden 
Tabellenwert einmal aufruft. Mit PWM wird die Auflösung nochmal 
verschlechtert, denn die muß in der Frequenz noch deutlich über dem 
Tabellenauslesetakt liegen.

von Loenny (Gast)


Lesenswert?

Bei Verwendung des 16Bit Timers bekommt man mit einem 3,68640MHz Quarz 
eine Auflösung von delta_f=56,25Hz. Bei einer Periode des Sinus mit 8Bit 
ist die max. Frequenz f_max=13,619kHz.

delta_f = 3.68640MHz / 2^16

f_max = 2^8 * 3,68640MHz / 2^16

init = f_soll * 2^16 / 3.6864MHz

Ich weiß jetzt nur nicht ob man den Timer auch mehr als "eins" erhöhen 
kann.


for (;;)
TEMP = TEMP + init;

u_sin = sintab[TEMP(15:8)];

von Karl H. (kbuchegg)


Lesenswert?

> Ich weiß jetzt nur nicht ob man den Timer auch mehr als "eins"
> erhöhen kann.

Das nicht. Aber mit dem CTC Modus kannst du dir
sehr einfach fast nach jeder beliebigen Taktzyklenzahl
einen Interrupt auslösen lassen.



Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.