Tut mir leid, noch immer Probleme, aber andere (ist eigentlich off topic). Das geringere ist: UART läuft nur ohne Interrupt - sobald ich "sei;" sage, gehts nicht mehr - habe ich aber vorerst zur Seite geschoben.
Aktuelles Problem: trotzt sicherer Funktion von Timer0 (LED´s signalisieren ihre Funktion korrekt ) läuft der extInt0 nicht (und auch nicht der extInt1).
Der code:läßt die LED auf PC1 genau mit 0,1 ms blinken, die LED auf PC2 im Sekundenrhythmus - 10 000 mal 0,1 ms - aber die in den ISR für extInt0 und ~1 angesprochenen LED´s tun nichts.Code:/* ================================================================================= ##### Hier ISR und ISR - Initialisierung(en) ================================================================================= */ /* === Initialisierung fuer EXT_INT0/1 auf Pin 16+17/mega16(32) ================== $002 jmp SIG_INTERRUPT0 ; IRQ0 Handler und $004 jmp SIG_INTERRUPT1 ; IRQ1 Handler */ void XTI_01_init( void ) { //Initialisiere beide Interrupts auf rising edge // d.h. MCUCR ISC00,01,10+11 auf 1 (doc,S68) MCUCR |= (1<<ISC11)|(1<<ISC10)|(1<<ISC01)|(1<<ISC00); GICR |= (1<<INT1)|(1<<INT0); // und erlaube diese I´s in GICR } /* ============================================================================== */ /* === Initialisierung fuer Timer mega16(32) ===================================== SIGNAL (SIG_OVERFLOW0) Beachte zu TIMSK: OCIE2 TOIE2 TICIE1 OCIE1A OCIE1B TOIE1 OCIE0 TOIE0 TIMSK Read/Write R/W R/W R/W R/W R/W R/W R/W R/W Initial Value 0 0 0 0 0 0 0 0 RNControl 0 0 1 1 1 1 0 0 hex 3c ###>>> dieser Wert wird GESETZT, d.h. Bit 0, 1, 6 und 7 gehen auf NULL. Hier wird: TIMSK |= (1<<OCIE0) mit ODER! eingeführt, d.h. 1 */ void TMR_0_init( void ) { //Initialisiere 8-Bit-Timer auf 10 kHz TCCR0 |= (1<<CS01 | 1<<CS00); // Prescaler 1/64 / Clock <- CPU TCCR0 |= (1<<WGM01 | 0<<WGM00); // Timer im CTC-Mode OCR0 = 25; // Preset 25 für 100µs bei 16Mhz TIMSK |= (1<<OCIE0); // Compare Match IRQ } /* ============================================================================== */ /* === Nicht unterbrechbare ISR für EXT_INT0 auf Pin 16/PD2/mega16(32) ======== */ /* Routine setzt einfach einen Zähler hoch. Der Zähler wird im main ausgelesen ##>> cli/sei setzen <<## und nach 2 (od. 5) hunderstel Sekunden auf den Speicher WEG_L/_R vorzeichenrichtig aufaddiert und dann zurückgesetzt. ##>> Beim Richtungswechsel (cli/sei) wird der Zähler ausgelesen und genullt, damit ist eine saubere Wegmessung möglich. Der zugehörige Motor auf RNControl auf PB0/PB1 = li,re und PD5 Geschwind. Der alternat. Motor auf RNControl auf PC7/PC6 = li,re und PB4 PWM/Geschw. $002 jmp EXT_INT0 ; IRQ0 Handler */ SIGNAL(SIG_INTERRUPT0) { Iencdr1 ++; //zähle Counter/encoder 1 hoch Iz_yseci1 = Izeit_1; //Weise musi den akt. Timerwert zu Iz_diff1 = Iz_yseci1-Iz_ysecv1; //Neue Zeit-Differenz1 ausrechnen Iz_ysecv1 = Iz_yseci1; //der aktuelle Zeitwert wird "Alter" { if (Iencdr1 == 5000); PORTC ^= (1<<PC3); //LED4 toggeln alle 5000 Interrupts } PORTC ^= (1<<PC4); //LED5 toggeln bei JEDEM Interrupt } /* ============================================================================== */ /* ============================================================================== */ /* === Nicht unterbrechbare ISR für EXT_INT1 auf Pin 17/PD3/mega16(32) ======== */ /* Routine setzt einfach einen Zähler hoch. Sonst wie ISR für EXT_INT0 für Motor auf PC7/PC6 = li,re und PB4 PWM/Geschw. $004 jmp EXT_INT1 ; IRQ1 Handler */ SIGNAL(SIG_INTERRUPT1) { Iencdr2 ++; //zähle Counter/encoder 2 hoch Iz_yseci2 = Izeit_1; //Weise Iz_yseci den akt. Timerwert zu Iz_diff2 = Iz_yseci2-Iz_ysecv2; //Neue Zeit-Differenz2 ausrechnen Iz_ysecv2 = Iz_yseci2; //der aktuelle Zeitwert wird "Alter" PORTC ^= (1<<PC5); //LED6 toggeln bei JEDEM Interrupt } /* ============================================================================== */ /* ============================================================================== */ /* === Nicht unterbrechbare ISR für timer ====================================== */ /* Diese Routine zählt hoch im Takt 10 kHz.setzen. Dieser Wert wird von den beiden anderen ISR ausgelesen und den Werten */ // SIGNAL(SIG_OVERFLOW0) // #define SIG_OUTPUT_COMPARE0 //Interuptvektor, siehe Tabelle SIGNAL(SIG_OUTPUT_COMPARE0) { { if (Izeit_1 <= 10000) Izeit_1 ++; //Zeitstand Interupt-Timer läuft von 1 .. 10 000 else Izeit_1 = 0; } { // von hier bis Ende (LED2 toggeln) nur Testphase if (Izeit_1 == 1) PORTC ^= (1<<PC2); //LED3 toggeln alle Sekunde } PORTC ^= (1<<PC1); //LED2 toggeln jeden Interrupt } /* ============================================================================== */
Ich habe PD2 und PD3 mit 10k gegen GND geschaltet und taste sie von Hand auf Vcc. Es geschieht nichts.
Frage:
Ist die Initialisierung in void XTI_01_init( void ) korrekt?
Sind die ISR SIGNAL(SIG_INTERRUPT0) und die SIGNAL(SIG_INTERRUPT1) korrekt?
Ich gehe davon aus, dass der mega16 seine Interrupt-Vektortabelle über die <avr/interrupt.h> einlädt. Das ist doch ok? Sonst würde ja schon die ISR für Timer0 nicht laufen. Und in der iom16.h steht ja auch:... und das ist genau meine Schreibweise.Code:/* Interrupt vectors */ /* Vector 0 is the reset vector. */ /* External Interrupt Request 0 */ #define INT0_vect _VECTOR(1) #define SIG_INTERRUPT0 _VECTOR(1) /* External Interrupt Request 1 */ #define INT1_vect _VECTOR(2) #define SIG_INTERRUPT1 _VECTOR(2)
Danke im Voraus.







Zitieren

Lesezeichen