Ist diese Strategie, um globale Variablen in C zu vermeiden, richtig? [geschlossen]

8

In meinem (persönlichen) eingebetteten Projekt häufen sich globale Variablen an. Ich brauche diese Variablen, um von der ISR (Interrupt-Service-Routine) und / oder von einem Menüsystem (so dass sie vom Benutzer geändert werden können) zugänglich zu sein, aber gleichzeitig möchte ich vermeiden, zu viele Globals zu haben.

Da sie für Module gruppiert werden können, dachte ich, dass ich sie in ihre eigene .c-Datei kapseln kann, die als static oder static volatile deklariert ist, und sie mit der Außenwelt in Verbindung bringen kann.

Etwas in der Richtung von:

in module1.c

%Vor%

module1.h würde die Funktion prototype, structs und alle anderen Elemente enthalten, um das Modul funktionsfähig zu machen, außer natürlich für die Definition der statischen Variablen

in main.c

%Vor%

Dieses Schema würde natürlich auf die anderen Module ausgedehnt.

Jetzt sind meine Fragen:
ist das ein guter Ansatz? Ist es das gleiche, einfach einen Haufen Globals zu haben? Irgendwelche großen Nachteile?

Ich dachte auch, ich könnte eine Mischung verwenden, die immer noch die globalen Variablen hat, um eine direkte Manipulation durch die ISR (da Funktionsaufrufe von der ISR manchmal missbilligt werden) und die Funktionen in jedem anderen Fall zu erlauben. Wäre das besser?

    
zakkos 19.04.2017, 13:04
quelle

1 Antwort

2

Da sind einige Fragen:

  

ist das ein guter Ansatz?

Ja. Es gibt vielleicht ein Argument für die Platzierung der ISR im selben Modul wie die Zugriffsfunktionen und Daten, die es teilt, und es als Zugriffsfunktion selbst behandelt, so dass es die Daten direkt ohne den Overlay des Access Wrappers lesen kann.

  

Ist es besser / schlechter / gleich, einfach einen Haufen Globals zu haben?

Viel schlimmer. Mit einem globalen, wo werden Sie Ihren Zugang Mutex, Datenvalidierung oder Haltepunkte platzieren? Es erhöht die Modulkopplung, und das sollte immer minimiert werden.

  

Irgendwelche großen Nachteile?

Nicht wirklich. Es gibt einen Funktionsaufruf-Overhead, der in einer ISR kritisch sein kann; aber wenn das ein Problem wäre, würdest du printf() in einer ISR nicht aufrufen! Sie können jede mögliche Leistungseinbuße unter Anwendung meines früheren Vorschlags zum Platzieren des ISR im Datenmodul oder durch Einfügen des Codes mindern - aber Ihr Compiler kann das ignorieren und kann dies tun, wenn das Debuggen aktiviert ist, und kann auch Inline sein unabhängig davon, ob die Optimierung aktiviert ist. Einige Compiler haben eine "erzwungene" Inline-Erweiterung, die der Compiler nicht ignorieren darf; aber es ist nicht tragbar.

Ein wichtiger Vorteil besteht darin, dass Sie, wenn die Variable nicht atomar ist, einen Zugriffsschutzmechanismus benötigen, um konsistenten Zugriff zu gewährleisten - und dies wird am einfachsten und sichersten mit Zugriffsfunktionen ausgeführt. In diesem Fall haben Sie vielleicht Funktionen, die den Interrupt um den Zugriff herum deaktivieren oder wieder aktivieren, oder verwenden Sie eine Spin-Lock-Funktion (passend für den ISR-Eintrag und den normalen Kontext) - nicht umgekehrt habe hier - verschließe den ISR nicht auf unbestimmte Zeit!).

  

Ich dachte auch, ich könnte eine Mischung verwenden, die immer noch die globalen Variablen hat, um eine direkte Manipulation durch die ISR (da Funktionsaufrufe von der ISR manchmal missbilligt werden) und die Funktionen in jedem anderen Fall zu erlauben. Wäre das besser?

Nicht wirklich - siehe meinen obigen Punkt über den Funktionsaufruf-Overhead und die Platzierung des ISR mit den Daten. Das Problem beim Aufrufen von Funktionen in einem ISR ist selten ein Zeitaufwand, sondern eher, dass der Implementierer der Funktion es nicht so entworfen hat, dass es sicher und effizient von einem ISR aufgerufen wird, und es kann exzessive stapelnde, nicht-deterministische Ausführungszeit verwenden , busy-warte oder nicht wiedereinsteiger oder thread-safe. Der Aufruf von Funktionen von Drittanbietern oder Standardbibliotheken kann zum Beispiel schlecht beraten sein; Funktionen aufzurufen, die Sie speziell für diesen Zweck geschrieben und entworfen haben und die Ihren spezifischen Anforderungen entsprechen, ist nicht unbedingt ein Problem.

Alles, was Sie darüber wissen müssen, warum Globals eine schlechte Idee sind und angemessene Möglichkeiten, sie zu vermeiden, finden Sie in Jack Ganssles Artikel " Ein Pox auf Globals " - es ist auch eine unterhaltsame Lektüre.

    
Clifford 19.04.2017 16:53
quelle