- LiFePO4 Speicher Test         
Ergebnis 1 bis 10 von 22

Thema: Verlassen einer Funktion um später zurück zu springen.

Hybrid-Darstellung

Vorheriger Beitrag Vorheriger Beitrag   Nächster Beitrag Nächster Beitrag
  1. #1
    Erfahrener Benutzer Robotik Visionär Avatar von oberallgeier
    Registriert seit
    01.09.2007
    Ort
    Oberallgäu
    Beiträge
    8.657
    Zitat Zitat von i_make_it Beitrag anzeigen
    Eine Hochsprachen Funktion (z.B. C++) hat genau einen Einsprungspunkt und mindestens einen Aussprungspunkt ... C++ wo es Überladungen gibt, dann stellen wir fest, das ein Einsprung in eine Funktion an einer anderen Stelle als dem Funktionsaufruf nicht funktionieren kann ...
    Meine Kenntnisse in C sind sehr begrenzt aber ich hab mich (vielleicht deshalb?) mit der Frage auch schon beschäftigt. Wegen mangelnden Zutrauens zu so einem Konstrukt hatte ich das nie getestet - auch nie geschrieben.

    Frage: KÖNNTE es nicht so gehen, dass man ein Flag mitschleppt? Beim Aufruf der Funktion informiert das Flag über die verschiedenen Zustände: Erster Aufruf, Aufruf nach Return am Ende des ersten Abschnittes, Aufruf nach Return am Ende des zweiten Abschnittes usf, Aufruf nach Abarbeiten der vollständigen Funktion. Ein switch nutzt nun diese Information zum Ansprung der verschiedenen Pseudoeingänge. Am Beginn jedes Cases wird dann das Flag erstmal passend gesetzt (?) und vor dem Break bzw. Return des aktuellen Cases (klingt aber jetzt irgendwie doppelt gemoppelt) wird das Flag entsprechend angepasst.

    Ich habs nie realisiert weil es mir irgendwie sehr seltsam vorkommt; wie sollte ich das testen??

    Nachtrag: Sorry, witzkatz ist schneller wach gewesen.
    Ciao sagt der JoeamBerg

  2. #2
    Neuer Benutzer Öfters hier
    Registriert seit
    24.05.2012
    Beiträge
    14
    Das mit dem "kaum pflegbar" würde ich nicht behaupten. Da die Funktionalität ja gut entkoppelt ist und auch sehr überschaubar. Mir schwebt da eine ähnliche Lösung (nur etwas leichter als deine) vor:

    1. Beim erreichen des Punktes wird die rücksprung Adresse in einem globalen Pointer gespeichert
    2. Zurück in die jobstack_execute und von da wieder in die Main
    3. Wird jobstack_execute erneut ausgeführt an den in Schritt 1 gesetzten Pointer springen

    Mein Problem hier ist, dass ich nicht weiß inwieweit ich damit mein Programm zerstöre. Muss ich vorher alle Register sichern, könnte ich Probleme mit den Funktions-Stack bekommen, ... .
    Welche Auswirkungen hat es, wenn ich eine Funktion einfach verlasse.

    - - - Aktualisiert - - -

    Zitat Zitat von witkatz Beitrag anzeigen
    Ist doch aufgeteilt, oder nicht?
    Ja ist aufgeteilt ist, bedeutet aber viel Aufwand in der Funktion und die Funktion wird dadurch sehr schwer lesbar.
    Der größte Nachteil dieser Lösung: Da die Funktion wirklich verlassen wird, verliert sie ihren Zustand. Will man zwischen den States zustände teilen muss das über globalen oder anderweitig geteilten Speicher geschehenm, was die Sache um einiges komplizierter macht.

  3. #3
    Erfahrener Benutzer Roboter-Spezialist Avatar von witkatz
    Registriert seit
    24.05.2006
    Ort
    NRW
    Alter
    53
    Beiträge
    542
    Blog-Einträge
    17
    Zitat Zitat von Iqon Beitrag anzeigen
    bedeutet aber viel Aufwand in der Funktion
    Nö, sehe ich nicht so.
    Zitat Zitat von Iqon Beitrag anzeigen
    und die Funktion wird dadurch sehr schwer lesbar.
    Im Gegenteil, es ist lesbarer als irgendein magisches Makro und gut debugbar mit Breakpoints in einzelnen Schritten. Aber wie meine Mutter immer zu sagen pflegte "de gustibus non est disputandum"
    Zitat Zitat von Iqon Beitrag anzeigen
    Da die Funktion wirklich verlassen wird, verliert sie ihren Zustand. Will man zwischen den States zustände teilen muss das über globalen oder anderweitig geteilten Speicher geschehenm, was die Sache um einiges komplizierter macht.
    static ?

  4. #4
    Erfahrener Benutzer Robotik Visionär Avatar von oberallgeier
    Registriert seit
    01.09.2007
    Ort
    Oberallgäu
    Beiträge
    8.657
    Zitat Zitat von Iqon Beitrag anzeigen
    Das mit dem "kaum pflegbar" würde ich nicht behaupten. Da die Funktionalität ja gut entkoppelt ist und auch sehr überschaubar ...
    Wäre also doch ne kleine Übung wert . . . wobei ich wohl die Version mit dem Flag brauche. Denn: Das Ergebnis der Funktion wird doch wohl (hoffentlich :.-.) ) von irgend einem Abschnitt benötigt. Und dieses Ergebnis ist nur dann gültig bzw. aktuell und brauchbar, wenn das Flag "Funktion mindestens einmal vollständig durchlaufen" gesetzt ist.

    Gute Mutter: "de gustibus non est disputandum" - meine verstand kein Latein, da musste ich selbst durch.
    Ciao sagt der JoeamBerg

  5. #5
    Neuer Benutzer Öfters hier
    Registriert seit
    24.05.2012
    Beiträge
    14
    Ja das Ergebnis wird benötitg. Der JobStack den ich nutze ruft Funktionen mit folgender Signatur auf:
    Code:
    void (*jobstack_job)(void *dataPtr)
    Die Ergebnisse werden also in eine beliebige Struktur geschrieben, die beim anlegen des Jobs übergeben wird.

    Code:
    struct mystruct shared_data;
    jobstack_put(&func_ptr, (void *) &shared_data);
    Zitat Zitat von oberallgeier;
    static ?
    Wäre möglich, in meinen Augen aber unsauber da lokale Variablen dadurch Datei-Global sind.

    @witkatz: Deine Lösung ist wahrscheinlich die einfachste. Ich hab mir nur überlegt, ob man das ganze Switch-Case gedöns irgendwie Sinnvoll verstecken könnte.

  6. #6
    Erfahrener Benutzer Roboter-Spezialist Avatar von witkatz
    Registriert seit
    24.05.2006
    Ort
    NRW
    Alter
    53
    Beiträge
    542
    Blog-Einträge
    17
    Zitat Zitat von Iqon Beitrag anzeigen
    ob man das ganze Switch-Case gedöns irgendwie Sinnvoll verstecken könnte.
    Verstecken kann man in C fast alles. Ob es sinnvoll ist, ist eine andere Frage. Wäre zwar nicht meine Art, aber bitte schön, ein Q&D Vorschlag zum Verstecken von "Switch-Case-Gedöns":
    Code:
    #include "StateMachine.h"
    void longrunning(void) {
        STATEMACHINE_INIT 
            ;/*...*/ // do something
            step++;
    
        STATEMACHINE_STEP(1)       
            ;/*...*/ // do something more
            step++;
    
        STATEMACHINE_STEP(2)
            ; // do even more
            if(error) 
                step = -1;
            else
                step = 0;
    
        STATEMACHINE_STEP(-1)
            ; // do some error handling
            step = 0;
    
        STATEMACHINE_END
    }
    Nachtrag:
    Ich hab die quick'n'dirty Macros etwas überarbeitet und mittlerweile gefällt mir die Lösung sogar
    Angehängte Dateien Angehängte Dateien
    Geändert von witkatz (17.09.2015 um 22:51 Uhr) Grund: Angehängte Headerdatei im eigenen PIC Projekt getestet und korrigiert

  7. #7
    Neuer Benutzer Öfters hier
    Registriert seit
    24.05.2012
    Beiträge
    14
    Zitat Zitat von witkatz Beitrag anzeigen
    Verstecken kann man in C fast alles.
    Das stimmt natürlich, ob das immer sinnvoll ist, ist die andere Frage Danke für eure Hilfe.

    Ich denke die Switch-Case (ohne Macros) Variante ist die einfachste und damit beste. Also getreu dem KISS Motto, bleibt es bei dieser Variante.

  8. #8
    Erfahrener Benutzer Robotik Einstein Avatar von i_make_it
    Registriert seit
    29.07.2008
    Ort
    Raum DA
    Alter
    56
    Beiträge
    2.814
    Wenn ich das richtig verstehe, willst Du eigentlich ein Multitasking realisieren.
    Task 1 ist dein Longrunning Prozess Task 2 alles andere.

    Man müsste mal prüfen ob sich das mit einer Timer IRQ Routine realisieren lässt.
    Das wäre die einzige Möglichkeit sicherzustellen, das der Longrunning Task sicher nach einer gewissen Zeit unterbrochen wird und in den andern Task zurückgekehrt wird.

    Da ja normalerweise die IRQ Routine komplett abgearbeitet wird, bevor in das unterbrochene Programm zurückgekehrt wird, sollte entweder die Hauptschleife die IRQ Routine sein und nach einem Durchlauf in den Longrunning Prozess zurückkehren oder du befasst dich mal damit was Linus Torvalds als ersten Teil von Linux realisiert hat (Ein präemptives Multitasking das zwichen zwei Tasks hin und her springt und dabei die Rettung aller Register, Pointer und des Stacks übernimmt). Was du versuchst ist ein kooperatives Multitaksing, damit ist Microsoft schon bei Windows 1 bis 3 gescheitert. Bleibt ein Task hängen ohne das ein Reset verursacht wird, fällt das ganze wie ein Kartenhaus in sich zusammen.

    Wie so was geht steht z.B. hier:
    http://www.gbv.de/dms/ilmenau/toc/592544346.PDF
    oder hier:
    Multitasking mit AVR RISC-Controllern
    Prof. Dr. Ernst Forgber
    Franzis Verlag
    Leseprobe:
    http://www.ciando.com/img/books/extr...5270558_lp.pdf

    Multitasking für AVR:
    http://www.controllersandpcs.de/pdfs/vmavr.pdf

    https://xivilization.net/~marek/bina...ltitasking.pdf

    http://www.wseas.us/e-library/conferences/2015/Dubai/CEA/CEA-24.pdf

    http://www.ripublication.com/irph/ij...4n17spl_16.pdf

    http://www.ijert.org/view-pdf/7712/r...icrocontroller

    http://citeseerx.ist.psu.edu/viewdoc...=rep1&type=pdf
    Geändert von i_make_it (17.09.2015 um 12:24 Uhr)

Ähnliche Themen

  1. Nach ISR in beliebige Funktion springen? Wie? Inline-Asm?
    Von Manu_91 im Forum C - Programmierung (GCC u.a.)
    Antworten: 15
    Letzter Beitrag: 17.09.2015, 08:56
  2. ein Int-Array einer Funktion
    Von oderlachs im Forum Arduino -Plattform
    Antworten: 13
    Letzter Beitrag: 17.02.2014, 22:50
  3. Stack beim verlassen einer Schleife...
    Von Klingon77 im Forum Software, Algorithmen und KI
    Antworten: 10
    Letzter Beitrag: 26.04.2009, 10:17
  4. Funktion gibt Funktion zurück... nächstes Problem
    Von Jaecko im Forum C - Programmierung (GCC u.a.)
    Antworten: 2
    Letzter Beitrag: 19.12.2008, 08:51
  5. Funktion als Rückgabewert einer Funktion?
    Von Jaecko im Forum C - Programmierung (GCC u.a.)
    Antworten: 1
    Letzter Beitrag: 08.09.2008, 10:25

Stichworte

Berechtigungen

  • Neue Themen erstellen: Nein
  • Themen beantworten: Nein
  • Anhänge hochladen: Nein
  • Beiträge bearbeiten: Nein
  •  

LiFePO4 Speicher Test