logo elektroda
logo elektroda
X
logo elektroda
REKLAMA
REKLAMA
Adblock/uBlockOrigin/AdGuard mogą powodować znikanie niektórych postów z powodu nowej reguły.

[atmega32] resetuje się przy ustawieniu timera1 w tryb CTC

qczek 05 Wrz 2010 22:24 1260 4
REKLAMA
  • #1 8480121
    qczek
    Poziom 14  
    Witam,
    Jestem początkującym w temacie, napisałem sobie sterowanie 8 serwami, ale chciałbym to robić bardziej dokładnie przy użyciu trybu CTC timera1 i sprzętowego rejestru przesuwającego. W następujący sposób go inicjalizuje
    
    //  na początek włączamy tryb czasomierza i ustawiamy wyjscie na 0 w trybie normalnym
    	TCCR1A = 0x00;								// tryb czasomierza
    	TIFR   &= ~_BV(OCF1A); 						// kasujemy wyjscie OCF1A
    	DDRD |= _BV(PD5);							// bit 5 OC1A na wyjscie
    	PORTD &= ~_BV(PD5);							// 0 na bit 5 portu D
    
    //  przechodzimy w tryb CTC
    	TCNT0 = 0;									// od 0 bedzie sobie liczył 
    	OCR1A = 2000;								// za pierwszym razem niech się uruchomi przerwanie po 1ms.
    	TCCR1A = _BV(COM1A1); 						// tryp CTC
    	TCCR1A &= ~_BV(COM1A0); 					// przy porównaniu ma być wstaiona 0 na 0C1A
    	TCCR1B = _BV(CS11) | _BV(WGM12);    		// preskaler ck/8 czyli mamy zegar 2MHz i CTC mode
    	TIMSK |= _BV(OCIE1A); 	 					//wlaczenie przerowania T1 (compare)
    
    
    // globalne wlaczenie przerwan
    	sei();
    
    


    obsługa przerwania wygląda tak, niemniej ciało funkcji może być puste i tak się atmega resetuje....

    
    // obsługa przerwania T1
    SIGNAL (SIG_OUTPUT_COMPARE1)
    {
    
    	if (servo_bit_state == 0)
    	{
    		// właśnie bit zmienił się na 0, wstawiamy jako następną wartośc dla serwa 1 i 
    		// wyliczamy ile jescze zostało czasu do pełnej 
    		servo_bit_state = 1;
    		TCCR1A |= _BV(COM1A0);
    		OCR1A = 40000 - qservo_servo_levels[0];
    	}else
    	{
    	 	// właśnie bit zmienił się na 1, wstawiamy jako następną wartośc dla serwa 0 i 
    		// czas wynikający z polozenia serwa 	
    		servo_bit_state = 0;
    		TCCR1A &= ~_BV(COM1A0);
    		OCR1A = 2 * qservo_servo_levels[0];
    	}
    	
    }
    
    


    Nawet w symulatorze AVR studi po wykonaniu sei jest reset i main zaczyna isc od nowa. Problem nie wystepuje jak wyłącze generowanie przerwania T1, wtedy licznik zlicza, niemniej nie mam przerwania......

    z góry dziekuje za podpowiedz co zwaliłem...
    Krzysiek
  • REKLAMA
  • Pomocny post
    #2 8480214
    michalko12
    Specjalista - Mikrokontrolery
    Zamiast SIGNAL użyj ISR(TIMER1_COMPA_vect)
    i tak poza tym to chyba powinno być SIGNAL( SIG_OUTPUT_COMPARE1A )
  • REKLAMA
  • #3 8480273
    qczek
    Poziom 14  
    dzieki zadziałało od strzału :)
    Krzysiek
  • REKLAMA
  • #4 8480679
    arturt134
    Poziom 27  
    No i zerujesz TCNT0, a nie TCNT1....
  • #5 8480680
    qczek
    Poziom 14  
    tak to zerowanie też poprawione :)
REKLAMA