Embedded-Software automatisiert testen

Testfallgüte problemlos prüfen

19. März 2021, 8:13 Uhr | Von Frank Büchner
© ronstik - Adobe Stock

Von TESSY, dem Werkzeug zum Unit-, Modul- und Integrationstest von eingebetteter Software, gibt es mit V4.3 eine neue Hauptversion. Die wichtigste neue Funktion dieser Version ist der automatisierte Mutationstest, mit dem sich die Qualität von Testfällen schnell und einfach beurteilen lässt.

Beim Mutationstest werden bereits bestandene Testfälle für ein Testobjekt, beispielsweise eine Software-Unit, wiederholt ausgeführt. Allerdings wendet man die Testfälle bei der Wiederholung nicht auf den originalen Quellcode des Testobjekts an, sondern auf Code, der mutiert wurde. Ein solcher Code ist gegenüber dem Originalcode verändert. Dabei können die Änderungen Kleinigkeiten betreffen, wie beispielsweise das Ersetzen eines logischen »Und« durch ein logisches »Oder«. Die Änderungen können aber auch schwerwiegend sein, beispielsweise das Entfernen des »Else«-Zweigs einer »If«-Anweisung. Natürlich muss das Testobjekt auch nach der Änderung übersetzbar bleiben, sonst ist es nicht möglich, den Test zu wiederholen.

Anbieter zum Thema

zu Matchmaker+
Das Testwerkzeug TESSY automatisiert den gesamten Mutationstestprozess.
Bild 1: Das Testwerkzeug TESSY automatisiert den gesamten Mutationstestprozess.
© Hitex

Bei der Wiederholung mit dem mutierten Quellcode geht es darum, ob die
vorhandenen Testfälle die Mutation aufdecken (der Fachbegriff hierfür lautet »töten«). Eine Mutation wird »getötet«, indem mindestens ein Testfall bei der Wiederholung fehlschlägt. Erfolgt dies nicht, bemerken die Testfälle nicht, dass sich der Quellcode geändert hat – oder anders ausgedrückt: Die Testfälle bewerten auch ein anderes Testobjekt als das originale als korrekt. Das ist bedenklich und muss näher untersucht werden. Hierfür ist es hilfreich, wenn man nur eine Mutation vorgenommen hat. Liegt keine Mutation vor, bei der sich das Verhalten des Testobjekts nach außen nicht ändert (äquivalente Mutation), so mangelt es an der Qualität der Testfälle. Dabei spielt es eine Rolle, wie radikal die Mutation war; eine subtile Mutation wird schwieriger aufzudecken sein als mehrere drastische Veränderungen. Üblicherweise erfolgen mehrere Testdurchläufe mit unterschiedlichen Mutationen. Hierdurch lässt sich einschätzen, wie hoch die Testfallqualität ist.

Diese Mutationen nimmt TESSY V4.3 standardmäßig vor
Bild 2: Diese Mutationen nimmt TESSY V4.3 standardmäßig vor
© Hitex

In Bild 1 ist der Mutationstestprozess dargestellt, wie ihn TESSY automatisiert durchführt. Nachdem der originale Quellcode die vorhandenen Tests bestanden hat, lässt sich der eigentliche Mutationstestprozess starten. TESSY führt genau eine Mutation durch und wiederholt die Tests. Dabei wird aufgezeichnet, ob eine Mutation getötet wurde oder nicht. Dann wird das originale Testobjekt wiederhergestellt und eine weitere Mutation durchgeführt.

In Bild 2 sind die Mutationen dargestellt, die TESSY seit der Version 4.3 ermöglicht (das Fehlermodell). Der Anwender kann die anzuwendenden Mutationen auswählen und dadurch auch die Anzahl der vorgenommenen Mutationen beeinflussen. Dies wiederum wirkt sich auf die Ausführungszeit des gesamten Mutationstestprozesses aus.

Annahmen für den Mutationstest

Die von TESSY standardmäßig durchgeführten Mutationen sind subtil, beispielsweise wird der relationale Operator < zu <=. Dem liegt die Annahme des »kompetenten Programmierers« zugrunde. Diese besagt, dass ein fähiger Softwareentwickler nur geringfügige Fehler macht, durch die beispielsweise eine Schleife einmal zu viel oder einmal zu wenig durchlaufen wird, oder durch die zum Beispiel ein Array-Zugriff auf eine Speicherzelle erfolgt, die gerade nicht mehr zum Array gehört (Off-by-one-Fehler).

Das originale Testobjekt besteht diese vier Testfälle
Bild 3: Das originale Testobjekt besteht diese vier Testfälle.
© Hitex

Um herauszufinden, ob die Testfälle solche geringfü­gigen Fehler finden und somit eine gute Qualität haben, müssen die Mutationen subtil sein. Grobe Mutationen, wie beispielsweise das Entfernen von einer oder gar mehreren Anweisungen, sollten auch Testfälle geringer Qualität aufdecken. Eine weitere, empirisch bestätigte Annahme [1] besagt, dass es einen Kopplungseffekt gibt: Ein Testfall, der genau einen Mutanten tötet, tötet auch mehrfache Mutationen. Deshalb reicht es, immer nur eine Mutation aufs Mal durchzuführen.

Als Beispiel betrachten wir ein Testobjekt, das vier Testfälle (Bild 3) bestanden hat und mit diesen Testfällen eine hundertprozentige Code-Abdeckung erreicht. Führt TESSY den Mutationstest (mit den Standardeinstellungen für die Mutation wie in Bild 2) durch, ergibt sich eine getötete Mutation und eine überlebende Mutation (Bild 4).

Resultat des Mutationstests, das TESSY ermittelt hat
Bild 4: Resultat des Mutationstests, das TESSY ermittelt hat.
© Hitex

Im oberen linken Teil von Bild 4 ist die getötete Mutation (Mutation caused test failure) dargestellt. Diese Mutation veränderte den relationalen Operator in der ersten if-Anweisung des Testobjekts (hervorgehoben oben auf der rechten Seite von Bild 4) von < zu <=. Dadurch schlägt ein Testfall fehl, was beim Mutationstest positiv ist. Deshalb ist diese Mutation auch mit einem grünen Häkchen gekennzeichnet.

Im unteren linken Teil von Bild 4 sieht man die überlebende Mutation (Mutation survived all test cases), die den relationalen Operator in der zweiten if-Anweisung des Testobjekts (hervorgehoben unten auf der rechten Seite von Bild 4) von > zu >= verändert hat. Kein Testfall hat diese Veränderung bemerkt. Das ist bedenklich und muss untersucht werden.

Der Mutation Score ist das Verhältnis von getöteten zu allen Mutationen. In Bild 5 ist der von TESSY ermittelte Mutation Score der vier Testfälle an­geben. Testfall 2 hat eine der zwei Mutationen getötet, was 50 Prozent entspricht. Weil er einen Mutanten getötet hat, ist Testfall 2 mit einem grünen Häkchen in der Spalte M markiert. Die anderen drei Testfälle haben keinen Mutanten getötet und haben deswegen ein rotes Kreuz beziehungsweise einen Mutation Score von 0 Prozent.

So wird der Mutation Score in TESSY dargestellt
Bild 5: So wird der Mutation Score in TESSY dargestellt.
© Hitex

Testfall 2 hat einen Mutanten getötet und hat somit eine höhere Qualität als die anderen Testfälle, die keinen Mutanten getötet haben. Das liegt am Wert für die Variable v1 in Testfall 2. Dadurch kommt es auf den relationalen Operator in der ersten if-Anweisung an. Sowohl die Variable v1 als auch die Variable r1.range_start haben im zweiten Testfall den Wert 5, somit lautet die Entscheidung in der ersten if-Anweisung 5<5, was »falsch« ergibt. In der Mutation lautet die Entscheidung 5<=5, was »wahr« bedeutet. Deswegen liefert der zweite Testfall ein unerwartetes Ergebnis (»no« anstelle des richtigen und erwarteten »yes«), was den Mutanten tötet.

Testfall 4 sollte eigentlich die andere Mutation in der Entscheidung der zweiten if-Anweisung töten. Das klappt aber nicht, weil der Wert für v1 in Testfall 4 ungünstig gewählt ist. Die Variable v1 hat den Wert 9 und r1.range_start+r1.range_len ergibt 5+2=7. Somit ist die Entscheidung in der zweiten if-Anweisung im Original 9>7 und im Mutanten 9>=7, was beides mal »wahr« ergibt. Also liefern Original und Mutant in beiden Fällen das korrekte Ergebnis »no«. Somit bestehen sowohl Original als auch Mutant den vierten Testfall; der Mutant wird nicht getötet.

Testfall 2 und Testfall 4 haben deswegen unterschiedliche Qualität, weil Testfall 2 einen Grenzwert (Boundary Value) verwendet und Testfall 4 nicht. Testfall 2 verwendet nämlich mit dem Wert 5 den Startwert des Bereichs, der bei 5 startet und die Länge 2 hat und somit die Werte 5 und 6 enthält. Testfall 4 verwendet mit dem Wert 9 für die Variable v1 keinen Grenzwert des Bereichs. Dies demonstriert, wieso Grenzwerte gute Testdaten sind und wieso Standards zur Entwicklung von sicherheitskritischer Software Grenzwerte als Testdaten empfehlen.

Beispielsweise empfiehlt die IEC 61508 [2] die Methode Boundary Value Analysis in Tabelle B.2 und B.3 ihres Teils 3. In beiden Tabellen ist diese Methode empfohlen für Safety Integrity Level (SIL) 1 und besonders empfohlen für SIL 2 bis 4. Auch die ISO 26262 [3] nennt als Methode 1c in der Tabelle 8 von Teil 6 Analysis of Boundary Values als Vorgehensweise, wie man zu Testdaten für den Software-Unit-Test kommen kann. Die Methode ist empfohlen für ASIL A und besonders empfohlen für ASIL B bis D.

Der Mutationstest kann auch Testfallmengen bewerten. Eine Testfallmenge heißt adäquat, wenn sie alle Mutanten tötet. Je kleiner eine adäquate Testfallmenge ist, um so besser. Damit lassen sich auch Testfall-Konstruktionsverfahren beurteilen.


  1. Testfallgüte problemlos prüfen
  2. Endlosschleifen und Abstürze bei Mutationen

Das könnte Sie auch interessieren

Verwandte Artikel

Hitex GmbH