Warum haben einige Pins eine andere PWM-Frequenz?

20

Gemäß der Arduino-Referenz füranalogWrite() beträgt die PWM-Frequenz an den meisten Pins ~ 490 Hz. Für die Pins 5 und 6 auf dem Uno und für die Pins 3 und 11 auf dem Leonardo sind es jedoch ~ 980 Hz.

Warum sind diese unterschiedlich? Handelt es sich um ein absichtliches Designmerkmal oder ist es irgendwie durch die Hardware vorgegeben?

Peter Bloomfield
quelle

Antworten:

23

Dies sind nicht die einzigen verfügbaren Frequenzen für die PWM-Signale. Dies sind jedoch die Frequenzen, die vom angewendeten Vorteiler bestimmt werden (den Sie wie unten beschrieben leicht ändern können).

Jedes der 3 Paare von PWM-Pins ist wie folgt mit einem Timer verbunden, von denen jeder seine eigene Grundfrequenz hat:

  • Die Pins 5 und 6 sind auf timer0 mit einer Grundfrequenz von 62500Hz gepaart
  • Die Pins 9 und 10 sind auf timer1 mit einer Grundfrequenz von 31250Hz gepaart
  • Die Pins 3 und 11 sind auf Timer2 mit einer Grundfrequenz von 31250 Hz gepaart

Dann kann für jeden Pinsatz eine Reihe von Prescaler-Werten ausgewählt werden, die die Grundfrequenz dieses Pinspaares teilen. Die verfügbaren Vorteilerwerte sind:

  • Die Pins 5 und 6 haben Vorskaliererwerte von 1, 8, 64, 256 und 1024
  • Die Stifte 9 und 10 haben Vorskaliererwerte von 1, 8, 64, 256 und 1024
  • Die Stifte 3 und 11 haben Vorskaliererwerte von 1, 8, 32, 64, 128, 256 und 1024

Die verschiedenen Kombinationen ergeben unterschiedliche Frequenzen in einem gegebenen PWM-Pin. Beachten Sie, dass für Timer 2 (verbunden mit den Pins 3 und 11) mehr Prescaler-Werte verfügbar sind, sodass mehr Frequenzen verfügbar sind.

Warum Timer 2 anders ist, ist eine andere Frage.

Bearbeiten: Hier ist eine Liste der möglichen PWM-Frequenzen pro Pin (aus diesem Artikel ):

Für die Pins 6 und 5 (OC0A und OC0B):

  • Wenn TCCR0B = xxxxx001 ist, beträgt die Frequenz 64 kHz
  • Wenn TCCR0B = xxxxx010 ist, beträgt die Frequenz 8 kHz
  • Wenn TCCR0B = xxxxx011, beträgt die Frequenz 1 kHz (dies ist die Standardeinstellung des Diecimila-Bootloaders).
  • Wenn TCCR0B = xxxxx100 ist, beträgt die Frequenz 250 Hz
  • Wenn TCCR0B = xxxxx101 ist, beträgt die Frequenz 62,5 Hz

Für die Pins 9, 10, 11 und 3 (OC1A, OC1B, OC2A, OC2B):

  • Wenn TCCRnB = xxxxx001 ist, beträgt die Frequenz 32 kHz
  • Wenn TCCRnB = xxxxx010 ist, beträgt die Frequenz 4 kHz
  • Wenn TCCRnB = xxxxx011, beträgt die Frequenz 500 Hz (dies ist die Standardeinstellung des Diecimila-Bootloaders).
  • Wenn TCCRnB = xxxxx100 ist, beträgt die Frequenz 125 Hz
  • Wenn TCCRnB = xxxxx101 ist, beträgt die Frequenz 31,25 Hz

TCCRnBHier stellen Sie die Prescaler-Bits für den Timer ein n, die ndurch 0, 1 oder 2 ersetzt werden, je nachdem, welchen Timer Sie einstellen möchten. Wenn Sie sich bei bitweisen Operationen immer noch unsicher sind, lesen Sie dieses Bit-Mathe-Tutorial .

Meine Quellen:

Beachten Sie, dass es in diesen Quellen Unterschiede zu geben scheint, ob die Pins 9 und 10 dasselbe Verhalten haben wie 5 und 6 oder 3 und 11, aber Sie verstehen es trotzdem. Ich lese den Datensatz, um herauszufinden, was richtig ist oder ob dies ein Unterschied zwischen den Boards ist.

Ricardo
quelle
1
Auf welches ATmega bezieht sich diese Antwort? Ich habe nicht nachgesehen, aber ich wette, dass es je nach Controller etwas anders ist.
jippie
@jippie Guter Punkt! Die Quellen beziehen sich auf ATmega168 und 328.
Ricardo
@jippie Nur um zu verdeutlichen, in meiner Antwort beziehen sich die Pin-Nummern darauf, wie sie auf der Uno-Platine zugewiesen sind (Pin 1 bedeutet beispielsweise Digital Pin 1 oder D1), nicht auf den IC (ATmega328 Pin 1 wird zurückgesetzt).
Ricardo
1
Ich glaube, diese Details ändern sich auch mit Brettern, Uno, Duemilanove, Mega, ...
jippie
@jippie Auf jeden Fall ja.
Ricardo
8

Mir sind die Designüberlegungen nicht bekannt, aber wenn Sie das Datenblatt für den Mikrocontroller auf Ihrem Arduino überprüfen, werden Sie feststellen, dass PWM-Pins zusammen gruppiert und pro Gruppe mit einem Timer verbunden sind. Die Geschwindigkeit, mit der dieser Timer erhöht wird, hängt vom konfigurierten Vorteiler ab. Wenn Sie den Vorteiler für einen bestimmten Timer ändern, ändern Sie die PWM-Frequenz für die zugehörigen PWM-Pins. Ich glaube einige Timer verdoppeln sich für andere Zwecke wie die millis();Funktion. Wenn Sie den Vorteiler für diesen Timer ändern, werden die von zurückgegebenen Werte millis()um denselben Faktor deaktiviert .

Sie können die Einstellung für den Vorteiler wie folgt berechnen:

$$ \ text {prescaler} = \ dfrac {f_ {CPU}} {PWM-Auflösung × f_ {PWM}} = \ dfrac {16 \ text {MHz}} {256 × 490} \ ca. 128 $$

Vorteiler = f [CPU] / (PWM-Auflösung × f [PWM]) = 16000000 / (256 × 490) = ca. 128.

Überprüfen Sie das Datenblatt und Sie werden feststellen, dass 128 tatsächlich einer der Prescaler-Werte ist, die Sie auswählen können.

jippie
quelle
2
Junge, vermissen wir MathJax oder was? Ich hoffe, wir werden es nach der Beta aktivieren.
Ricardo
1
@ Ricardo Ich habe eine MathJax-Schaltfläche in meinem Browser; o) meta.arduino.stackexchange.com/questions/13/…
jippie