Das Diagramm in Abbildung 2 verdeutlicht den Aufbau einer seriellen Datenübertragung. Reale Schaltungen invertieren häufig die Signalpegel – wundern Sie sich also nicht, wenn Sie die Information in Quellen genau andersherum sehen.

Abbildung 2: Beim asynchronen seriellen Übertragen der Daten senden die Gegenstellen neben den eigentlichen Daten außerdem Bits, die Beginn und Ende eines Transfers kennzeichnen.
Bei frühen CPUs mit Taktraten im einstelligen MHz-Bereich war es ziemlich schwierig bis unmöglich, eine serielle Schnittstelle in Software zu implementieren. Daher verbauten die Rechnerhersteller einen speziell für diesen Zweck entwickelten Halbleiter in den Schnittstellen, den sogenannten UART. Das Kürzel steht für “Universal Asynchronous Receiver/Transmitter”. Ein solcher verfügt über eigene Puffer und unterschiedliche Mechanismen zum Steuern des Datenflusses.
Letztere dienen unter anderem dazu, dem Sender über zusätzliche Steuerleitungen mitzuteilen, dass er die Datenübertragung unterbrechen soll. Damit bremst der Empfänger die Übermittlung, wenn er nicht in der Lage ist, die Daten schnell genug zu verarbeiten. Alles in allem waren UARTs sehr flexibel, recht kompliziert und auch teuer. Dank höherer Taktraten kann heute meist der Chipsatz des Rechners ihre Funktionen übernehmen.
Entwicklungsumgebung
Um mehrere serielle Interfaces zu implementieren, verwenden Sie eine Bibliothek des Arduino-Projekts, die eine serielle Schnittstelle als Software-Implementation bereitstellt. Das ermöglicht es, fast jeden GPIO-Pin des ESP8266 zu einer seriellen Schnittstelle zu machen. “Fast” bedeutet in diesem Zusammenhang, dass Sie die Pins 0 bis 5 und 12 bis 15 für serielle Schnittstellen verwenden dürfen. Damit lässt sich der ESP8266 mit bis zu fünf solcher Interfaces ausstatten.
Um die Daten dann anzuzeigen, kommt ein einfacher Webserver zum Einsatz, der auf dem ESP8266 läuft. Als Entwicklungsumgebung dient die Arduino IDE, die Sie aus Teil 1 dieser Reihe bereits kennen. Dort finden Sie auch eine detaillierte Beschreibung zur Installation der IDE.
Testaufbau
Für das Projekt wurde der Testaufbau (Abbildung 3) fest auf einer Lochrasterplatine verlötet, da er in der Nähe der Elektroverteilung zum Einsatz kommt. Dort ist es sicherer, alle Bauteile fest zu verbinden.

Abbildung 3: Testaufbau auf einer Prototypen-Platine fest verlötet, da die Komponenten in der Nähe der Elektroverteilung zum Einsatz kommen.

Abbildung 4: Der Schaltplan zu unserem Testaufbau zeigt eine ganze Reihe von altbekannten Bauteilen.
Den zugehörigen Schaltplan zeigt Abbildung 4. Der Aufbau besteht aus den bekannten Bauteilen, die man benötigt, um den ESP8266 zu betreiben und Programme hochzuladen. Der TTL-Lesekopf ist über Schraubverbinder an die Platine angeschlossen, die zwei Datenleitungen des Lesekopfs hängen an den GPIOs 14 und 12 des ESP8266.
Die Spannungsversorgung basiert auf dem DC/DC-Modul OKLT1W12NC [3]. Es bietet mit 2,9 bis 14 Volt einen weiten Bereich für die Eingangsspannung. Als Spannungsquelle kommt ein USB-Netzteil oder eine im Schaltschrank möglicherweise vorhandene Spannungsquelle mit 12 Volt infrage. Das als Schaltregler ausgeführte OKLT1W12NC hat einen Wirkungsgrad von etwa 90 Prozent, die Ausgangsspannung legen Sie über einen Spannungsteiler fest.
Beim Widerstand R5 handelt es sich um ein Spindelpoti, mit dem sich die Ausgangsspannung des Wandlermoduls sehr präzise einstellen lässt. Prüfen Sie beim Zusammenbau unbedingt erst die Versorgungsspannung, bevor Sie Jumper 3 schließen: Ansonsten besteht die Gefahr, den ESP8266 dauerhaft zu beschädigen. Der Kondensator C1 stabilisiert die Betriebspannung des ESP8266, was die komplette Schaltung weniger anfällig für Störungen macht. Je nachdem, wie dicht Sie die Elektronik an den Starkstrom führenden Teilen positionieren, treten erhebliche Störungen auf.
Falls Sie eine Adapterplatine für den ESP8266 verwenden, sollten Sie vorab prüfen, welche Widerstände dort schon bestückt sind und ob Sie einen davon überbrücken müssen. Bei einigen Adapterplatinen liegt in der Zuleitung für VCC ein 10-kOhm-Widerstand – üblicherweise keine gute Idee.
Testprogramm
Das Testprogramm stellt einen Webserver bereit, der die Daten zum Verbrauch aus dem Stromzähler anzeigt. Abbildung 5 demonstriert die Ausgabe des Programms, den Quellcode dazu sehen Sie in Listing 1.

Abbildung 5: Ein eigens auf dem ESP8266 installierter Webserver übernimmt die Ausgabe der Daten aus dem intelligenten Stromzähler.
Listing 1
#include <ESP8266WiFi.h>
#include <WiFiClient.h>
#include <ESP8266WebServer.h>
#include <SoftwareSerial.h>
const char* ssid = "SSID WLAN";
const char* pass = "Passwort";
IPAddress serverip(192, 168, 1, 99);
IPAddress gateway(192, 168, 1, 1);
IPAddress subnet(255, 255, 255, 0);
IPAddress dns(192, 168, 1, 1);
ESP8266WebServer server(80);
SoftwareSerial irSerial(14, 12, false, 512); // RX, TX, inverse, buffsize
void handleRoot() {
String data;
String message = "";
message += "<html><body>\n";
message += "Verbrauchswerte<BR>";
message += data;
message += "\n";
Serial.println("Send /?!");
irSerial.write(0xAF); // "/"
irSerial.write(0x3F); // "?"
irSerial.write(0x21); // "!"
irSerial.write(0x8D); // "\r"
irSerial.write(0x0A); // "\n"
data ="";
delay(1000);
while(irSerial.available() > 0) {
yield();
char in = irSerial.read();
in &= 0x7F;
data = data + String(in);
delay(10);
}
Serial.println(data);
Serial.println("Send -000");
irSerial.write(0x06); // "-"
irSerial.write(0x30); // "0"
irSerial.write(0x30); // "0"
irSerial.write(0x30); // "0"
irSerial.write(0x8D); // "\r"
irSerial.write(0x0A); // "\n"
delay(4000);
data ="";
while(irSerial.available() > 0) {
yield();
char in = irSerial.read();
in &= 0x7F;
if (in==0x0A) data = data + "<br>";
data=data + String(in);
delay(10);
}
Serial.println(data);
delay(5000);
message += data;
message += "</body></html>\n";
server.send(200, "text/html", message);
}
void setup(void) {
irSerial.begin(300);
Serial.begin(115200);
WiFi.begin(ssid, pass);
WiFi.config(serverip, gateway, subnet, dns);
while(WiFi.status() != WL_CONNECTED) {
delay(500);
Serial.print(".");
}
Serial.println("");
Serial.print("Connected to ");
Serial.println(ssid);
Serial.print("IP address: ");
Serial.println(WiFi.localIP());
server.on("/", handleRoot);
server.begin();
Serial.println("HTTP server started");
}
void loop(void) {
server.handleClient();
}
Haben Sie alle nötigen Bibliotheken importiert, definieren Sie die für den Betrieb nötigen Konstanten. Achten Sie darauf, die passenden Zugangsdaten für das WLAN in Ihrem Netzwerk zu verwenden. Darüber hinaus passen Sie die IP-Konfiguration des Servers an die IP-Range im LAN an.
Das Objekt SoftwareSerial irSerial (Zeile 14) initialisieren Sie mit den Pinnummern für RX und TX, der Größe des Puffers und einem Parameter zum Invertieren des Signals. Haben Sie versehentlich die zwei Datenleitungen vertauscht, brauchen Sie deswegen auch nicht zum Lötkolben zu greifen: Sie “verdrahten” sie einfach an dieser Stelle im Programm wieder richtig.
Die Größe des Lesepuffers ist ein sehr wichtiger Parameter, den Sie mit Bedacht wählen sollten. Das Testprogramm wartet zunächst, bis die komplette Nachricht des Stromzählers im Buffer ankommt, und beginnt dann erst, ihn auszulesen. Entsprechende Buffer baut man immer als Ringspeicher auf: Laufen sie voll, überschreibt der Rechner die ältesten Daten.
Jetzt bleibt noch zu klären, was der Parameter inverse in Zeile 14 bewirkt. Zu Anfang des Artikels haben wir kurz erwähnt, dass es unter Umständen vorkommt, dass ein System die Daten invertiert überträgt. Die in Software implementierte serielle Schnittstelle arbeitet von Haus aus nicht invertiert. Falls Sie sie aber mit einem invertiert arbeitenden Gerät verbinden, können Sie über diesen Parameter das Verhalten der Schnittstelle anpassen.





