Donnerstag, 25. September 2014

Ein Rigol DS1052E 50Mhz Oszilloskop in ein 100Mhz MSO verwandeln?

Ich bin ja schon seit längerem auf der Suche nach einem brauchbarem Logic Analyzer für meine Hobbyprojekte. Vor einiger Zeit habe ich mir aus einem STM32F4Discovery Board einen simplen 16 Kanal Logic Analyzer gebaut, auf das ich in einem späteren Blogpost nochmal genauer eingehen werde. Es gibt ja so einige günstige Logic Analyzer am Markt wie z.B. den Sealogic 8 Kanal USB Logicanalyzer. Für kleine Arduino basteleien sind die sogar recht ok. Allerdings haben die in der Regel nur sehr begrenzten Speicher und mit 20Mhz eine ziemlich lächerliche Bandbreite.

Als ich letztens einige ältere EEVblog Folgen durchstöberte und mir eher aus Langeweile einen Teardown eines Rigol DS1052E Oszilloskops anschaute, hat es ziemlich schnell mein Interesse geweckt. Nicht nur dass es verglichen mit anderen Oszilloskopen recht günstig ist, es ist auch recht gut verarbeitet und es gibt das gleiche Oszilloskop auch als MSO (Mixed Signal Oszilloscope), also mit zusätzlicher logic analyzer Funktionalität. Einige Videos weiter wurde es noch interessanter. Vom DS1052E, was eine Bandbreite von 50MHz hat, gibt es ein baugleiches Modell mit der Bezeichnung DS1102E was 100Mhz Bandbreite hat. Das Oszi kann also technisch 100Mhz, wird aber per Software künstlich auf 50Mhz beschnitten und dann günstiger verkauft. Mit einem einfachen Software-Mod kann man ein DS1052E also in ein 100Mhz Oszilloskop verwandeln! 100Mhz sind jetzt auch nicht die Welt, aber für etwa 300€ Kaufpreis ist das schon recht in Ordnung.

Aber ich bin ja eigentlich auf der Suche nach einem Logic Analyzer. Die Frage, die ich mir derzeit stelle ist, ob es wohl möglich sei, das DS1052E in ein DS1102D zu verwandeln. Im DS1052E Teardown sieht man, dass ungenutzte Pinheader vorhanden sind. Nach etwas recherche fand ich dann heraus, dass das Logic Analyzer Eingänge sind. Prinzipell müsste man also nur das Logicanalyzermodul nachbauen, passende Tastköpfe verbauen und die entsprechende Firmware auf das Oszi flashen. Wenn das wirklich funktionieren sollte, werde ich mir das Oszi besorgen und den Mod durchführen. Weitere Infos gibts demnächst in einem weiteren Post.

Montag, 22. September 2014

Einen Bus mit RS485 aufbauen

[Under Construction] (Achtung, der Beitrag ist noch nicht ganz fertig!)


Wenn man mit Microcontrollern arbeitet, will man früher oder später mehrere Microcontroller miteinander reden lassen. Eine bewährte Möglichkeit ist die Serielle Schnittstelle (Auch UART oder RS232 genannt). Will man aber mehr als zwei Microcontroller miteinander kommunizieren lassen, kann es schnell kompliziert werden, zumal viele Microcontroller gerade mal eine einzige serielle Schnittstelle bieten. Prinzipell könnte man einfach mehrere Sender und Empfänger jeweils gleichzeitig auf ein und die selben TX und RX Leitungen hängen, allerdings muss man dafür sorgen, dass niemals zwei Teilnehmer gleichzeitig senden. Außerdem darf man niemals zwei GPIO Ausgänge zusammen schalten (Was bei mehreren Microcontrollern auf der gleichen TX-Leitung der Fall ist), da man sich damit seine Hardware zerschießen kann. Die Lösung des Problems liegt in einem Bussystem. In der Industrie ist der RS485 Bus sehr verbreitet. Das mag vielleicht kompliziert klingen, ist es aber eigentlich nicht. In diesem Beitrag gebe ich einleitende Informationen zu RS485 und zeige am Ende eine kleine Beispielschaltung zum nachbauen. Wer diese Seite also über google gefunden hat und es nicht abwarten kann, kann also Direkt zu Abschnitt 3 springen. Wer sich tiefer für die Materie interessiert, liest einfach weiter.

1. Was ist RS485? Wo ist der Unterschied zu RS232?

Bei RS485 handelt es sich um einen sogenannten Feldbus. Das Wort Feld bedeutet salopp gesagt, dass das Übertragungskabel nicht nur unter Laborbedingungen gut funktioniert, sondern dass man es getrost auch mal "in den dreck" schmeißen kann und auch bei Umgebungen mit Störeinflüssen immer noch eine saubere Datenübertragung hat. Der Grund, warum das bei RS485 funktioniert, ist die Differentialübertragung. D.h. Es werden zwei Leitungen für die gleiche Information genutzt, die sog. A und B Leitung. In einigen Bussystemen auch Busplus und Busminus genannt. Auf Kanal A wird die Information genauso wie bei RS232 übertragen. Auf Kanal B allerdings invertiert. Der Empfänger subtrahiert nun beide Signale und wertet das Ergebnis aus. Wenn jetzt von außen eine Störung einstreut (Gleichtaktstörung), rechnet sich der Fehler wieder heraus:



Im diesem Bild ist der Signalverlauf von Leitung A und B dargestellt. Der untere Signalverlauf ist das Ergebnis, was der Empfänger "sieht". Eine fehlerhafte Einstreuung ist in Rot dargestellt. (Sowas passiert z.B. wenn man das Licht einschaltet). Da der gleiche Fehler auf beiden Leitungen auftritt, wird der Fehler herausgerechnet und ist im resultierendem Signal praktisch nicht mehr vorhanden.

Hier ein etwas extremeres Beispiel:



Hierbei handelt es sich zwar nicht um RS485 sondern um den FlexRay Bus, dieser verwendet jedoch ebenfalls ein Differenzsignal. Grün ist hierbei Kanal A, Blau ist Kanal B. Und Rot ist das resultierende Signal, was nach Subtraktion von A und B herauskommt. Man sieht hier sehr deutlich ein unsauberes Eingangssignal. Und Obwohl die Kurven sehr verbogen aussehen, kommt am Ende ein sauberes Signal heraus, weil sich der Fehler herausrechnen lässt. Ohne Differenzsignal würde man hier unter Umständen Datenmüll erhalten.

2. Warum einen Bus verwenden?


Bei einem Bussystem werden mehrere Teilnehmer mit nur einer einzigen Leitung verbunden..Das ist sehr vorteilhaft, da man nicht jedes mal eine extra Leitung zu jedem Teilnehmer ziehen muss und somit GPIO Pins sparen kann. Ich habe derzeit ein Projekt, bei dem ich genau vor diesem Problem stehe. Ich habe einen Hauptcontroller und acht weitere Microcontroller (Slaves), denen ich Befehle geben möchte. In Zukunft plane ich noch mehr Slaves zu verwenden und so langsam entwickelt sich auf meiner Platine ein regelrechter Kabelsalat.

In diesem Abschnitt möchte ich erläutern, wie man einen RS485 Baustein verschalten muss und was es mit den merkwürdigen Pinbezeichnungen auf sich hat. Ich beziehe mich hierbei auf einen MAX485 Baustein. Schauen wir uns die Pins also einmal an:




Die Belegung der Pins ist:

1: RO (Receiver Output)
2: /RE (Receive Output Enable)
3: DE (Driver Outputs Enable)
4: DI (Driver Input)
5: GND (Masse)
6: A (Bus Plus)
7: B (Bus Minus)
8: Vcc (+5V)

Setzt man /RE auf low, wird der Transceiver in den Empfangsmodus versetzt. Sämtliche Busaktivitäten an den A und B pins wird dann an den RO pin weitergeleitet, der beim Microcontroller überlicherweise mit dem RX-Pin verbunden ist.

Ist analog dazu DE auf high gesetzt, wir der Transceiver in den Sendemodus versetzt. Daten die per TX-Pin vom Microcontroller am DI Pin angelegt werden, werden an den Bus weitergeleitet.

Ist /RE auf low und DE gleichzeitig auf high, so empfängt der sender seine soeben gesendeten daten gespiegelt zurück, da er gleichzeitig am Bus lauscht.

Setzt man /RE auf high und DE auf low, versetzt man den Transceiver in einen Sleep modus. Das ist sehr praktisch, wenn der verwendete Microcontroller nur über eine einzige UART Schnittstelle verfügt. Dann kann man immer noch bequem per printf() debuggen, ohne den Bus vollzumüllen bzw. den chip per FTDI flashen, ohne dass die Programmiersoftware bzw. der Bus dadurch gestört wird.

Während der DE Pin eines Teilnehmers auf high gesetzt ist, kann kein anderer Teilnehmer senden, da der Bus dann blockiert ist! Daher sollte man DE nach jedem Sendevorgang wieder zurück auf LOW setzen, um den Bus für die Anderen wieder freizugeben!

Im folgendem Beispiel sind zwei MAX485 Bausteine miteinander verschaltet. Der Linke ist dabei als Sender und der rechte als Empfänger konfiguriert:





Die Konfiguration geschieht über die /RE und DE pins. Praktischerweise sind /RE und DE komplementär ausgeführt. Die Pins vom linken MAX485 werden, wie man im Schaltplan sehen kann, direkt mit VCC (also +5V) verbunden. Dadurch befindet er sich im Sendemodus, aber lauscht nicht am Bus. Umgekehrt dazu liegen beim rechten MAX485 Baustein die Pins auf Masse (0V). Dadurch ist der Baustein im Empfangsmodus. Daten die auf den DI pin gehen, werden dann einfach ignoriert und nicht an den Bus weitergeleitet.

Selbstverständlich kann man die /RE und DE Pins auch einzeln an GPIO Pins des Microcontrollers hängen und im Betrieb entscheiden, ob man gerade Sender oder Empfänger oder beides sein will.
Es ist wichtig, dass an den jeweiligen RX pins ein pulldown Widerstand vorhanden ist! Legt man nämlich \RE auf high, wird der RO Ausgang elektrisch abgeschaltet und geht daher in einen undefinierten Zustand über. Ohne Pulldown Widerstand erhält man dann irgendwelchen zufälligen Datenmüll!


3. Eine Beispielschaltung


demnächst...

4. Und wo ist der Haken?


Bussysteme haben natürlich auch Nachteile. Einer davon sind Leitungsreflektionen. Bei kleinen Bussen mit nur zwei Microcontrollern fällt das noch nicht so doll auf. Je länger der Bus allerdings wird und je mehr Teilnehmer man dran hängt, desto stärker fallen diese Reflektironen ins Gewicht. Irgendwann kommt es dann zu fehlerhaftem Datenempfang. Um das zu vermeiden verbaut man sog. Abschlusswiderstände an beiden Leitungsenden. Bei RS485 sind das jeweils 120 Ohm.

[Bild mit Abschlusswiderständen]

Außerdem kann ein einziger Amoklaufender Microcontroller den gesamten Bus blockieren und somit die gesamte Kommunikation lahmlegen. (Beispielsweise wenn einer den DE Pin nicht mehr auf LOW setzt und den Bus somit nicht mehr freigibt!)

Und damit sind wir fertig! Bei bedarf können mehr Teilnehmer in den Bus gehängt, oder wieder entfernt werden. Bei den normalen Transceivern kann man maxmal 32 Teilnehmer in den Bus hängen. Es gibt jedoch auch Bausteine, bei denen mehr möglich ist. Diese werden dann z.B. mit 1/2 Load bezeichnet, bei denen dann 64 Teilnehmer möglich sind. Die mir maximal bekannten Bausteine können 1/8 load, mit denen 256 teilnehmer möglich sind. Solche Bausteine sind dann aber auch dementsprechend teurer.

Ich hoffe ich konnte dem ein oder Anderen mit diesem Beitrag helfen.
Bei Unklarheiten oder sonstigem Feedback könnt ihr gerne einen Kommentar hinterlassen. :)