Große Erwartungen Systemprogrammierung: Steigerung der Effizienz

Nicht immer führt die Einführung einer neuen Methode oder eines Werkzeuges zur erwarteten Steigerung der Effizienz. Daraus zu schließen, Werkzeug oder Methode funktionierten nicht, wäre voreilig. Ursachen dafür gibt es viele, unter anderem falsche Erwartungen. Zum Beispiel, wenn mit der Einführung der Notation C++ in Kombination mit einem C++-Com-piler die Erwartung verbunden ist, dass die Methode OOP damit automatisch folgt. Die Enttäuschung ist dann vorprogrammiert. Auch in der Modellierung sorgen falsche Ziele für Enttäuschung.

Eines ist gewiss: Elektronische Systeme werden immer schneller immer komplexer. Um dem gerecht zu werden, muss das Engineering mit neuen Methoden reagieren. Aber nicht immer bringen diese den gewünschten Erfolg. Das bedeutet jedoch nicht, dass die Werkzeuge, Methoden oder Notationen deswegen nicht leistungsfähig sind.

Oft bekämpfen neue Engineering-Vorgehensweisen lediglich die Symptome und nicht die Ursachen der Probleme. Exemplarisch soll im Folgenden für die Modellierung mit UML gezeigt werden, woran es liegen kann, wenn erwartete Erfolge ausbleiben. Zu den häufigsten Gründen für den Einsatz von UML zählt die Hoffnung auf Verbesserung der Verstehbarkeit und Dokumentation von Software.

Seit einigen Jahren befragt der Autor Software-Entwickler, beispielsweise im Rahmen von Vorträgen auf Kongressen, wie sie die Situation ihrer Softwaredokumentation beurteilen würden. Sie sollen sich einer der drei folgenden Kategorien zuordnen:

  • Unsere Dokumentation ist gut.
  • Unsere Dokumentation ist schlecht.
  • Die Dokumentation an sich ist nicht so schlecht, das eigentliche Problem liegt darin, dass sie nicht konsistent zum Code ist.

98% dieser Entwickler stufen den Zustand ihrer Dokumentation beim letzten Punkt ein. Das eigentliche Problem ist also nicht schlechte Dokumentation, sondern Inkonsistenz zum Code. Und die Ursache dahinter ist Redundanz, verbunden mit Zeitdruck, sodass die redundanten Anteile nicht systematisch konsistent gehalten werden können.

»3GL«-Notationen (3GL = Third Generation Languages wie C, C++, Pascal, ...) besitzen ihrem Charakter nach eine hohe Informationsdichte, verbunden mit vergleichsweise schlechter Verstehbarkeit und geringer Redundanz. »4GL«-Notationen (etwa UML, SDL, etc.) hingegen besitzen eine geringe Informationsdichte, verbunden mit wesentlich besserer Verstehbarkeit, aber erkauft durch - auch wenn es schwerfällt, das zu glauben - hohe Redundanz.

4GL-Notationen stellen verschiedene Gesichtspunkte der Systeme dar, etwa zeitliche Abläufe, Kommunikation oder statische Aufteilung. Das erhöht die Verstehbarkeit, aber gleichzeitig auch
die Redundanz.

Ein Ereignis kann dann in verschiedenen Ansichten mehrfach auftauchen. Wenn nun nicht gleichzeitig eine Lösung zum Managen der Redundanzen eingeführt wird, vergrößert sich das eigentliche Problem. Nach einem Jahr des Erstellens von UML-Diagrammen, gefolgt von händischer Programmierung, ist nur mehr inkonsistente Dokumentation übrig, die niemand nutzt. Denn sie repräsentiert das nicht, was im Zielsystem an Software läuft. Grundsätzlich gibt es zwei Maßnahmen, die notwendig sind, um die redundanten Anteile zu verringern:

  • Einsatz eines Repository, auf dessen Basis die Diagramme dynamisch entstehen, oder
  • Einsatz von Codegenerierung, sodass zwischen den nun besser verstehbaren 4GL-Modellen und dem eigentlichen Quellcode keine Inkonsistenzen mehr entstehen.

Ohne eine der beiden Vorgehensweisen ist es nur eine Frage der Zeit, wann die Modelle inkonsistent zum Code und dann nicht mehr genutzt werden.

Muster, Normen, Halbzeuge und Werkzeuge

Vor einiger Zeit erbte der Autor von seinen Großeltern einen »Bauernkasten« (ein alter Schrank aus der Steiermark), 1807 gebaut. Er besteht aus zwei Teilen, die mit vier Holzschrauben und Muttern verbunden sind.

Für den Transport nach Deutschland hat er ihn auseinandergeschraubt. Als der Autor ihn dann, zuhause angekommen, wieder zusammen bauen wollte, stellte er mit Erstaunen fest, dass jeweils nur eine Mutter auf genau eine Schraube passte.

Die Gewinde waren noch von Hand erstellt (Bild 1 zeigt eine der Schrauben mit der dazugehörigen Mutter). Ein Grundprinzip lässt sich aber schon an der 200 Jahre alten Schraube erkennen: das Muster (Pattern) des Gewindes.

Dies ist ein Konzept, um leicht lösbare Verbindungen herzustellen. Heute sehen Schrauben anders aus, etwa wie in Bild 2 zu sehen. Das Konzept des Gewindes ist gleich geblieben, was ist dazu gekommen? Die Norm für metrische Gewinde. Der Einsatz von so genannten Mustern erhöht die Effizienz im Engineering enorm. Verbunden mit Normen wird diese noch einmal potenziert.

Muster in Kombination mit Normen ermöglichen hoch effizientes Outsourcing. Heute ist es egal, wo auf der Welt Sie eine Schraube kaufen und wo sie hergestellt wurde. Wenn sie ein metrisches Gewinde und eine metrisches Schlüsselmaß hat, passt sie, und das Werkzeug ebenso. Ohne Muster in Verbindung mit Normen wäre der Maschinenbau nicht dort, wo er heute ist.

Produktion und Wartung heutiger Produkte wären nicht denkbar. Das Software-Engineering steckt in dieser Beziehung noch in den Kinderschuhen - jedenfalls teilweise. Muster (Pattern) kommen im Software-Engineering bereits seit Jahrzehnten zum Einsatz, beispielsweise in Form von »Scheduling Pattern«. Eines der meisteingesetzten Muster in Embedded-Software ist sicher die »main()«-Loop.

Leistungsfähigere Scheduling-Pattern können in Form von Halbzeugen als RTOS eingekauft werden. Jedoch sind diese proprietär. Abgesehen davon, dass die Notation nicht einheitlich ist, ist auch die Implementierung eines Patterns unterschiedlich. Wechselt man zu einem Halbzeug eines anderen Lieferanten, ist dies mit erheblichem Aufwand verbunden.

Aber auch im Software-Engineering gibt es Normen wie OSEK-OS, RIF (ReqIF), XMI, SDL oder UML. Die Norm UML besitzt im Vergleich zu 3GL-Notationen Notationselemente, die auch heute häufig eingesetzte Pattern adressieren, zum Beispiel die Nutzung von Timern, Scheduling-Pattern, Kommunikations-Pattern oder OO-Pattern wie Instantiierung oder Vererbung. All diese Pattern sind im Grund nichts neues, sie werden seit Jahren, häufig sogar Jahrzehnten eingesetzt.

Neu ist die Norm. Unabhängig vom Lieferanten des Werkzeugs (UML-Modellierungstool, Codegenerator, etc.) oder des Halbzeugs (RTOS, Framework, usw.) lassen sich die Modelle mit wesentlich geringerem Aufwand weiterverwenden. Das ist der eigentliche Grund, warum die Modellierung mit 4GL-Notationen die Effizienz erhöhen kann, aber nur, wenn aus dem Modell Code generiert wird. Der Codegenerator adaptiert den Standard auf die herstellerspezifischen Halbzeuge.

Im Codegenerator ist es ein Schalter, der bewirkt, dass ein anderes System unterstützt wird. In wenigen Sekunden ist die Software dadurch auf einem anderen System lauffähig - mit händischer Codierung ein Aufwand von mehreren Tagen. Änderungen und Erweiterungen werden im Modell durchgeführt. Dort ist die Verstehbarkeit um ein Vielfaches höher als auf Code-Ebene.

Auf Basis des Repository und der Codegenerierung entsteht dann vollständiger Code. Redundanzen müssen nicht gepflegt werden. Das ist Stand der Technik im Software-Engineering, wenn auch leider nicht immer Stand der Praxis. Generell werden Methoden oder Werkzeuge häufig nicht orientiert am grundlegenden Problem eingesetzt.

Die Effizienz kann dann nicht wie erwartet steigen, und das neue Vorgehen wird als nicht praktikabel dargestellt. Häufig finden Methode, Notation und Werkzeug keine einheitliche Anwendung, dafür kommen alte oder zugekaufte Sourcen zum Einsatz, in Kombination mit nicht dafür geeigneten Pattern (zum Beispiel synchrone Kommunikation mit präemptivem Scheduling).

Würde ein schwedischer Möbelhersteller die Regale mit einer wilden Kombination an Pattern liefern, dann bekäme die Parodie »Wohnst du schon, oder schraubst du noch?« eine ganz andere Bedeutung, abgesehen von den Kosten für unzählige Werkzeuge, die mitgeliefert werden müssten. Eines steht fest: Die Anwendung von Mustern in Verbindung mit Normen und Werkzeugen hat den Maschinenbau revolutioniert.

Dasselbe wird in den kommenden Jahren im Software-Engineering geschehen. Heute liegen vor allem im Architekturdesign ein grundlegendes Potenzial für den effizienten Einsatz von Mustern und damit auch ein Grundstein zur Anwendung von Notationen wie UML und effizienter Codegenerierung (Bild 3). Die Frage ist häufig nicht: »Programmieren Sie noch, oder modellieren Sie schon?«, sondern: »Malen Sie noch, oder modellieren Sie schon?«.

Über den Autor:

Andreas Willert ist Gründer von Willert Software Tools.