In vielen Projekten benötigt der Mikrocontroller Schnittstellen, um mit der Außenwelt oder der Peripherie in Verbindung zu treten. Dabei kann es sich um eigenständige Geräte oder Komponenten handeln, die Messwerte, Einstellungen oder andere Informationen mit dem Mikrocontroller austauschen. In diesem Falle bedarf es meist eines mehr oder minder komplexen Übertragungsprotokolls, um beispielsweise verschiedene Teilnehmer des Kommunikationskanals zu differenzieren oder komplexe Datenstrukturen zu übertragen.
Eine andere Geräteklasse sind Hardware-orientierte Module wie beispielsweise A/D-Wandler, Speicher, Echtzeituhren oder Porterweiterungen, die die Hardware-Fähigkeiten des Systems erweitern, aber keine eigene Informationsverarbeitung besitzen. Hier kommt es dann eher darauf an, eine möglichst einfache Anbindung der Komponente an die Mikrocontroller-interne Speicherstruktur zu schaffen, die aber gegebenenfalls dafür mit größerem Datendurchsatz ausgestattet sein muss.
Da die Anzahl der Schnittstellen begrenzt ist, werden oftmals so genannte Bus-Systeme verwendet. Von einem Bus-System spricht man dann, wenn alle Komponenten die gleichen Signalleitungen verwenden und durch eine Protokoll- oder Steuerlogik festgelegt wird, welche der Komponenten im Moment die Leitungen verwenden darf.
Bei der Datenübertragung unterscheidet man prinzipiell parallele und serielle Datenübertragung. Während bei paralleler Übertragung für jedes Datenbit eine eigene Leitung zur Verfügung steht, wird bei einer seriellen Datenübertragung die Information sequentiell übertragen. Beispiele für eine serielle Datenübertragung sind der I2C-Bus, der SPI-Bus sowie das RS232-Protokoll. Die im MSP430 integrierten Kommunikationsmodule implementieren genau diese und sollen in den folgenden Kapiteln vorgestellt werden. Natürlich kann man mit dem MSP430 auch eine parallele Datenübertragung realisieren, aber dies setzt man direkt mit den digitalen I/O-Ports um. Eine spezielle Unterstützung definierter Kommunikationsstandards gibt es hier nicht, und das jeweilige Kommunikationsprotokoll muss ”von Hand” umgesetzt werden.
Die RS232-Schnittstelle ist und bleibt die beliebteste Schnittstelle für Elektronikprojekte, wenn es darum geht Informationen zum PC zu übertragen. Sie ist gut in die meisten Betriebssysteme eingebunden, wird ohne spezielle Treiber unterstützt, es gibt viele einfache Programme, die eingehende Daten anzeigen (z.B. Hyperterminal) und bis vor kurzem hatte auch jeder PC eine solche Schnittstelle. Glücklicherweise sind auch heute noch USB-RS232-Adapter für kleines Geld zu bekommen, so dass die RS232-Schnittstelle zumindest im Embedded-Sektor ihre Bedeutung behalten wird. Ursprünglich einmal zur Kommunikation über Telefonleitungen mit unglaublichen 300 Baud verwendet, kann man bei kurzen Leitungslängen mittlerweile ganz ordentliche Datenraten von 115200 Baud und mehr erreichen.
Zur Umsetzung der Kommunikation werden insgesamt drei Leitungen benötigt. Zwei Datenleitungen (Send und Receive) sowie eine Masseverbindung. Die Logikpegel der Schnittstelle sind -12V und +12V, wobei letzterer einer logischen 1 entspricht. Im Gegensatz zu SPI und I2C fehlt aber eine Taktleitung. Beim asynchronen Protokoll der Schnittstelle werden vielmehr das Timing (bzw. die Datenrate) und weitere Festlegungen des Protokolls im Vorhinein vereinbart. Zum Start des Datenrahmens wird zur Synchronisierung ein Start-Bit gesendet. Danach folgen die sieben oder acht Datenbits, wobei das niederwertigste Bit (LSB - Least Significant Bit) zuerst gesendet wird. Darauf folgt das Parity-Bit und der Frame wird mit 1, 1.5 oder 2 Stopp-Bits beendet. Ein Beispiel einer vollständigen Übertragungssequenz ist in Bild 8.1 zu sehen.
Da in der Frühzeit der Digitalrechner auch die Telefonleitungen nur in eine Richtung Daten übertragen konnten bzw. die Endgeräte nicht schnell genug waren, gleichzeitig Sende- und Empfangsbetrieb zu realisieren, wurde die Datenübertragung mitunter nur im Halb-Duplex, d.h. abwechselnd nur in eine Richtung betrieben. Zur Koordinierung dieses Betriebs besitzt die RS232-Schnittstelle Mechanismen, beide Kommunikationsteilnehmer zu koordinieren (sog. Handshake). Beim Software-Handshake werden Beginn und Ende eines Datenpaketes durch ein Steuerzeichen (meist 0x11 für den Beginn und 0x13 für das Ende) markiert. Alternativ sendet der Empfänger diese Steuerzeichen um anzuzeigen ob er empfangsbereit ist oder micht. Allerdings setzt das natürlich voraus, dass diese Zeichen dann nicht mehr in den Nutzdaten verwendet werden dürfen. Als dritte Möglichkeit besitzt die RS232-Schnittstelle auch Statusleitungen, die für ein Hardware-Handshake verwendet werden können. Die Leitungen CTS (Clear to Send) und RTS (Request to send) wurden dafür vorgesehen. Bild 8.2 zeigt die typischen 9-Pol-Sub-D-Stecker einer RS232-Schnittstelle und Tabelle 8.1 die zugehörige Pinbelegung.
Abkürzung | Bezeichnung | Pin | Richtung |
DCD | Data Carrier Detect | Pin 1 | IN |
RxD | Receive Data | Pin 2 | IN |
TxD | Transmit Data | Pin 3 | OUT |
DTR | Data Terminal Ready | Pin 4 | OUT |
GND | Ground = Masse | Pin 5 | |
DSR | Data Set Ready | Pin 6 | IN |
RTS | Request to Send | Pin 7 | OUT |
CTS | Clear to Send | Pin 8 | IN |
RI | Ring Indicator | Pin 9 | IN |
Die Pegel der RS232-Schnittstelle sind invertiert. Das heißt ein logischer HIGH-Pegel wird durch ein Signal von -12V repräsentiert, ein logischer LOW-Pegel entspricht einem Pegel von +12V. Demgegenüber folgen die Ausgangssignale des MSP430 dem normalen Pegelschema mit VCC als HIGH-Pegel und GND als LOW-Pegel. Realisierungen einer geeigneten Pegelwandlerschaltung finden sich in Kapitel 9.4.5
Der Inter-Integrated-Circuit-Bus (kurz I2C, gesprochen I-square-C) ist ein von der Firma Philips entwickelter serieller Datenbus, der mit einer Takt- und einer Datenleitung arbeitet. Da I2C eine Bezeichnung von Philips bzw. des Nachfolgers NXP ist, verwenden einige Hersteller auch die Bezeichnung TWI für Two-Wire-Interface. Das zugehörige Patent ist 2006 abgelaufen, so dass mittlerweile lizenzfrei alle Hersteller dieses Protokoll nutzen können. Eine Vielzahl von Komponenten, wie Temperatur- oder Beschleunigungssensoren, EEPROM-Speicher oder Echtzeituhren können mit dem Bus angesteuert werden. Grundsätzliche Informationen sind beispielsweise auf der Hersteller-Homepage [NXP09] zu finden. Neben der eigentlichen Spezifikation [PS00] bietet auch das dort angebotene I2C-Manual [PS03] wertvolle Hintergrundinformationen.
Wie schon erwähnt sind für den Betrieb des Busses neben der Versorgungsspannung und dem Masseanschluss im Wesentlichen nur zwei Leitungen erforderlich. Die Taktleitung wird als Serial-Clock, kurz SCL, und die Datenleitung als Serial-Data (SDA) bezeichnet. Ein typischer Aufbau eines I2C-Netzwerks ist in Bild 8.3 dargestellt.
Die Widerstände RP sind Pull-Up-Widerstände. Um bei Signalkollisionen keine Kurzschlüsse zu verursachen, hat ein I2C-Knoten nur einen Open-Kollektor-Ausgang. Das heißt, er kann die Datenleitung nur aktiv auf Masse schalten. Der HIGH-Signalpegel entsteht bei hochohmiger Stellung aller Ausgangstransistoren durch die Pull-Up-Widerstände. Die Dimensionierung dieser Widerstände hängt von verschiedenen Faktoren, wie parasitären Kapazitäten, Längswiderstand der Leitung, Leitungslänge und beabsichtigter Übertragungsgeschwindigkeit ab. Üblicherweise ist ein Pull-Up-Widerstand im Bereich von 10kΩ bis 1MΩ ausreichend. Den Aufbau dieses Netzwerks bezeichnet man als Master-Slave-Netzwerk, wobei der Mikrocontroller den Master und die Sensoren, das EEPROM und die Echtzeituhr RTC die Slave-Komponenten darstellen. Es gibt noch andere Strukturen, wie Multi-Master-Systeme, auf die wir hier nicht näher eingehen. Beim Master-Slave-Netzwerk wird die Taktleitung nur vom Master gesteuert. Die Datenleitung ist bidirektional. Das heißt, der Informationsaustausch erfolgt sowohl vom Master (MSP430) als auch von den Slaves gemeinsam über SDA.
Wie in der Abbildung zu erkennen ist, wird ein vom Mikrocontroller gesendeter Befehl von allen Slaves empfangen, da sich ja alle Komponenten eine Daten- und eine Taktleitung teilen. Aus diesem Grund verfügt jede Slave-Komponente im Netzwerk über eine eindeutige Adresse, die zu Beginn des Datenaustauschs vom Master quasi als Aktivierungsbefehl gesendet werden muss. Je nach Spezifikation des I2C-Busses ist die Adresse 8 oder 10 Bit breit. In der Regel ist in der Komponente eine feste 4 Bit breite Stammadresse implementiert. Mit herausgeführten Pins (häufig „A0“ bis „A2“ genannt) kann man weitere drei Bits festlegen. Damit lassen sich also 23 = 8 verschiedene Komponenten mit der gleichen Stammadresse unterscheiden. Das niederwertigste Bit, das LSB, definiert, ob auf die Komponente lesend (LSB = 1) oder schreibend (LSB = 0) zugegriffen werden soll. Einige Komponenten verfügen nicht über herausgeführte Pins. Ihre Adresse ist (bis auf die Zugriffsart lesend oder schreibend) fest implementiert. Um dennoch unterschiedliche Komponenten des gleichen Typs im selben Bus unterscheiden zu können, gibt es unterschiedliche Ausführungen dieser Bausteine mit unterschiedlichen fest einprogrammierten Adressen. Die genaue Spezifikation ist dabei dem jeweiligen Datenblatt des Bausteins zu entnehmen.
Die ursprüngliche inoffizielle Spezifikation aus den 1980iger Jahren sah eine 8 Bit breite Adresse mit einer maximalen Datenrate von 100kBit∕s vor. Die heute verfügbaren Komponenten lassen sich in der Regel alle über diesen Standard ansprechen. 1992 veröffentliche Philips die Spezifikation 1.0, die neben einer 10-Bit-Adresse nun auch einen schnelleren 400kBit∕s-Modus vorsah. Dabei wurde die Abwärtskompatibilität beibehalten. Die aktuelle Spezifikation 2.1 aus dem Jahr 2000 sieht einen Hochgeschwindigkeits-Modus mit einer Datenrate von 3.4MBit∕s vor. Für die meisten Anwendungen reicht aber die ursprüngliche Spezifikation aus, auf die wir hier näher eingehen werden. Prinzipiell sollte beachtet werden, dass diese Datenraten nur maximale Richtwerte sind. Die eigentliche Bus-Geschwindigkeit legt der Master fest und die Slave-Komponenten müssen in dem vorgegebenen Takt antworten. Aus diesem Grund ist der I2C-Bus sehr einfach auf einem Mikrocontroller per Software zu implementieren.
Bild 8.4 verdeutlicht die Zusammensetzung einer typischen Adresse im I2C-Bus. Wir gehen dabei von einer 4 Bit breiten Stammadresse und drei frei wählbaren Adressbits A0 bis A2 aus. Das unterste Bit, das LSB, legt den Zugriffsmodus (1: lesend, 0: schreibend) fest.
Das Ablaufdiagramm in Bild 8.5 verdeutlicht den Datenfluss für den Fall eines typischen Informationsaustausches. Dieser findet in einem Datenrahmen statt, der durch eine Start-Stopp-Bedingung eingeleitet und terminiert wird.
Das Ablaufdiagramm könnte zum Beispiel die Auswertung der Temperatur mit einem I2C-Temperatursensor beschreiben. Damit der Sensor die Temperatur erfassen kann, muss der Master einen Befehl zur Messung der Temperatur senden. Der Zugriff erfolgt dabei schreibend, sonst könnte der Master der Slave-Komponente keinen Befehl senden. Nachdem die Adresse gesendet wurde, besteht ausschließlich eine logische Verbindung zwischen Master und dem entsprechenden Slave. Der Mikrocontroller kann nun den Befehl zur Messung der Temperatur senden und danach mit der Stopp-Bedingung die Kommunikation terminieren. Das ist erforderlich, weil auf die Slave-Komponente nun lesend (also mit einer anderen Adresse) zugegriffen wird, um die Temperatur zu lesen. In diesem Fall sendet der Master nach einer Start-Bedingung die Adresse der Slave-Komponente inkrementiert um 1 (lesender Zugriff). Der Master kann nun mit dem Senden von Taktimpulsen den Messwert einlesen. Mit der Stopp-Bedingung wird auch dieser Informationsaustausch terminiert und der Bus in den ursprünglichen Zustand versetzt.
Der Ablauf der Übertragung von Bits ist in Bild 8.6 skizziert. Start- und Stopp-Bedingungen sind wichtig, damit alle Komponenten auf den Beginn und das Ende eines Datenaustausches synchronisieren können und auf die Adresse des Bausteins warten. Vor Beginn der Übertragung sind Daten- und Taktleitung auf HIGH gesetzt. Bei der Start-Bedingung wird zunächst die SDA-Leitung und anschließend die SCL-Leitung auf den LOW-Pegel gezogen. Die Stopp-Bedingung läuft genau umgekehrt ab. Hier wird zunächst SCL und dann SDA auf HIGH gesetzt. Die Übertragung von Bits erfolgt, indem je nach Zustand des zu übertragenen Bits (0 oder 1) die SDA-Leitung auf LOW oder HIGH gesetzt wird. Mit einem kurzen Puls der SCL-Leitung wird das Bit dann gesendet. Analog dazu wird beim Empfangen die SCL-Leitung kurz auf HIGH gesetzt und der Zustand der SDA-Leitung erfasst.
Die Übertragung von Informationen erfolgt in Bytesequenzen aus jeweils acht Bits. Jedes Byte wird bei der Übertragung vom Master zum Slave durch ein Acknowledge-Signal bestätigt. Dabei sendet der Master einen neunten Taktimpuls über die SCL-Leitung. Die Signalleitung SDA muss dann vom Slave auf dem LOW-Pegel liegen. Ein fehlendes Acknowledge-Signal weist auf einen Fehler in der Kommunikation hin. Zum Beispiel könnte ein Takt während der Übertragung nicht korrekt empfangen worden sein. In diesem Fall muss die Übertragung mit der Stopp-Bedingung abgebrochen und erneut durchgeführt werden.
Die Übertragung eines Bytes mit Start- und Stop-Bedingung und Acknowledge-Signal ist in Bild 8.7 dargestellt. Während der Übertragung der ersten acht Bits ist der SDA-Port des Slaves als Eingang definiert und der SDA-Port des Masters als Ausgang. Nach dem achten Bit ändert sich diese Einstellung, so wird der Master-Port zum Eingang und der Slave-Port zum Ausgang, damit der Master das Acknowledge-Signal empfangen kann.
Der Synchronous-Peripheral-Interface-Bus, kurz SPI (oft auch Serial-Peripheral-Interface-Bus genannt) ist ein ursprünglich von Motorola entwickeltes Bus-System. Im Vergleich zu I2C ist der ebenfalls auf dem Master-Slave-Netzwerk basierende SPI-Bus weit weniger spezifiziert und lässt der Anpassung an eigene Protokolle mehr Spielräume. Ein großer Teil der Bausteine, die mit dem I2C-Bus angesprochen werden können, sind auch in einer SPI-kompatiblen Bauweise erhältlich. Ein Betrieb von SPI-Bausteinen an einem I2C-Bus und umgekehrt ist dabei allerdings nicht möglich.
Vom Master geht wie beim I2C-Bus eine Taktleitung SCK aus, allerdings erfolgt der Datenaustausch auf der Datenleitung nicht bidirektional. Das heißt, dass der Master eine Leitung zum Senden (MOSI = Master OUT - Slave IN) und eine Leitung zum Empfangen (MISO = Master IN - Slave OUT) benötigt. Mitunter ist eine Leitung zum Senden nicht erforderlich, wenn der Master Daten nur empfangen soll. Wir kommen darauf später noch zurück. Ein weiterer Unterschied zum I2C-Bus ist das Fehlen einer Adresse zur Auswahl einer bestimmten Slave-Komponente.
Die Ansteuerung bzw. Auswahl eines oder mehrerer Slaves erfolgt in Hardware über eine oder mehrere Chip-Select-Leitungen (kurz CS, oft auch Slave-Select, dann mit der Abkürzung SS). Der Informationsaustausch eines Masters mit einer angeschlossenen Slave-Komponente ist in Bild 8.8 dargestellt. Um die Informationsübertragung einzuleiten, muss die Chip-Select-Leitung vom LOW- auf den HIGH-Pegel gezogen werden (bei einigen SPI-Komponenten ist es genau umgekehrt, hier sollte das Datenblatt genau beachtet werden). Damit wird die Kommunikation initiiert. Die Datenübertragung erfolgt dann gleichzeitig in beide Richtungen, wobei die Übertragung mit der Taktleitung vom Master gesteuert wird. Hierbei kann der Slave sofort mit der Datenübertragung beginnen (zum Beispiel mit einem AD-Wert). Mitunter muss aber auch erst ein Kommando an den Slave übertragen werden, so dass dieser weiß, welche Funktion gewünscht ist. Die Kommunikation kann aus beliebig vielen aufeinanderfolgenden Bytesequenzen bestehen. Nach Abschluss der Kommunikation schaltet der Master die Chip-Select-Leitung wieder auf den LOW-Pegel.
Der SPI-Bus lässt sich in zwei Netzwerk-Topologien verschalten: Stern- und Kaskaden-Verbindung, die in Bild 8.9 dargestellt sind. Dabei ist SCK die serielle Taktleitung, CS bzw. CS1 bis CS3 die Chip-Select- Leitungen, MISO die Master-In-Slave-Out und MOSI die Master-Out-Slave-In-Leitung. Bei der Stern-Topologie kann jeder Slave einzeln angesteuert werden. Im Gegensatz dazu werden bei der Kaskadierung alle Slaves gleichzeitig aktiviert. Die Übertragung der Informationen zum Master erfolgt dann von Slave zu Slave, bis zum letzten Slave in der Kette, der die Daten an den Master weiterleitet.
Wie schon erwähnt ist der SPI-Bus auf Protokollebene nicht so detailliert spezifiziert, wie beispielsweise das I2C-Protokoll. Daher ist der Daten- und Informationsfluss abhängig von der gewählten Slave-Komponente. Insgesamt haben sich vier sogenannte SPI-Modes durchgesetzt, die sich im Timing des Protokolls unterscheiden. Dazu werden zwei Bezeichnungen eingeführt: CKPL und CKPH. Während CKPL die Polarität der Clock-Leitung in Übertragungspausen kennzeichnet, bezeichnet CKPH die Phase des Clock-Signals, ob der Signalwechsel der Clock-Leitung am Anfang oder in der Mitte des Datenframes erfolgt. Nachfolgendes Bild 8.10 zeigt das Timing des SPI-Übertragungsprotokolls in den verschiedenen Übertragungsmodi. Dabei muss die Datenübertragung auch nicht zwingend schon nach acht Bits zu Ende sein, sondern kann auch beliebige Bitfolgenlängen dauern. Einzig die Registerlängen von Master und Slave müssen diese aufnehmen können, sonst ginge Information verloren.
Stellvertretend für einen typischen Datenaustausch betrachten wir in diesem Abschnitt die Auswertung eines analogen Messsignals mit dem ADS7816, einem 12-Bit-SPI-A/D-Wandler.
Der Chip befindet sich bei einem am Eingang CS anliegenden HIGH-Pegel im Ruhemodus. Sobald der Master den CS-Eingang des A/D-Wandlers auf Masse zieht, beginnt der Chip mit der Erfassung und Wandlung des analogen Signals. Während dieser so genannten Sample-Phase wird der analoge Messwert erfasst. Die zeitliche Steuerung erfolgt mit Hilfe der Taktflanken der seriellen Clock-Leitung durch den Master. Das Ende der Sample-Zeit wird dem Master durch einen LOW-Pegel der MISO-Leitung (bzw. der DOUT-Leitung, also der Datenleitung vom Slave zum Master) angezeigt. Danach wird bei jedem weiteren Taktflankenpuls über die MISO-Leitung das 12 Bit breite digitale Ergebnis der A/D-Wandlung gesendet. Dabei beginnt die Übertragung mit dem MSB. Jetzt setzt der Master die CS-Leitung wieder auf den HIGH-Pegel, um den Chip in den Ruhemodus zu versetzen. Ein Ablaufschema der Daten- und Informationsübertragung ist in Bild 8.11 dargestellt. An Hand dieses Beispiels wird ersichtlich, dass im Gegensatz zum I2C-Bus nicht bei jedem SPI-Device eine Leitung zum Übertragen von Befehlen vom Master zum Slave benötigt wird, andererseits auch das SPI-Übertragungsprotokoll sehr gerätespezifisch interpretiert werden kann und muss, um den notwendigen Logikaufwand in der Peripherie so gering wie möglich zu halten.