www.mikrocontroller.net

Forum: GCC Variablenname entscheidet ob Programm spinnt oder nicht?

Autor: Paul Hamacher (powl)
Datum: 04.07.2008 07:39

Hi,

ich habe da grad ein seltsames Problem entdeckt. Ich habe einen
Charlieplexer und noch 4 weitere LEDs dran hängen die ich als Lauflicht
betreiben möchte. Über den ADC stell ich die Lauflichtgeschwindigkeit
ein. Wenn ich bestimmte Werte einstelle kommt das irgendwie dem
Charlieplexingalgorithmus in die Quere und eine LED Gruppe flackert
dann.

Ich hab mich natürlich gefragt was das soll und den Fehler systematisch
eingegrenzt bis ich auf folgendes gestoßen bin:

vor der main-function:
volatile uint8_t adc_lights;

in der main-function:
adc_lights = ADCH;

Nur durch das Belegen der Variable mit ADCH fängt das Programm an zu
spinnen. Ich hab keine Ahnung warum. Das Lauflicht funktioniert unter
diesen Umständen übrigens auch nicht.

Wenn ich die Variable nun überall in adc_light, also ohne das s am
ende, umbenenne, dann funktioniert alles prima.

Ist das ein Bug im Compiler? Die Codegröße verändert sich dabei auch
nicht.

Wenn ich mir das Assembler-file anschaue fällt an der stelle in der main
folgendes auf:
in der lights-version:
 128:  80 93 9e 00   sts  0x009E, r24

in der light-version:
 128:  80 93 9a 00   sts  0x009A, r24

wieso nimmt er hier denn eine andere speicherposition?
mit anderen optimierunggstufen gibt es den gleichen flacker-effekt.

lg PoWl
Autor: Oliver (Gast)
Datum: 04.07.2008 07:52

>Ist das ein Bug im Compiler?

Nein. Das ist mit Sicherheit ein Bug in deinem Programm, der ganz
woanders zu suchen ist. Daher, wie immer: Zeig mal den ganzen Code.

Oliver
Autor: Paul Hamacher (powl)
Datum: 04.07.2008 09:25
Dateianhang: Bin_r-Uhr_Discolights.c (2,8 KB, 52 Downloads) | formatierter Code

sry, hab vergessen den dateianhang nochmal neu rauszusuchen.

hm.. aber ich habe ausser dem variablennamen rein garnichts verändert.
nur den namen. ich könnte die variable auch bla oder moep nennen.
ansonsten keine veränderung.

nur diese kleinigkeit, die ja mit dem programm an sich ja garnichts zu
tun hat und sache des compilers ist, verändert das verhalten des
programms.

meinetwegen ist der programmcode nicht ganz optimal, das hab ich auch so
schnell da hingeschnuddelt. aber dann kann es doch nicht sein, dass er
funktioniert / nicht funktioniert, wenn ich eine variable anders nenne?

ich habe bestimmte codeteile auskommentiert die nicht zum fehler
beitragen.

lg PoWl
Autor: MartinH (Gast)
Datum: 04.07.2008 09:33

Solche Probleme klingen immer nach amokgelaufenen Zeigern, bzw. Array
Zugriffen. Das erste was mir aufgefallen ist:

phase_DDR hast du mit 4 Elementen deklariert.
Gleich am Anfang schreibst du über das Array hinaus -> phase_DDR[4] = 0;
Autor: MartinH (Gast)
Datum: 04.07.2008 09:37

Und natürlich dann weiter in der Schleife bei
phase_DDR[map[a]] --> in map gibt Elemente mit dem Wert 4, also das
gleiche Problem.
deklariere phase_DDR mal mit 5 Elementen, also phase_DDR[5].

Gruß
Autor: Oliver (Gast)
Datum: 04.07.2008 09:45

Und sach mal, welchen Prozessor du verwendest.

Oliver
Autor: Paul Hamacher (powl)
Datum: 04.07.2008 09:46

bingo :-)

volatile uint8_t phase_DDR[5];

jetzt funktionierts. ich war irritiert weil ich es nun so gewohnt bin ab
0 zu zählen aber hier muss man ja ab 1 zählen.

danke!

was mich dennoch interessiert, wieso entscheidet der variablenname
darüber ob das programm trotzdem funktioniert bzw. wieso kompiliert er
es anders? interessant ist auch, dass das die ganze zeit so gelaufen
ist.

lg PoWl
Autor: Oliver (Gast)
Datum: 04.07.2008 09:58

>was mich dennoch interessiert, wieso entscheidet der variablenname
>darüber ob das programm trotzdem funktioniert bzw. wieso kompiliert er
>es anders?

Tut er nicht, und kompiliert auch nicht anders. Ich würde es ja gern mal
nachstellen, aber dazu müsstest du schon verraten, für welchen AVR dein
Programm ist.

Oliver
Autor: Stefan Ernst (sternst)
Datum: 04.07.2008 09:58

Paul Hamacher wrote:

> was mich dennoch interessiert, wieso entscheidet der variablenname
> darüber ob das programm trotzdem funktioniert bzw. wieso kompiliert er
> es anders? interessant ist auch, dass das die ganze zeit so gelaufen
> ist.

Weil du mit dem Schreiben nach phase_DDR[4] eine andere Variable
überschrieben hast. Und wie du ja selbst festgestellt hast, sorgt das
Umbenennen dafür, dass die Variablen in einer anderen Reihenfolge im
Speicher liegen. In der einen Version hast du irgendetwas weniger
kritisches überschrieben, so dass das Programm anscheinend funktioniert
hat.
Autor: MartinH (Gast)
Datum: 04.07.2008 10:05

Das ist immer schwierig zu sagen wo der Compiler, oder besser hier
Linker, die Variablen genau platziert.
Wie du im Assembler schon gesehen hast, platziert er sie je nach dem
Namen, den du verwendet hast, an unterschiedliche Positionen. Evtl hat
er in der funktionierenden ohne s Version die Variablen so im Speicher
platziert, dass nichts mehr hinter dem phase_DDR Array liegt, und so
beim darüber hinausschreiben nichts passiert.

Kannst ja mal schaun, welche Variable du überschreibst, wenn du über das
Array hinausschreibst.
Autor: MartinH (Gast)
Datum: 04.07.2008 10:05

oh da war ich zu langsam :)
Autor: Paul Hamacher (powl)
Datum: 04.07.2008 10:10

Ok, das gibt der ganzen Sache einen Sinn :-)

Das Programm ist für einen ATtiny26.

Sollte eine Binär-Uhr für mein Schulmäppchen werden, als nettes Gimmick
sorgt dann noch ein kleines LEDlauflicht an dunklen Tagen oder im
verdunkelten Physik-Saal vorm Unterricht für Stimmung (ich wollte nur
einfach meine LEDs loswerden die ich mir zum Ausprobiern bestellt hab)

lg PoWl

Antwort schreiben

Die Angabe einer Email-Adresse ist freiwillig. Wenn Sie automatisch per Email über Antworten auf Ihren Beitrag informiert werden möchten, melden Sie sich bitte an.

Wichtige Regeln - erst lesen, dann posten!

  • Suchfunktion und Betreffsuche benutzen - vielleicht gibt es schon einen ähnlichen Beitrag
  • Aussagekräftigen Betreff wählen
  • Im Betreff angeben um welchen Controllertyp es geht (AVR, PIC, ...)
  • Groß- und Kleinschreibung verwenden
  • Längeren Sourcecode nicht im Text einfügen, sondern als Dateianhang
  • JPEG-Dateien (.jpg) nur für Fotos und Scans verwenden
  • Schaltpläne, Screenshots usw. als PNG oder GIF anhängen

Formatierung (mehr Informationen...)

  • [c]C-Code[/c]
  • [avrasm]AVR-Assembler-Code[/avrasm]
  • [pre]vorformatierter Text (z.B. Code in anderen Sprachen)[/pre]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] - Link zu Artikel






webmaster@mikrocontroller.netImpressumWerbung auf Mikrocontroller.net