Hallo zusammen, ich befasse mich erst seit kurzem wieder mit Mikrocontroller und habe bisher eigentlich nur Spielereien damit programmiert. Jetzt habe ich mich an einen Drehzahlmesser rangewagt. Zur Erklärung: Die Drehzahl wird mit einem Hall-Sensor abgenommen und liefert mir pro Umdrehung ein High-Signal. Um die Drehzahl zu bestimmen wollte ich nun die Zeit zwischen den Flankenwechseln messen. Die U/min sollen mir dann auf einem LCD (2 Zeilen, 32 Zeichen) angezeigt werden. Der verwendete Mikrocontroller ist ein Atmega16, da ich die Flankenwechsel an PD6/ICP einlesen wollte. Programmieren wollte ich mit C. Aus älteren Schulunterlagen hatte ich noch einen Quelltext, mit dem man die Zeit zwischen zwei Flankenwechsel messen kann. Die Zeit wird dann auf vier BCD 7-Segment-Anzeigen ausgegeben die an Port A und Port B hängen. Jetzt zu meinem Problem, ich bekomme den Quelltext nicht so abgeändert, das es mir die Zeit, bzw. die U/min auf dem Display anzeigt. Ich bekomme den „wert“ aus der Service-Funktion nicht in das Main-Programm. Die LCD-Initialisierung klappt und zeigt mir auch was an. Ich habe die LCD-Routines aus dem AVR-GCC-Tutorial verwendet und auf Port C umgeschrieben. Ich bin für jede Hilfe dankbar. Die C-File befindet sich im Anhang Gruß Daniel
Das Problem ist, das "wert" einmal in der Signal Funktion als lokale int Variable und einmal vor main als globale float variable deklariert ist. Mach die mal ganz an den Anfang als int und in der Signal funktion lässt du das weg. Normalerweise müsste der Compiler auch so meckern. (mach mal gcc -Wall)
>Das Problem ist, das "wert" einmal in der Signal Funktion als lokale int >Variable und einmal vor main als globale float variable deklariert ist. >Normalerweise müsste der Compiler auch so meckern. (mach mal gcc -Wall) Dem Compiler ist es ziemlich egal, wie wo welche Variable mit welchem Namen deklariert wird. >Mach die mal ganz an den Anfang als int und in der Signal funktion lässt >du das weg. Mit einem "volatile" bei der Deklaration geht man sicher, dass der Compiler die Variable nicht einfach wegoptimiert, wenn er der "Meinung" ist, dass sie nirgends weiter benutzt wird.
hi, du hast wert in deiner interrupt routine declariert und noch einmal in deiner main funkition. wenn du auf die variable sowohl im interrupt, als auch in der main funktion zugreifen willst musst du sie erstens ueber beiden funktionen deklarieren und somit global, und ich denke du kannst dir das register keyword sparen und durch ein 'volatile' ersetzen. ungefaehr so:
1 | volatile uint16_t wert; |
2 | |
3 | ISR (TIMER0_OVF_vect) { |
4 | /* Interrupt routine */
|
5 | wert = blubb; |
6 | }
|
7 | |
8 | int
|
9 | main (void) { |
10 | /* hauptroutine */
|
11 | |
12 | /* ausgabe wert */
|
13 | }
|
gruss Marc
>Dem Compiler ist es ziemlich egal, wie wo welche Variable mit welchem >Namen deklariert wird. Ihm ist es aber nicht egal, wenn eine Variable mit gleichem Namen zweimal deklariert wird. >Mit einem "volatile" bei der Deklaration geht man sicher, dass der >Compiler die Variable nicht einfach wegoptimiert, wenn er der "Meinung" >ist, dass sie nirgends weiter benutzt wird. Verhindert aber auch keine doppel-deklaration.
der compiler wird das nicht als fehler erkennen. fuer den compiler ist der namespace der globalen ab der deklaration abwaertz. somit wird die lokale in der interrupt routine nicht von der globalen ueberdeckt, denn die ist erst ab kurz vor der main gueltig. volatile bringt da auch nichts, aber volatile ist notwendig, damit du in der ISR den wert aendern kannst und er auch im in der main schleife aktuell ist Gruss Marc
Erstmal vielen Dank für eure Hilfe. Es war mir schon klar, das ich die Variable „wert“ 2x deklariert habe. Bzw, es war ein versehen das diese noch im Quelltext stand den ich gepostet habe. Durch die 2te deklarierung und das gleichzeitige Setzen der Variable auf 9999 (float wert=9999;) wollte ich die Berechnungen und die LCD-Ausgabe testen. @ Marc: Dein Vorschlag war genau der Richtige, jetzt funktioniert es... theoretisch zumindest. Habe diese Schaltung bisher nur mit der Software „Proteus 7 Professional“ von Labcenter simuliert, da läuft sie. Man tastet an PD6 und auf dem LCD erscheinen die U/min. Nach dem ich sie jetzt Hardware-Technisch aufgebaut habe lässt sich das LCD nicht initialisieren. Woran kann das liegen? Selbst mit dem Quelltext aus dem AVR-Tutorial, womit man nur „Test – Hallo Welt“ auf das LCD schreibt, Funktioniert nicht. Mit einem Atmega8 gibt es keine Probleme. Nur der 16er will nicht. Ich muss ehrlich gesagt zugeben, dass ich das erste Mal einen Atmega16 benutze, bisher hat ein 8er immer gereicht. Die Verdrahtung und die Funktion des LCD habe ich mehrere male überprüft. Lasse den Atmega16 derzeit mit den ab Werk eingestellten 1 MHz laufen. Kann sich jemand mal die header-files ansehen? Packe das ganze Projekt mal in den Anhang. Vielen Dank
Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.