Dies ist eine alte Version des Dokuments!


Hallo XMC-Welt in C++ und UML

So, dann frisch ans Werk. Die erste Übung mit der wahrscheinlich ungewohnten Umgebung soll wieder das einfache Einschalten einer LED sein. Der Sinn und Zweck von Klassenbibliotheken ist natürlich vor allen auch der, dass Dinge die öfters gebraucht werden oder typische Problemstellungen die einfach schon mal gelöst wurden, dem Anwender komfortabel zur Wiederverwendung zur Verfügung stehen.

Die Aufgabe

Die Objektorientierung zeichnet sich durch zunehmende Abstraktion von der tatsächlichen inneren Struktur und dem internen Verhalten der Maschine, hin zu einer anwenderbezogenen Sichtweise aus.

Die Aufgabe lautet: Entwickeln Sie eine Mikrocontrolleranwendung (Applikation) die eine LED anschaltet.

Vorbereitung

Falls Sie jetzt noch das Klassendiagramm geöffnet haben wählen Sie im Kontextmenü (rechte Maustaste) des Diagramms den Menüpunkt nach oben. Falls das Projekt nicht mehr geöffnet ist, öffnen sie das SiSy UML-Projekt wieder. Legen Sie ein neues Klassendiagramm an und wählen Sie die Sprache ARM C++. Beachten Sie die Einstellungen für die Zielplattform XMC4500 Relax Kit. Beim Öffnen des Diagramms (rechte Maustaste, nach unten) laden Sie die Diagrammvorlage für eine PEC Applikation und weisen das Treiberpaket für den XMC4500 zu.

Lösungsansatz

Die Aufgabe besteht darin eine LED anzusteuern. Folgen wir der objektorientierten Sichtweise, ist die Led unser Klassenkandidat. Eine Klasse Led soll die spezifische Initialisierung und Programmierung eines GPIO Pin auf der Anwenderebene abstrahieren. Also fragen wir uns, was eine LED denn aus Anwendersicht so tut. Sie kann an oder aus sein, vielleicht blinkt sie ja auch.

Die Abbildung genau dieser Verhaltensmerkmale fordern wir von der Klasse Led. Sich mit XMC_GPIO_OUTPUT_TYPE_PUSH_PULL und PORT1→OUT |= (1«0) herumzuschlagen ist mit Sicherheit wichtig, um zu erlernen, wie ARM Controller intern funktionieren und um ggf. eigene Klassen für die Erweiterung der Bibliothek zu realisieren. Aber es ist für die Lösung eines konkreten Anwendungsproblems eher zeitfressend und vielleicht sogar kontraproduktiv. Welcher GUI-Entwickler kümmert sich noch wie vor 25 Jahren von Hand um Peek-, Get-, Translate- und DispatcheMessage, nur weil es grundlegende und extrem wichtige Funktionen in einer grafischen Benutzeroberfläche sind. Er möchte eine konkrete Anwendung schreiben. Dazu reicht das Grundverständnis der Funktionsweise einer GUI und eine leistungsfähige Klassenbibliothek.

Für die Ansteuerung von LEDs gibt es im SiSy PEC Framework fertige Klassen. Die Kunst besteht jetzt darin, sich diese zugänglich zu machen. In klassischen Entwicklungsumgebungen schaut man in die Hilfe, ins Lehrbuch oder in ein Tutorial, schreibt die Zeilen ab, die dort erklärt werden und darf unter Umständen nicht vergessen benötigte Pakete per include, using oder import einzubinden.

In unserem Klassendiagramm ist die Bibliothek bereits eingebunden. Sie steckt in dem Ordner Pec. Das Suchen geeigneter Klassen in den Bibliotheken erfolgt in SiSy am besten über den Navigator. Öffnen Sie das Kontextmenü des Navigators mit der rechten Maustaste. Wählen sie den Menüpunkt UML-Pakete

.

Wir werden recht schnell beim Durchstöbern der Pakete fündig. Im Paket pec_InOut findet sich neben anderen Klassen eine fertige Klasse Led. In dieser sind all die mühseligen Kommandos für die Initialisierung bereits gelöst und das auch noch portabel. Das bedeutet für den Entwickler, dass diese Klasse auch auf einen anderen Controllertyp verwendbar ist. Die Klasse kann übrigens auch wesentlich mehr als wir für diese einfache Aufgabe brauchen. Mit etwas Übung im SiSy-Handling kann man sich elegant zum Quelldiagramm der Basisklasse durch hangeln, um sich all das anzuschauen. Dort sind das Klassendiagramm und der Quellcode der Bibliotheksklasse einseh- und ggf. auch änderbar (Modell- und Quellcodeoffen).

.

Wir könnten die eine einfachere Klasse benutzen, die einen simplen IO-Pin abbildet, aber was soll's … nehmen wir die sexy Led. Dazu ziehen wir die Led aus dem Navigator per Drag & Drop in das Klassendiagramm.

Wenn wir die Klasse Led hereingezogen haben, müssen wir diese mit der Anwendung verbinden. Vergleichen sie dazu die Ausführungen zur Aggregation im Grundlagenteil dieses Tutorials. Selektieren Sie dazu die Klasse Controller. Am unteren Rand erscheint eine große, rote Selektionsmarke. Das ist der Verteiler. Ziehen Sie von hier aus per Drag & Drop eine Verbindung von der Klasse Controller zur Klasse Led. Wählen Sie als Verbindungstyp die Aggregation und als Rollenbezeichner +led. Der Controller hat jetzt eine Led.

Das ist dann unser Entwurf der Struktur unserer Anwendung in Form eines UML-Klassendiagramms. Die meisten UML-Werkzeuge bieten an dieser Stelle das Generieren der Klassenrümpfe, um diese dann in eine IDE einzufügen. Dort können dann die konkreten Verhaltensmerkmale der so entworfenen Klassen fertig programmiert und ggf. die Klassen angepasst oder erweitert werden. Damit stimmen Konstruktionszeichnung und Quellcode jedoch nicht mehr miteinander überein. Das ist wie der richtige Schaltplan zur falschen Schaltung oder umgekehrt. Für diesen Defekt gibt es manchmal die Möglichkeit, dass das UML-Tool sich wiederum mit den Quelltextänderungen synchronisiert. In SiSy bleiben wir im Klassendiagramm und realisieren hier auch gleich das System.

Realisierung

Der Entwurf sollte der folgenden Darstellung entsprechen:

  • die zentrale Klasse ist die Controller
  • diese verfügt über die Operationen onStart und onWork
  • Die Applikationsklasse Controller ist ein PecAppKernel
  • Das globale Objekt app ist die Instanz der Klasse Controller
  • Die Klasse Controller verfügt über eine Led mit dem Attributnamen led
  • Das Attribut led der Klasse Controller ist öffentlich

Die Aufgabenstellung fordert, dass eine LED einzuschalten ist. Diese ist bekanntlich an Pin 1.0 angeschlossen. Für die Initialisierung von Geräten steht die Operation onStart zur Verfügung. Selektieren Sie diese Operation und geben im Quelltexteditor folgenden Code ein:

Controller::onStart:

led.config(PORT1,BIT0);

Beobachten Sie gleichzeitig das rechts neben dem Quelltexteditor befindliche Sequenzdiagramm. Dies wird automatisch aus dem von Ihnen eingegebenen Code erzeugt. Das Sequenzdiagramm kann zum einen für Dokumentationszwecke genutzt werden zum anderen soll es gleichzeitig als Review für den Quellcode dienen.

Selektieren sie danach die Operation onWork und geben den folgenden Code ein:

Controller::onWork:

led.on();

Test

Übersetzen Sie das Programm. Korrigieren Sie ggf. Schreibfehler. Übertragen Sie das lauffähige Programm in den Programmspeicher des Controllers.

  1. Erstellen (Kompilieren und Linken)
  2. Brennen

Videozusammenfassung

Erlernte und gefestigte Arbeitsschritte:

  1. Klassendiagramm anlegen und öffnen
  2. Diagrammvorlage für eine PEC Applikation auswählen laden und Treiberpaket für den XMC4500 einfügen
  3. Navigator auf UML Pakete umschalten
  4. gewünschte Klasse Led im Navigator suchen und ins Diagramm ziehen
  5. Klassen aggregieren
  6. den nötigen Quellcode in den Operationen eintragen
  7. Erstellen und Brennen eine XMC Applikation im Klassendiagramm

Und weil es so schön war hier das Ganze noch mal als Video.

Übung

Erweitern Sie zur Übung zum Blinky-Beispiel. Beachten Sie, dass Sie keine eigene Mainloop aufbauen müssen sonderen dass die Operation onWork aus der bereits realisierten Mainloop im PecAppKernel getriggert wird!

Nächstes Thema

hallo_uml.1491840231.txt.gz · Zuletzt geändert: 2017/04/10 18:03 von huwaldt