Gast
#1715635
Hallo Leute Habe mir mal eine leichten Code zusammengebastelt, beí dem über die ISR Overflow Routine vier Taster abgefragt werden. Diese sollen anschließend eine LED toggeln. Ohne Interrupt funzt es und auch mit Interrupt, aber nur, wenn ich diesen zusammen mit einer lcd_init IN die while(1) schleife tue. Leider erhalte ich dabei starke Displayfehler, da das Display dadurch ja immer neu initialisiert wird. Packe ich das ganze außerhalb der while(1) Schleife kann ich die LED nicht mehr toggeln. habe mir auch die lcd_init mal näher betrachtet und bei dieser werden zu Beginn die Interrupts ausgeschalten cli() und am Ende wieder eingeschalten sei()! kann es damit zusammenhängen? also hier mal mein Code! // Deklarationen ============================================================== // Festlegung der Quarzfrequenz #ifndef F_CPU // optional definieren #define F_CPU 18432000UL // MiniMEXLE mit 18,432 MHz Quarz #endif // Include von Header-Dateien #include <avr/io.h> // I/O-Konfiguration (intern weitere Dateien) #include <stdbool.h> // Bibliothek fuer Bit-Variable #include <avr/interrupt.h> // Definition von Interrupts #include <util/delay.h> // Definition von Delays (Wartezeiten) #include "lcd_lib_de.h" // Header-Datei fuer LCD-Anzeige // Makros #define SET_BIT(PORT, BIT) ((PORT) |= (1 << (BIT))) // Port-Bit Setzen #define CLR_BIT(PORT, BIT) ((PORT) &= ~(1 << (BIT))) // Port-Bit Loeschen #define TGL_BIT(PORT, BIT) ((PORT) ^= (1 << (BIT))) // Port-Bit Toggeln // Konstanten #define ON_TIME 50 // "Ein-Zeit" in Inkrementen zu 100 ms #define OFF_TIME 10 // "Aus-Zeit" in Inkrementen zu 100 ms #define ENABLE 7 // Variable bool sw1a = 1; // Bitspeicher fuer Taste 1 alt bool sw2a = 1; // Bitspeicher fuer Taste 2 alt bool sw3a = 1; // Bitspeicher fuer Taste 3 alt bool sw4a = 1; // Bitspeicher fuer Taste 4 alt bool sw1n = 1; // Bitspeicher fuer Taste 1 neu bool sw2n = 1; // Bitspeicher fuer Taste 2 neu bool sw3n = 1; // Bitspeicher fuer Taste 3 neu bool sw4n = 1; // Bitspeicher fuer Taste 4 neu bool Taste_x = 0; bool Taste_4 = 0; unsigned int Lux_Ausgabe(void); unsigned int Interruptzeit = 900; int i; int x; void initDisplay_Timer1(void); // Initialisierung Display und Timer1 void sound(void); // Unterprogramm für Piepton und Countdown Ausgabe void initTimer0(void); // Timerfunktion für Soundausgabe void countDown(void); // 30sec-CountDown mit Displayausgabe void Tastenabfrage(void); //====================================================================== == // Hauptprogramm========================================================== int main(void) { initDisplay_Timer1(); sei(); while(1) { if(Taste_x==1) { Taste_x=0; SET_BIT(DDRB, DDB2); TGL_BIT(PORTB, PB2); } } //countDown(); } //====================================================================== === // Interruptroutine======================================================== // Interrupt Timer 2 18432000/256=72000hz / pre8 = 9000hz => 0,11111ms/OVF ISR (TIMER2_OVF_vect) { --Interruptzeit; // Interruptzeit 900*0,111ms=0,1s bis Tastenabfrage if(Interruptzeit==0) { Interruptzeit=900; Tastenabfrage(); } } //==================================================================== // Tastenabfrage=========================================================== void Tastenabfrage() { CLR_BIT(PORTD, ENABLE); // Enable-Signal auf 0 DDRC = DDRC & 0xF0; // Port C auf Eingabe schalten PORTC = 0x0F; // Pullup-Rs eingeschaltet _delay_us(10); // Wartezeit Umstellung Hardware-Signal sw1n = (PINC & (1 << PC0)); sw2n = (PINC & (1 << PC1)); sw3n = (PINC & (1 << PC2)); sw4n = (PINC & (1 << PC3)); if ((sw1n==0)&(sw1a==1)) // wenn Taste 1 soeben gedrueckt wurde: Taste_x = 1; // Flankenbit Taste 1 setzen if ((sw2n==0)&(sw2a==1)) // wenn Taste 2 eben gedrueckt wurde: Taste_x = 1; // Flankenbit Taste 2 setzen if ((sw3n==0)&(sw3a==1)) // wenn Taste 3 eben gedrueckt wurde: Taste_x = 1; // Flankenbit Taste 3 setzen if ((sw4n==0)&(sw4a==1)) // wenn Taste 4 eben gedrueckt wurde: Taste_4 = 1; // Flankenbit Taste 4 setzen sw1a = sw1n; // aktuelle Tastenwerte speichern sw2a = sw2n; // in Variable f?r alte Werte sw3a = sw3n; sw4a = sw4n; DDRC = DDRC | 0x0F; // Port C auf Ausgabe schalten } //===================================================================== // Initialisierung Display und Timer1=============================== void initDisplay_Timer1() // Start der Displayinitialisierung { lcd_init(); // Initialisierungsroutine aus der lcd_lib lcd_clearDisplay(); TCCR2A = 0; // Timer 1 auf "Normal Mode" schalten TCCR2B |= (1<<CS21); // mit Prescaler /8 betreiben TIMSK2 |= (1<<TOIE2); // Overflow-Interrupt aktivieren } Vielen Dank schonmal für eure Ratschläge!