Forum: Mikrocontroller und Digitale Elektronik Atmega162 (MLF) timer interrupt will nicht, AVRstudio debugger mit mega16 funktioniert (AVR-GCC)


von Michael M. (mikmik)


Lesenswert?

Hallo,
habe hier einen simplen code. Timer1 wird mit prescaler 1024 aktiviert 
und soll den Interrupt aufrufen. Wenn ich im AVR Studio 5 den code 
compiliere und auf meinen Atmega162 (MLF Version) spiele, wird die ISR 
nie aufgerufen. Wenn ich den Debugger aktiviere (mit Atmega16 -weil 
einen Atmega162 gibts nicht als Debugger im AVER Studio 5 ?), 
funktioniert alles super.

Danke für jeden Tipp!
BTW: Weis jemand wie man einen atmega162 im AVR Studio 5 debugger 
aktiviert?
1
//Atmega162, int 8 MHz with clk div 8 => 1 MHz
2
#define F_CPU 1000000L
3
#include <avr/io.h>
4
#include <stdint.h>
5
#include <stdlib.h>
6
#include<util/delay.h>
7
#include <avr/interrupt.h>
8
9
10
ISR(TIMER1_COMPA_vect) {
11
    //1 sec. timer
12
    cli();
13
    PORTC =  1;
14
    sei();
15
}
16
17
int main(void) {
18
    sei();
19
    TIMSK = (1<<OCIE1A); //enable interrupts 
20
    OCR1A=976; //1 sec.
21
    TCCR1B = (1<<CS12)|(1<<CS10)|(1<<WGM12); //CTC with prescaler 1024
22
23
    while(1) {}
24
}

von spess53 (Gast)


Lesenswert?

Hi

>Wenn ich im AVR Studio 5 den code
>compiliere und auf meinen Atmega162 (MLF Version) spiele, wird die ISR
>nie aufgerufen.

Du hast den Port nicht als Ausgang initialisiert.

>    cli();
>    sei();

ClI und SEI haben in einer Interruptroutine nichts zu suchen.

MfG Spess

von Michael M. (mikmik)


Lesenswert?

Hallo,
SORRY, habe in der main eine menge kommentare stehen, die ich nicht 
mitkopiert habe. Habe dadurch auch die 2 obersten zeilen vergessen:
1
DDRC=0b11111111; //sry für diese schreibweise
2
PORTC =  2; //zum test

>ClI und SEI haben in einer Interruptroutine nichts zu suchen.
Ist es nicht normal das so zu machen? Am Anfang der ISR die Interrupts 
zu blocken, um zu verhindern, dass der "wichtigere" Interrupt 
unterbrochen wird?

danke
MM

von Cyblord -. (cyblord)


Lesenswert?

Michael M. schrieb:
>>ClI und SEI haben in einer Interruptroutine nichts zu suchen.
> Ist es nicht normal das so zu machen? Am Anfang der ISR die Interrupts
> zu blocken, um zu verhindern, dass der "wichtigere" Interrupt
> unterbrochen wird?

Bein Einsprung in eine ISR wird das I-Bit automatisch gelöscht. Ein 
erfahrener Programmierer kann dann aber mit sei() das I-Bit wieder 
setzen um höher priorisierten Interrupts zu erlauben, die aktuelle ISR 
zu unterbrechen, oder gar verschachtelte Interupts zu ermöglichen. Aber 
das ist, wie gesagt, nur was für Fortgeschrittene.

gruß cyblord

von spess53 (Gast)


Lesenswert?

Hi

>SORRY, habe in der main eine menge kommentare stehen, die ich nicht
>mitkopiert habe. Habe dadurch auch die 2 obersten zeilen vergessen:

Wenn kein Hardwarefehler vorliegt sollte es eigentlich funktionieren. 
Beim PortC solltest du aber beachten, das im Auslieferzustand des 
ATMega162 PC4..PC7 vom JTAG-Interface belegt sind.

>DDRC=0b11111111; //sry für diese schreibweise

veständlicher als

>PORTC =  2; //zum test


>Am Anfang der ISR die Interrupts
>zu blocken, um zu verhindern, dass der "wichtigere" Interrupt
>unterbrochen wird?

Das cli/sei macht der AVR bei einem Interrupt automatisch.

MfG Spess

von Stefan E. (sternst)


Lesenswert?

Michael M. schrieb:
> Wenn ich im AVR Studio 5 ...

Sowohl das Studio5 selber, als auch die damit ausgelieferte Toolchain, 
haben reichlich Bugs. Erste Maßnahme wäre also mal ein Update auf was 
Aktuelles.

von Michael M. (mikmik)


Lesenswert?

Es ist zum Mäusemelken....
Habe jetzt die letzte Version vom Atmega Studio 6.1 installiert, und den 
Code auf das Essenziellste gekürzt, und benutze zur Sicherheit (wegen 
JTAG) nur noch PORTA und PORTB.
Wieder das selbe: wähle ich als Device Atmega16 im Debugger, 
funktioniert alles (ISR wird nach ca. 500 ms angesprungen), wähle ich 
Atmega162 und lade das auf den Atmega162 (MLF Gehäuse) läuft das 
Programm zwar (Led leuchtet) aber die ISR wird nie angesprungen. Weiß 
jemand woran das liegen könnte?

Werde wohl ein Board mit einem Atmega16 rauskramen müssen, und dort mal 
hochladen. Wenns dann geht, muss ic nur noch rausfinden obs am uC oder 
am Programmer  liegt.
1
#define F_CPU 1000000L
2
#include <avr/io.h>
3
#include <stdint.h>
4
#include <stdlib.h>
5
#include <avr/interrupt.h>
6
7
ISR(TIMER1_COMPA_vect) {
8
  //1 sec. timer
9
  PORTA=0b00000001;
10
  PORTB = 0b00000011;  
11
}
12
13
14
int main(void) {
15
  DDRB=0xFF;
16
  DDRA=0b00000001;
17
  
18
  PORTA=0;
19
  PORTB = 0b00000001;
20
  
21
  sei();
22
  //time countdown (every sec.)
23
  TIMSK = (1<<OCIE1A);
24
  OCR1A=500;           //976 for 1 sec.,CLK DIV 8 enabled => timer frequ=1.000493 Hz ~ 1 sec.
25
  TCCR1B = (1<<CS12)|(1<<CS10)|(1<<WGM12);  // CTC Mode, Start Timer1 with prescaler 1024
26
  
27
  while(1) {
28
  }
29
}

von Stefan E. (sternst)


Lesenswert?

Michael M. schrieb:
> Wieder das selbe: wähle ich als Device Atmega16 im Debugger,
> funktioniert alles (ISR wird nach ca. 500 ms angesprungen), wähle ich
> Atmega162 und lade das auf den Atmega162 (MLF Gehäuse) läuft das
> Programm zwar (Led leuchtet) aber die ISR wird nie angesprungen.

Du änderst aber schon auch die Device-Einstellung des Projektes, oder? 
Du kompilierst nicht für den Mega16, und lädst dann das Ergebnis auf 
einen Mega162?

von Michael M. (mikmik)


Lesenswert?

Stefan Ernst schrieb:
> Du änderst aber schon auch die Device-Einstellung des Projektes, oder?
> Du kompilierst nicht für den Mega16, und lädst dann das Ergebnis auf
> einen Mega162?

Ja natürlich. Das meinte ich mit "..wähle ich Atmega162 und lade das auf 
den Atmega162..."

von Michael M. (mikmik)


Lesenswert?

Noch ein Versuch mit noch simpleren code und timer0 mit overflow. Leds 
leuchten, aber die ISR wird nicht angesprungen...
Werde das am Abend mit einem Atmega16 und einem anderen Programmer 
probieren.
1
//Atmega162, int 8 MHz 
2
#define F_CPU 8000000L
3
#include <avr/io.h>
4
#include <avr/interrupt.h>
5
6
ISR(TIMER0_OVF_vect) {
7
  
8
  PORTA=0b00000001;
9
  PORTB = 0b00000011;
10
}
11
12
int main(void) {
13
  DDRB=0xFF;
14
  DDRA=0b00000001;
15
  
16
  PORTA=0;
17
  PORTB = 0b00000001;
18
  PORTB = 0b00010001;
19
20
  //time countdown (every sec.)
21
  TIMSK = (1<<TOIE0);
22
  sei();
23
  TCCR0 = (1<<CS00);  // Overflow mode, no prescaler
24
  while(1) {
25
    
26
  }
27
  
28
}

von Michael M. (mikmik)


Lesenswert?

Also falls es wen interessiert, so ist das ausgegangen:
Hab mal AtmelStudio 6.1 latest build installiert (danke uC.net für den 
direkt download link), und nochmal probiert. Wieder das selbe. Dann hab 
ich in meiner Verzweiflung den Atmega162 wieder rausgelötet (mit der 
Heißluftpistole) und einen Atmega16 reingelötet. Und siehe da, alles 
funktioniert! Die paar Pininkompatibilitäten konnte ich mit Leiterbahn 
durchtrennen hinbiegen.

Frage mich echt was das war, allerdings war es nicht der erste Atmega 
den ich bei einem großen elCtronic Versand gekauft hab, der ein Problem 
hatte.

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
Noch kein Account? Hier anmelden.