Hallo,
habe deine Einwände zum Teil beseitig und Kommentare im Code ergänzt.
Die Werte für TCNT0 errechnen sich folgendermaßen:
1/(16000000/256) = 1.6exp-5
Das erste Intervall soll bis zur Mitte des low-Pegels vom Togglebit dauern, also 1.778ms/2->55.5 Timersteps
Danach sollen die Intervalle jeweils 1.778ms dauern, so dass immer die das 2. Halbbit erfasst wird.
Selbst wenn meine Timings nicht ganz stimmen würden, dürfte rc5.code doch nicht immer 0 sein??
Ich meine doch, ich habe hier den OpenCollector berücksichtigt, und wenn nicht, wäre das Signal halt invertiert.
Code:#include <avr/io.h> #include <avr/interrupt.h> #include <math.h> struct rc5_parts { volatile char s_bit; volatile int8_t addresse; volatile int8_t code; volatile char rdy; } rc5; char mid; volatile uint8_t bitnummer = 0; void init_rc5() { MCUCR |= (1<<ISC11) | (1<<ISC10); GICR |= (1<<INT1); TCCR0 |= (1<<CS02); } //****************************************************USART****************************** void init_usart(void) { UBRRL |= 0b01100111; UCSRB = (1<<TXEN) | (1<<RXEN); UCSRC = (1<<URSEL) | (1<<UCSZ1) | (1<<UCSZ0); } void send_char(unsigned char s) { while (!(UCSRA & (1<<UDRE))); UDR = s; } void send_string(char *s) { while(*s != '\0') { send_char(*s); s++; } } //**********************************************************USART-ENDE******************** SIGNAL(SIG_OVERFLOW0) { bitnummer++; TCNT0 = 145; //Timer soll nach 1.778ms Overflow haben if(bitnummer == 12) { TIMSK &= ~(1<<TOIE0); //Wenn die 11 Bits davor erfasst wurden, TimerIRQ deaktivieren rc5.rdy = 1; rc5.s_bit = 0; bitnummer = 13; } if(bitnummer<6) //Wenn i<6, werden die ausgelesenen Bits zu Addresse hinzugefügr { if((PORTD & (1<<3)) != 0) { rc5.addresse |= (1<<(-1)*(bitnummer-6)); } else { rc5.addresse &= ~(1<<(-1)*(bitnummer-6)); } } if((bitnummer>=6 && bitnummer<=11)) //6 - 11 werden zu rc5.code hinzugefügt { if((PORTD & (1<<3)) != 0) { rc5.code |= (1<<(-1)*(bitnummer-7)); } else { rc5.code &= ~(1<<(-1)*(bitnummer-7)); } } } SIGNAL(SIG_INTERRUPT1) { if(rc5.s_bit<4) { rc5.s_bit++; } if(rc5.s_bit == 4) { TIMSK |= (1<<TOIE0); // Timer0 Interrupts enablen TCNT0 = 200; //Timer so vorladen, dass er zur Mitte des 2. Halbbits den ersten Timeroverflow hat GICR &= ~(1<<INT1); //Int1 disablen } } int main(void) { init_usart(); init_rc5(); char i = 1; sei(); char result[10]; char hello[15] = "Hallo Martin"; send_string(hello); for(;;) { if(rc5.rdy == 1) { itoa(rc5.code,result,10); char hello2[15] = "RC5-Code: "; send_string(hello2); send_string(result); rc5.rdy = 0; GICR |= (1<<INT1); // ext. Interrupt wieder aktivieren } } }







Zitieren

Lesezeichen