- Akku Tests und Balkonkraftwerk Speicher         
Ergebnis 1 bis 5 von 5

Thema: Timer/Interrupt Problem. LED soll jede Minute blinken

Hybrid-Darstellung

Vorheriger Beitrag Vorheriger Beitrag   Nächster Beitrag Nächster Beitrag
  1. #1

    Timer/Interrupt Problem. LED soll jede Minute blinken

    Hallo Zusammen,

    irgendwie komme ich mit einem simplem Programmteil für einen Tiny25 nicht weiter.
    Ich habe mal das Problem auf so wenig Code wie möglich reduziert.

    Die LED soll einfach nur jede Minute kurz aufblinken. Leider blinkt sie viel zu schnell und mein Zähler i wird trotz volatile ignoriert.

    Hier der Code:

    Code:
    #include <inttypes.h>
    #include <avr/io.h>
    #include <avr/interrupt.h>
    #include <util/delay.h>
    
    // Flags f�r IRQs
    volatile uint8_t EveryMinuteFlag;
    
    // Z�hler f�r IRQs
    volatile uint8_t i=0;
     
    int main(void) {
    
    	// Ausg�nge setzen
        DDRB |= ((1 << PB2) | (1 << PB3) | (1 << PB1));
    
    	//Action-Flags
    	EveryMinuteFlag = 1;
        
    	// Timer0 Prescaler 1024
    	TCCR0B |= ((1<<CS02) | (0<<CS01) | (1<<CS00));		 
    
        OCR0A = 0x00;
    //	OCR0B = 0x00;
    
    	// Interrupts f�r Timer0
    	TIMSK |= (1<<OCIE0A); //Interrupt bei Compare
    	TIMSK |= (1<<TOIE0); //Interrupt bei Overflow
    
    	// Interrupts aktivieren
    	sei();
    
    	while (1) {
    
    		if (EveryMinuteFlag) {
    
    			// LED bliken lassen
    			PORTB |= ( 1 << PB2 );            
            	_delay_ms(5);
    			PORTB &= ~( 1 << PB2 );            
    
    			EveryMinuteFlag = 0;
    		}
    
       	}
    }
    
    SIGNAL(SIG_OVERFLOW0) 
    {
    	i++;
    	if (i==250) {
    		EveryMinuteFlag=1;
    		i=0;
    	}
    }
    Egal welchen vergleichswert ich für i nehme die LED blinkt immer genauso schnell.

    Ich mach daran seit Tagen rum und es will einfach nicht. Hat jemand noch ne Idee?

    Vielen Dank
    daniel

  2. #2
    Erfahrener Benutzer Robotik Einstein
    Registriert seit
    22.05.2005
    Ort
    12°29´ O, 48°38´ N
    Beiträge
    2.731
    Hallo,

    als erstes würde ich die Zeile rauswerfen, die den Compare Interrupt (OCIE0A) aktiviert, denn dazu gibts ja hier keine ISR, und der AVR macht dann einen Reset falls der IRQ mal auftritt.

    Mit Wieviel MHz läuft der Tiny ?

  3. #3
    ich hab jetzt mal die Interrupts für den Timer0-Compare rausgeschmissen, verändert hat das leider nix. Der Tiyn25 läuft mit 8MHz.
    meine Vermutung ist das der compiler das wegoptimiert. Leider sind meine letzten Kontakte mit Assembler zu lange her.

    Hier mal der ASM Output:

    Code:
    test-timer.o:     file format elf32-avr
    
    Disassembly of section .text:
    
    00000000 <main>:
    
    // Zähler für IRQs
    volatile uint8_t i=0;
     
    int main(void) {
       0:	c0 e0       	ldi	r28, 0x00	; 0
       2:	d0 e0       	ldi	r29, 0x00	; 0
       4:	de bf       	out	0x3e, r29	; 62
       6:	cd bf       	out	0x3d, r28	; 61
    
    	// Ausgänge setzen
    	DDRB |= ((1 << PB2) | (1 << PB3) | (1 << PB1));
       8:	87 b3       	in	r24, 0x17	; 23
       a:	8e 60       	ori	r24, 0x0E	; 14
       c:	87 bb       	out	0x17, r24	; 23
    
    	//Action-Flags
    	EveryMinuteFlag = 1;
       e:	81 e0       	ldi	r24, 0x01	; 1
      10:	80 93 00 00 	sts	0x0000, r24
        
    	// Timer0 Prescaler 1024
    	TCCR0B |= ((1<<CS02) | (0<<CS01) | (1<<CS00));		 
      14:	83 b7       	in	r24, 0x33	; 51
      16:	85 60       	ori	r24, 0x05	; 5
      18:	83 bf       	out	0x33, r24	; 51
    
    
    	// Interrupts für Timer0 bei Overflow
    	TIMSK |= (1<<TOIE0);
    
    	// Interrupts aktivieren
    	sei();
      1a:	89 b7       	in	r24, 0x39	; 57
      1c:	82 60       	ori	r24, 0x02	; 2
      1e:	89 bf       	out	0x39, r24	; 57
    
    	while (1) {
    
      20:	78 94       	sei
      22:	a8 ee       	ldi	r26, 0xE8	; 232
      24:	b3 e0       	ldi	r27, 0x03	; 3
      26:	c0 e0       	ldi	r28, 0x00	; 0
      28:	d0 e0       	ldi	r29, 0x00	; 0
    		if (EveryMinuteFlag) {
    
    			// LED blinken lassen
    			PORTB |= ( 1 << PB2 );            
      2a:	80 91 00 00 	lds	r24, 0x0000
      2e:	88 23       	and	r24, r24
      30:	e1 f3       	breq	.-8      	; 0x2a <main+0x2a>
    	        	_delay_ms(5);
    			PORTB &= ~( 1 << PB2 );            
    
      32:	c2 9a       	sbi	0x18, 2	; 24
     */
    void
    _delay_loop_2(uint16_t __count)
    {
    	__asm__ volatile (
      34:	8a 2f       	mov	r24, r26
      36:	9b 2f       	mov	r25, r27
      38:	01 97       	sbiw	r24, 0x01	; 1
      3a:	f1 f7       	brne	.-4      	; 0x38 <main+0x38>
    			EveryMinuteFlag = 0;
    		}
      3c:	c2 98       	cbi	0x18, 2	; 24
    
       	}
      3e:	10 92 00 00 	sts	0x0000, r1
      42:	f3 cf       	rjmp	.-26     	; 0x2a <main+0x2a>
    
    00000044 <__vector_5>:
    }
    
    SIGNAL (SIG_OVERFLOW0) 
    {
    	i++;
    	if (i==250) {
    		EveryMinuteFlag=1;
      44:	1f 92       	push	r1
      46:	0f 92       	push	r0
      48:	0f b6       	in	r0, 0x3f	; 63
      4a:	0f 92       	push	r0
      4c:	11 24       	eor	r1, r1
      4e:	8f 93       	push	r24
    		i=0;
      50:	80 91 00 00 	lds	r24, 0x0000
      54:	8f 5f       	subi	r24, 0xFF	; 255
      56:	80 93 00 00 	sts	0x0000, r24
    	}
      5a:	80 91 00 00 	lds	r24, 0x0000
      5e:	81 30       	cpi	r24, 0x01	; 1
      60:	21 f4       	brne	.+8      	; 0x6a <__vector_5+0x26>
    } 
      62:	80 93 00 00 	sts	0x0000, r24
      66:	10 92 00 00 	sts	0x0000, r1
      6a:	8f 91       	pop	r24
      6c:	0f 90       	pop	r0
      6e:	0f be       	out	0x3f, r0	; 63
      70:	0f 90       	pop	r0
      72:	1f 90       	pop	r1
      74:	18 95       	reti

  4. #4
    habs hinbekommen. war tatsächlich so, daß es mit -Os wegoptimiert wurde.

    ein -O2 hats gebracht, allerdings nur unter linux mit gcc-Version 3.4.5 AVR-Ada-0.4.1 (CDK4AVR 3.0 3.4.5-2006070 der aktuelle WinAVR optimiert es trotz -O2 weg

    Vielen Dank

  5. #5
    Erfahrener Benutzer Robotik Einstein
    Registriert seit
    22.05.2005
    Ort
    12°29´ O, 48°38´ N
    Beiträge
    2.731
    Hab auch grad mit den Optimierungen rumprobiert, wenn man garnicht optimiert wird der Code so gross, da er nicht mehr in den Tiny passt !

Berechtigungen

  • Neue Themen erstellen: Nein
  • Themen beantworten: Nein
  • Anhänge hochladen: Nein
  • Beiträge bearbeiten: Nein
  •  

MultiPlus Wechselrichter Insel und Nulleinspeisung Conrad