Hallo liebe Mikrocontroller, ich sitze jetzt schon ne woche vor nem problem, nämlich möchte ich ein pwm-signal erzeugen welches zur Motoransteuerung geeignet ist, sprich ein PWM das seinen Dutycycle kontinuierlich verändert. (In PSpice durch Vergleich von Dreieckspannung und Sinus). Ich habe zum Programmieren den TMS320F2808, ein PWM Signal auszugeben stellt kein Problem mehr dar, jedoch ich weiß nicht wie ich es anstellen soll das man praktisch wie in pspice das Dreiecksignal (ich nehm mal an das ist beim 2808 dann das UP-DOWN-Count Signal) mit einer Sinusspannung zu vergleichen, und jenachdem den Dutycycle verändert, sodass ich am ausgang dann wie im beigefügten bild eine rechteckspannung hab (negative halbwelle nat. keine negative spannung sondern einfach weniger highphasen) die wenn ich über einen entsprechenden Tiefpass gebe wieder ein "schönes" Sinus Signal rausbekomme. Hoffe damit hat schon jemand Erfahrung gesammelt. Grüße Tom
Für diese Art von Signal braucht der Sinus einen Gleichanteil in Höhe der Amplitude, dann schwingt er von 2*Amplitude bis 0 hin und her.
Wie du richtig geschrieben hast stellt der Timer-Wert (z.B. Up-/Down-Count-Mode) einen der beiden Vergleichswerte dar und gleichzeitig die Schaltfrequenz. Den anderen Vergleichswert musst du selbst ins Compare-Register schreiben. Wenn du einen festen Wert im Compare-Register stehen hast wird sich ein fester Pegel einstellen, mehr nicht. Daher musst du den Compare-Wert verändern und zwar je nach gewünschter Ausgangsfrequenz und Auflösung/Genauigkeit/Signalverlauf (und Schaltfrequenz). Ob du diese veränderlichen Werte aus einer Tabelle nimmst oder jedesmal neu berechnest bleibt dir überlassen. Du wirst dafür eine zweite Zeitbasis brauchen, die dir vorgibt wann du den Compare-Wert verändern musst. Vielleicht hilft dir auch der Artikel DDS und die Links dort weiter.
Ob du diese > veränderlichen Werte aus einer Tabelle nimmst oder jedesmal neu > berechnest bleibt dir überlassen. Du wirst dafür eine zweite Zeitbasis > brauchen, die dir vorgibt wann du den Compare-Wert verändern musst. Schonmal Danke für die Antwort Michael, aber ich kann mir nicht richtig vorstellen wie ich den Wert für das Compare-Register berechnen soll und dann zur richtigen Zeit in das Register schreiben soll (Also das neue schreiben dann evtl. wenn der Counter = 0 ist, dann könnte man das ja gleich ins active Register anstatt in das shadow register schreiben, sodass es gleich benutzt werden kann). Vom Verständis her hab ichs glaub ich schon einigermaßen begriffen, aber es scheitert halt gnadenlos an der Umsetzung.=( Wäre für jede weitere Hilfe sehr dankbar! Grüße Tom
Der Wert, der in das Compareregister geschrieben wird, ist direkt proportional zu der Spannung die du dem Motor an der jeweiligen Phase geben möchtest. Es gibt es verschiedene Methoden, wie man die Spannung der drei Motorphasen vorgibt. Ich zähle mal ein paar auf: 1.) u/f=const 2.) (u-Unull)/f=const 3.) Stromregelung mit Feldorientierung und Encoder 4.) Stromregelung mit Feldorientierung nach Rotorpositionsschätzung Jetzt kann man noch weiter optimieren, schließlich kann man den Motorsternpunkt verschieben, ohne, dass das eine negative Auswirkung hat. Stichwort Raumzeigermodulation. >dann könnte man das ja >gleich ins active Register anstatt in das shadow register schreiben, >sodass es gleich benutzt werden kann Das ist keine so gute Idee. Prinzipiell ist es aber richtig, dass das Register bei jedem Timerduchlauf einmal geschrieben wird. Grüße, Peter
> Ich zähle mal ein paar auf: > 1.) u/f=const > 2.) (u-Unull)/f=const > 3.) Stromregelung mit Feldorientierung und Encoder > 4.) Stromregelung mit Feldorientierung nach Rotorpositionsschätzung Hallo Peter, ja eine der Methoden hab ich auch vor in Zunkunft umzusetzen nämlich die Stromregelung mit Feldorientierung und Encoder. Aber jetzt am Anfang möchte ich erst versuchen das "Sinus"PWM Signal zu erzeugen, bevor ich weitere schritte mache. > Der Wert, der in das Compareregister geschrieben wird, ist direkt > proportional zu der Spannung die du dem Motor an der jeweiligen Phase > geben möchtest. Aber hier liegt noch mein Problem, ich weiß nicht wie ich das umsetzen soll damit ich, wie in meinem angehängten Bild ganz oben, das Compare Register zu jeder neuen Periode des UP-DOWN-Counters so beschreibe damit das ausgegebene PWM Signal bei einer Tiefpassfilterung auch wieder eine Sinusform bekommt. Also Praktisch wie berechne ich zu jeder neuen Periode meinen dutycycle. Wahrscheinlich ist das problem so simple zu lösen, aber weiß leider nicht wie.=( grüße tom
Als erstes musst du einen Interrupt einrichten, der immer dann auslöst, wenn das Zählregister einmal durchgelaufen ist. Üblicherweise lässt man den triggern, wenn der Zähler 0 erreicht. Damit ist die Zeitbasis für die Modulationsfrequenz festgesetzt und man erhält eine Funktion (den Interrupt), die immer dann aufgerufen wird, wenn ein neuer Puls ausgegeben wird. Dort hat man die Möglichkeit das shadowregister zu schreiben. Dieser Interrupt kommt regelmäßig immer nach der gleichen Zeit. Dadurch hat man zusätzlich die Information, wie viel Zeit vergangen ist, wenn man mitzählt, wie oft der Interrupt aufgetreten ist. Wenn man diese Zeit jetzt kennt und eventuell sogar in Mikrosekunden oder was auch immer umrechnet, kann man sie direkt für die Erzeugung des Sinus verwenden: U = Unull * sin (omega * t + phi); Omega ist hier die gewünschte Ausgangsfrequenz, Unull die gewünschte Amplitude. Man muss nur ein bisschen mit den Einheiten aufpassen: Spannungen sind hier in counts des Timers anzugeben und die Kreisfrequenz so, dass das mit der Einheit der Zeit t klappt. Diese Berechnung macht man für alle 3 Phasen mit der jeweils richtigen Phasenverschiebung phi (0°, 120°, 240°). Achtung: t sollte niemals überlaufen oder man muss einen Überlauf handhaben können. Das war die Methode mit dem direkt berechneten Sinus. Damit das Programm schneller läuft (wenn die Rechenzeit für den Sinus nicht reicht), kann man Sinustabellen verwenden, anstatt in Echtzeit zu rechnen. Komplizierter wird es dann, wenn sich die Frequenz über die Zeit ändert. Dann sollte man eine komplexe Zeigerdarstellung verwenden und in jedem Zeitschritt eine Drehoperation mit der gewünschten Winkelgeschwindigkeit ausführen. Der Realteil des Zeigers ergibt die gewünschte Spannung. Das multipliziert man dann noch mit der gewünschten Amplitude und schreibt es in das shadowregister. Hier genauso getrennt für alle 3 Phasen. Die Phasenverschiebung von 120° kann man beispielsweise durch eine Drehoperation auf den Raumzeiger erreichen. Das Ergebnis ist eine dreiphasen-Pulsweitenmodulation nach dem Unterschwingungsverfahren, wobei der Motorsternpunkt im schnellen zeitlichen Mittel spannungsfrei ist. Um einen höheren Modulationsindex (mehr Spannung am Motor) zu erreichen, braucht man dann weitere Optimierungen. Aber ich denke, es ist schon noch ein bisschen Programmierarbeit bis dahin. Es gibt da dann auch noch einige mathematische Werkzeuge, die einem die Zeigerrechnung vereinfachen. Wichtig sind die folgenden beiden, die sollte man sich genau anschauen: -Clarke transformation -Park transformation Dazu gibts ein Paper von TI: http://www.ti.com/sc/docs/psheets/abstract/apps/bpra073.htm Und einige von Atmel: http://www.atmel.com/dyn/resources/prod_documents/doc7545.pdf http://www.atmel.com/dyn/resources/prod_documents/doc7546.pdf http://www.atmel.com/dyn/resources/prod_documents/doc32126.pdf Ich hoffe, das genügt vorerst um die ersten Versuche zum Laufen zu bekommen. Ein Oszilloskop mit mindestens 4 Kanälen ist dabei sehr hilfreich. Mit 3 Kanälen kann man die PWM-Kanäle anschauen und mit dem 4 irgendeinen Hilfspin am Controller um z.B. bestimmte Events (Timerüberlauf...) anzuzeigen.
Hi Thomas, auf der TI Seite findest Du auch eine Digital Motor Control Library die du dir frei runterladen kannst. Unter anderem enthält die Lib den Quellcode von allen möglichen Funktionen (auch von der Raumzeigermodulation (SVM = space Vector Modulation)) und auch eine relativ ausführlich PDF Doku zu den einzelnen Funktionsblöcken. Vielleicht hilft dir die Lib weiter. Gruß, Ralf
Hallo zusammen, vielen Dank für die Beitrage, helfen weiter!! Jetzt steh ich vor dem Problem wie ich den Sinus in Code Composer ausrechnen soll. Die eingebundene "IQMathLib.h" scheint irgendwie das nicht zu haben, weil er weiterhin fehler bringt den funktionsaufruf nicht zu kennen?! weiß für dieses Problem noch jemand rat?? Vielen Dank an die freundliche Unterstützung!! Viele Grüße Tom
Hi Tom, mit der IQMath Lib kenne ich mich nicht im Detail aus, d.h. ich habe sie noch nie verwendet weil ich keine TI Prozessoren einsetze. Aber ich mache das normalerweise mit einer look-up-table. D.h. ich habe im Code eine Tabelle mit z.B. 1024 Einträgen die vorberechnete Sinuswerte enthält. Die Sinuswerte sind im Festkommaformat berechnet, d.h. sin(90°)=1=32767=0x7FFF und sin(270°)=-1=-32768=0x8000. Weiterhin verwende ich eine 16Bit Winkelvariable die Winkel im Bereich von 0 bis 65535 entsprechend 0 bis 360° speichert. Möchte ich nun den Sinus berechnen, so nehme ich einfach die oberen zehn Bit meiner Winkelvariable und nehme diese als Index in der Sinustabelle. Dieses Element ist dann der Sinuswert. Den Cosinus berechne ich gleich, nur mit einem Offset von 90°, d.h. Winkelvariable + 16384. Viele Grüße, Ralf
IQmath muss man erst installieren. Hier die Beschreibung: http://focus.ti.com/lit/sw/sprc990/sprc990.pdf Und hier gibt es den Download: http://focus.ti.com/docs/toolsw/folders/print/sprc087.html Grüße, Peter
Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.