mikrocontroller.net

Forum: Mikrocontroller und Digitale Elektronik PWM, Frequenz und Vorteiler


Autor: Gast (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo, ich habe einen ATMEGA8 mit 16 Mhz getaktet. Nun will ich mal ein 
Projekt mit PWM realisieren. Wie berechne ich die Frequenz? Aus dem 
Tutorial werde ich nicht schlau.

Ich will eine Frequenz mit 500 Hz hinbekommmen. Bevor ich anfange zu 
programmieren, will ich erstmal gerne wissen, wie man das mit dem 
Vorteiler, der Taktfrequenz usw. berechnet. Erstmal für den 8 Bit Modus.

Kann mir jemand da irgendwie helfen? Im Datenblatt finde ich zwar einige 
Formeln, aber ich weiß nicht welche Werte ich einsetzen muss.

Autor: Karl Heinz (kbuchegg) (Moderator)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Gast wrote:

> Kann mir jemand da irgendwie helfen? Im Datenblatt finde ich zwar einige
> Formeln, aber ich weiß nicht welche Werte ich einsetzen muss.


Hmm. Vergissa einfach mal die Formeln.
Versuch zu verstehen, wie ein Timer arbeitet und wie die Zusammenhänge 
sind. Das ist wirklich nicht schwer. Sobald du dieses Verständnis hast, 
ergeben sich dann nämlich die Formeln wie von selber.


Der Timer tickt vor sich hin. Zählt immer 1 zu einem Timerregister 
hinzu.
Wie schnell macht er das.
Grundsätzlich macht er das zb. mit der Quarzfrequenz.
D.h bei einer Quarzfrequenz von 16Mhz zählt der Timer in 1 Sekunde bis 
16000000.
Nun ist das oft zu schnell. Also kann man einen Vorteiler zuschalten. 
Dieser Vorteiler teilt die Quarzfrequenz durch einen bestimmten Faktor. 
Sei der Vorteiler zb. 2, dann kommt der Timer in 1 Sekunde nicht mehr 
bis 16000000 sondern nur noch bis 8000000. Und bei einem Vorteiler von 
1024 schafft er es nur noch bis 16000000 / 1024 = 15625.
Logisch, oder nicht.

Jetzt wissen wir also, wie weit der Timer in 1 Sekunde überhaupt 
theoretisch zählen kann.
Ein 8 Bit Timer kann aber grundsätzlich gar nicht bis 15625 zählen, weil 
er ja als 8-Bit Ding, bereits bei 255 ansteht, einen Überlauf verursacht 
und wieder bei 0 anfängt.

Wie oft passiert denn das in 1 Sekunde.
Na, offensichtlich 15625 / 256 = 61.035 mal

Ein 8 Bit Timer, der bei einem 16Mhz Quarz und einem Vorteiler von 1024 
betrieben wird, 'erzeugt' also eine Overflow Frequenz von 61.035 Hz
Wird der Timer mit einer PWM betrieben, so dass zb der Pin-ein bei 0 und 
das Pin-aus bei irgendeiner anderen Zahl im Bereich 0 bis 255 erfolgt, 
dann ist die PWM Frequenz logischerweise ebenfalls 61.035 Hz, denn sooft 
wird ja der Bereich 0 bis 255 vom Timer in 1 Sekunde überstrichen.
Ist die PWM so eingestellt, dass der Timer beim 'Hochfahren 0 bis 255' 
einen Pin einschaltet und beim Runterfahren '255 - 0' wieder 
ausschaltet, dann braucht der Timer offensichtlich 2 Duchrgänge um einen 
PWM Zyklus zu absolvieren und das kann er logischerweise dann nur noch 
61.035 / 2 = 30.5 mal in der Sekunde und daher ist die PWM Frequenz nur 
noch 30.5 Hz.

Wie gesagt: Vergiss fürs erste die Formeln. Versteh was da intern abgeht 
und die Formeln ergeben sich von selbst.

Autor: Christian Rieger (bastler14)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
das ist gut

Autor: Gast (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
freqeunz = CPU_takt / prescaler (1 + OCR0A)

in deinem Fall:
500 = 16000000 / 64 * (1 + OCR0A)

Formel umstellen nach OCR0A:
OCR0A = 16000000 / 500 * 64 - 1
OCR0A = 499

OCR0A ist 16 bit groß.

Durch Änderung von OCR0A oder dem Prescaler, kannst du deine PWM 
Frequenz einstellen. Oder man ändert den CPU-Takt...

Autor: Gast (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
danke für eure antworten. bei 500 hz hätte ich ja ein tastverhältnis von 
2 ms. wie mache ich das nun per software? also das ich z.b. 75% an und 
25 aus habe?

Autor: Johannes M. (johnny-m)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Gast wrote:
> danke für eure antworten. bei 500 hz hätte ich ja ein tastverhältnis von
> 2 ms.
Nö. Die 2 ms sind die Periodendauer.

> wie mache ich das nun per software? also das ich z.b. 75% an und
> 25 aus habe?
Indem Du in das Register, in das der PWM-Wert (also der Wert für das 
Tastverhältnis) kommt, einen entsprechenden Wert hineinschreibst. 
Welches Register das ist, hängt davon ab, welchen Timer Du benutzt, mit 
welcher Compare-Einheit und in welchem PWM-Modus Du arbeitest.

Es gibt immer zwei Werte: Den TOP-Wert, der die Frequenz des PWM-Signals 
definiert, und den PWM-Wert, der das Tastverhältnis darstellt. Der 
TOP-Wert kann je nach Timer und Modus entweder fest sein (8-, 9- oder 
10-Bit-PWM mit TOP von 255, 511 oder 1023) oder über ein Register frei 
definiert werden (entweder eines der Compare-Register oder das 
Input-Capture-Register, sofern vorhanden).

Autor: Gast (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
danke erstmal, soweit bin ich bis jetzt gekommen:
#define F_CPU 16000000UL

#include <avr/io.h>
#include <util/delay.h>
#include <inttypes.h>


int main(void) 
{
  DDRD = 0xFF;

  PORTB = 0x00;


  TCCR1A = (1<<WGM10)|(1<<COM1A1);
  TCCR1B = (1<<CS11) |(1<<CS10); 

  OCR1A = 499;

  while(1)
  {};
}


kapieren tu ich es leider immer noch nicht richtig.

Autor: Johannes M. (johnny-m)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Gast wrote:
>   TCCR1A = (1<<WGM10)|(1<<COM1A1);
Das stellt eine 8-Bit-PWM ein, weshalb dieser Compare-Wert
>   OCR1A = 499;
... keinen Sinn macht, da er größer als TOP ist. In 8 Bit gehen nur 255 
rein!

Du musst, um auf einigermaßen genaue 500 Hz zu kommen, schon einen der 
Modi nehmen, bei denen Du TOP frei vorgeben kannst. Abgesehen davon ist 
bei dem von Dir gewählten Modus (Phase Correct PWM) die PWM-Frequenz 
noch mal einen Faktor 2 kleiner als eingstellt. Das ergibt zwar 
zufällig mit Deinen Einstellungen ungefähr 500 Hz (genauer 488,28 
Hz), ist aber vermutlich so nicht beabsichtigt...

Du solltest eine Fast PWM nehmen, und zwar eine, bei der TOP in ICR1 
kommt. Und das trifft nur auf Modus 14 zu...

Autor: Gast (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
den wert hab ich aus der obrigen rechnung genommen? dort steht doch das 
OCR1A 16 bit breit ist?
sei();

//fast hardware pwm
sbi(TCCR0A, WGM01);
sbi(TCCR0A, WGM00);

sbi(TCCR1B, CS11);
sbi(TCCR1B, CS10);

sbi(TCCR1A, COM1A1);

//0 - 255
OCR1A = 0; 

Autor: Johannes M. (johnny-m)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Gast wrote:
> den wert hab ich aus der obrigen rechnung genommen? dort steht doch das
> OCR1A 16 bit breit ist?
Erstens hast Du nur WGM10 gesetzt, und das gibt eine 8-Bit-PWM. Und die 
geht nunmal nur bis 255, da kann das OCR noch so breit sein!

Außerdem: Bringe nicht Timer 0 und 1 durcheinander!

Schau ins Datenblatt, da ist eine große und imho sehr übersichtliche 
Tabelle, in der sehr präzise steht, welche Bits wofür gesetzt werden 
müssen.

Antwort schreiben

Die Angabe einer E-Mail-Adresse ist freiwillig. Wenn Sie automatisch per E-Mail über Antworten auf Ihren Beitrag informiert werden möchten, melden Sie sich bitte an.

Wichtige Regeln - erst lesen, dann posten!

  • Groß- und Kleinschreibung verwenden
  • Längeren Sourcecode nicht im Text einfügen, sondern als Dateianhang

Formatierung (mehr Informationen...)

  • [c]C-Code[/c]
  • [avrasm]AVR-Assembler-Code[/avrasm]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] - Link zu Artikel
  • Verweis auf anderen Beitrag einfügen: Rechtsklick auf Beitragstitel,
    "Adresse kopieren", und in den Text einfügen




Bild automatisch verkleinern, falls nötig
Bitte das JPG-Format nur für Fotos und Scans verwenden!
Zeichnungen und Screenshots im PNG- oder
GIF-Format hochladen. Siehe Bildformate.
Hinweis: der ursprüngliche Beitrag ist mehr als 6 Monate alt.
Bitte hier nur auf die ursprüngliche Frage antworten,
für neue Fragen einen neuen Beitrag erstellen.

Mit dem Abschicken bestätigst du, die Nutzungsbedingungen anzuerkennen.