PWM出力周波数の駆動


8

何時間も無駄な検索と読み取りを行った後も、他の​​誰かの「ブラックボックス」を使用せずに、RPiのハードウェアPWMピンから特定の周波数を出力する方法と理由を完全に理解していませんでした。

詳細については、不正確または不完全な情報、および使用されているさまざまな用語「クロック分周器」、「デューティサイクル」、「PWM範囲」、PWMデータ自体、およびそれらすべてがどのように関連しているかがかなりあるようです特定の周波数を出力するために一緒に-私の場合、圧電サウンダから特定のオーディオ周波数を駆動します。

回答:


14

私はようやくbcm2835.hドライバーヘッダーファイルから完全に理解できるようになったので、他の人のために自分の質問を投稿して答えようと思いました。

ヘッダーからの関連ビット:

PWM

BCM2835は、GPIOピンの限られたサブセットでハードウェアPWMをサポートします。このbcm2835ライブラリは、これらのピンのPWM出力を構成および制御するための関数を提供します。

BCM2835には2つの独立したPWMチャネル(0と1)が含まれており、それぞれがGPIOピンの限られたサブセットに接続されています。次のGPIOピンは、次のPWMチャネルに接続できます。

  GPIO PIN    RPi pin  PWM Channel    ALT FUN
  12                    0             0
  13                    1             0
  18          1-12      0             5
  19                    1             5
  40                    0             0
  41                    1             0
  45                    1             0
  52                    0             1
  53                    1             1

GPIOピンがPWMチャネルから出力を放出するには、上記のAlt関数に設定する必要があります。Raspberry Piの現在のバージョンでは、IOヘッダーでこれらのピンの1つ(GPIO 18 = RPiピン1〜12)しか公開されていないため、これがPWMに使用できるRPiの唯一のIOピンであることに注意してください。さらに、PWM出力を取得するには、ALT FUN 5に設定する必要があります。

両方のPWMチャネルは同じPWMクロックで駆動され、そのクロック分周器はを使用して変更できますbcm2835_pwm_set_clock()。を使用して、各チャネルを個別に有効にすることができますbcm2835_pwm_set_mode()。PWMチャネルの平均出力は、そのチャネルのDATA / RANGEの比率によって決まります。bcm2835_pwm_set_range()範囲bcm2835_pwm_set_data()を設定し、その比率でデータを設定するために使用し ます

各PWMチャネルは、平衡モードまたはマークスペースモードで実行できます。平衡モードでは、ハードウェアはRANGEパルスごとに全体的なDATAパルスになるクロックパルスの組み合わせを送信します。Mark-Spaceモードでは、ハードウェアは、DATAクロックパルスの出力をHIGHに設定し、RANGE-DATAクロックパルスの出力をLOWに設定します。

PWMクロックは、PWMパルス幅を制御するように設定できます。PWMクロックは19.2MHzクロックから生成されます。任意の分周器を設定できますが、いくつかの一般的な分周器はbcm2835PWMClockDivider

たとえば、DCモーターを約1kHzのPWMで駆動し、速度を0/1024(停止)から1024/1024(フルオン)まで1/1024刻みで制御するとします。その場合、クロック分周器を16に設定し、RANGEを1024に設定します。パルス繰り返し周波数は1.2MHz / 1024 = 1171.875Hzになります。

bcm2835PWMClockDividerシステムクロックからPWMクロックを生成するために使用される分周器を指定します。以下の図は、分周器、クロック周期、およびクロック周波数を示しています。分周されたクロックは、19.2MHzの公称PWMベースクロックレートに基づいています。各分周器に示された周波数は測定によって確認されています

typedef enum
{
    BCM2835_PWM_CLOCK_DIVIDER_2048  = 2048,    /*!< 2048 = 9.375kHz */
    BCM2835_PWM_CLOCK_DIVIDER_1024  = 1024,    /*!< 1024 = 18.75kHz */
    BCM2835_PWM_CLOCK_DIVIDER_512   = 512,     /*!< 512 = 37.5kHz */
    BCM2835_PWM_CLOCK_DIVIDER_256   = 256,     /*!< 256 = 75kHz */
    BCM2835_PWM_CLOCK_DIVIDER_128   = 128,     /*!< 128 = 150kHz */
    BCM2835_PWM_CLOCK_DIVIDER_64    = 64,      /*!< 64 = 300kHz */
    BCM2835_PWM_CLOCK_DIVIDER_32    = 32,      /*!< 32 = 600.0kHz */
    BCM2835_PWM_CLOCK_DIVIDER_16    = 16,      /*!< 16 = 1.2MHz */
    BCM2835_PWM_CLOCK_DIVIDER_8     = 8,       /*!< 8 = 2.4MHz */
    BCM2835_PWM_CLOCK_DIVIDER_4     = 4,       /*!< 4 = 4.8MHz */
    BCM2835_PWM_CLOCK_DIVIDER_2     = 2,       /*!< 2 = 9.6MHz, fastest you can get */
    BCM2835_PWM_CLOCK_DIVIDER_1     = 1        /*!< 1 = 4.6875kHz, same as divider 4096 */
} bcm2835PWMClockDivider;

要約すれば:

  1. ハードウェアPWMが必要な場合-ピン12(BCM18)で立ち往生している場合、他のGPIOピンはソフトウェアPWMを使用します。

  2. 上記のように、ほとんどのユースケースと健全性の理由から、おそらくPWMモードを「Mark-Space」モードに設定する必要があります。

  3. このモードでは、各「パルス」がHIGH対LOWである期間は、PWMデータのPWM範囲に対する比率によって決定されます。これは、PWMクロック速度に関係ありません。

  4. PWM範囲は、事実上、各パルスの「分解能」または考えられる「分割」の数です。分割数が多いほど解像度が高くなり、特定のパルス幅でエンコード可能な状態が多くなります。

  5. 「デューティサイクル」は、PWMデータのPWM範囲に対する比率で、パーセンテージで表されます。PWMデータが8で10のPWM範囲は、80%のデューティサイクルです。

  6. PWMクロック速度は、2の除数の累乗です。したがって、PWMに選択したクロック速度はdivisor & (divisor -1) == 0、12個の有効な値が上記にリストされていますが、

  7. PWMクロック周波数を目的の出力周波数で除算すると、パルス範囲の値が得られます。

  8. オーディオをエンコードし、ピエゾサウンダを使用していたため、ピエゾ振動を最大化してボリュームを最大化するには、50%のデューティサイクルが必要でした。したがって、PWMデータ値は常にPWM範囲値の半分-50%HIGH 50%LOWです。

必要な周波数を計算するには、アプリケーションに適したクロック除数を選択します。私は16を選択しました。これは1.2Mhzに相当します。そう:

Aのノートは440Hz、F#は370Hz、C#は277Hzです

PWMClock = 16; // 1.2Mhz

const A4_RANGE = 1.2e6 / 440;  // 1.2Mhz/440Hz
A4Data = A4_RANGE / 2;

const F4S_RANGE = 1.2e6 / 370;  // 1.2Mhz/370Hz
F4SData = F4S_RANGE / 2;

const C4S_RANGE = 1.2e6 / 277;  // 1.2Mhz/277Hz
C4SData = C4S_RANGE / 2;

PWM範囲は、オクターブ単位で簡単に上下にシフトできます。範囲* 2で1オクターブ下がり、範囲* 0.5で1オクターブ下がります。

たとえば50Hzでサーボを駆動したい場合、同じ範囲の計算が当てはまります。

PWM Range = PWM frequency / Desired Output Frequency

(いくつかの投稿によると、最大PWM範囲の値は4096です。私の経験では、C#を上記のように再生すると、PWM範囲4332が期待どおりに機能するため、これは当てはまりません。)

ほとんどの場合と同様に、方法を知っていれば簡単です。

〜N


3
「ピン12のみ」ビットは26ピンモデルに適用されることに注意してください。40ピンモデルにはさらに3つ(13、18、19)がありますが、まだ2つのクロックチャネルしかなく、ピンはどちらか一方とハードワイヤードに関連付けられています(ピン12と18はチャネル0、13と19はチャネルです) 1); 上記のlibbcm2835で引用されているドキュメントのように、両方のチャネルと4つすべてのピンを構成できます。そのためのALT機能はピンごとに異なります。ここには、Broadcom SoCデータシートから直接取り上げられた表があります。取り消し線の付いたエントリは、40ピンモデルのみです。
ゴルディロックス

7

最近のPi(40ピン拡張ヘッダーと計算モジュールを備えたもの)では、GPIO 12/13/18/19を使用してハードウェアPWM信号を提供できます。

PWMクロックソースは19.2MHzクリスタルである必要はありません。pigpioは500MHz PLLDを使用します。

ハードウェアPWM周波数を設定する簡単なコマンドライン方法については、http://abyz.me.uk/rpi/pigpio/pigs.html#HPを参照してください

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.