Forum: Projekte & Code hardware-pwm mit variabler auflösung in xilinx cpld


von G. O. (aminox86)


Angehängte Dateien:

Lesenswert?

Anbei der VHDL-Code für einen PWM-Generator, den ich in einem XC9572 
untergebracht habe. Der Code beruht zum größten Teil auf der Atmel 
AppNote 2324.pdf 
http://www.atmel.com/dyn/resources/prod_documents/DOC2324.PDF
Hintergrund:
Als hartgesottener 8051-Fan will ich eine PWM_Motoransteuerung mit einem 
8051-Derivat aufbauen. Da der einfache 8051 bekanntermaßen über keine 
PWM-Eiheit verfügt und auch sonst nicht gerade der schnellste ist, habe 
ich mich nach einer Hardwarelösung sowohl im Netz als auch hier im Forum 
umgeschaut und bin auf besagtes Papier von Atmel gestossen. Dort ist der 
VHDL-Code für einen PWM-Generator beschrieben, dessen Auflösung durch 
einige marginale Änderungen am Quelltext offensichtlich beliebig 
angepasst werden kann.
Folgendes ist am originalen Quelltext geändert( das zugehörige 
User-Package bleibt !!unverändert!! und muß für die Entwicklungsumgebung 
erreichbar sein):
- Erweiterung der Auflösung auf 16 Bit, wovon zZt 11 Bit genutzt werden
- PWM-Daten werden seriell statt parallel eingelesen
- Chip-Select zur Bausteinauswahl eingeführt
- einige Konstanten wegen besserer Übersicht eingeführt
Den Code habe ich mit der ISE, Version 8 Servicepack 3, compiliert. Das 
JED-File passt geradeso in einen XC9536, in einem XC9572 könnte man 
vermutlich 2 PWM-Module unterbringen.
Wie bereits erwähnt wird der CPLD von einem 8051, in diesem speziellen 
Fall von einem DS89C450, angesteuert. Der Baustein ist mit der zweiten 
seriellen Schnittstelle des Prozessors verbunden, die im Modus 
0(=sysnchrone 8 Bit Datenübertragung, Standartkonfiguration nach Reset), 
arbeitet.
Um die Arbeit mit dem PWM-Generator zu verdeutlichen, hier noch ein 
Code-Schipsel(Flag- und Registerbezeichnungen aus Prozessordatenblatt):
1
#define LSB             0
2
#define MSB             1
3
#define AKTIV           0
4
#define NICHT_AKTIV     1
5
#define PWM_SELECT(x)   P.n=x
6
7
union u{ unsigned      pwm;        
8
         unsigned char p[2];}pwm; /*wg 8 bit senderegisterbreite*/
9
10
void pwm_out(void);
11
12
void main(void)
13
{ .
14
  .
15
 pwm.pwm=2048;                    /*maximalwert bei bei 11 bit auflösung*/
16
 pwm_out();
17
 while(1);
18
}
19
20
void pwm_out(void)
21
{ PWM_SELECT(AKTIV);              
22
  TI_1=0;                          /*tx-flag immer löschen*/
23
  SBUF1=pwm.p[LSB];                /*lsb senden*/
24
  while(!TI_1);                    /*auf tx warten*/
25
  TI_1=0;
26
  SBUF1=pwm.p[MSB];                /*msb senden*/
27
  while(!TI_1);                    /*wieder auf tx warten*/
28
  PWM_SELECT(NICHT_AKTIV);         /*16 bit gesendet-> fertig*/
29
}

mfg

von Chris B. (Gast)


Lesenswert?

Und damit kann man jetzt genau was machen?

Du hast nur den Code modifiziert, ist das richtig?

von G. O. (aminox86)


Lesenswert?

Chris B. schrieb:
> Und damit kann man jetzt genau was machen?
Erstaunliche Frage. Wenn ich 'PWM' lese, dann fällt mir sofort H-Brücke, 
Schaltnetzteil, Led dimmen usw. ein. In meinem speziellen Fall ist das 
CPLD mit zwei Halbbrückentreibern verbunden, die eine H-Brücke 
ansteuern.
> Du hast nur den Code modifiziert, ist das richtig?
Ja, das ist richtig. Danach habe ich den Code compiliert, in das CPLD 
übertragen und in die Schaltung eingesetzt. Dort verhält sich das CPLD 
wie erwartet.
mfg

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
Noch kein Account? Hier anmelden.