1 ; Serial interface using the ATmega8/88 USART.
2 ; This is part of the Z80-CP/M emulator written by Sprite_tm.
4 ; Copyright (C) 2010 Leo C.
6 ; This file is part of avrcpm.
8 ; avrcpm is free software: you can redistribute it and/or modify it
9 ; under the terms of the GNU General Public License as published by
10 ; the Free Software Foundation, either version 3 of the License, or
11 ; (at your option) any later version.
13 ; avrcpm is distributed in the hope that it will be useful,
14 ; but WITHOUT ANY WARRANTY; without even the implied warranty of
15 ; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 ; GNU General Public License for more details.
18 ; You should have received a copy of the GNU General Public License
19 ; along with avrcpm. If not, see <http://www.gnu.org/licenses/>.
24 #define UBRR_VAL ((F_CPU+BAUD*8)/(BAUD*16)-1) /* clever rounding */
26 #define RXBUFMASK RXBUFSIZE-1
27 #define TXBUFMASK TXBUFSIZE-1
53 ldi temp, (1<<TXEN0) | (1<<RXEN0) | (1<<RXCIE0)
56 ldi temp, (1<<URSEL) | (1<<UCSZ01) | (1<<UCSZ00)
58 ldi temp, (1<<UCSZ01) | (1<<UCSZ00)
61 ldi temp, HIGH(UBRR_VAL)
63 ldi temp, LOW(UBRR_VAL)
67 ; Save received character in a circular buffer. Do nothing if buffer overflows.
69 ; USART receive interrupt
79 lds zh,rxcount ;if rxcount < RXBUFSIZE
80 cpi zh,RXBUFSIZE ; (room for at least 1 char?)
83 sts rxcount,zh ; rxcount++
90 sts rxidx_w,zh ; rxidx_w = ++rxidx_w % RXBUFSIZE
94 st z,temp ; rxfifo[rxidx_w] = char
104 ;Fetches a char from the buffer to temp. If none available, waits till one is.
107 lds temp,rxcount ; Number of characters in buffer
109 breq uartgetc ;Wait for char
127 ld temp,z ;don't forget to get the char
132 ; USART transmit interrupt
139 lds temp,txcount ;if txcount != 0
144 sts txcount,temp ; --txcount
148 ldi zh,high(txfifo) ;
154 andi temp,TXBUFMASK ;
164 ldi temp, (1<<TXEN0) | (1<<RXEN0) | (1<<RXCIE0)
173 ;Sends a char from temp to the uart.
179 lds temp,txcount ;do {
181 brsh putc_l ;} while (txcount >= TXBUFSIZE)
184 ldi zh,high(txfifo) ;
190 andi temp,TXBUFMASK ;
191 sts txidx_w,temp ; txidx_w = ++txidx_w % TXBUFSIZE
193 st z,temp ; txfifo[txidx_w] = char
198 ldi zl, (1<<UDRIE0) | (1<<TXEN0) | (1<<RXEN0) | (1<<RXCIE0)
205 ; vim:set ts=8 noet nowrap