Interrupt-Problem

Gast #2410614
Lesenswert?

Liebe yC-Gemeinde,

Ich habe den ATUSB646 von Atmel und versuche daruf meine ersten kleinen 
Programme zum Laufen zu kriegen.
Folgendes Programm habe ich geschrieben. Es soll einfach nur einen 
Interrupt beim Timer1 overflow auslösen und einen PIN/LED Toggeln.
Letzten Freitag lief das Programm noch, wenn ich mich recht erinnere. 
Nun 3 Tage später lade ich es erneut auf den yC und es geht nichts. nun 
folgt der Code:

#include <avr/io.h>
#include <avr/interrupt.h>



volatile uint8_t flag = 0;

int main(void) {

  // PORTB als Ausgang

  DDRB = 0xFF;

  // Schreiberlaubnisprozedur für system clock prescaler
  // Anschließend divide by 32

  CLKPR = (1<<CLKPCE) & ~(1<<6) & ~(1<<5) & ~(1<<4) & ~(1<<3) & ~(1<<2) 
& ~(1<<1) & ~(1<<0); // set prescaler to 16
  CLKPR = ~(1<<CLKPCE) & ((1<<CLKPS2) | (1<<CLKPS0));

  // aktiviere Timer1, kein clki/o prescaling

  TCCR1B |= (1<<CS10);

  // Einschalten von overflow interrupt in timer1

  TIMSK1 |= (1<<TOIE1);

  // Einschalten des Global interrupt flag

  sei();


  while(1) {

    if(flag==1) {

    PORTB ^= (1<<0);

    flag = 0 ;

    }
  }

}



ISR(TIMER1_OVF_vect) {

  flag = 1;

  }


das wars.
Klammere ich sei(); mit // aus und setze das Flag manuell, leuchtet die 
entsprechende LED. Es muss also irgendwas mit dem Interrupt sein. Mit 
gesetztem Global interrupt flag, bleibt der code bei sei(); anscheinend 
hängen und nichts passiert. Es leuchtet mir nicht ein warum.

Wäre toll wenn ihr mir einen Tipp geben könntet, was das problem ist.

MFG
#2410944
Lesenswert?

Hier mal auch noch der formatierte Code für Klaus Wachtler :-)
1
#include <avr/io.h>
2
#include <avr/interrupt.h>
3

4

5

6
volatile uint8_t flag = 0;
7

8
int main(void) {
9

10
  // PORTB als Ausgang
11

12
  DDRB = 0xFF;
13

14
  // Schreiberlaubnisprozedur für system clock prescaler
15
  // Anschließend divide by 32
16

17
  CLKPR = (1<<CLKPCE) & ~(1<<6) & ~(1<<5) & ~(1<<4) & ~(1<<3) & ~(1<<2)
18
& ~(1<<1) & ~(1<<0); // set prescaler to 16
19
  CLKPR = ~(1<<CLKPCE) & ((1<<CLKPS2) | (1<<CLKPS0));
20

21
  // aktiviere Timer1, kein clki/o prescaling
22

23
  TCCR1B |= (1<<CS10);
24

25
  // Einschalten von overflow interrupt in timer1
26

27
  TIMSK1 |= (1<<TOIE1);
28

29
  // Einschalten des Global interrupt flag
30

31
  sei();
32

33

34
  while(1) {
35

36
    if(flag==1) {
37

38
    PORTB ^= (1<<0);
39

40
    flag = 0 ;
41

42
    }
43
  }
44

45
}
46

47
ISR(TIMER1_OVF_vect) {
48

49
  flag = 1;
50

51
  }
Gast #2413126
Lesenswert?

Danke für eure Hilfe, der Code scheint also keinen groben Fehler zu 
enthalten.

@andy andy

Das CLKPR Register gibts bei meinem AT90USB646. Das runtertakten 
funktioniert auch. Lasse ich die Systemclock bei default und prescale 
stattdessen timer1 funktioniert der interrupt trotzdem nicht bzw 
kommentiere ich sei() aus und lasse mittels Hochzählregister toggeln, 
funktioniert alles.
v.a. sehr merkwürdig, dass es schon funktioniert hat.

Vielleicht gibts Pobleme beim flashen? Ich lade die .hex via FLIP auf 
den µC.

Antwort schreiben

Bitte melde dich an, um einen Beitrag zu schreiben.

oder

Mit Google-Account einloggen

Die Registrierung ist kostenlos und dauert nur eine Minute.

Jetzt registrieren