7.4  PWM-Ports

Wie wir in der Einleitung ja schon erörtert haben, ist die Ausgabe pulsweitenmodulierter Signale eine Möglichkeit den Übergang von der digitalen in die analoge Welt zu realisieren. Dies wird durch die meisten Prozessoren der MSP430-Serie direkt durch das Timer-Modul unterstützt. Der MSP430F1612 verfügt beispielsweise über zwei I/O-Pins, P1.1 (TA0) und P1.2 (TA1), die eine direkte PWM-Funktionalität besitzen [Tex00b].

7.4.1  Übersicht

Bei einem pulsweitenmodulierten Signal wird eine Periode T0 in N Zeitabschnitte unterteilt. Dabei entspricht N der Anzahl der Quantisierungsstufen zur Auflösung des analogen Signals. Man ist so in der Lage innerhalb einer Periode die Ausgangsspannung so vieler Zeitabschnitte wie gewünscht auf den HIGH-Pegel (zum Beispiel 3.3V) zu setzen. In den restlichen Zeitabschnitten ist die Ausgangsspannung gleich dem LOW-Pegel (0V). Der Spannungsmittelwert einer Taktperiode entspricht dann dem gewünschten analogen Ausgangssignal. Abbildung 7.11 verdeutlicht den zeitlichen Verlauf eines pulsweitenmodulierten Signals mit einer Auflösung von 2 Bit (das entspricht vier Quantisierungsstufen).


PIC

Bild 7.11.: Zeitlicher Verlauf eines 2-Bit-pulsweitenmodulierten Signals. Der PWM-Wert wird in diesem Beispiel in jeder Periode T0 inkrementiert.


In der Mikrocontroller-Schaltungstechnik arbeitet man oft mit pulsweitenmodulierten Signalen, da diese Signale einfach zu erzeugen sind. Echte Digital/Analog-Wandler, wie sie zum Beispiel bei den D/A-Ports eingesetzt werden, sind aufwendiger in der Konzeption und nur die wirklich großen und teuren Modelle der MSP430-Serie haben diese integriert. Oftmals benötigt man aber auch keine wirklich ”glatten” analogen Spannungen. Will man beispielsweise mit einem Mikrocontroller einen Gleichstrommotor ansteuern, so reicht ein pulsweitenmoduliertes Signal auf Grund der Trägheit des Rotors aus, um die Drehzahl des Motors einzustellen. Auch die Helligkeit einer LED lässt sich mit einem pulsweitenmodulierten Signal einstellen. Das Auge ist zu träge, um ein Flackern der LED bei einer ausreichend kurzen Periodendauer des PWM-Signals wahrzunehmen. Stattdessen sieht man je nach PWM-Wert unterschiedliche Helligkeitsstufen.

Einfaches Beispielprogramm

Listing 7.4 zeigt ein einfaches Beispielprogramm unter Verwendung des Timers A (vgl. Kapitel 4.1). Zunächst müssen wir dafür den Port 1 konfigurieren. Die Pins P1.1 und P1.2 mit ihrer Sonderfunktion TA0 und TA1, die für die Bereitstellung des pulsweitenmodulierten Signals zur Verfügung stehen, werden dafür als Ausgänge definiert. Um die Sonderfunktion zu aktivieren, müssen wir darüber hinaus auch die entsprechenden Bits im Function-Select-Register P1SEL setzen.

Nun konfigurieren wir den Timer. Als Taktquelle wird die Sub-Main-Clock SMCLK mit dem Vorteiler 2 gewählt. Damit wird der Timer A mit einer Frequenz von etwa 500kHz betrieben. Der Timer soll so konfiguriert werden, dass er bis zum Wert TACCR0 hochzählt. Ist diese Grenze erreicht, so soll der Port TA0 getoggelt, also invertiert werden. Mit dem Befehl TACTL | = MC0 wird der Timer A dafür in den Up-Modus gesetzt. Mit TACCTL0 = OUTMOD_4 wird der Ausgabe-Modus des Portpins ausgewählt. Die PWM-Frequenz ergibt sich dann zu:

            fPW-M,Takt
fPW M   =       28    = 1953, 125Hz                  (7.1)
Am Pin P1.1 können wir die halbe Frequenz davon messen.

Das eigentliche PWM-Signal soll an Pin P1.2 abgreifbar sein. Dafür müssen wir zuerst den Ausgang aktivieren und mit dem Timer verbinden. Wir laden nun unsere Digitalzahl in das TACCR1-Register und setzen den OUTMOD = 7. Damit ist, solange der Timer-Wert kleiner als TACCR1 ist, der Ausgang HIGH, wechselt ab TACCR1 zu LOW und wird erst wieder HIGH, wenn der Timer-Wert TACCR0 erreicht und der Timer wieder von 0 beginnt. Nachlesen kann man das auch gut in der Abbildung 4.9 in Kapitel 4.1.

Die Signale des Beispiels lassen sich am besten mit einem Oszilloskop (oder der Soundkarte des PCs) verfolgen. Alternativ kann man die Helligkeit einer angeschlossenen LED in Abhängigkeit von der PWM beobachten. Der dem PWM-Signal entsprechende digitale Wert wird dabei in der Variable dutyCyclePercent abgelegt und in der WHILE-Schleife jeweils um 1% erhöht.

#include <msp430x16x.h> 
int main( void ) 
{ 
  int i; 
  int dutyCyclePercent = 0;    // Duty-Cycle 
 
  WDTCTL  = WDTPW | WDTHOLD;   // Watch-Dog ausschalten 
 
  P1DIR   = BIT1 | BIT3;       // PWM-Port initialisieren 
  P1SEL   = BIT1 | BIT3; 
 
  TACTL   = TASSEL_2 | ID_1;   // SMCLK/2 als PWM-Frequenz 
  TACCTL0 = OUTMOD_4;          // Toggle wenn TACCR0 
  TACCTL1 = OUTMOD_7;          // RESET/SET-Mode 
 
  TACCR0  = 256; 
  TACTL  |= MC_1;              // Timer im UP-Mode starten 
 
  while( 1 ) 
  { 
    TACCR1 = dutyCyclePercent * TACCR0 / 100; 
    dutyCyclePercent += 1;    // Duty-Cycle um 1 erhöhen 
    if( dutyCyclePercent > 100 ) 
      { dutyCyclePercent = 0; } 
  } 
}
Listing 7.4: Einfaches Beispielprogramm zur PWM-Ausgabe

7.4.2  Dimensionierung des Ausgangsfilters

Manchmal benötigt man eine ”glatte” analoge Spannung. Wenn die D/A-Ports schon für andere Anwendungen verwendet werden oder nicht vorhanden sind, so kann man mit Hilfe eines passiven oder aktiven Filters aus einem pulsweitenmodulierten Signal eine ”glatte” analoge Spannung ohne Oberwellen erzeugen. Dabei sollte jedoch berücksichtigt werden, dass die Ausgangsspannung immer noch werte- und zeitdiskret vorliegt. Gleichzeitig sollte man beachten, dass bei der Verwendung eines aktiven und vor allem bei der Verwendung eines passiven RC-Filters immer eine (wenn auch teils geringe) Restwelligkeit im Signal messbar ist. Auf der anderen Seite verringert man durch den Ausgangsfilter die erreichbare Dynamik des Ausgangssignals.

Passiver RC-Filter

Das passive RC-Filter, das in Bild 7.12 dargestellt ist, zeigt einen Tiefpassfilter. Das Ausgangssignal kann an der Klemme uA abgegriffen werden. Dabei sollte man darauf achten, dass eine angeschlossene Last die Schaltung und damit auch die Filtereigenschaften verändern kann.


PIC

Bild 7.12.: Passives RC-Filter zur Erzeugung einer glatten analogen Ausgangsspannung


Die Wahl der passenden Bauteilgrößen für den Widerstand R und die Kapazität C ist entscheidend für die Güte der erzeugten Ausgangsspannung. Dazu müssen wir zunächst die Grenzfrequenz der Schaltung 7.12 bestimmen. Mit Hilfe der Spannungsteilerregel erhalten wir:

                  -1--
   uA   =  uE ⋅ -1jωC---                       (7.2)
                jωC + R
   uA-      ----1-----
⇒  uE   =   1+ jωRC                            (7.3)

Die Grenzfrequenz fG ist als die Frequenz definiert, bei der der Betrag der Übertragungsfunktion von uAuE um 3dB (also das 1√ --
  2-fache) abgefallen ist. Dann wird

           1
fG   =   -----.                            (7.4)
         2πCR

Die PWM-Frequenz unseres Programmierbeispiels beträgt etwa 1950Hz. Wählen wir beispielsweise C1 = 100nF und R1 = 100, so erhalten wir eine Grenzfrequenz des Filters von etwa fG = 16Hz. Somit hat unser Filter an der PWM-Frequenz eine Dämpfung von etwa 20dB. Misst man mit einem Oszilloskop das Ausgangssignal, würde man trotzdem eine recht hohe Restwelligkeit, die man häufig auch Ripple nennt, von bis zu V Ripple = 42mV feststellen. Mit Hilfe der Faustformel

V       ≈   -----VCC-------                      (7.5)
  Ripple     4 ⋅fPW M ⋅R ⋅C
lässt sich die Größe der Restwelligkeit in erster Näherung gut abschätzen. Die Gleichung 7.5 lässt sich nicht analytisch herleiten, weil die Restwelligkeit vom PWM-Wert (also vom Duty-Cycle) abhängt. Bei einem PWM-Wert von 0 oder 255 ist die Restwelligkeit gerade 0, weil das PWM-Signal dann genau der entsprechenden analogen Ausgangsspannung 0V bzw. 3.3V entspricht. Die größte Restwelligkeit erhält man bei einem Duty-Cycle-Wert von 50%, was einem PWM-Wert von 128 entspricht. Mit einer Auflösung von 8 Bit bei einer maximalen Spannung von 3.3V würden wir theoretisch eine Spannung mit einer Genauigkeit von etwa 13mV auflösen können. Durch die Wahl der Bauteile des passiven Tiefpasses haben wir also die Auflösung um mehr als den Faktor 3 verschlechtert. Um die Genauigkeit und damit auch die Güte der analogen Ausgangsspannung zu verbessern, müssen wir also entweder einen höheren Widerstands- oder Kapazitätswert wählen. Mit C = 100nF und V CC = 3.3V und Restwelligkeit maximal V Ripple = 10mV erhalten wir für den Widerstand
R  =   --------VCC---------= 423,1kΩ.                 (7.6)
       4 ⋅fPW M ⋅VRipple ⋅ C

Für R käme also ein Widerstand von rund 470 in Frage. Dabei verändert sich jedoch auch die Grenzfrequenz zu fG = 3.38Hz. Unter Umständen beschränkt dies den Dynamikbereich des Ausgangssignals zu sehr. Für sich schnell ändernde analoge Spannungen eignet sich dieser passive Tiefpass somit nicht.

Aktives Filter

Um eine höhere Bandbreite des Analogsignals bei gleichzeitiger Dämpfung der Welligkeit zu erhalten, kann man Tiefpässe höherer Ordnung verwenden. Da passive Tiefpässe jedoch nicht sehr gut hintereinander geschaltet werden können, bietet sich ein universelles Koeffizientenglied wie die in Abbildung 7.13 dargestellte so genannte ”Sallen-Key-” Schaltung an.


PIC

Bild 7.13.: Aktiver ”Sallen-Key” Tiefpass 2. Ordnung


Mit dieser Schaltung können komplexe Filter, wie zum Beispiel Bessel- oder Butterworth-Filter realisiert werden. Die genaue Berechnung der Koeffizienten dafür würde aber an dieser Stelle den Rahmen unseres Buches sprengen. Sehr gut ist dies beispielsweise in dem schon mehrfach zitierten Buch [TSG02] beschrieben.

Die Übertragungsfunktion des Filters ist gegeben durch:

         uA(s)-  ---------------1---------------
G (s) =   uE(s) = C1C2R1R2s2  + C2 (R1 + R2 )s+ 1
(7.7)

Für einen einfachen Filter 2. Ordnung können bei einer PWM-Frequenz von etwa 1950Hz R1 = R2 = 33 und C1 = C2 = 470nF gewählt werden.