Synchrone Programmiersprache

Eine synchrone Programmiersprache ist eine Programmiersprache, die sich aufgrund ihres Verhaltens vorwiegend für reaktive Systeme eignet.

Allgemeines

Synchrone Programmiersprachen basieren grundsätzlich auf der synchronen Hypothese, die aus folgenden Annahmen besteht:

  • multi-form time,
  • zero-delay model of circuits,
  • perfectly synchronous model.

Multi-form time: Hierauf basiert der grundsätzliche Ablauf eines synchronen Programms. Die Zeit wird einzig durch die Rangfolge von Eingaben bestimmt. Eine Zeitdauer kann durch die Anzahl und Form von Eingaben definiert werden, beispielsweise dreimaliger Empfang eines selbst definierten Signals MINUTE ergibt eine Zeitdauer von drei Minuten.

Zero-delay model of circuits: Ein Programmablauf kann in einzelne (Prozess-)Schritte zerlegt werden. Ein Prozessschritt bedeutet den Übergang von einem (Programm-)Zustand in den nächsten, z. B. das Schließen einer offenen Aufzugstür: aktueller Zustand = Tür offen, nächster Zustand = Tür zu. Der lineare Programmcode für den Prozessschritt wird in endlicher, vorhersagbarer Zeit, aber ohne weitere Zeitauflösung abgearbeitet. Um beim Beispiel Aufzugstür zu bleiben: Das Programm kann den Zustandsübergang entweder ausführen, wenn die Tür geschlossen werden soll (Timeout oder »«-Taste) oder wenn die Tür tatsächlich geschlossen ist, aber es kann den Vorgang des Schließens nicht wahrnehmen. Um die Funktionalität zu implementieren, dass ein Benutzer das Schließen unterbrechen kann («»-Taste, Lichtschranke, Fuß), müsste ein weiterer Zustand vorgesehen werden.

Perfectly synchronous model: Diesem Modell nach laufen alle Prozessschritte (zumindest im Konzept) parallel (=gleichzeitig) ab. Ist die kleinste Zeiteinheit (zwischen zwei zeitlich unterschiedlichen Eingaben) ein Zyklus und agieren mehrere Prozesse miteinander, so kommunizieren diese prinzipiell zur gleichen Zeit, das heißt im selben Zyklus. Die Ausgabe eines Prozesses dient im selben Zyklus einem anderen Prozess als Eingabe, ähnlich einer Kette. Als einfaches Beispiel dienen eine Glühlampe und ein Helligkeitssensor. Schaltet sich die Glühlampe ein, erkennt der Sensor dies sofort und gibt im Idealfall noch im selben Zyklus ein Resultat aus.

Determiniertes Verhalten, eine Eigenheit etwa von Esterel und Lustre, bildet die Grundlage für einfache Programmverifikation und Möglichkeiten zur Bestimmung von (Programm-)Laufzeiten. Letzteres ist bei nicht-determinierten Systemen oder Sprachen, wie Ada, sehr aufwendig. Deswegen sind azyklische (lineare) Programme, die keine Schleifen enthalten, im Allgemeinen zu bevorzugen.

Synchrone Programmiersprachen

Vor- und Nachteile

Synchrone Programmiersprachen finden überwiegend Anwendung bei sicherheitskritischen Systemen. Durch ihren deterministischen Aufbau und die leichter abschätzbare Laufzeit haben synchrone Sprachen hier einen klaren Vorteil gegenüber imperativen Sprachen. Durch die Automaten-Struktur wird die Verifikation der Programme mittels Modellprüfung (model checking) möglich und gibt somit zusätzliche Sicherheit bei der Implementierung.

Sprachen wie Esterel können ein statisches Scheduling (fester Ablauf der Anweisungen über alle beteiligten Prozesse betrachtet) erzeugen, da alle in diesem Programm vorkommenden nebenläufigen Prozesse und alle Anweisungen zur Compilezeit bekannt sind. Programme mit statischen Scheduling sind im Hinblick auf Nebenläufigkeit sicher.

Synchrone Sprachen sind natürlich nicht für jede Art von Problemstellung geeignet. Das was ihnen Sicherheit verschafft, beispielsweise nämlich das Wissen, wie viele Prozesse überhaupt vorkommen, geht zu Lasten dynamischer Eigenschaften. Es können also z. B. nicht spontan Prozesse erzeugt werden, die eine Netzwerkverbindung bedienen, der Prozess müsste schon zur Compile-Zeit erzeugt werden. Genauso wenig wird dynamisch Speicher alloziert oder freigegeben. So sind sie z. B. auch für Datenbank-Systeme ungeeignet, da hier enorme Datenmengen anfallen können und die Vorhersehbarkeit des benötigten Speichers nicht oder nur teilweise gegeben ist.

Software für Mikrocontroller mit Pipelining und Caching ist auch nicht erstellbar, da hier undefinierte Zustände, resultierend aus dem Caching, auftreten können. Diese Art von komplexen Programmen ist nur in Verbindung mit anderen Sprachen möglich.

Gut geeignet sind sie aber beispielsweise für regelungstechnische Anwendungen, oder allgemein für alles, was sich vernünftig in einem Endlichen Automat mit der entsprechenden Semantik ausdrücken lässt.

Weitere Literatur

  • D. Potop-Butucaru, R. de Simone, J.-P. Talpin: The synchronous hypothesis and synchronous languages. In: R. Zurawski (ed.), The Embedded Systems Handbook. CRC Press. to appear (2005)