kannst ja mal folgendes ausprobieren, da hast du 0 code in der main routine aber die auslastung ist schon heftig (hab ich aufm ATMEGA8 @8MHz intern geschrieben)
die duty berechne ich in der ISR weil ich mir den ADC wert zum eistellen geholt habe, kannste aber theoretisch zwischen 0 und 100 variieren.Code:#include <avr/io.h> #include <avr/interrupt.h> #include <avr/timer.h> #include <avr/signal.h> #include <avr/sleep.h> #define ON 1 #define OFF 0 #define ULONG_MAX 199 volatile unsigned char OFVal; unsigned char LED1Duty; unsigned char LED1Stat; SIGNAL(SIG_OUTPUT_COMPARE2) { if (OFVal++ == 200) OFVal = 0; LED1Duty = (ADC*10)/(1024/10)-1; if (LED1Stat == OFF && (ULONG_MAX-LED1Duty) == OFVal) { PORTB |= BV(PB1); LED1Stat = ON; } if (LED1Stat == ON && ULONG_MAX-(ULONG_MAX-LED1Duty) == OFVal) { PORTB &= ~BV(PB1); LED1Stat = OFF; } } int main(void) { cli(); OFVal = 0; DDRB = BV(PB1)|BV(PB2)|BV(PB3)|BV(PB4); TIMSK = BV(OCIE2)|BV(TOIE2); //TOIE2 musste ich mit einschalten hat sonst nciht fuinktioniert (komisch ....) TCNT2 = 0; OCR2 = 100; //damit kannste die auflösung einstellen 100% sind wegen der ADC formel notwendig TCCR2 = BV(WGM21)|BV(CS20); //CTC modus, prescaler 1 LED1Duty = 1; LED1Stat = OFF; ADCSRA = BV(ADFR) | BV(ADPS2) | BV(ADPS1); // ADC einstellungen ADMUX = BV(REFS0); ADCSRA |= BV(ADEN); ADCSRA |= BV(ADSC); sei(); while(1) ; }
Wenn du OCR2 auf 256 stellst sollte mehr rechenzeit frei werden, aber die frequenz sinkt dann, musste einfach mal rumprobieren
PS: Bitte um kommentare zur optimierung des code







Zitieren

Lesezeichen