Hallo zusammen!
Bin gerade dabei mich etwas mit freeRTOS auf dem ATMega32 zu
beschäftigen.
Dazu habe ich einen Task erstellt, der eine LED ständig ein- und
ausschalten soll, indem er auf die entsprechende Position im
PINx-Register eine 1 schreibt.
(Datenblatt: Writing a logic one to PINxn toggles the value of PORTxn,
independent on the value of DDRxn.)
Der Task sieht dementsprechend so aus:
void prvLEDTest(void *pvParameters )
{
while(1) {
PIND = (1<<5);
vTaskDelay(100);
}
}
Das Problem ist, dass der Compiler dieses wegen "Unsinnigkeit"
wegoptimiert.
PIND ist wie folgt definiert: #define PIND _SFR_IO8(0x10)
Dementsprechend kann ich hier soviel, ich weiß auch nicht mit 'volatile'
arbeiten...
Ich bin euch für jeden Tip und Ratschlag zur Lösung dieses Problems
dankbar und hoffe dass ihr mir hier weiterhelfen könnt.
Gruß
Manu
Manuel wrote:
> Das Problem ist, dass der Compiler dieses wegen "Unsinnigkeit"> wegoptimiert.> PIND ist wie folgt definiert: #define PIND _SFR_IO8(0x10)
...und _SFR_IO8 markiert das Register als volatile. Daran liegt es
also nicht.
Kann es sein, dass du ihn irgendwie auf aggressive Optimierung
gestellt hast und dass er die komplette Funktion eliminiert, weil er
nicht erkennen kann, dass sie irgendwo benutzt wird? Dagegen würde
ggf. ein __attribute__((used)) helfen.
> (Datenblatt: Writing a logic one to PINxn toggles the value of PORTxn,> independent on the value of DDRxn.)
Aus dem Datasheet vom Mega32 wirst du das Zitat kaum haben. Diese
Funktionalität ist das erste Mal beim deutlich neueren Tiny2313 in
Erscheinung getreten, davor war PINx readonly, was im Datasheet vom
Mega32 auch so drinsteht.
Könnte es sein, dass genau dies dein Problem ist? Vermuteter
Compilerfehler weil Programm verhält sich nicht so wie erwartet?
> Kann es sein, dass du ihn irgendwie auf aggressive Optimierung> gestellt hast und dass er die komplette Funktion eliminiert, weil er> nicht erkennen kann, dass sie irgendwo benutzt wird?
Kann eigentlich nicht sein. Es wird ja ein Zeiger auf die Funktion
gebildet, über den sie dann aufgerufen wird. Das reicht, um solche
Optimierungen zu verhindern.
> Wie immer in solchen Fällen hilft ein kurzer Blick in das ASM-Listing> des Compilers oder das Disassembly-Fenster des Debuggers.
Es hilft zumindest bei der Feststellung, ob irgendwas wegoptimiert wird.
> Kann eigentlich nicht sein. Es wird ja ein Zeiger auf die Funktion> gebildet, über den sie dann aufgerufen wird. Das reicht, um solche> Optimierungen zu verhindern.
Zumal ein Compiler, der wie gcc jedes Quellfile einzeln übersetzt, bei
einer Funktion, die nicht als "static" deklariert wurde, annehmen muss,
dass sie anderswo gebraucht wird. Wenn man also nicht pro Funktion eine
eigene Section verwendet und so dem Linker die Entscheidung überlässt,
sind solche Funktionen immer drin. Nur der Aufruf wird u.U. wegoptimiert
weil inlined.
Andreas Kaiser wrote:
> Zumal ein Compiler, der wie gcc jedes Quellfile einzeln übersetzt, bei> einer Funktion, die nicht als "static" deklariert wurde, annehmen muss,> dass sie anderswo gebraucht wird. Wenn man also nicht pro Funktion eine> eigene Section verwendet ...
Daher schrieb ich auch von ,,aggressiver Optimierungseinstellung''.
Das bezog sich also schon auf Dinge wie -ffunction-sections/ +
--gc-sections und -fwhole-program.
Hallo Manuel,
bei mir (ATTINY2313) optimiert er da nichts weg - super Trick, wieder 4
Byte(gegen ^=) gespart.
Ich hoffe, du findest die Ursache.
Viel Erfolg,
Bombastix