Hallo Moritz,
danke Moritz, jetzt wird mir einiges klarer, aber noch nicht alles:
Chris' Projekt beinhaltet mehrere Sketches, was mich verwirrt. Ein Sketch - sketch_aquarium_a4 - ist das eigendliche Programm und ruft alle Funktionen wie Pumpensteuerung, Switch-Checking, pH- und Sauerstoff-Elektrodenverarbeitung auf und steuert ein LCD an? Und die anderen sind Utilities und werden bei Bedarf in den Arduino geladen, überschreiben somit sketch_aquarium_a4, um andere Tätigkeiten auszuführen?
MajorMadness":1wjknvxs schrieb:
Das Script was du meinst macht den Arduino nicht Tasking fähig sondern implentiert nur eine nicht lineare abarbeitung durch setzen verschiedener interrupts und aufrufen von programmschritten nach einander, unabhängig von einander.
Aber genau das ist Multi-Tasking, hier genauer Multi-Threading. Multi-Tasking deckt auch Multi-Processing ab, wozu es aber der Process-Isolation bedarf, die Arduino nicht kennt und sich ohne Hardwareunterstützung (MMU) nicht robust implementieren läßt.
Preemptiv wie schon zu Amiga-Zeiten ist ChibiOS/RT nicht, aber kooperativ wie zu Windows 3.1- und Atari ST-Zeiten, wenn auch auf eine recht einfache Weise. Threads ermöglichen ja, unterschiedliche Aufgaben - wenn schon nicht physisch durch je einen eigenen Adressraum - zumindest aber logisch voneinander zu trennen. Diese logische Trennung macht ein Programm erheblich übersichtlicher, leichter zu verstehen und zu warten. Dadurch erhöht sich die Robustheit und reduziert sich die Fehleranfälligkeit. Insgesamt erhöht sich also die Stabilität, und zwar ganz erheblich, genauso wie bei sauber geschnittenen Modulen/Klassen/Packages in C, C++ und Java. Sogenannte God-Classes in z.B. C++ und Java wären das genau Gegenteil.
Wenn ich das richtig sehe, verfügt ein Arduino über sehr wenig Speicher, weshalb man wohl eher God-Class-like implementiert, weil zusätzlicher Verwaltungsaufwand zusätzlich Speicher kostet?
Man kann sich das Leben aber dennoch leichter gestalten und sich dem Thread-Konzept nähern, indem man vielleicht keine Thread-Library wie ChibiOS/RT nutzt, aber die unterschiedlichen Aufgaben, mit denen man seinen Arduino betreut, dennoch wie in C modularisiert oder objektorientiert wie in C++ jeweils in eine Hauptklasse mit optional zusätzlichen Delegate-Classes packt (also pro Aufgabe ein oder mehrere Objekte verwaltet).
All diese Hauptklassen können dieselbe Basisklasse besitzen. Diese Basisklasse könnte man Task nennen, und sie könnte eine virtual execeute-Methode besitzen. Ein Sketch instanziiert diese Klassen in der setup-Funktion (mit new auf dem Heap, nicht auf dem Stack!), hält sich die Instanzen in einem Pointer-Array und führt sie in der loop-Funktion mit einer Schleife über den Pointer-Array aus. Der Sketch muß diese Klassen in der setup-Funktion natürlich kennen. Dabei handelt es sich aber um einfachen flachen Code ohne große Logik, ist also hierfür extrem leicht wartbar. In der loop-Funktion muß der Sketch die einzelnen Klassen aber nicht mehr kennen. Die loop-Funktion muß - einmal codiert - nie mehr angefaßt werden, da sie nur noch abstrakte Task-Objekte, aber nicht mehr die einzelnen Klassen kennt. So wie in diesem
Beispiel, nur halt nicht mit einzelnen Pointer auf A- und B-Instanzen sondern als Array deklariert und mit einer Schleife über diesen Array.
Beispielsweise bezogen auf Chris' Projekt: es gäbe dann die definitions.h in der Form nicht mehr. Aktuell stellt sie ein All-In-One-Sammelsurium von Konstanten und Variablen quer über alle Funktionalitäten des Programms dar. Das widerspricht den Grundsätzen der Modularisierung, dem Information Hiding und dem Separation-Of-Concern Principle (kann man alles Ergoogeln).
pH-relevanter Teile würden in eine pH-Klasse wandern, O2-relevant in eine O2-Klasse etc. Die Datei definitions.h würde dann nur noch echte Globals enthalten, die also von mehr als einer Klasse oder dem Haupt-ino und mindestens einer Klasse benutzt werden.
definitions.h birgt auch eine Gefahr: würde sie von mehreren Modulen/Klassen included, würden die dort definierten Variablen mehrfach existieren (wenn es dieses Konzept in Arduino überhaupt gibt, ich seh auch nur einen Include dieser Datei).
sketch_aquarium_a4.ino würde auch viel schlanker. Aktuell widerspricht sie dem Single-Responsibility-Principle, da sie sich recht detailliert um alle Aufgaben kümmert. In C++/Java würde man sie als Monster-Class bezeichnen, würde sie eine Klasse beinhalten.
MajorMadness":1wjknvxs schrieb:
Wenn du dich gut mit Softwareentwicklung auskennst (nicht webentwicklung) dann solltest du C, evt auch C++ kennen und alle damit verbundenen vor und nachteile.
Und weiter?
MajorMadness":1wjknvxs schrieb:
Grundsätzlich wird ein Sketch eigentlich nie ausgeführt. Er dient nur dazu den Code zu schreiben. Ein Sketch wird kompiliert und dann als HEX auf den Controller überspielt.
Mit Sketch meine ich natürlich schon den Maschinencode, der aus dem Sketch etc. beim Compile entsteht. Das war mir zu lang, so zu formulieren. Mit "HEX" (also hexadezimal) meinst Du wohl "binär", also z.B. ein ELF-Binary?
MajorMadness":1wjknvxs schrieb:
Wichtig dabei ist zu wissen wie der Build Prozess ist:
Zuerst werden Header files ausgewertet (*.h) und preProzessor anweisungen (#define, incluide) interpretiert. Danach werden aus allen Files function defines und typedefs gesucht. Damit hat Arduino eine Struktur die an C erinnert (.h, .ccp).
Zur besseren Struktur kann man Teile des programms in andere Files lagern. Diese haben immer die endung .ino und werden vom kompiler gelesen als ständen sie UNTER dem main file (der heist wie der Ordner). Hierbei geht der Kompiler von links nach rechts vor. Sollte also eine Typedef in einem File mit Namen zweitertab.ino sein "kennt" Arduino diese nicht in erstertab.ino. Will man dies doch machen muss statt eine rino ein header file gebaut werden und dieser VOR der verwendung mit #include eingebunden werden.
Chris' "sketch_aquarium_a4.ino" ist also vergleichbar mit einer C-Datei, die die main-Funktion enthält. Und die anderen INOs in dem Ordner "sketch_aquarium_a4" sind Module? Das gesamte Programm besteht also aus dem Ordner "sketch_aquarium_a4"? Die anderen Odner sind jeweils ein eigenes Programm?
Jetzt seh' ich's auch langsam auf arduino.cc. Man muß die Beispiele durchackern, um rauszufinden, wie Arduino-Software grundlegend funktioniert oder zigfach Google fragen. Find ich schon blöd und zeitaufwendig, daß es da keine gscheite Systembeschreibung gibt, um einen Überblick zu erhalten.
Viele Grüße,
Markus