; ; Copyright (C) 2003 Chris Benndorf (chrisb@ganzfix.de) ; ; This program is free software; you can redistribute it and/or ; modify it under the terms of the GNU General Public License ; as published by the Free Software Foundation; either version 2 ; of the License, or (at your option) any later version. ; ; This program is distributed in the hope that it will be useful, ; but WITHOUT ANY WARRANTY; without even the implied warranty of ; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ; GNU General Public License for more details. ; ; You should have received a copy of the GNU General Public License ; along with this program; if not, write to the Free Software Foundation, ; Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. ; ; ;******************************************************************* ;******************************************************************* ; ;Description ; ; Serial FMS interface ; ; Author = Chris Benndorf ; Target = AT90S2313 with 11.0592MHz Clock ; or ; Target = ATtiny2313 with 8.000 MHz Clock ; Date = 2005-06-15 ; ; Code is written for use with AVR-GCC in assembler mode ; flag: -x assembler-with-cpp ; ; Set FMS to "Serial PIC Interface", 9600 Baud, 0xF0 Sync ; ; PB0..7 not used ; ; PD0 not used ; PD1 TXD (Pin 3) ; PD2 not used ; PD3 INT1 (Transmitters Student-Signal) (Pin 7) ; PD4..6 not used ; ;******************************************************************* ;******************************************************************* ; ;****************************************************************************** ; start of code ;****************************************************************************** #ifdef __AVR_ATtiny2313__ #undef __AVR_AT90S2313__ #endif #include .section .text .org 0 rjmp RESET .org 4 rjmp INT1_LEVEL ;****************************************************************************** ; code ;****************************************************************************** .org 0x20 RESET: ldi r16, RAMEND out _SFR_IO_ADDR(SPL), r16 ; setup stack pointer clr r17 clr r18 clr r26 clr r27 ldi r28,0x60 clr r29 ; Clear X, Y ldi r30,lo8(OUTPUT_DATA) ldi r31,hi8(OUTPUT_DATA) ; init Z ldi r16,0x03 ; CLK/64 = 172.8 Beats/ms @11.0592MHz or 125Beats/ms@8.000MHz out _SFR_IO_ADDR(TCCR1B),r16 #ifdef __AVR_AT90S2313__ ldi r16,0x47 ; set uart speed to 9.6 kbps @11.0592MHz (0x47 = 71) out _SFR_IO_ADDR(UBRR),r16 ldi r16,(_BV(TXEN)) ; enable TX out _SFR_IO_ADDR(UCR),r16 #endif #ifdef __AVR_ATtiny2313__ ldi r16,0 ; set uart speed to 9.6 kbps @8.0MHz out _SFR_IO_ADDR(UBRRH),r16 ldi r16,51 ; set uart speed to 9.6 kbps @8.0MHz out _SFR_IO_ADDR(UBRRL),r16 ldi r16,(_BV(TXEN)) ; enable TX out _SFR_IO_ADDR(UCSRB),r16 #endif ldi r16,0x0C ; Wait for rising edge of INT1 out _SFR_IO_ADDR(MCUCR),r16 ldi r16,0x80 ; enable INT1 out _SFR_IO_ADDR(GIMSK),r16 clr r16 ; out _SFR_IO_ADDR(DDRB),r16 ; set all PORTB bits as input ldi r16,0x10 ; PD4 Output out _SFR_IO_ADDR(DDRD),r16 ; set all PORTB bits as input ser r16 ; out _SFR_IO_ADDR(PORTB),r16 ; PullUp all PORTB bits sei ; global enable interrupts ; main loop LOOP1: rcall SENDDATA rjmp LOOP1 ;********************************************************************** ; communication functionality ;********************************************************************** ; ; send char in r16 ; send_char: sbi _SFR_IO_ADDR(PORTD),4 push r20 ; save r16 send_c2: #ifdef __AVR_AT90S2313__ in r20,_SFR_IO_ADDR(USR) ; wait for the transmitter to be ready #endif #ifdef __AVR_ATtiny2313__ in r20,_SFR_IO_ADDR(UCSRA) ; wait for the transmitter to be ready #endif sbrs r20,UDRE ; ready ? rjmp send_c2 ; no, wait some more pop r20 ; restore r16 out _SFR_IO_ADDR(UDR),r20 ; send char cbi _SFR_IO_ADDR(PORTD),4 ret ; and return ; ; send the current frequency to the PC ; as a 5 byte sequence : ; 'F' folowed by a 32 bit phase accumulator value ; ; SENDDATA: ldi r20,0xf9 ; 0xF0 = sync rcall send_char in r20,PINB ; BUTTON states andi r20,0x0F rcall send_char lds r20,0x0060 ; Channel 1 rcall send_char lds r20,0x0061 ; Channel 2 rcall send_char lds r20,0x0062 ; Channel 3 rcall send_char lds r20,0x0063 ; Channel 4 rcall send_char lds r20,0x0064 ; Channel 5 rcall send_char lds r20,0x0065 ; Channel 6 rcall send_char lds r20,0x0066 ; Channel 7 rcall send_char lds r20,0x0067 ; Channel 8 rcall send_char EXIT_SEND: ret ; ; Interrupt routine ; ; Signal looks like: ___________________||___||__||___||_||_||__||_____________________||___||... ; falling edge: clear timer, set INT to rising edge ; rising edge: set INT to falling edge, read timer, save val, ; ; MCUCR INT1 ; Falling Edge = 0x08 ; Rising Edge = 0x0C INT1_LEVEL: HANDLRISE: cpi r28,0x68 ; Wrote 8 Bytes/Channels? brmi TESTR25 ; if not get data and store... ldi r28,0x60 ; Memptr Y = 0x0060 clr r29 TESTR25: in r24,_SFR_IO_ADDR(TCNT1L) ; read timer in r25,_SFR_IO_ADDR(TCNT1H) ; into r24/r25 sbiw r24,50 ; substract 173 (172.8) = 1 ms sbiw r24,50 #ifdef __AVR_AT90S2313__ sbiw r24,48 ;or just 125 if its a Tiny2313 #endif sbiw r24,25 tst r25 ; looooooong pulse? ( >2,5ms ) breq STOREVAL ldi r28,0x60 ; Y = 0x0060 clr r29 rjmp HANDLFALL STOREVAL: ldi r30,lo8(OUTPUT_DATA) ldi r31,hi8(OUTPUT_DATA) add r30, r24 adc r31, r25 ; is 0 lpm ; get translation st Y+,r0 ; store data and inc HANDLFALL: clr r16 out _SFR_IO_ADDR(TCNT1H),r16 inc r16 out _SFR_IO_ADDR(TCNT1L),r16 EXIT_INT1: reti .org 0x200 OUTPUT_DATA: #ifdef __AVR_AT90S2313__ .byte 0x64,0x65,0x65,0x66,0x66,0x67,0x67,0x68,0x69,0x69,0x6A,0x6A,0x6B,0x6B,0x6C,0x6D .byte 0x6D,0x6E,0x6E,0x6F,0x6F,0x70,0x71,0x71,0x72,0x72,0x73,0x73,0x74,0x75,0x75,0x76 .byte 0x76,0x77,0x77,0x78,0x79,0x79,0x7A,0x7A,0x7B,0x7B,0x7C,0x7D,0x7D,0x7E,0x7E,0x7F .byte 0x7F,0x80,0x80,0x81,0x82,0x82,0x83,0x83,0x84,0x84,0x85,0x86,0x86,0x87,0x87,0x88 .byte 0x88,0x89,0x8A,0x8A,0x8B,0x8B,0x8C,0x8C,0x8D,0x8E,0x8E,0x8F,0x8F,0x90,0x90,0x91 .byte 0x92,0x92,0x93,0x93,0x94,0x94,0x95,0x96,0x96,0x97,0x97,0x98,0x98,0x99,0x99,0x9A .byte 0x9B,0x9B,0x9C,0x9C,0x9D,0x9D,0x9E,0x9F,0x9F,0xA0,0xA0,0xA1,0xA1,0xA2,0xA3,0xA3 .byte 0xA4,0xA4,0xA5,0xA5,0xA6,0xA7,0xA7,0xA8,0xA8,0xA9,0xA9,0xAA,0xAB,0xAB,0xAC,0xAC .byte 0xAD,0xAD,0xAE,0xAF,0xAF,0xB0,0xB0,0xB1,0xB1,0xB2,0xB2,0xB3,0xB4,0xB4,0xB5,0xB5 .byte 0xB6,0xB6,0xB7,0xB8,0xB8,0xB9,0xB9,0xBA,0xBA,0xBB,0xBC,0xBC,0xBD,0xBD,0xBE,0xBE .byte 0xBF,0xC0,0xC0,0xC1,0xC1,0xC2,0xC2,0xC3,0xC4,0xC4,0xC5,0xC5,0xC6,0xC6,0xC7,0xC8 .byte 0xC8,0xC8,0xC8,0xC8,0xC8,0xC8,0xC8,0xC8,0xC8,0xC8,0xC8,0xC8,0xC8,0xC8,0xC8,0xC8 #endif #ifdef __AVR_ATtiny2313__ .byte 0x64,0x65,0x66,0x66,0x67,0x68,0x69,0x69,0x6A,0x6B,0x6B,0x6C,0x6D,0x6E,0x6E,0x6F .byte 0x70,0x71,0x71,0x72,0x73,0x73,0x74,0x75,0x76,0x76,0x77,0x78,0x79,0x79,0x7A,0x7B .byte 0x7B,0x7C,0x7D,0x7E,0x7E,0x7F,0x80,0x80,0x81,0x82,0x83,0x83,0x84,0x85,0x86,0x86 .byte 0x87,0x88,0x88,0x89,0x8A,0x8B,0x8B,0x8C,0x8D,0x8E,0x8E,0x8F,0x90,0x90,0x91,0x92 .byte 0x93,0x93,0x94,0x95,0x96,0x96,0x97,0x98,0x98,0x99,0x9A,0x9B,0x9B,0x9C,0x9D,0x9D .byte 0x9E,0x9F,0xA0,0xA0,0xA1,0xA2,0xA3,0xA3,0xA4,0xA5,0xA5,0xA6,0xA7,0xA8,0xA8,0xA9 .byte 0xAA,0xAB,0xAB,0xAC,0xAD,0xAD,0xAE,0xAF,0xB0,0xB0,0xB1,0xB2,0xB2,0xB3,0xB4,0xB5 .byte 0xB5,0xB6,0xB7,0xB8,0xB8,0xB9,0xBA,0xBA,0xBB,0xBC,0xBD,0xBD,0xBE,0xBF,0xC0,0xC0 .byte 0xC1,0xC2,0xC2,0xC3,0xC4,0xC5,0xC5,0xC6,0xC7,0xC8,0xC8,0xC8,0xC8,0xC8,0xC8,0xC8 #endif ;****************************************************************************** ; end of file ;******************************************************************************