Mit Continuous Integration (CI) erhält der Embedded-Softwareentwickler unmittelbar Rückmeldung, ob neuer oder geänderter Code alle Vorgaben erfüllt und die Software wie gewünscht arbeitet. In das CI-System lassen sich auch das Debugging und die Timing-Analysen für die Zielhardware einbinden.
Verteilte Entwicklungsteams, eine zunehmend komplexe Codebasis, wachsende funktionale Anforderungen und wenig Zeit: Auch in der Entwicklung von Embedded-Software kann dem Druck, ein zuverlässiges und sicheres Produkt in möglichst kurzer Zeit zur Marktreife zu bringen, nur mit einem höheren Maß an Automatisierung begegnet werden. Daher setzt sich der Ansatz der Continuous Integration (CI) mit ihren automatisierten Builds und Tests auch in der Embedded-Softwareentwicklung immer mehr durch.
Continuous Integration sieht vor, dass jedes Teammitglied, das gemeinsam mit anderen an einer Software arbeitet, seinen geänderten oder neu erstellten Code in kurzen Abständen in ein mit dem Team geteilten Repository »integriert«. Hierfür gibt es eine Reihe von geeigneten Continuous-Integration-Servern wie Jenkins, GitLab, TeamCity, CircleCI oder GitHub Actions. Mit der Integration wird über eine CI-Software, die Inhouse oder in der Cloud gehostet wird, schnell und automatisiert eine Reihe von Schritten – eine sogenannte Pipeline – ausgelöst. Die Pipeline umfasst in der Regel den Build, statische Analysen sowie Unit- und Systemtests (Bild 1).
Ein abschließend erstellter Report zeigt dem Entwickler, wie sich die Codeänderungen auf die Funktion und die Qualität der Software ausgewirkt haben: Zum Beispiel könnte der Build fehlerhaft, ein Test fehlgeschlagen oder gegen wichtige Metriken verstoßen worden sein. Dank der zeitnahen Rückmeldung kann der Entwickler dann seinen Code entsprechend korrigieren und erneut in das Repository »committen«, wodurch ein weiterer Pipeline-Lauf getriggert wird, um die zuletzt erfolgten Änderungen erneut automatisch zu überprüfen.
Durch die Automatisierung per Continuous Integration und die unmittelbare Rückmeldung werden Fehler in der Embedded-Softwareentwicklung frühzeitig erkannt und können schnell behoben werden. Die Codebasis bleibt davon unberührt, denn wenn zum Beispiel Tests fehlschlagen, wird die Codeänderung nicht in den auszuliefernden Code eingefügt. Dabei können sich die Entwickler auf den Code konzentrieren und müssen keine Test-Set-ups auf ihren lokalen Rechnern pflegen. Ein richtig implementierter CI-Prozess steigert also die Produktivität in der Embedded-Softwareentwicklung, erhöht unmittelbar die Softwarequalität und spart Ressourcen sowie Zeit.
Grundsätzlich kann eine Software auch unabhängig von Zielhardware umfangreichen Tests unterzogen werden. So ist die benötigte Hardwareperipherie oft nicht verfügbar oder verhält sich nicht exakt gleich wie auf realer Hardware, das Timing-Verhalten ist anders oder der Cross-Compiler generiert zielspezifischen Objektcode und damit nicht den gleichen Code wie der Compiler, der für die Testumgebung verwendet wird. Dennoch werden in simulierten Umgebungen oft nicht alle potenziellen Fehler aufgedeckt. Deshalb ist es sinnvoll, schon frühzeitig so nah wie möglich an der realen Hardware zu testen, um die korrekte Funktion des Endprodukts sowie das exakte Timing-Verhalten der Anwendung sicherzustellen.
Da Anwendungen immer komplexer werden und die Prozessorleistung oft bis zum Anschlag genutzt werden muss, ist es notwendig, sich einige Fragen von Beginn an zu stellen, zum Beispiel: Wie wirkt sich eine Codeänderung auf die Leistung der Anwendung aus? Oder: Welchen Einfluss hat ein Modul auf das Laufzeitverhalten des Systems? Antworten hierzu liefert die Timing-Analyse mit Hardware-Tracing, das basierend auf einem speziellen On-Chip-Trace-Modul des jeweiligen Zielprozessors Daten zur Programmlaufzeit aufzeichnet. Mit der Implementierung einer automatisierten Analyse kann der Entwickler Timing-Einschränkungen überprüfen und wichtige Timing-Metriken während der Entwicklung der Software im Auge behalten. Engpässe können frühzeitig erkannt und gegebenenfalls Korrekturmaßnahmen eingeleitet werden. Die Verwendung von Hardware-Tracing erlaubt dem Testingenieur auch eine nicht-intrusive Messung der Code-Coverage, also das Aufdecken von nicht getestetem Code. Instrumentierungscode, der das Laufzeitverhalten beeinflusst, ist nicht erforderlich.
Jedoch ist das Hardware-Tracing mit einigen Herausforderungen verbunden, etwa weil die Hardware, Evaluierungsboards und Tools nicht für jeden im Entwicklerteam verfügbar sind und die Test-Set-ups aufwendig im Aufbau und der Aktualisierung sein können. Eine Lösung bieten dedizierte Testracks für Hardware: Dort ist eine Vielzahl an Debuggern mit den verschiedenen Embedded-Zielsystemen verbunden und per USB und Ethernet zugänglich. Damit können Entwickler unabhängig von ihrem eigenen Standort jederzeit auf die Zielhardware zugreifen und parallel Tests für mehrere Zielsysteme gleichzeitig auslösen.
Das Hardware-Tracing lässt sich in einen bereits existierenden Ablauf von Continuous Integration eines Unternehmens einbinden (Bild 2). Die Entwickler können dann wie gewohnt per Commit die Funktionsfähigkeit und Qualität ihres Codes speziell in der Ausführung auf der Zielhardware überprüfen und gegebenenfalls optimieren.
In den vergangenen Jahren hat iSystem viel Wissen rund um CI in der Embedded- Softwareentwicklung aufgebaut und in reale CI-Systeme umgesetzt – für die eigene Softwareentwicklung und für Kunden mit hohen Ansprüchen an neue Softwarefunktionen und deren schnelle Verfügbarkeit. Bei der Implementierung von automatischen Software- und Hardwaretests in einem Continuous-Integration-System greift iSystem auf bewährte Produkte zurück und nutzt sein Know-how in der individuellen Kundenberatung. Die BlueBox iC5000/iC5700 CI wurde eigens für die Implementierung in ein CI-Testrack-Set-up entwickelt. In Verbindung mit den Softwareprodukten winIDEA und testIDEA von iSystem und den jeweiligen Schnittstellen und Automatisierungsmöglichkeiten dient die BlueBox als »On-Target«-Testframework.
Um Tests auf der Zielhardware über eine BlueBox durchzuführen, muss die Hardware in die Continuous-Integration-Pipeline(s) integriert werden. Dies geschieht über die Automatisierungsschnittstelle, die ein fester Bestandteil von winIDEA ist. Die Integration kann dabei über verschiedene Sprachen wie z.B. Python, Java oder C# erfolgen.
Für die unternehmenseigene Softwareentwicklung hat iSystem in seinen »iSystem Labs« Testracks mit mehr als 150 Einzeltestplätzen, verteilt auf Schubladen in mehreren Testschränken, eingerichtet (Bild 3). Diese bestehen jeweils aus dem Testframework mit der BlueBox und einem Embedded-Zielsystem. Alle Einschübe haben eine Stromversorgung und können dadurch einzeln und ferngesteuert runter- und wieder hochgefahren werden.
Jede Zielhardware kann vom CI-System, aber auch direkt von Entwicklungs- und Testingenieuren, genutzt werden. Hierfür stellt iSystem eine selbst entwickelte, Web-basierte Softwareanwendung zur Verfügung. Über diese werden initiierte Tests gesammelt, in Queues auf verfügbaren PC-Knoten eingereiht und schließlich auf der jeweiligen Zielhardware zur Ausführung gebracht. Die Testergebnisse werden in einer entsprechenden Testdatenbank abgelegt sowie Änderungen der Funktionen automatisiert an die jeweiligen Stakeholder weitergeleitet. Die gesamte Hardware steht zentral in einer geeigneten Umgebung und muss nicht mehr am jeweiligen Arbeitsplatz der weltweit verteilt arbeitenden Entwickler eingerichtet werden. Sie können die verschiedenen Hardware-Set-ups parallel nutzen, um Tests auf Zielsystemen auszuführen. Das führt zu kürzeren Durchlaufzeiten und Entwickler erhalten schneller eine Rückmeldung für Codeänderungen.
Die Vorteile von Continuous Integration für die Embedded-Softwareentwicklung liegen klar auf der Hand: Tester und Integratoren können Softwarefehler schneller aufdecken und beheben, können Fehler besser reproduzieren, haben eine ständig verfügbare, auslieferbare und lauffähige Software, behalten einen guten Überblick über die Projektstände an sich – und haben insgesamt weniger Stress. CI von Anfang fachlich in der Tiefe zu durchdringen, ist eine Grundvoraussetzung für die erfolgreiche Umsetzung dieser Strategie. Die Effizienz der CI-Hardware und -Software als Ganzes entscheidet über die Akzeptanz bei den Entwicklern und letztendlich den Erfolg.
Der Autor
Matthias Scheid
ist Systems Engineer bei iSystem. Nach dem Studium der Technischen Informatik an der OTH Regensburg entwickelte er als Software Development Engineer hardwarenahe Softwaremodule mit Anforderungen an die funktionale Sicherheit für unterschiedliche Prozessoren. Bei iSystem beschäftigt sich Scheid mit hardwarebasiertem Tracing, AUTOSAR, Continuous Integration und Testen.