Was sind die Gründe, warum ein Java / Linux-Stack nicht "Echtzeit" ist?

20

Ich habe oft gehört , Entwickler erwähnt , dass Java nicht „ tun Echtzeit “, eine Java - Anwendung auf Linux bedeutet nicht die Anforderungen eines deterministischen Echtzeit - System gerecht zu werden , wie etwas läuft auf RIOT-OS usw.

Ich versuche zu verstehen warum . Mein SWAG sagt mir, dass dies wahrscheinlich größtenteils auf Javas Garbage Collector zurückzuführen ist, der jederzeit ausgeführt werden kann und das System vollständig anhält. Und obwohl es so genannte "pausenlose GCs" gibt, glaube ich nicht unbedingt an ihre Werbung und habe auch keine $ 80K-pro-JVM-Instanz für ein Hobby-Projekt!

Ich habe auch diesen Artikel über das Ausführen von Drohnen-Software unter Linux gelesen . In diesem Artikel beschreibt der Autor ein Szenario, in dem Linux seine Drohne fast zum Absturz gebracht hätte:

Nachdem ich mich für den Low Level Control Loop (PIDs) auf dem Pi entschieden hatte, lernte ich eine harte Lektion. Um klug zu sein, beschloss ich, ein Protokoll in die Mitte des Loops zu schreiben, um Fehler zu beheben. Das Quad flog zunächst einwandfrei, aber dann entschied sich Linux 2 Sekunden brauchen, um einen Logeintrag zu schreiben und der Quad ist fast gegen mein Auto gekracht!

Obwohl dieser Autor seine Drohnen-Software in C ++ geschrieben hat, würde ich mir vorstellen, dass eine Java-App, die unter Linux läuft, das gleiche Schicksal erleiden könnte.

Laut Wikipedia:

Ein System wird als Echtzeit bezeichnet, wenn die Gesamtkorrektheit einer Operation nicht nur von ihrer logischen Korrektheit abhängt, sondern auch von der Zeit, in der sie ausgeführt wird.

Für mich bedeutet dies also: " Sie haben keine Echtzeit, wenn die vollständige Korrektheit logische Korrektheit und Aktualität erfordert. "

Stellen wir uns vor, ich habe eine Java-App geschrieben, die überdurchschnittlich performant ist, und ich habe sozusagen "die Zitrone herausgepresst", und es könnte vernünftigerweise (in Java) nicht schneller sein.

Alles in allem ist meine Frage: Ich suche jemanden, der mir alle / die meisten Gründe erklärt, warum eine Java-App unter n Linux keine "Echtzeit-App" ist. Was sind also alle Kategorien von Dingen auf einem Java / Linux-Stack, die verhindern, dass er "aktuell" ist und daher " völlig korrekt "? Wie bereits erwähnt, sieht es so aus, als ob das Leeren von GC- und Linux-Protokollen die Ausführung unterbrechen kann, aber ich bin mir sicher, dass es außerhalb der Java-App noch weitere Dinge gibt, die zu einem schlechten Timing / einer schlechten Leistung führen und die Einhaltung strenger Fristen zur Folge haben. Was sind Sie?

smeeb
quelle
3
Siehe JSR001
coredump
1
FWIW, Linux kann dazu gebracht werden, sich für harte Echtzeitsysteme in geeigneter Weise zu verhalten, es beinhaltet jedoch einige Techniken, die von typischen Embedded-Entwicklern von Hobbyisten übersehen werden können. Es gibt gute Bücher für die Linux-Echtzeitentwicklung; Ich würde vorschlagen, eine zu erwerben.
Jules
@coredump leider, soweit ich in der Liste der Implementierungen von jsr-1 sehen kann, gab es immer nur vier Implementierungen, von denen zwei derzeit nicht verfügbar sind, und die anderen beiden scheinen recht teure kommerzielle Angebote zu sein, die wahrscheinlich herauskommen der Preisspanne des Fragestellers.
Jules

Antworten:

28

Eine Software ist nicht in Echtzeit, wenn sie so schnell wie möglich ist, sondern wenn gewährleistet ist, dass ein Prozess innerhalb eines festgelegten Zeitfensters abgeschlossen wird. In einem weichen Echtzeitsystem ist es gut, aber nicht unbedingt erforderlich, dass dies garantiert ist. Zum Beispiel sollten in einem Spiel die für einen Frame erforderlichen Berechnungen innerhalb des Zeitraums eines Frames abgeschlossen sein, sonst sinkt die Framerate. Dies verschlechtert die Qualität des Spiels, macht es aber nicht falsch. ZB Minecraft macht Spaß, obwohl das Spiel gelegentlich stottert.

In einem harten Echtzeitsystem haben wir solche Freiheiten nicht. Eine Flugsteuerungssoftware muss innerhalb einer bestimmten Frist reagieren, da sonst das Fahrzeug abstürzen kann. Und die Hardware, das Betriebssystem und die Software müssen zusammenarbeiten, um Echtzeit zu unterstützen.

Das Betriebssystem verfügt beispielsweise über einen Scheduler, der entscheidet, wann welcher Thread ausgeführt wird. Für ein Echtzeitprogramm muss der Scheduler ausreichend große und häufig genug verfügbare Zeitfenster garantieren. Jeder andere Prozess, der in einem solchen Slot ausgeführt werden möchte, muss zugunsten des Echtzeitprozesses unterbrochen werden. Dies erfordert einen Scheduler mit expliziter Echtzeitunterstützung.

Außerdem führt ein User-Space-Programm Systemaufrufe im Kernel durch. In einem Echtzeitbetriebssystem müssen auch diese Echtzeit sein. Zum Beispiel müsste das Schreiben in ein Datei-Handle garantiert nicht länger als x Zeiteinheiten dauern , was das Protokollproblem lösen würde. Dies hat Auswirkungen darauf, wie ein solcher Systemaufruf implementiert werden kann, z. B. wie Puffer verwendet werden können. Dies bedeutet auch, dass ein Aufruf fehlschlagen muss, wenn er nicht innerhalb der erforderlichen Zeit abgeschlossen werden kann, und dass das User-Space-Programm auf diese Fälle vorbereitet sein muss. Im Falle von Java sind die JVM und die Standardbibliothek ebenfalls kernelartig und benötigen explizite Echtzeitunterstützung.

Für alles, was in Echtzeit läuft, ändert sich Ihr Programmierstil. Wenn Sie keine endlose Zeit haben, müssen Sie sich auf kleine Probleme beschränken. Alle Ihre Schleifen müssen durch eine Konstante begrenzt sein. Der gesamte Speicher kann statisch zugewiesen werden, da Sie eine Obergrenze für die Größe haben. Uneingeschränkte Rekursion ist verboten. Dies widerspricht vielen Best Practices, gilt jedoch nicht für Echtzeitsysteme. Beispielsweise kann ein Protokollierungssystem einen statisch zugewiesenen Ringpuffer verwenden, um Protokollnachrichten zu speichern, wenn sie geschrieben werden. Sobald der Start erreicht ist, werden alte Protokolle verworfen, oder dieser Zustand kann ein Fehler sein.

amon
quelle
4

Aus Wikipedia :

Ein Schlüsselmerkmal eines RTOS ist die Konsistenz in Bezug auf die Zeit, die erforderlich ist, um die Aufgabe einer Anwendung zu akzeptieren und abzuschließen. Die Variabilität ist Jitter.

Wichtig ist, dass der Jitter quantifiziert wird, damit das System als Echtzeit betrachtet werden kann . In dem Artikel heißt es weiter, dass das System in Echtzeit weich ist , wenn der Jitter normalerweise begrenzt ist . Wenn der Jitter immer begrenzt ist, ist das System in Echtzeit hart .

Sofern die von Ihnen verwendeten Java- und Linux-Versionen nicht in Bezug auf Jitter quantifiziert sind, sind sie nicht in Echtzeit. Garbage Collection und Log-Writing sind sicherlich Quellen von Jitter, aber selbst die autonome Verarbeitung von (z. B.) Netzwerkpaketen zählt, wenn sie Jitter in Ihre Prozesse einführt .

Lawrence
quelle
1

Für den Anfang kann das Vanilla Linux selbst keine Echtzeit ausführen. Deshalb wurde RTLinux entwickelt.

Nehmen wir an, Sie führen einige Java-Prozesse unter RTLinux aus. Sie werden weiterhin als Echtzeitprozesse betrachtet, da alle diese Prozesse vom Kernel geplant werden. Wenn also ein Prozess zu spät ist, kann für andere Prozesse immer noch die CPU-Zeit garantiert werden.

Wenn auf den Java-Prozessen Green-Threads ausgeführt werden , erfolgt die Ausführung dieser Threads nicht mehr in Echtzeit, da die JVM keine Echtzeitplanung durchführt.

imel96
quelle