一部のピンのPWM周波数が異なるのはなぜですか?


20

ArduinoリファレンスにanalogWrite()よると、ほとんどのピンのPWM周波数は〜490 Hzです。ただし、Unoのピン5と6、およびLeonardoのピン3と11の場合は約980 Hzです。

なぜこれらが異なるのですか?それは意図的な設計機能ですか、それともハードウェアによって何らかの形で指示されていますか?

回答:


23

PWM信号に使用できる周波数はこれらだけではありません。ただし、これらは適用されたプリスケーラによって決定される周波数です(詳細は以下で簡単に変更できます)。

次のように、3組のPWMピンはそれぞれ1つのタイマーに結び付けられており、各タイマーには独自のベース周波数があります。

  • ピン5と6はtimer0でペアリングされ、ベース周波数は62500Hzです
  • ピン9と10はtimer1でペアになっており、ベース周波数は31250Hzです
  • ピン3と11はタイマー2でペアになっており、ベース周波数は31250Hzです

次に、ピンの各セットには、選択可能なプリスケーラ値がいくつかあります。これらの値は、そのピンのペアの基本周波数を分割します。利用可能なプリスケーラ値は次のとおりです。

  • ピン5と6のプリスケーラー値は1、8、64、256、および1024です
  • ピン9および10のプリスケーラー値は1、8、64、256、および1024です
  • ピン3および11のプリスケーラー値は1、8、32、64、128、256、および1024です

異なる組み合わせにより、特定のPWMピンで異なる周波数が生成されます。タイマー2(ピン3および11に接続)には、より多くのプリスケーラー値があり、より多くの周波数が利用できることに注意してください。

さて、タイマー2が異なる理由は、別の質問です。

編集:ここに、ピンごとの可能なPWM周波数のリストがあります(この記事から):

ピン6および5(OC0AおよびOC0B)の場合:

  • TCCR0B = xxxxx001の場合、周波数は64kHzです
  • TCCR0B = xxxxx010の場合、周波数は8 kHzです
  • TCCR0B = xxxxx011の場合、周波数は1kHzです(これはDiecimilaブートローダーのデフォルトです)
  • TCCR0B = xxxxx100の場合、周波数は250Hzです
  • TCCR0B = xxxxx101の場合、周波数は62.5 Hzです

ピン9、10、11、および3(OC1A、OC1B、OC2A、OC2B)の場合:

  • TCCRnB = xxxxx001の場合、周波数は32kHzです
  • TCCRnB = xxxxx010の場合、周波数は4 kHzです
  • TCCRnB = xxxxx011の場合、周波数は500Hzです(これはDiecimilaブートローダーのデフォルトです)
  • TCCRnB = xxxxx100の場合、周波数は125Hz
  • TCCRnB = xxxxx101の場合、周波数は31.25 Hzです

TCCRnBtimerのプリスケーラービットを設定する場所で、設定するタイマーに応じて0、1、または2にn置き換えnます。それでもビット単位の操作について不明な場合は、このビット数学チュートリアルをお読みください

私の情報源:

ピン9と10が5と6または3と11と同じ動作をするかどうかについては、これらのソースに相違があるように見えますが、とにかくアイデアを得ることに注意してください。私はデータシェットを読んで、どちらが正しいか、またはこれがボード間の違いであるかどうかを判断しようと試みています。


1
この回答は何のATmegaを指しますか?私はチェックしませんでしたが、私はそれがコントローラーごとにわずかに異なるに違いないと確信しています。
ジッピー

@jippie良い点!ソースはATmega168と328を参照
リカルド

@jippie私の答えでは、ピン番号は、ICではなく、Unoボード上のピンの割り当て方法を指します(ピン1はデジタルピン1、またはD1などを意味します)(ATmega328ピン1はリセットされます)。
リカルド

1
私は、これらの詳細は、ボード、宇野、Duemilanove、メガ、...とあまりにも変更と信じて
jippie

@jippie確かに、はい。
リカルド

8

設計上の考慮事項は知りませんが、Arduinoのマイクロコントローラーのデータシートを確認すると、PWMピンがタイマーに接続されているグループごとにグループ化されていることに気付くでしょう。このタイマーが増加する速度は、構成されたプリスケーラーによって異なります。特定のタイマーのプリスケーラーを変更すると、関連するPWMピンのPWM周波数が変更されます。millis();関数のような他の目的のために、いくつかのタイマーが倍になると思います。そのタイマーのプリスケーラを変更すると、によって返される値millis()は同じ係数でオフになります。

プリスケーラの設定は次のように計算できます。

$$ \ text {prescaler} = \ dfrac {f_ {CPU}} {PWMresolution×f_ {PWM}} = \ dfrac {16 \ text {MHz}} {256×490} \ approx 128 $$

プリスケーラー= f [CPU] /(PWMresolution×f [PWM])= 16000000 /(256×490)=約128

データシートを確認すると、128が実際に選択できるプリスケーラー値の1つであることがわかります。


2
男の子、MathJaxが恋しいですか?ベータ版の後に有効にしたいと思います。
リカルド

1
@Ricardo私は私のブラウザでMathJaxボタンを持っている; O) meta.arduino.stackexchange.com/questions/13/...
jippie
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.