Sie sind auf Seite 1von 84

Mikrocontroller

Umdruck zur Vorlesung mit integrierter Übung

Prof. Dr.-Ing. R. Roskam Februar 2009

Einleitung

Dieses Skript gibt den Inhalt der Vorlesung "Mikrocontroller" wieder. Die Vorlesung wird im Fachbereich Maschinenbau an der Fachhochschule Braunschweig/Wolfenbüttel in der Vertie- fungsrichtung Mechatronik gelehrt. Voraussetzung zum Verständnis der Vorlesung sind Grund- kenntnisse der Elektrotechnik und Informatik, wie sie im Grundstudium eines ingenieurwissen- schaftlichen Studiengangs gelehrt werden.

Ziel der Vorlesung ist es, die Studenten in der Lage zu versetzen, die Funktionsweise eines Mik- rocontrollers auf mechatronische Systeme anwenden zu können.

Roter Faden

Die wesentlichen Begriffe und Stichworte zum Inhalt werden am Textrand des Skriptes darge- stellt, so dass schnell eine Übersicht gewonnen werden kann. Ich wünsche allen, die mit diesem Skript arbeiten, viel Spaß beim Lesen und zugleich beim Lernen.

Wolfenbüttel, Februar 2009.

Rolf Roskam

r.roskam@fh-wolfenbuettel.de

1

Inhaltsverzeichnis

1 Einleitung

 

1

2 Grundlagen

2

2.1 Digitale Zustandsinformation

2

2.2 Informationsdarstellung

5

2.3 Informationsverarbeitung

9

3 Entwicklungsumgebung für Mikrocontroller

11

3.1 Programmierung von Mikrocontrollern

11

3.2 Programmer

14

3.3 Debugger

14

3.4 Debugger Accemic MDE

15

4 Speicher

19

5 IO-Ansteuerung

 

25

6 Strukturierte Programmierung

32

7 Timer

41

8 D/A-Wandler

 

45

9 PWM Ansteuerung

48

10 A/D-Wandler und Interruptfunktion

57

11 Lösungen ohne Kommentar

67

12 Literatur

74

13 Anlage

75

13.1 Funktionsschema Mechatronic Evaluation Board (MEB)

75

13.2 Schaltplan Mechatronic Evaluation Board

 

77

13.3 Funktionsweise Treiberbaustein 6206Fehler!

Textmarke

nicht

definiert.

13.4

Funktionsweise Up-/Down-Counter PE 12024

80

1

Einleitung

1

Mechatronische Systeme setzen sich aus den 3 Teildisziplinen Informatik, Elektro- nik und Mechanik zusammen. Ein typisches Beispiel eines mechatronischen Sys- tems zeigt Bild 1.1.

Informatik Elektronik Elektronik Elektronik Mechanik Regelung Aktoren Aktoren Aktoren + - Software Hardware
Informatik
Elektronik
Elektronik
Elektronik
Mechanik
Regelung
Aktoren
Aktoren
Aktoren
+
-
Software
Hardware
Hardware
Hardware
Sensoren
Sensoren

Bild 1.1: Mechatronisches System

Zwischen dem Sollwertgeber, in diesem Fall der Fahrer eines PKWs, und der ei- gentlichen Mechanik existiert bei mechatronischen Systemen ein informationsver- arbeitendes Modul, welches sich aus Hard- und Software zusammensetzt. Herz- stück dieses Moduls ist der Mikrocontroller, der Schnittstellen zu Aktoren und Sensoren zur Verfügung stellt. Die Informationen der Sensoren werden über ein Programm, welches vom Mikrocontroller abgearbeitet wird, eingelesen und verar- beitet. Das Ergebnis dieser Verarbeitung dient zur Ansteuerung der Aktoren.

Der Mikrocontroller stellt damit die Schnittstelle zwischen den Disziplinen Infor- matik und Elektronik dar (Bild 1.2). Da jede Schnittstelle erfahrungsgemäß Ein- schränkungen mit sich bringt, müssen Ingenieure der Mechatronik diese Ein- schränkungen kennen. Hierzu ist es erforderlich, die Funktionsweise eines Mikro- controllers zu kennen und auf mechatronische Systeme anwenden zu können.

Vorlesung:

Antriebe

Messtechnik

Systeme anwenden zu können. Vorlesung: Antriebe Messtechnik Mechanik Vorlesung: Regelungstechnik Simulation Aktoren

Mechanik

Vorlesung:

Regelungstechnik

Simulation

Aktoren Sensoren Elektronik
Aktoren
Sensoren
Elektronik

Systemtheorie

Mikrocontroller

InformatikAktoren Sensoren Elektronik Systemtheorie Mikrocontroller Vorlesung: Vorlesung: Vorlesung: Elektrotechnik

Vorlesung:

Vorlesung:

Vorlesung:

Elektrotechnik

Mikrocontroller

Informatik

Schaltungstechnik

Steuerungstechnik

Bild 1.2: Grunddisziplinen der Mechatronik und deren Schnittstellen

In dieser Vorlesung werden zunächst einige Grundlagen wiederholt, die dem Leser bereits aus Vorlesungen der Elektrotechnik und Informatik bekannt sein sollten. Hierbei wird ebenfalls ein gewisses Maß an Grundlagenwissen der C- Programmierung vorausgesetzt. Anschließend erfolgt eine Einführung in den Auf- bau und die Funktionsweise eines Mikroprozessors, der als Teilsystem des Mikro- controllers die Informationsverarbeitung übernimmt. In dem darauf folgenden Ka- piteln folgt der Schwerpunkt dieser Vorlesung, nämlich die Vorstellung typischer Schnittstellen eines Mikrocontrollers. Die Darstellung der Schnittstellen wird in Verbindung mit realen Anwendungen vertieft, die im vorlesungsbegleitenden La- bor in die Praxis umgesetzt werden. Als wichtige Schnittstelle wird als Bussystems exemplarisch der CAN-Bus vorgestellt. Abgerundet wird die Vorlesung durch ei- nen Einblick in den Softwareentwicklungsprozess für Mikrocontroller.

2

Grundlagen

2

2.1 Digitale Zustandsinformation

Die grundsätzliche Informationsverarbeitung mit Mikrocontrollern basiert auf digi- tale Spannungssignale, die den Zustand 0 (low) oder 1 (high) annehmen können (Bild 2.1).

U

Zustand 0 (low) oder 1 (high) annehmen können (Bild 2.1). U 2 Zustände: 0 low Lampe

2 Zustände:

0 low

Lampe aus

U = 0V

1 high

Lampe an

U = U 0

Bild 2.1: Digitale Zustandsinformation

Man spricht von dem Bit (binary digit) als kleinste Dateneinheit. Um eines sichere Verarbeitung der Zustände zu gewährleisten, wurden Spannungsbereiche für die Zustände 0 (low) und 1 (high) definiert, die je nach Technologie in bestimmten Bereichen definiert wurden (Bild 2.2)

Baustein 1 A E Baustein 2
Baustein 1
A
E Baustein 2

GND

TTL transistor transistor logic

CMOS complementary metal oxide semiconductor

GND 0 0,4 0,8 1,5 2,4 3,5 5 U (V) Ausgang Eingang Ausgang 0,05 4,95
GND
0
0,4
0,8
1,5
2,4
3,5
5
U (V)
Ausgang
Eingang
Ausgang
0,05
4,95
Eingang

Bild 2.2: Spannungsbereiche für digitale Zustände /1/

Üblicherweise wird nur die Verbindung von einem Baustein zum nächsten betrach- tet, die allgemeine Masseleitung, an der alle Bausteine angeschlossen sind, wird häufig nicht weiter erwähnt.

CMOS-Bausteine haben gegenüber TTL-Bausteine den Vorteil geringerer Leis- tungsaufnahme (µW anstelle von mW). Neueste Bausteine verwenden HC/HCT- Technologie, die den Vorteil geringer Leistungsaufnahme mit den Spannungsbe- reichen der TTL-Bausteine verbinden.

Soll vom Zustand 0 auf den Zustand 1 geschaltet werden, so durchläuft die Span- nung in Abhängigkeit der Zeit den undefinierten Bereich zwischen 2 Zuständen (Bild 2.3). Oberhalb von 0,8V und unterhalb von 2V erkennt der 2. Baustein den Eingang als ungültig. Dieser Zeitraum sollte daher möglichst schnell durchschritten werden. Eine entscheidende Kenngröße ist dabei die Schaltverzögerungszeit t p (propagation delay time), in der das Signal zwischen 10% und 90% des endgülti- gen Spannungssignals durchlaufen hat. Typische Werte für HCT-Bausteine liegen im Bereich von wenigen ns.

Bit

0 – low

1 – high

TTL

CMOS

HC/HCT

propagation

delay time

3 U (V) 5,0 high 90% 2,0 t p 0,8 10% low t
3
U (V)
5,0
high
90%
2,0
t p
0,8
10%
low
t

Bild 2.3: Zustandswechsel von low nach high

Werden externe Signale (z.B. Schalter) an einen HCT-Baustein angelegt, so sollte der Zustandswechsel des externen Signals in der Schaltzeit des HCT-Bausteins liegen. Durch kapazitive Effekte (z.B. langes Kabel zum Schalter) können jedoch größere Schaltzeiten auftreten. In diesem Fall ist ein Schmitt-Trigger vorzusehen (Bild 2.4).

5V R Schmitt- E A Trigger C 5V R C
5V
R
Schmitt-
E
A
Trigger
C
5V
R
C

U (V)

5,0

high τ low t
high
τ
low
t

2,0

0,8

Schmitt-Trigger

Bild 2.4: Schmitt-Trigger

Obwohl die Schaltzeiten nur wenige ns betragen, besteht dennoch die Gefahr unde- finierte Schaltzustände zu verarbeiten. Aus diesem Grund werden digitale Systeme der Datenverarbeitung getaktet. Hierzu existiert ein zentraler Taktgenerator, der ein Rechtecksignal erzeugt. Eine Verarbeitung der Information und damit ein Zu- standswechsel des Ausgangs der einzelnen Bausteine erfolgt immer nur zur stei- genden Flanke des Taktsignals.

t c U Taktgenerator t Baustein 1 Baustein 2 Baustein 3
t c
U
Taktgenerator
t
Baustein 1
Baustein 2
Baustein 3

Takt

Bild 2.5: Getaktete Informationsverarbeitung

Die Taktzeit t c muss somit größer sein als die Schaltverzögerungszeit t p der einzel- nen Bausteine. Taktfrequenzen moderner Mikrocontroller liegen im Bereich von 10…100 MHz, so dass sich eine Taktzeit von 100…10ns ergibt.

4

Beim Ausgang eines Bausteins werden 2 Prinzipien unterschieden:

Tri-state

Open collector

Tri-State

Baustein 1 5V T1 CS T2 GND Baustein 2 5V T1 CS T2 GND
Baustein 1
5V
T1
CS
T2
GND
Baustein 2
5V
T1
CS
T2
GND

Open Collector

5V Baustein 1 R T GND Baustein 2 T GND
5V
Baustein 1
R
T
GND
Baustein 2
T
GND

Bild 2.6: Ausgänge digitaler Bausteine

Beim Tri-State Ausgang existieren 3 mögliche Zustände:

Ausgang auf high, T1 ist durchgeschaltet

Ausgang auf low, T2 ist durchgeschaltet

Ausgang hochohmig, kein Transistor wird angesteuert

Werden mehrere Ausgänge parallel auf eine Leitung geschaltet, muss über einen zusätzlichen Eingang (CS: chip select, auch CE chip enable) selektiert werden, welcher Baustein gerade aktiv ist und die Leitung auf low oder high schalten darf. Sonst könnte ein Baustein T1 ansteuern, ein anderer T2 und damit einen Kurz- schluss mit der Zerstörung der Transistoren der Ausgangsstufe.

Beim Open-Collector Ausgang existiert am Ausgang nur ein Transistor, der den Ausgang entweder hochohmig oder auf low schalten kann. Damit überhaupt ein high Signal erzeugt werden kann, muss die Ausgangsleitung über einen so genann- ten Pull-Up-Widerstand auf 5V Pegel gelegt werden. Werden mehrere Ausgänge parallel geschaltet, ist ein separater CS-Eingang nicht erforderlich. Durch den OC- Ausgang wird indirekt eine UND-Verknüpfung realisiert (Tabelle 2.1).

Baustein 1

Baustein 2

Ausgang

0

0

0

0

1

0

1

0

0

1

1

1

Tri-State

Open Collector

Chip Select/Enable Pull-Up-Widerstand

Tabelle 2.1: Ausgang mehrerer OC-Bausteine

Verwendet wird der OC-Ausgang häufig zur Meldung eines Fehlers, der mit dem Zustand 0 signalisiert wird. Im fehlerfreien Betrieb liegt auf der gemeinsamen Lei- tung über den Pull-Up Widerstand 5V an. Sobald ein Baustein einen Fehler auf- weist, wird dieser über das Schalten des Transistors signalisiert und die gemeinsa- me Leitung nimmt den Zustand 0 an.

2.2

Informationsdarstellung

5

Mit einer Leitung können somit nur 2 Informationen (0/1) dargestellt werden. Um jedoch Zahlen oder Buchstaben abbilden zu können, müssen mehrere Informatio- nen darstellbar sein. Hierzu werden mehrere Leitungen parallel geschaltet.

D7 D6 D5 D4 D3 D2 D1 D0 Zustand
D7
D6
D5
D4
D3
D2
D1
D0
Zustand

0

0

0

0

0

0

0

0

= 0

0

0

0

0

0

0

0

1

= 1

0

0

0

0

0

0

1

0

= 2

0

0

0

0

0

0

1

1

= 3

 
 
 
 

1

1

1

1

1

1

1

0

= 254

1

1

1

1

1

1

1

1

= 255

2 8 = 256 Zustände

Bild 2.7: Parallelisierung von Datenleitungen

Die Anzahl möglicher Zustände n wird berechnet aus der Anzahl der zur Verfü- gung stehenden Leitungen k zu:

(1)

Der sich aus den einzelnen Leitungen D7…D0 ergebende Zustand wird aus dem Dualzahlensystem berechnet (Bild 2.8). Bei der Entwicklung auf einem PC kann der im Betriebssystem Window unter Zubehör vorhandene Rechner in der Ansicht „Wissenschaftlich“ genutzt werden.

n = 2

k

MSB

 

LSB

D7

D6

D5

D4

D3

D2

D1

D0

1

0

1

1

0

1

0

1

2

7

2

6

2

5

2

4

2

3

2

2

2

1

2

0

1x2 7

0x2 6

1x2 5

1x2 4

0x2 3

1x2 2

0x2 1

1x2 0

1x128

0x64

1x32

0x16

0x8

1x4

0x2

1x1

= 181

1x32 0x16 0x8 1x4 0x2 1 x 1 = 181 Bild 2.8: Umrechnung Binär in Dezimal

Bild 2.8: Umrechnung Binär in Dezimal

Man bezeichnet das Bit mit dem höchsten Wert (D7 = 128) als MSB (most signifi- cant bit), das Bit mit dem niedrigsten Wert (D0 = 1) als LSB (least significant bit).

Im Bereich der Mikrocontroller wird häufig mit dem Hexadezimalzahlensystem gearbeitet. Dieses System bietet den Vorteil, die 8-Bit breite Darstellung in zwei 4- Bit breite Elemente zu zerteilen und diesen direkt einen Wert zuzuordnen. 4-Bit

Binärzahl

MSB / LSB

6

breite Elemente entsprechen genau einer Interpretation (0…F) im hexadezimalen System (Bild 2.9)

D3

D2

D1

D0

0

0

0

0

0

0

0

1

0

0

1

0

0

0

1

1

0

1

0

0

0

1

0

1

0

1

1

0

0

1

1

1

1

0

0

0

1

0

0

1

1

0

1

0

1

0

1

1

1

1

0

0

1

1

0

1

1

1

1

0

1

1

1

1

 

Hexa-

Dezimal

Dezimal

0

0

1

1

2

2

3

3

4

4

5

5

6

6

7

7

8

8

9

9

10

A

11

B

12

C

13

D

14

E

15

F

Bild 2.9: Binär-Dezimal-Hexadezimal

Eine Umrechnung einer 8-Bit breiten Darstellung kann somit einfacher erfolgen, ein Beispiel hierzu zeigt Bild 2.10.

Dezimal

Hexa-

dezimal

D7

D6

 

D5

D4

 

D3

D2

D1

D0

1

0

 

1

1

 

0

 

1

   

0

 

1

2

7

2

6

2

5

2

4

2

3

2

2

2

1

2

0

1x2 3

0x2 2

 

1x2 1

1x2 0

0x2 3

1x2 2

0x2 1

1x2 0

1x8

0x4

1x2

0x1

0x8

1x4

0x2

1x1

 

= 11

 

= 5

 

= B

= 5

= 11x16 + 5 = 181

= B5

Binärzahl

Bild 2.10: Umrechnung 8-Bit breite Darstellung in eine Hexadezimalzahl

Bei Mikrcontroller besteht eine unterschiedliche Anzahl an Leitungen, die parallel Daten übertragen. Es werden unterschieden.

8 Bit

16 Bit

32 Bit

Anzahl Bits

Die Programmierung eines Mikrocontrollers erfolgt in der Regel in der Program- miersprache C. Hier stehen dem Entwickler unterschiedliche Variablentypen zur Verfügung (Bild 2.11).

1 Byte

2

4

8

Byte

Byte

Byte

7

char

short

unsigned

short

0…255

-127…+127

0…255

int

-32767…32767

0…65535

unsigned int

unsigned long

0…429467295

-2147483647…-2147483647

+/- 1,2·10 -38 …+/-3,4 · 10 +38

long

float

double

+/- 2,2·10 -308 …+/-1,8 · 10 +308

8

16

32

64

Bits

char

short

int

long

float

double

Bild 2.11: Variablentypen in C und deren Repräsentierung (nach /1/)

Ein char repräsentiert prinzipiell ein Zeichen. Jedem Zeichen ist jedoch wieder ein Wert zugeordnet. Der Mikcontroller unterscheidet nicht, ob es sich um ein Zeichen oder ein Wert handelt, er verarbeitet lediglich 8 Leitungen parallel.

Für die Verarbeitung von kleinen Werten ist in C das short bzw. unsigned short vorgesehen. Hierbei ist zu unterscheiden, ob es ein vorzeichenbehafteter Wert (short) oder ein ausschließlich positiver Wert (unsigned short) ist (Bild 2.12).

1111

1111 1101

1000

0000 0000 0 1111 1111 0000 0001 255 1 1110 0000 0010 254 2 0000
0000 0000
0
1111 1111
0000 0001
255
1
1110
0000 0010
254
2
0000 0011
253
3
.
.
unsigned
short
.
.
.
.
130
0010
126 0111 1110
129
128
127 0111 1111
1000 0001

1000

0000

1111

1111 1101

1000

0000 0000

0 1111 1111 0000 0001 -1 1 1110 0000 0010 -2 2 0000 0011 -3
0
1111 1111
0000 0001
-1
1
1110
0000 0010
-2
2
0000 0011
-3
3
.
.
short
.
.
.
.
-126
0010
126 0111 1110
-127
-128
127 0111 1111
1000 0001

1000

0000

Bild 2.12: Werterepräsentation eines short und unsiged short

Problematisch sind numerische Operationen, bei denen der Wertebereich verlassen wird. Hierzu dient folgendes Beispiel:

main()

{

unsigned short a;

a=255;

a++;

}

carry

 

1

1

1

1

1

1

1

1

1

0

0

0

0

0

0

0

0

Beim Inkrementieren (a++) der Variablen a wird der Wertebereich verlassen und als Ergebnis wird der Wert a=0 interpretiert. Hierbei entsteht gedanklich ein Über- trag (carry) auf die nächst höherer Bit-Stelle.

Alternativ kann der Zahlenbereich aber auch unterschritten werden, wie folgendes Beispiel zeigt:

main()

{

unsigned short a;

a=0;

a--;

}

0 0

0 0

0

0

0

0

1 1

1 1

1

1

1

1

folgendes Beispiel zeigt: main() { unsigned short a; a=0; a--; } 0 0 0 0 0

negative

Übertrag

carry

8

In diesem Fall würde als Ergebnis a=255 erscheinen, es entsteht ein Überlauf ins Negative (negativ). Die Variable a müsste als negative Zahl interpretiert werden.

Negative Zahlen werden im so genannten Zweierkomplement dargestellt. Hierbei wird das MSB als negative Zahl interpretiert (Bild 2.12).

MSB

 

LSB

D7

D6

D5

D4

D3

D2

D1

D0

1

0

1

1

0

1

0

1

2

7

2

6

2

5

2

4

2

3

2

2

2

1

2

0

-1x2 7

0x2 6

1x2 5

1x2 4

0x2 3

1x2 2

0x2 1

1x2 0

1x(-128)

0x64

1x32

0x16

0x8

1x4

0x2

1x1

= -75

negativ

Negative Zahlen Zweierkomplement

Bild 2.12: Umrechnung Zweierkomplement

Bei Verwendung negativer Zahlen kann ein Überlauf (overflow) in beide Richtun- gen entstehen, wie folgende Beispiele zeigen:

main()

{

short a;

a=127;

a++;

}

main()

{

short a;

a=-128;

a--;

}

0

1

1

1

1

1

1

1

1

0

0

0

0

0

0

0

1

0

0

0

0

0

0

0

0

1

1

1

1

1

1

1

overflow1 1 1 1 1 1 1 0 0 0 0 0 0 0 1 0

a=-128

0 0 0 0 0 0 1 0 0 0 0 0 0 0 0 1

overflow

a=127

Überlauf

overflow

In beiden Beispielen wird der Zahlenkreis aus Bild 2.12 beim In- bzw. Dekremen- tieren weiter durchlaufen, so dass fehlerhafte Werte entstehen.

Eine weitere Problematik ergibt bei der Verarbeitung von Werten mit Nachkom- mastellen, wenn z.B. zwei Zahlen a=2,8 und b=1,6 addiert werden sollen. Zur Ver- arbeitung bieten sich 2 Möglichkeiten an:

Festkomma,

Gleitkomma.

Festkomma

Gleitkomma

Bei der Festkomma-Arithmetik sind zunächst alle Werte mit einem Faktor k zu multiplizieren, so dass sich keine Nachkommastellen mehr ergeben. Anschließend erfolgt die Verarbeitung und am Ende wird wieder durch den Faktor k dividiert (Bild 2.13). Wenn die Division erst am Ende der gesamten Verarbeitung erfolgt, werden keine Rundungsfehler auftreten. Problematisch ist dabei, dass es insbeson- dere bei Multiplikationen sehr schnell zu einem Überkauf kommen kann, so dass dann bereits während der Verarbeitung durch den Faktor k geteilt werden muss.

Wert

2,8

1,6

Faktor

k

x10

x10

Short 28 16 Σ 44
Short
28
16
Σ
44

Faktor

k

/10

Wert

4,4

Bild 2.13: Verarbeitung von Festkommawerten

Wird als Faktor ein Vielfaches der Basis 2 genommen, kann eine Mulitplikation und Division einfach durch eine Schiebeoperation der einzelnen Bits nach links (Multiplikation) oder rechts (Division) erfolgen (Bild 2.14)

÷4

÷2

•2

•4

10

21

43

86

172

0

0

0

0

1

0

1

0

0

0

0

1

0

1

0

1

0

0

1

0

1

0

1

1

0

1

0

1

0

1

1

0

1

0

1

0

1

1

0

0

0 1 0 1 0 1 0 0 1 0 1 0 1 1 0 1

0 1 0 1 0 1 0 0 1 0 1 0 1 1 0 1

9

>>2 (schiebe 2 nach rechts)

>>1 (schiebe 1 nach rechts)

<<1 (schiebe 1 nach links)

<<2 (schiebe 2 nach links)

Schiebeoperation

Bild 2.14: Schiebeoperationen zum Dividieren und Multiplizieren

Mikrocontroller können Schiebeoperationen in einem Bearbeitungstakt durchfüh- ren während für Multiplikationen und insbesondere für Divisionen häufig mehrere Arbeitstakte aufgewendet werden müssen. Aus diesem Grund hat die Normierung auf Basis 2 in der Praxis ihre Berechtigung.

Gleitkommawerte werden über Mantisse und Exponent dargestellt (Bild 2.15).

float

(single precision)

31

22

0

V E7

E0 M1

M23

Byte 3

Byte 2

Byte 1

Byte 0

V

0
0

E7

E0

1

1

0

1

0

1

1

1

M0

M1

M2

M3

M21 M22 M23

1
1

1

0

1

1

0

1

·2

2 7

2 6

2 -1 2 -2 2 -3 2 -21 2 -22 2 -23
2 -1
2 -2
2 -3
2 -21
2 -22
2 -23

1,xxxx

2 5

2 4

2 3

2 2

2 1

2 0

Gleitkomma

Mantisse

Exponent

Bild 2.15: Darstellung Gleitkommazahl (float – single precision)

Eine Gleitkommazahl wird immer normiert auf einen Wert 1,xxx, so dass der Wert 1 für die Mantisse (Stelle M0) entfallen kann. Diese Normierung ist immer mög- lich, da die Gleitkommadarstellung mit einem Exponenten der Basis 2 operiert. Ein Wert größer gleich 2,xxx könnte noch einmal durch 2 dividiert werden.

Zu unterscheiden ist die Darstellung der Form float (single precision) und double (double precision). Der Variablentyp float verwendet 4 Bytes (Aufteilung Mantisse und Exponent siehe Bild 2.15). Der Variablentyp double benötigt 8 Bytes (Mantis- se 52 Bit, Exponent 11 Bit, Vorzeichen 1 Bit).

Zur Verarbeitung von Gleitkommazahlen benötigt ein Mikrocontroller eine speziel- le Recheneinheit, die FPU (Floating Point Unit). Die meisten Mikrocontroller ver- fügen aus Kosten-/Nutzengründen nicht über eine FPU. Prinzipiell ist eine Verar- beitung auch ohne FPU möglich, jedoch wird dann eine hohe Rechenzeit benötigt, in der der Mikrocontroller für andere Aufgaben nicht zur Verfügung steht. Aus diesem Grund sollte die Verarbeitung von Festkommawerten bekannt sein.

2.3

Informationsverarbeitung

Da auf Mikrocontroller häufig eine Manipulation einzelner Bits innerhalb einer Variablen durchgeführt werden muss, sollen hier kurz die elementaren Operationen wiederholt werden.

Die wesentlichen Operationen auf digitaler Ebene sind in Bild 2.16 dargestellt.

10

UND

ODER

NICHT

AND

OR

NOT

E1

&
&
 

E1

≥1
≥1
 
1
1
 

A

A

E1

A

E2

 

E2

 
E1 E2 A E1 E2 A E A 0 0 0 0 0 0 0
E1
E2
A
E1
E2
A
E
A
0
0
0
0
0
0
0
1
0
1
0
0
1
1
1
0
1
0
0
1
0
1
1
1
1
1
1
1

UND

ODER

NICHT

Bild 2.16: Elementare logische Verknüpfungen

Bei einer logischen Verknüpfung von Variablen werden die jeweiligen Bits mitein- ander verknüpft. Beispiele hierzu zeigt Bild 2.17.

main()

{

short a,b,c;

a=0x5B;

b=0x92;

c=a&b;

}

main()

{

short a,b,c;

a=0x5B;

b=0x92;

c=a|b;

}

main()

{

short a,b;

a=0x5B;

b=~a;

}

0 1 0 1 1 0 1 1 a = 0x5B 1 0 0 1
0
1
0
1
1
0
1 1
a = 0x5B
1
0
0
1
0
0
1 0
b = 0x92
0
0
0
1
0
0
1 0
c = 0x12
0
1
0
1
1
0
1 1
a = 0x5B
1
0
0
1
0
0
1 0
b = 0x92
1
1
0
1
1
0
1 1
c = 0xDB
0 1
0
1
1
0
1
1
a = 0x5B
1 0
1
0
0
1
0
0
b = 0xA4

Operanden

&

|

~

Bild 2.17: Logische Verknüpfungen von Variablen

Die Operation „~“ ist nicht zu verwechseln mit der Operation „!“ in der Program- miersprache C. Während die Operation „~“ lediglich die einzelnen Bits einer Vari- ablen invertiert, wird mit der Operation „!“ das Zweierkomplement einer Zahl be- rechnet.

Das Setzen bzw. Löschen einzelner Bits innerhalb einer Variablen, ohne dabei die übrigen Bits der Variablen zu beeinflussen, benötigt eine entsprechende ODER- bzw. UND-Verknüpfung, wie Bild 2.18 zeigt.

main()

{

short a,b,c;

a=0x5B;

b=0x06;

c=a|b;

}

main()

{

short a,b,c;

a=0x5B;

b=0xF9;

c=a&b;

}

main()

{

short a,b,c;

a=0x5B;

b=~0x06;

c=a&b;

}

Setzen von Bit 1 und 2

0 1 0 1 1 0 1 1 0 0 0 0 0 1 1
0
1
0
1
1
0 1
1
0
0
0
0
0
1 1
0
0
1
0
1
1
1 1
1

a = 0x5B

b = 0x06

c = 0x5F

Löschen von Bit 1 und 2

0 1 0 1 1 0 1 1 1 1 1 1 1 0 0
0
1 0
1 1
0
1
1
1
1 1
1 1
0
0
1
0
1 0
1 1
0
0
1
0
1 0
1 1
0
1
1
1
1 1
1 1
0
0
1
0
1 0
1 1
0
0
1

a = 0x5B

b = 0xF9

c = 0x59

a = 0x5B

b = 0xF9

c = 0x59

Bit Setzen

Bit Löschen

Bild 2.18: Setzen und Löschen einzelner Bits in Variablen

11

3 Entwicklungsumgebung für Mikrocontroller

Zur Entwicklung lauffähiger Programme auf einem Mikrocontroller wird übli- cherweise eine IDE und ein Debugger eingesetzt, welche im Folgenden vorgestellt werden.

3.1 Programmierung von Mikrocontrollern

Programme für Mikrocontroller werden heutzutage in der Regel in der Program- miersprache C entwickelt. Vereinzelt kommt die Programmiersprache C++ zum Einsatz, die jedoch höhere Ressourcen (Speicherplatz, Taktrate) des Mikrocontrol- lers voraussetzt. Für Programmteile, bei denen es auf eine besonders kurze Re- chenzeit ankommt, wird in seltenen Fällen in Assembler programmiert. Die prinzi- pielle Funktionsweise von Assembler wird im Kapitel 5 vorgestellt.

Um ein Programm, welches in der Programmiersprache C geschrieben wurde, in ein ausführbares Programm für einen Mikrocontroller (unter Windows die EXE) zu transferieren, muss dieses übersetzt werden. Bild 3.1 zeigt den prinzipiellen Ablauf eines solchen Übersetzungsvorgangs (nach /3/, /4/).

Text-Editor Textdatei.c Header.h Message Textdatei.asm Präprozessor Textfile.xxx (Optionen) Textdatei.lst
Text-Editor
Textdatei.c
Header.h
Message
Textdatei.asm
Präprozessor
Textfile.xxx
(Optionen)
Textdatei.lst
Präprozessor
Compiler
(Listfile)
Assembler
Stack-
Information
Objektmodul.obj
Bibliothek.obj
Textdatei.xxx
Linker
(Mapping)
Textfile.xxx
(Optionen)
Datei.xxx

C-Programm

Assembler

Präprozessor

Compiler

Assembler

Bibliothek

Linker

Bild 3.1: Übersetzung eines C-/Assembler-Programms in eine ausführbare Datei

Ausgangspunkt für die Übersetzung eines C-Programms ist eine Textdatei (Textda- tei.c im Bild 3.1), in der die Anweisungen des Programms stehen. Diese Datei wird vom Präprozessor und Compiler verarbeitet. Der Präprozessor verarbeitet Makros, Definitionen (#define) und eingebundene Dateien (#include), in der Regel Header- files. Zur Übersetzung können eine Reihe von Optionen eingestellt werden. Die Übersetzung gibt eine Assembler-Textdatei aus. Diese Datei wird wiederum vom Assembler übersetzt in eine Objektdatei. Über ein Listfile werden Informationen zum Assemblerprogramm ausgegeben, die später der Debuggger (siehe Kapitel xx) benötigt werden. Abschließend wandelt der Linker das Objektmodul in eine aus- führbare Datei um. Hierzu können wiederum eine Reihe von Optionen eingestellt werden. In der Regel wird sich ein Programm aus mehreren Textdateien und ggf. auch aus vorübersetzten Textdateien, den Bibliotheksmodulen, zusammensetzen.

Die einzelnen Entwicklungsprogramme (Texteditor, Präprozessor, Compiler, As- sembler, Linker) werden i.d.R. auf einem PC ausgeführt. Um eine bessere Über-

12

sicht zu bekommen, wurden so genannte IDE (integrated development enviroment, integrierte Entwicklungsumgebung) zur Verfügung gestellt.

In dem vorlesungsbegleitenden Labor wird die IDE softune der Firma fujitsu mic- rocontroller verwendet (Bild 3.2).

der Firma fujitsu mic- rocontroller verwendet (Bild 3.2). compile make build Projekt- Text-Editor Verwaltung

compile

make

build

Projekt- Text-Editor Verwaltung Ausgabe-Fenster
Projekt-
Text-Editor
Verwaltung
Ausgabe-Fenster

Bild 3.2: IDE softune der Firma fujitsu microcontroller

Das Programm wird im Tex-Editor erstellt. Häufig besteht ein ausführbares Pro- gramm aus mehreren Einzeldateien, die in einem Projekt zusammengefasst sind. Aus diesem Grund wird von den IDEs neben den einzelnen Programmdateien zu- sätzlich eine Projektdatei (Datei.prj) erstellt und gespeichert.

Soll nur eine Textdatei übersetzt werden (C-Compiler oder Assembler), ist der Button COMPILE zu aktivieren. Sollen alle Dateien des Projektes übersetzt wer- den und eine ausführbare Datei erzeugt werden, ist der Button BUILD zu betätigen. Sollen lediglich die geänderten Module neu übersetzt werden und von den nicht veränderten Modulen die bereits erstellten Objekt-Module zur Erzeugung einer ausführbaren Datei verwendet werden, ist der Button MAKE zu wählen.

Zum Projekt können eine Reihe von Einstellungen vorgenommen werden (Bild 3.3). Unter General wird der Projekttyp (Erstellung einer ausführbaren Datei: Lo- admodul), der Projektname und die zugehörigen Dateiordner für die Ausgabedatei- en definiert. Unter MCU wird der Typ des Mikrocontrollers, für den die ausführba- re Datei erzeugt werden soll, ausgewählt und spezielle Einstellungen vorgenom- men. Die Optionen für den C-Compiler werden ebenfalls mit diesem Fenster ver- waltet (Bild 3.4).

Eine für Mikrocontroller wichtige Einstellmöglichkeit ist die Art der Übersetzung des C-Programms mit den Anforderungen:

optimiert für schnelle Programmausführung

optimiert für wenig Speicherplatzbedarf

IDE softune

project

compile

build

make

Compiler

Optimierung

13

Diese beiden Anforderungen widersprechen einander, d.h. eine Auslegung auf schnelle Programmausführung benötigt einen erhöhten Speicherplatzbedarf und umgekehrt. Aus diesem Grund existieren häufig noch Zwischenstufen. Für den Beginn einer Entwicklung und aus Didaktischen Gründen wird empfohlen, zu- nächst die Variante ohne Optimierung (None) zu wählen.

Menü: Projekt – Setup Project …

Empfehlung:

Ohne Optimierung

Projekt – Setup Project … Empfehlung: Ohne Optimierung Bild 3.3: Projekteinstellungen Bild 3.4: Einstellungen des

Bild 3.3: Projekteinstellungen

Empfehlung: Ohne Optimierung Bild 3.3: Projekteinstellungen Bild 3.4: Einstellungen des C-Compilers Die Einstellungen
Empfehlung: Ohne Optimierung Bild 3.3: Projekteinstellungen Bild 3.4: Einstellungen des C-Compilers Die Einstellungen

Bild 3.4: Einstellungen des C-Compilers

Die Einstellungen beim Linker umfassen unter Anderem die Verwendung des zur Verfügung stehenden Speichers (Bild 3.5). Hierauf wird im Kapitel xx näher ein- gegangen.

Speicherbereiche

Linker

14

14 Bild 3.5: Einstellungen des Linkers Die Hersteller von Mikrocontrollern stellen dem Entwickler üblicherweise so ge-

Bild 3.5: Einstellungen des Linkers

Die Hersteller von Mikrocontrollern stellen dem Entwickler üblicherweise so ge- nannte Templates zur Verfügung. Templates sind kleine Beispielprojekte, die sämt- liche Einstellungen auf einen Standardwert gesetzt haben und die ein ausführbares Programm erzeugen. Üblicherweise beginnt eine Entwicklung auf Basis eines sol- chen Templates.

3.2 Programmer

Moderne Mikrocontroller sind häufig mit einem Flash-Speicher ausgestattet. Die Übertragung eines ablauffähigen Programms auf den Mikrocontroller erfolgt i. d. R. über eine serielle Schnittstelle (typisch RS232, Bild 3.6). Hierzu wird ein spezielles Programm (Flash-Programmer) benötigt.

wird ein spezielles Programm (Flash-Programmer) benötigt. Entwicklungsumgebung Steuerung mit Mikrocontroller RS 232
Entwicklungsumgebung Steuerung mit Mikrocontroller RS 232
Entwicklungsumgebung
Steuerung mit
Mikrocontroller
RS 232

Template

Programmer

Bild 3.6: Flashen des ablauffähigen Programms eines Mikrocontrollers

Nach dem Download des Programms wird dieses selbständig ausgeführt. In der Entwicklungsphase kann ein Programm jedoch Fehler enthalten. Zur Fehleranalyse wird ein Programm (Debugger) benötigt, welches über eine geeignete Schnittstelle den Mikrocontroller analysieren kann.

3.3 Debugger

Werden Programme für einen PC entwickelt, kann die Programmausführung direkt am PC beobachtet werden. Dies kann bei Programmen für Mikrocontroller so di- rekt nicht erfolgen, da das Programm lediglich auf dem Mikrocontroller abläuft, der i.d.R. nicht über einen eigenen Bildschirm verfügt. Es werden zwei Varianten von Debuggern unterschieden:

In-Circuit-Emulator

In-System-Debugger

15

Beim In-Circuit-Debugger wird der Mikrocontroller ersetzt durch einen Emulator. Dieser verhält sich an den Anschlüssen des Emulator-Tastkopfes wie der ursprüng- liche Mikrocontroller, ist aber intern mit einer erheblich höheren Rechenleistung ausgestattet. Somit kann der PC über den Emulator den Ablauf des Programms analysieren. In-Circuit Emulatoren verfügen über die größten Analysemöglichkei- ten, allerdings sind diese Geräte sehr teuer.

Emulator Emulator- Tastkopf
Emulator
Emulator-
Tastkopf

Bild 3.7: In-Circuit Emulator

Eine kostengünstige Alternative sind Mikrocontroller, die über eine integrierte Debug-Schnittstelle verfügen (In-System Debugger). Eine solche Schnittstelle wur- de unter dem Begriff JTAG bekannt, die eigentlich eine Arbeitsgruppe mehrerer Firmen zur Standardisierung einer Testschnittstelle war (Joint Test Action Group). Die Kommunikation zum PC erfolgt über ein spezielles Interface.

RS 232 Mikrocontroller mit
RS 232
Mikrocontroller mit

Debug-Schnittstelle

Bild 3.8: In-System Debugger

Alternativ gibt es Mikrocontroller, die eine Debug-Schnittstelle intern zur Verfü- gung stellen. Zum Verwalten dieser Schnittstelle ist ein Monitor-Programm erfor- derlich, welches parallel zum eigentlichen Programm abläuft. Das Monitor- Programm stellt damit das Interface dar zwischen der internen Debug- und einer seriellen Schnittstelle des Mikrocontrollers. Nachteilig bei dieser Variante ist der Speicherbedarf des Monitor-Programms und die zusätzliche Rechenzeit, die das Programm benötigt. Zusätzliche Rechenzeit ist immer dann erforderlich, wenn ein Datenaustausch zwischen PC und Mikrocontroller über die serielle Schnittstelle erfolgen soll. Der Vorteil dieser Lösung ist die kostengünstige Realisierung, da keine weitere Hardware erforderlich ist.

In-Circuit-Emulator

In-System Debugger

Monitor-Program

3.4 Debugger Accemic MDE

Im vorlesungsbegleitenden Labor wird ein In-System Debugger der Firma accemic verwendet. Die wichtigsten Funktionen werden in diesem Kapitel kurz vorgestellt. Als Template dient ein einfaches Programm, welches im Bild 3.9 dargestellt ist.

16

#include “irq.h”

// Zugriff auf Funktion initIRQ()

short t;

 

// globale Variable

void toggle(void)

// Funktion invertiert globale Variable

{

 

t=~t;

}

void main(void)

 

{

 

short

i;

// lokale Variable

initIRQ();

// Freigabe Interrupt (Monitor-Programm)

i

= 0;

// lokale Variable initialisieren

t

= 1;

// globale Variable initialisieren

while( 1 )

// Endlosschleife

{

 

i++; if (i > 3)

// lokale Variable inkrementieren // wenn lokale Variable größer 3

{

 

i=0;

// lokale Variable zuruecksetzen

toggle();

// Funktionsaufruf zum Invertieren globale Variable

 

}

 

}

}

Bild 3.9: Template zum Test des Debuggers

Nach der Erzeugung eines lauffähigen Programms unter der IDE softune wird der Debugger gestartet. Wird der Mikrocontroller das erste Mal verwendet oder ist ein Systemabsturz des Monitor-Programms aufgetreten, muss zunächst das Monitor- Programm (Kernel) geladen werden (Bild 3.10). Ist das Monitor-Programm bereits auf dem Mikrocontroller vorhanden, genügt ein Starten der seriellen Verbindung (connect).

genügt ein Starten der seriellen Verbindung (connect). Connect-Butten Menü: Start - Connect wenn Monitor-Programm

Connect-Butten Menü: Start - Connect wenn Monitor-Programm bereits geladen wurde

Menü: Preference – Processor … zum Laden des Monitor-Programms

Preference – Processor … zum Laden des Monitor-Programms Accemic MDE Verbindungsaufbau Bild 3.10: Verbindungsaufbau

Accemic MDE Verbindungsaufbau

Bild 3.10: Verbindungsaufbau mit dem Mikrocontroller.

ACHTUNG: Es ist darauf zu achten, dass der Mikrocontroller eingeschaltet und die serielle Kabelverbindung gesteckt ist.

HINWEIS: Tritt eine Fehlermeldung beim Verbindungsaufbau auf, kann häufig ein Reset (Aus-/Einschalten) des Mikrocontrollers den Fehler beheben.

17

Nach dem Start des Debuggers muss das lauffähige Programm (project.abs) gela- den werden, wenn es nicht bereits automatisch geladen wurde. Das Laden des Pro- gramms erfolgt über das Menü: Load File oder durch Aktivieren des entsprechen- den Buttons. Nach dem Laden des Programms werden standardmäßig folgende Fenster angezeigt (Bild 3.11):

Variablen-Browser

Datei- und Funktions-Browser

C-Quelltext

Assembler-Quelltext

Variablen Browser C-Quelltext Datei- und Funktions- Browser Assembler Quelltext
Variablen
Browser
C-Quelltext
Datei- und
Funktions-
Browser
Assembler
Quelltext

Programm laden

Variablen-/Datei-/

Funktions-Browser

Quelltextanzeige

Bild 3.11: Standardansicht des Debuggers

Der Mikrocontroller ist zunächst angehalten, der nächste auszuführende Befehl wird im Quelltextfenster blau markiert. Im Variablen-Browser wird die lokale Va- riable i zunächst nicht angezeigt, da der Befehl zur Deklaration noch nicht abgear- beitet wurde. Ein Aktivieren des Reiters „Global“ im Variablen-Browser zeigt die globale Variable t, die bereits vorab deklariert wurde.

Zum Ausführen des Programms existieren unterschiedliche Möglichkeiten (Bild 3.12). So können nur einzelne Programmzeilen bearbeitet werden (mit der Option Unterfunktionen zu überspringen oder hineinzuspringen) oder es wird das PRo- gramm permanent ausgeführt.

oder es wird das PRo- gramm permanent ausgeführt. Reset (Programm beginnt erneut bei main) Start Stopp
oder es wird das PRo- gramm permanent ausgeführt. Reset (Programm beginnt erneut bei main) Start Stopp
oder es wird das PRo- gramm permanent ausgeführt. Reset (Programm beginnt erneut bei main) Start Stopp
oder es wird das PRo- gramm permanent ausgeführt. Reset (Programm beginnt erneut bei main) Start Stopp
oder es wird das PRo- gramm permanent ausgeführt. Reset (Programm beginnt erneut bei main) Start Stopp
oder es wird das PRo- gramm permanent ausgeführt. Reset (Programm beginnt erneut bei main) Start Stopp
oder es wird das PRo- gramm permanent ausgeführt. Reset (Programm beginnt erneut bei main) Start Stopp

Reset (Programm beginnt erneut bei main)

Start

ausgeführt. Reset (Programm beginnt erneut bei main) Start Stopp des Programms Nächste Programmzeile (Funktionen

Stopp des Programms

Nächste Programmzeile (Funktionen überspringen)

Nächste Programmzeile (Funktionen hineinspringen)

Funktion beenden

Programmzeilen schrittweise in Assembler ausführen

Bild 3.12: Funktionen zur Kontrolle des Programmablaufs

Funktionen zur Programmausführung

18

Gerade durch die Möglichkeit, Programmzeilen einzeln ausführen zu lassen, kann in Verbindung mit dem Variablen-Browser sehr gut die Funktionsweise des Pro- gramms analysiert werden.

Soll das Programm bis zu einer bestimmten Stelle ohne Unterbrechung ausgeführt werden, und an diesem Punkt stoppen, müssen Unterbrechungspunkte (Break- points) gesetzt werden (Bild 3.13).

Breakpoint

(Break- points) gesetzt werden (Bild 3.13). Breakpoint Bild 3.13: Setzen von Unterbrechungspunkten (Breakpoints)

Bild 3.13: Setzen von Unterbrechungspunkten (Breakpoints)

Bild 3.13: Setzen von Unterbrechungspunkten (Breakpoints) Zum Starten wird der Button betätigt. Das Programm wird bis

Zum Starten wird der Button betätigt. Das Programm wird bis zum Breakpoint ausgeführt. Insgesamt können mit accemic mde bis zu 4 Breakpoints gesetzt wer- den. Bei der Unterbrechung wird die Zeile, in der der Breakpoint gesetzt ist, nicht mehr ausgeführt. Hierzu muss nach der Unterbrechung der Einzelschrittmodus

aktiviert werden.Hierzu muss nach der Unterbrechung der Einzelschrittmodus AUFGABE: Analysieren Sie das Template-Programm mit dem

AUFGABE: Analysieren Sie das Template-Programm mit dem Debugger. Nutzen Sie dabei den Variablen-Browser und den Einzelschrittmodus bzw. Breakpoints. Wie verändert sich die lokale und globale Variable?

und den Einzelschrittmodus bzw. Breakpoints. Wie verändert sich die lokale und globale Variable? Ergebnis

Ergebnis

4

Speicher

19

Das Programm, welches der Mikrocontroller verarbeitet und sämtliche Daten müs- sen in einem Speicher abgelegt werden. Das Grundprinzip eines Speichers verdeut- licht Bild 4.1.

15 14 13 12 11 10 9 8 7 6 5 4 3 2 1
15
14
13
12
11
10
9
8
7
6
5
4
3
2
1
0
D
1
7
D
0
6
D
1
5
D
0
4
D
1
3
D
0
2
D
0
1
D
1
0
Demultiplexer
1
0
1
0
Adresse
A 3
A 2
A 1
A 0
Daten

Bild 4.1: Grundprinzip Speicher

Bei dem hier dargestellten Speicher wird an den Leitungen der Adresse, dem so genannten Adressbus, ein Datum vorgegeben. Ein Demultiplexer aktiviert gemäß der binärcodierten Adresse eine Leitung. Über Speicherelemente (hier vereinfacht Dioden) wird definiert, welche Datenleitung aktiviert werden. Im obigen Beispiel verfügt der Speicher über 8 Datenleitungen, so dass je Adresse 1 Byte ausgelesen werden kann.

Mit dem in Bild 4.1 dargestellten Speicher können insgesamt 16 Byte unterschied- liche Daten gespeichert werden, wozu ein 4-Bit breiter Adressbus ausreichend ist. Soll z.B. ein Speicher von 1MByte byteweise adressiert werden, sind 20 Adresslei- tungen erforderlich.

Speicher verfügen typischerweise über 8, 16 oder 32 parallele Datenleitungen, d.h. sie werden entweder byte- oder wort- oder doppelwortweise organisiert. Ein Zugriff auf die Daten ist demnach nur in diesen Datenbreiten möglich.

Grundsätzlich werden Speicher unterschieden in Festwertspeicher, genannt ROM (Read Only Memory) und Schreib-/Lesespeicher, genannt RAM (Random Access Memory. Eine Übersicht aktuell verwendeter ROM-Typen zeigt Tabelle 4.1. Bei Mikrocontrollern werden aktuell werden OTP oder Flash-Speicher verwendet.

Typ

Typ

Bezeichnung

Bezeichnung

Programmier-

Programmier-

Dauer

Dauer

Hinweis

Hinweis

MROM

MROM

Masken-

Masken-

ROM

ROM

- -

Spezieller Speicherbaustein, wird durch den Herstellprozess

Spezieller Speicherbaustein, wird durch den Herstellprozess

programmiert. Nur für große Stückzahl geeignet, kostengünstig

programmiert. Nur für große Stückzahl geeignet, kostengünstig

PROM

PROM

OTP

OTP

Programmable-ROM

Programmable-ROM

One Time PROM

One Time PROM

min

min

Allgemeiner Baustein, der einmalig mit speziellem

Allgemeiner Baustein, der einmalig mit speziellem

Programmiergerät beschrieben werden kann,

Programmiergerät beschrieben werden kann,

für kleinere Stückzahlen

für kleinere Stückzahlen

EPROM

EPROM

Erasable PROM

Erasable PROM

min

min

Beschreiben mit speziellem Programmiergerät, Löschen für

Beschreiben mit speziellem Programmiergerät, Löschen für

erneutes Beschreiben durch UV-Licht

erneutes Beschreiben durch UV-Licht

EEPROM

EEPROM

Electrical EPROM

Electrical EPROM

ms

ms

Beschreiben und elektrisches Löschen, teilweise spezielles

Beschreiben und elektrisches Löschen, teilweise spezielles

Programmiergerät erforderlich, max. 10 4 …10 6 Löschzyklen

Löschzyklen

Programmiergerät erforderlich, max. 10

4

…10

6

möglich

möglich

FLASH

FLASH

 

µs

µs

Beschreiben und elektrisches Löschen, , max. 10

Beschreiben und elektrisches Löschen, , max. 10 4 …10 6

4

…10

6

Löschzyklen möglich

Löschzyklen möglich

Tabelle 4.1: Übersicht ROM

Adressbus

Datenbus

RAM / ROM

MROM

OTP

EPORM

EEPROM

FLASH

20

RAM-Bausteine ermöglichen das Lesen und Schreiben einzelner Speicherstellen mit einer Zugriffszeit im Bereich weniger Nanosekunden. Tabelle 4.2 gibt einen Überblick über aktuellen RAM-Varianten. Mikrocontroller verwenden üblicher- weise SRAM-Bausteine.

Typ

Typ

Bezeichnung

Bezeichnung

Zugriffszeit

Zugriffszeit

Speichergröße

Speichergröße

Hinweis

Hinweis

DRAM

DRAM

(SDRAM)

(SDRAM)

(DDR-RAM)

(DDR-RAM)

Dynamisches RAM

Dynamisches RAM

(Synchrones DRAM)

(Synchrones DRAM)

(Double Data Rate SDRAM)

(Double Data Rate SDRAM)

ns…wenige ns

ns…wenige ns

100.1000MBit

100.1000MBit

Kapazitiver Speichereffekt, geringste Zugriffszeit und

Kapazitiver Speichereffekt, geringste Zugriffszeit und

größte Speicher, benötigt kontinuierliche Refresh-Zyklen

größte Speicher, benötigt kontinuierliche Refresh-Zyklen

zum Halten der Information, günstig

zum Halten der Information, günstig

FRAM

FRAM

Ferroelektrisches RAM

Ferroelektrisches RAM

mehrere 10ns

mehrere 10ns

Bis 10MBit

Bis 10MBit

Schreib-

Ferromagnetischer Speicher, mind. 10 12 Schreib-

Ferromagnetischer Speicher, mind. 10

12

/Lesezyklen, mind. 20…40 Jahre Speicherung auch

/Lesezyklen, mind. 20…40 Jahre Speicherung auch

ohne Spannungsversorgung, teuer

ohne Spannungsversorgung, teuer

SRAM

SRAM

Statisches RAM

Statisches RAM

wenige ns…wenige 10ns

wenige ns…wenige 10ns

bis 4MBit

bis 4MBit

Benötigt keine Refresh-Zyklen, aufgebaut aus Halbleiter

Benötigt keine Refresh-Zyklen, aufgebaut aus Halbleiter

(Flip-Flop), Informationsverlust bei Spannungsausfall

(Flip-Flop), Informationsverlust bei Spannungsausfall

(ggf. Batteriegepuffert)

(ggf. Batteriegepuffert)

DRAM

FRAM

SRAM

Tabelle 4.2: Übersicht RAM

Wie bereits oben erwähnt, sind Adress- und Datenleitungen für den Zugriff auf den Speicher erforderlich. Zusätzlich sind weitere Steuersignale erforderlich, die die Zugriffsart, Lesen oder Schreiben, definieren und die den Speicherbaustein aktivie- ren. Steuersignale arbeiten üblicherweise mit negativer Logik, d.h. das Signal ist aktiv bei Logikpegel 0. Gekennzeichnet wird die negative Logik mit einem Quer- strich über der Signalbezeichnung. Einen typischen Schreib-/Lesezugriff eines SRAM beschreibt Bild 4.2.

X: don‘t care CECE WEWE OEOE Modus A 0 1 X X D 0 …D
X: don‘t care
CECE
WEWE
OEOE
Modus
A 0
1
X
X
D 0 …D 7 : hochohmig
32KByte
D 0
0
1
1
D 0 …D 7 : hochohmig
A 14
Write Enable
(256KBit)
WEWE
0
1
0
D 0 …D 7 : Lesen
SRAM
D 7
Output Enable
OEOE
0
0
X
D 0 …D 7 : Schreiben
Chip Enable
CECE
Lese-Zugriff
Schreib-Zugriff
t RC
t WC
Adress
Adress
t AA
t AS
t WP
WEWE
D
Data valid
t WP
t DW
D
Data valid
CECE
t OE
OEOE
t ACE
D
Data valid
t
Write cycle time:
min 10ns
WC
t
Read cycle time:
min 10ns
t
Adress setup time:
min 0ns
AA
AS
t
Adress access time:
max 10ns
Write pulse width:
min 7ns
AA
t WP
t
Output enable access time: max 5ns
t
Data valid to write end:
min 5ns
OE
DW
t
Chip enable access time:
max 10ns
t
Data hold time:
min 0ns
ACE
DH

Zeitverhalten SRAM CE Chip Enable WE Write Enable OE Output Enable

Bild 4.2: Zeitverhalten beim Schreib-/Lesezugriff eines SRAM (nach /5/)

Bei einem Lesezugriff wird zunächst die Adresse angelegt. Gleichzeitig kann das Chip Enable (CE) Signal aktiviert werden. Frühestens 10ns nach Anlegen der Ad- ressleitungen bzw. des CE-Signals sind die Signale auf den Datenleitungen gültig und können vom Mikrocontroller verarbeitet werden. Hierzu ist zusätzlich das Output Enable (OE) Signal zu aktivieren (low), welches mindestens 5ns vor den gültigen Daten erfolgen muss.

Beim Schreibzugriff kann unmittelbar nach dem Anlegen der Adresse das Write Enable (WE) Signal zur Initiierung eines Schreibzugriffs aktiviert (low) werden. Der über das WE-Signal aktivierte Schreibzugriff muss mindestens 7ns dauern, wobei die Datenleitungen mindestens 5ns stabil angestanden haben müssen, bevor

21

das WE-Signal wieder deaktiviert (high) wird. Typischerweise wird bei der stei- genden Flanke des WE-Signals das aktuelle Datum in die Speicherstelle übernom- men. Da die Adressleitungen mindestens 10ns aktiviert bleiben müssen, benötigt der gesamte Schreibzugriff diese Zeit.

Die Lese- und Schreibzugriffsdauer ist mit entscheidend für die Geschwindigkeit des Prozessors bei der Bearbeitung der Informationen.

Der Zugriff auf den Speicher erfolgt durch die CPU (Central Processing Unit), auf die im nachfolgenden Kapitel näher eingegangen wird. Bei der Anordnung der Speicher werden zwei Architekturen unterschieden (Bild 4.3):

Von Neumann Architektur

Harvard Architektur

Steuerleitungen CPU Adressbus Datenbus Daten/Programm von Neumann Speicher Architektur Steuerleitungen 1
Steuerleitungen
CPU
Adressbus
Datenbus
Daten/Programm
von Neumann
Speicher
Architektur
Steuerleitungen 1
Steuerleitungen 2
Adressbus 1
CPU
Adressbus 2
Datenbus 1
Datenbus 2
Daten
Programm
Harvard
Speicher
Speicher
Architektur
Bild 4.3: Architektur der Speicheranordnung
CPU
Programm
Daten
Speicher
Speicher
(I-RAM)
(D-RAM)
Programm/
Bus
Datenspeicher
Konverter
(RAM)

Bei der von Neumann Architektur wird nicht zwischen Programm oder Daten un- terschieden, es gibt nur einen Adressbus. Hierdurch gibt es eine größere Flexibili- tät. Die Harvard-Architektur bietet zwei getrennte Speicher, jeweils einen Speicher für Daten und Programm. Durch 2 getrennte Bussysteme kann der Zugriff schneller erfolgen.

Es sind auch Kombinationen denkbar, wie z.B. eine Harvard-Architektur, die an- schließend über einen Buskonverter auf einen gemeinsamen Speicher zugreift (Bild 4.4). Dies ist im Mikrocontroller der Baureihe FR der Firma Fujitsu, der im vorle- sungsbegleitenden Labor verwendet wird, der Fall.

Architektur

von Neumann

Harvard

Kombinationen

Bild 4.4: Kombinierte Architektur Harvard und von Neumann

Ein wichtiges Kriterium ist, ob es sich um internen (on board) Speicher des Mikro- controllers handelt, oder ob dieser extern zur Verfügung steht (Bild 4.5). Vorteil bei der externen Variante ist der flexible Ausbau des Speichers, je nachdem wie viel benötigt wird. Nachteilig ist der zusätzliche Fertigungsaufwand, da weitere Bausteine benötigt werden, die gelagert, bestückt und verlötet werden müssen. Durch die hohen Taktraten auf dem Adress- und Datenbus kommt es bei externer Ausführung zu erhöhter Störstrahlungsaussendung, so dass zusätzliche EMV-

22

Maßnahmen erforderlich sind. Aus diesen Gründen wird in vielen Anwendungen eine Single Chip Lösung favorisiert. Viele Mikrocontroller stellen gar keinen ex- ternen Bus mit Adress-, Daten- und Steuerleitungen mehr zur Verfügung.

CPU Internes RAM Internes ROM Interner Bus
CPU
Internes
RAM
Internes
ROM
Interner Bus

Single Chip

CPU Internes RAM Internes ROM Interner Bus Single Chip CPU Internes RAM Internes ROM Externes RAM
CPU Internes RAM Internes ROM Externes RAM Externes ROM Externer Bus Interner Bus
CPU
Internes
RAM
Internes
ROM
Externes
RAM
Externes
ROM
Externer Bus
Interner Bus

Internes RAM/ROM Externes RAM/ROM Single Chip

Bild 4.5: Interner und Externer Speicher

Der im vorlesungsbegleitendem Labor eingesetzte Mikrocontroller MB91F364 verfügt über:

2 KByte Boot-ROM

256KByte Flash

12KByte D-RAM (Daten)

4 KByte RAM (Programm und Daten)

Kein Erweiterungsbus

Das Boot-ROM dient zum Hochfahren des Mikrocontrollers. Das dort abgelegte Programm prüft, ob an der seriellen Schnittstelle ein definiertes Zeichen ange- kommen ist. Ist dies der Fall, werden die Daten in den Flash-Speicher geschrieben. Dieses Programm nennt sich „Bootstraploader“. Die Adressierung der unterschied- lichen Bausteine erfolgt in der Regel linear, d.h. der gesamte zur Verfügung ste- hende Adressraum wird fortlaufend an die einzelnen Bausteine vergeben (Bild 4.6). Der gesamte Adressraum wird dabei unterteilt in unterschiedliche Bereiche, deren genaue Lage im Adressraum häufig einstellbar ist. Damit das aus dem C-Programm erstellte Programm in den richtigen Speicherstellen geladen wird, werden dem Linker die einzelne Bereiche als Option mitgeteilt (Bild 3.5).

16 Adressleitungen für 64KByte

mitgeteilt (Bild 3.5). 16 Adressleitungen für 64KByte A 0 A 15 0000 64KByte FFFF IO RAM
A 0 A 15 0000 64KByte FFFF IO RAM ROM Externes ROM
A 0
A 15
0000
64KByte
FFFF
IO
RAM
ROM
Externes ROM

18 Adressleitungen für 256KByte

IO RAM ROM Externes ROM 18 Adressleitungen für 256KByte A A A A 17 16 15
A A A A 17 16 15 0 CS 0 0000 =00 64KByte 0 FFFF
A
A
A
A
17
16
15
0
CS
0
0000
=00
64KByte
0
FFFF
CS
1
0000
=01
64KByte
1
FFFF
CS
2
0000
=10
64KByte
2
FFFF
CS
3
0000
=11
64KByte
3
FFFF

Adressdekodierung

Bootstraploader

Speichersegmente

Adressdekodierung

Bild 4.6: Aufteilung des Adressraums und Adressdekodierung

Stehen mehr als 16 Adressleitungen zur Verfügung, wird der Speicher häufig in Segmente aufgeteilt. Die Größe der Segmente ist unterschiedlich, ein Beispiel einer Segmentierung in 64KByte Segmente zeigt Bild 4.6.

Häufig kann die Lage der einzelnen Segmente im Mikrocontroller eingestellt wer- den, d.h. die Adresscodierung kann umprogrammiert werden.

23

Bild 4.7 zeigt den Adressbereich des Mikrocontrollers aus dem Labor.

00 0000

00 07FF

00 1000

00 1024

01

01

03

03

04

04

05

05

1000

1FFF

D000

FFFF

C000

0FFF

C000

07FF

0C 0000

0F FFFF

10

10

0000

C7FF

IO

DMA

I-RAM (nicht beim 91F364)

D-RAM

RAM

Boot ROM

Flash

CAN

Bild 4.7: Linearer Adressbereich MB91F364

AUFGABE: Über den Debugger soll eine Variable im Adressraum angezeigt wer- den. Die Adresse der globale Variable aus obigem Beispiel (Bild 3.9) wird im Speicherabbild eingetragen und deren Veränderung im Einzelschrittmodus nach- verfolgt (Bild 4.8). Welche Besonderheit stellen Sie bei der Variablen vom Typ short fest?

stellen Sie bei der Variablen vom Typ short fest? Ergebnis 1) Globale Variable aktivieren, dann wird

Ergebnis

stellen Sie bei der Variablen vom Typ short fest? Ergebnis 1) Globale Variable aktivieren, dann wird
stellen Sie bei der Variablen vom Typ short fest? Ergebnis 1) Globale Variable aktivieren, dann wird

1) Globale

Variable

aktivieren,

dann wird

Adresse

angezeigt

5) Adresse

Befehl

2) Anzeige des Speicherabbildes

3) Adresse der Variablen eintragen

4) Zuweisung der Variablen überprüfen

Bild 4.8: Überprüfung einer Variablenänderung im Speicherabbild

24

AUFGABE: Verändern Sie den Wert im Speicherabbild. Welchen Effekt stellen Sie fest?

Ergebnis

AUFGABE: Verfolgen Sie im Einzelschrittmodus die Adresse des Befehls (Num- mer 5 im Bild 4.8). Was stellen Sie fest?

Ergebnis

AUFGABE: Beobachten Sie den bisher nicht erläuterten Adressbereich IO ab Ad- resse 0. Betätigen Sie einen Schalter und halten Sie diesen gedrückt. Beobachten Sie die Veränderung für jeden Schalter. An welcher Adresse ändert sich ein Wert und wie viele Bits ändern sich jeweils?

Hinweis: Das Speicherabbild wird nicht kontinuierlich aktualisiert. Ein manuelles Aktualisieren erfolgt über die Taste F3.

Ergebnis

5

IO-Ansteuerung

25

Wie in der letzten Aufgabe festgestellt werden konnte, gibt es einen direkten Zu- sammenhang zwischen einem Hardwarezustand und einer Variablen an einer be- stimmten Adresse. Dieser Adressbereich wird mit IO (Input/Output) gekennzeich- net. Die Speicherstellen, die den IO-Zugriff ermöglichen, werden Register genannt.

Den Anschlüssen des Mikrocontrollers, den so genannten Pins, werden bestimmte

Register

Registeradressen zugeordnet. Häufig ist es Möglich, die Funktion einzelner Pins zu

Pin

beeinflussen, z.B. ob es sich um einen digitalen Eingang (z.B. zum Einlesen einer

Funktionszuordnung

Taste) oder um einen digitalen Ausgang (z.B. zur Ansteuerung einer LED) handelt. Die Funktionszuordnung erfolgt ebenfalls über Register.

Port

Register haben i. d. R. eine Bitbreite von 8 oder 16, selbst bei einem 32-Bit Mikro- controller. Somit werden über ein Register mehrere Pins des Mikrocontrollers ver- waltet. Man fasst die Pins des Mikrocontrollers daher zusammen und bezeichnet sie als Port. Beim Mikrocontroller MB91F364 werden immer 8 Pins zu einem Port zusammengefasst. Insgesamt hat dieser Mikrocontroller 120 Pins. Ein Großteil dieser Pins werden für IO-Zugriffe zur Verfügung gestellt (Bild 5.1).

Pin 120 Pin 1
Pin 120
Pin 1
zur Verfügung gestellt (Bild 5.1). Pin 120 Pin 1 Bild 5.1: Zuordnung der Pins zu Ports

Bild 5.1: Zuordnung der Pins zu Ports des Mikrocontroller MB91F364 /6/

Die im vorlesungsbegleitenden Labor verwendete Hardware ist das „Mechatronic Evaluation Board“, kurz MEB, welches eine Eigenentwicklung des Instituts für Mechatronik der Fachhochschule Braunschweig/Wolfenbüttel ist. Das Funktions- schema ist in der Anlage beschrieben.

Insgesamt stehen 3 Taster zur Verfügung, wobei 1 Taster in einem Drehcodier- schalter integriert ist. Der Drehcodierschalter schaltet beim Drehen zwei weitere Signale. Die Zuordnung der Signale ist dem Ausschnitt des Schaltplans in Bild 5.2 zu entnehmen.

S1

S2

5V-D

IC7 (6) R30 74HC14 2k2 R31 2k2 13 12 X1.E4 (INT6, PK6) C31 100n 50V
IC7 (6)
R30
74HC14
2k2
R31
2k2
13
12
X1.E4 (INT6, PK6)
C31
100n
50V
GND-D
GND-D
5V-D
R32
2k2
R33
2k2
X1.E5 (INT7, PK7)

GND-D

26

5V-D

R24 R25 IC7 (2) R26 2k2 2k2 74HC14 2k2 R27 3 2k2 IC7 (3) 74HC14
R24
R25
IC7 (2)
R26
2k2
2k2
74HC14
2k2
R27
3
2k2
IC7 (3)
74HC14
R28
5
2k2
IC7 (4)
74HC14
R29
9
2k2
A
B
1
C28
C29
C30
S3
10n
10n
10n
50V
50V
50V
C
2

GND-D

X1.E9 (IN2, PL2)

X1.E10 (IN3, PL3)

X1.E2 (INT5, PK5)

Bild 5.2: Schaltplan zum Einlesen der Taster

Taster S1 ist im unbetätigten Zustand geöffnet. Über den Pull-Up-Widerstand wird der Eingang des Schmitt-Triggers auf Zustand 1 (5V) gelegt. Da es sich um einen invertierenden Schmitt-Trigger (dargestellt durch den Kreis am Ausgang) handelt, wird am Ausgang der Zustand 0 vorhanden sein, der über Port K, Bit 6 eingelesen werden kann. Beim Betätigen des Tasters wird der Eingang des Schmitt-Triggers auf 0V gelegt, der Ausgang wird auf den Zustand 1 wechseln. Beim Taster S2 fehlt der invertierende Schmitt-Trigger, so dass im unbetätigtem Fall der Zustand 1 und im betätigtem Fall der Zustand 0 am Port K, Bit 6 anliegt.

Der Drehcodierschalter betätigt beim Drehen die Schalter S3-ABC. Wird der Drehcodierschalter gedrückt, wird der Schalter S3-1/2 aktiviert. Der Drehcodier- schalter wird über den Port L, Bit 2, 3 und 5 eingelesen.

Die Registerzuordnung der Ports ist in Bild 5.3 dargestellt.

Die Registerzuordnung der Ports ist in Bild 5.3 dargestellt. Port Adresse H 0x0011 I 0x0012 J

Port

Adresse

H

0x0011

I

0x0012

J

0x0013

K

0x0014

L

0x0015

M

0x0016

N

0x0017

O

0x0018

P

0x0019

Q

0x001A

R

0x001B

S

0x001C

T

0x001D

Schaltplan

Taster

Portzuordnung

Bild 5.3: Adresszuordnung zu IO-Ports

Demnach sind die einzelnen Schalter den Registern wie im Bild 5.4 beschrieben zugeordnet.

Adresse D7 D0 0x0014 x x - x - - - - Port K S3:
Adresse
D7
D0
0x0014
x
x -
x -
- -
-
Port K
S3: 1 – Drehkodierschalter gedrückt
S1: 1 – Taster betätigt
S2: 1 – Taster nicht betätigt
Adresse D7 D0 0x0015 - - x - x - - - Port L S3:
Adresse
D7
D0
0x0015
-
- x
- x
- -
-
Port L
S3: Spur A des Drehcodierschalters
S3: Spur B des Drehkodierschalters

Bild 5.4: Schalterzuordnung zu Bits der entsprechenden Register

27

Als Besonderheit bietet der Debugger MDE der Firma accemic neben dem Spei- cherabbild ein Prozessorabbild (Bild 5.5).

Prozessorabbild Zustand Port K (Pins) Detaillierung Port K Inhalt Register für Port K Aktualisierung Nach
Prozessorabbild
Zustand Port K (Pins)
Detaillierung Port K
Inhalt Register für Port K
Aktualisierung
Nach Taste F3

Bild 5.5: Prozessorabbild

Im Prozessorabbild wird der Zustand der zugehörigen Pins der einzelnen Ports dargestellt. Durch einen Doppelklick auf den zugehörigen Port wird eine Detaillie- rung des Ports dargestellt, der den Zustand der zugehörigen Bits und den entspre- chenden hexadezimalen Wert angibt.

HINWEIS: Wird ein Schalter betätigt, so ändert sich das Prozessorabbild zunächst nicht. Hierzu ist eine manuelle Aktualisierung über die Taste F3 erforderlich. Die Aktualisierungszeit kann 1-2 Sekunden benötigen.

Wird gleichzeitig das Speicherabbild visualisiert, so kann bei Tastendruck eine Änderung sowohl im Prozessorabbild als auch im Speicherabbild beobachtet wer- den.

AUFGABE: Verifizieren Sie, welche Werte sich beim Betätigen der Taster 1-3 ergeben. Die Taster sollen einzeln betätigt werden. Stimmen die Werte mit den im Bild 5.4 dargestellten Bits überein (Binärdarstellung)?

Prozessorabbild

werden. Stimmen die Werte mit den im Bild 5.4 dargestellten Bits überein (Binärdarstellung)? Prozessorabbild Ergebnis

Ergebnis

28

Wie die Detaillierung des Prozessorabbild für den Port K zeigt, sind insgesamt 3 Register für die Funktion dieses Ports zuständig. Im Register PDRK (port data register K) wird ein Abbild der Pins des Prozessors abgelegt. Die Bedeutung der Register DDRK und PFRK zeigt Bild 5.6.

Eingang Fkt

PDR lesen 0 1 Ausgang Fkt 1 PDR 0 PFR ≥1 DDR Bus
PDR lesen
0
1
Ausgang Fkt
1
PDR
0
PFR
≥1
DDR
Bus

Pin

PDR

DDR

PFR

Bild 5.6: Konfiguration IO-Ports /6/

Über das DDR (data direction register) wird die Richtung des Port-Pins festgelegt. Wird im DDR-Register für den entsprechenden Pin eine 0 geschrieben, handelt es sich um einen Eingang (Default-Einstellung), wird eine 1 geschrieben, wird der Pin zu einem Ausgang. Das Register PFR (port function register) kann dem Pin eine Sonderfunktion zuweisen. Eine Sonderfunktion wäre z.B. ein analoger Eingang des A/D-Wandlers oder ein externer Interrupteingang (Erläuterung der Sonderfunktion folgt in den nachfolgenden Kapiteln). Für den Port K sind die 3 Register und die Funktionen in Bild 5.7 wiedergegeben.

Adresse D7 D0 0x0014 PK7 PK6PK5PK4 PK3 PK2PK1PK0 PDRK Pin 0: 1=highPegel Pin 7: 1=high
Adresse
D7
D0
0x0014
PK7
PK6PK5PK4
PK3
PK2PK1PK0
PDRK
Pin 0: 1=highPegel
Pin 7: 1=high Pegel
Adresse
D7
D0
0x0404
PK7
PK6PK5PK4
PK3
PK2PK1PK0
DDRK
Pin 0: 0=Eingang, 1=Ausgang
Pin 7: 0=Eingnag, 1=Ausgang
Adresse
D7
D0
0x0414
PK7
PK6PK5PK4
PK3
PK2PK1PK0
PFRK
Pin 0: 0=allgemeiner Ein/Ausgang, 1=Externer Interrupt
Pin 7: 0=allgemeiner Ein-/Ausgang, 1=Externer Interrupt
Bild 5.7: Register PDR, PFR, DDR für Port K

Wird ein Pin für eine Sonderfunktion konfiguriert, ist das DDR ohne Bedeutung. Die Funktionszuordnung stellt automatisch die Richtung (Ein- oder Ausgang) kor- rekt ein.

Hinweis: Wird ein Pin als Ausgang konfiguriert, muss dies elektrisch auch umge- setzt werden können. Die Ausgänge sind als Tri-State-Ausgänge ausgeführt, was bedeutet, dass beim Zustand 1 5V über den internen Transistor an den Ausgang geschaltet wird. Ist allerdings an diesem Ausgang z.B. ein Schalter angeschlossen, der den Ausgang mit Masse verbindet, würde der interne Transistor des Mikrocont- rollers zerstört werden. Aus diesem Grund empfiehlt sich der Einbau eines Aus- gangswiderstandes (Bild 5.2, R27-29, R31, R33), so dass eine Überlastung vermie- den wird.

Überlast Ausgang Widerstand

29

Wird der IO-Port als Ausgang konfiguriert, können damit dem Bediener Zustände, z.B. über LEDs angezeigt werden. Für den Port K steht hierfür eine Sonderfunktion LED zur Verfügung.

5V

  R3   R3   R3   R3 1K 1K 1K 1K LED 3  
  R3   R3   R3   R3 1K 1K 1K 1K LED 3  
  R3   R3   R3   R3 1K 1K 1K 1K LED 3  
 

R3

 

R3

 

R3

 

R3

1K

1K

1K

1K

LED 3          

LED 3

 
LED 3          
   
LED 3          
   
LED 3          

LED 2

LED 1

LED 0

   

105 (LED3, PJ3)

     

104 (LED2, PJ2)

     

103 (LED1, PJ1)

   

102 (LED0, PJ0)

Bild 5.8: Schaltplan zur Ansteuerung der LEDs

AUFGABE: Steuern Sie über den Debugger die LED 0 und LED 2 an und schalten Sie die LED 1 und 3 aus. Welche Einstellungen müssen hierfür vorgenommen werden?

Welche Einstellungen müssen hierfür vorgenommen werden? Ergebnis Beim Zugriff auf die Register innerhalb eines

Ergebnis

Beim Zugriff auf die Register innerhalb eines C-Programms ist es sinnvoll, diese über #define zu definieren. Hierzu dient der Header „mb91364ec.h“. Durch #inlcu- de „mb91364ec.h“ können die Definitionen in das eigene Programm übernommen werden. Ein Zugriff auf die Register erfolgt dann über den entsprechenden Regis- ternamen. Ein Beispiel, welches die LED 0 einschaltet, zeigt Bild 5.9.

#include "irq.h" #include "mb91364ec.h"

// Zugriff auf Funktion initIRQ() // Zugriff auf Register

void main(void)

{

initIRQ();

// Freigabe Interrupt (Monitor-Programm

PFRJ = PFRJ | 0x0F; // Bit0…3 setzen, Sonderfunktion LED

while( 1 )

// Endlosschleife

{

PDRJ = ~0x01;

// Bit0 auf low (LED 0 aktiv), Rest aus.

}

}

Bild 5.9: Programm zur Ansteuerung der LED 0

30

AUFGABE: Schreiben Sie ein Programm, das ein kontinuierliches Lauflicht der LEDs (LED 0 - LED 1 - LED 2 - LED 3 - LED 0 -…) erzeugt. Nutzen Sie dabei den Schiebebefehl (a = a << 1; Inhalt von Variable a wird um 1 Bit nach links ver- schoben)

Inhalt von Variable a wird um 1 Bit nach links ver- schoben) Ergebnis AUFGABE: Schreiben Sie

Ergebnis

AUFGABE: Schreiben Sie eine Funktion (Übergabeparameter Wert 0…15), die den Übergabewert binärcodiert mit den LEDs darstellt.

ACHTUNG: nicht benutzte Bits (PFRJ 4

werden. Nutzen Sie die Funktion „Bit Setzen“, „Bit Löschen“ aus Kapitel 2.3.

dürfen nicht verändert

7,

PDRJ 4

7)

Ergebnis

31

AUFGABE: Schreiben Sie ein Funktion mit zwei Übergabeparameter mit den fol- genden Daten 1: Nummer der LED (0…3), Übergabeparameter 2: Zustand der LED (0 – aus, 1 – ein). Testen Sie diese Funktion und prüfen Sie, ob nicht benutzte Bits verändert werden.

dürfen nicht verändert

ACHTUNG: nicht benutzte Bits (PFRJ 4 werden.

7,

PDRJ 4

7)

Ergebnis

32

6 Strukturierte Programmierung

Elementares Kennzeichen zur Strukturierung von Programmen ist der Einsatz von Funktionen. Funktionen werden verwendet, wenn es wiederkehrende Aufgaben gibt. Funktionen sollten aber auch verwendet werden, um Informationen zu kap- seln. Hiermit ist gemeint, dass z.B. in der Hauptprogrammschleife kein Zugriff auf elementare Hardwareschnittstellen erfolgen soll.

Einsatz Funktionen

- Wiederholung

- Kapselung

#include "irq.h"

// Zugriff auf Funktion initIRQ() // Zugriff auf Register

   

#include "irq.h"

 

// Zugriff auf Funktion initIRQ() // Zugriff auf Register

 

#include "mb91364ec.h"

#include "mb91364ec.h"

void writeLED(char cValue)

// cValue: 0…15

1
1
 

void initLED(void)

 
2
2

{

{

 

char c;

PFRJ = PFRJ | 0x0F;

// Bit0-3 setzen, Sonderfunktion LED

c

= PDRJ;

// Zustand PDRJ lesen

}

 

c

= c | 0x0F;

// unteren 4 Bit ausschalten

 

void writeLED(char cValue)

// cValue: 0…15

1
1

cValue = cValue | 0xF0;

// nur untere 4 Bit auswerten

{

 

= c & ~cValue; PDRJ = c;

c

// aktive Bits invertieren

char c;

 

c

= PDRJ;

// Zustand PDRJ lesen

}

c

= c | 0x0F;

// unteren 4 Bit ausschalten

void main(void)

cValue = cValue | 0xF0;

// nur untere 4 Bit auswerten

{

char

c;

= c & ~cValue; PDRJ = c;

c

 

// aktive Bits invertieren

unsigned int

i;

}

 

i=0;

 

void main(void)

 

c=0;

initIRQ(); PFRJ = PFRJ | 0x0F; while( 1 )

c=0; initIRQ(); PFRJ = PFRJ | 0x0F; while( 1 )

// Freigabe Interrupt (Monitor-Programm) // Bit0-3 setzen, Sonderfunktion LED // Endlosschleife

{

char

unsigned int

i=0;

c;

i;

{

c=0;

i++;

initIRQ(); initLED(); while( 1 )
initIRQ();
initLED();
while( 1 )
 

// Freigabe Interrupt (Monitor-Programm) // LEDs freigeben // Endlosschleife

if (i>1000000)

// nicht jeden Durchlauf ausfuerhen

{

i=0; writeLED(c); c++;
i=0;
writeLED(c);
c++;
 

{

// Zustand ausgeben

 

i++;

if (i>1000000)

// nicht jeden Durchlauf ausfuerhen

if (c>0x000f)

{

c=0;

i=0; writeLED(c); c++;
i=0;
writeLED(c);
c++;
 

}

}

// Zustand ausgeben

}

if (c>0x000f)

 

c=0;

}

}

}

Bild 6.1: Verwendung von Funktionen in C

Das in Bild 6.1 links dargestellte Programm enthält die Funktion „writeLED“, wel- che die wiederkehrende Aufgabe der binärcodierten Ansteuerung übernimmt. Al- lerdings findet sich im Hauptprogramm links noch der Zugriff auf das PDRJ, wel- ches eine elementare Hardwareschnittstelle darstellt. Diese Information sollte über eine Funktion gekapselt werden, wie es im Bild 6.1 rechts dargestellt ist.

Eine weitere Möglichkeit zur Strukturierung von Programmen ist die Verwendung von Modulen. Ein Modul ist eine separate Datei (datei.c), welche lediglich Funkti- onen beinhaltet. Die Beschreibung des Moduls erfolgt über den sogenannten Hea- der (datei.h). Dieser Header muss im Hauptprogramm eingebunden (#include „da- tei.h“) werden.

main.c

#include "irq.h"

// Zugriff auf Funktion initIRQ() // Zugriff auf Register

 

#include "led.h"

#include "led.h"

void main(void)

 

{

char

c;

 

unsigned int

i;

i=0;

c=0;

initIRQ(); initLED(); while( 1 )

// Freigabe Interrupt (Monitor-Programm) // LEDs freigeben // Endlosschleife

{

i++;

if (i>1000000)

// nicht jeden Durchlauf ausfuerhen

{

i=0;

writeLED(c);

// Zustand ausgeben

c++;

if (c>0x000f)

 

c=0;

}

}

}

led.h

void initLED(void); void writeLED(char cValue);

// Initialisierung LEDs // cValue: 0…15

led.c

void initLED(void)

 

{

 

PFRJ = PFRJ | 0x0F;

// Bit0-3 setzen, Sonderfunktion LED

}

void writeLED(char cValue)

// cValue: 0…15

{

 

char c;

 

c

= PDRJ;

// Zustand PDRJ lesen

c

= c | 0x0F;

// unteren 4 Bit ausschalten

cValue = cValue | 0xF0;

// nur untere 4 Bit auswerten

= c & ~cValue; PDRJ = c;

c

// aktive Bits invertieren

}