; *************************************************************************** ; copyright : (C) 2025 by Martin Preuss ; email : martin@libchipcard.de ; ; *************************************************************************** ; * This file is part of the project "AqHome". * ; * Please see toplevel file COPYING of that project for license details. * ; *************************************************************************** .equ COMONUART0_IFACENUM = 1 .dseg comOnUart0_iface: .byte UART_HW_IFACE_SIZE .cseg ; --------------------------------------------------------------------------- ; @routine ComOnUart0_Init @global ; ; @clobbers Y (R16, R17, X) ComOnUart0_Init: ldi yl, LOW(comOnUart0_iface) ldi yh, HIGH(comOnUart0_iface) rcall UART_HW_Interface_Init ; (R16, R17, X) rcall UART_HW_Uart0_Init ; (R16, R17, X) ldi r16, COMONUART0_IFACENUM std Y+NET_IFACE_OFFS_IFACENUM, r16 ret ; @end ; --------------------------------------------------------------------------- ; @routine ComOnUart0_Periodically @global ; ; @clobbers R16, Y ComOnUart0_Periodically: ldi yl, LOW(comOnUart0_iface) ldi yh, HIGH(comOnUart0_iface) ldd r16, Y+NET_IFACE_OFFS_READTIMER inc r16 breq ComOnUart0_Periodically_l1 std Y+NET_IFACE_OFFS_READTIMER, r16 ComOnUart0_Periodically_l1: ldd r16, Y+NET_IFACE_OFFS_WRITETIMER inc r16 breq ComOnUart0_Periodically_l2 std Y+NET_IFACE_OFFS_WRITETIMER, r16 ComOnUart0_Periodically_l2: ret ; @end ; --------------------------------------------------------------------------- ; @routine ComOnUart0_RxCharIsr @global @isr ; ; @clobbers none ComOnUart0_RxCharIsr: push r15 in r15, SREG push r16 push r17 push r18 push r24 push r25 push xl push xh push yl push yh ldi yl, LOW(comOnUart0_iface) ldi yh, HIGH(comOnUart0_iface) rcall UART_HW_Uart0_RxCharIsr ; (R16, R17, R18, R24, R25, X) pop yh pop yl pop xh pop xl pop r25 pop r24 pop r18 pop r17 pop r16 out SREG, r15 pop r15 reti ; @end ; --------------------------------------------------------------------------- ; @routine ComOnUart0_TxUdreIsr @global @isr ; ; @clobbers none ComOnUart0_TxUdreIsr: push r15 in r15, SREG push r16 push r17 push xl push xh push yl push yh ldi yl, LOW(comOnUart0_iface) ldi yh, HIGH(comOnUart0_iface) rcall UART_HW_Uart0_TxUdreIsr ; (R16, R17, X) pop yh pop yl pop xh pop xl pop r17 pop r16 out SREG, r15 pop r15 reti ; @end ; --------------------------------------------------------------------------- ; @routine ComOnUart0_TxCharIsr @global @isr ; ; @clobbers none ComOnUart0_TxCharIsr: push r15 in r15, SREG push r16 push r17 push r18 push xl push xh push yl push yh ldi yl, LOW(comOnUart0_iface) ldi yh, HIGH(comOnUart0_iface) rcall UART_HW_Uart0_TxCharIsr ; (R16, R17, R18, X) pop yh pop yl pop xh pop xl pop r18 pop r17 pop r16 out SREG, r15 pop r15 reti ; @end ; --------------------------------------------------------------------------- ; @routine ComOnUart0_Run @global ; ; @clobbers all ComOnUart0_Run: push r15 in r15, SREG cli ldi yl, LOW(comOnUart0_iface) ldi yh, HIGH(comOnUart0_iface) rcall comOnUart0RunWriteModes rcall comOnUart0RunReadModes pop r15 out SREG, r15 ret ; @end ; --------------------------------------------------------------------------- ; @routine comOnUart0RunWriteModes ; ; @clobbers all, !Y comOnUart0RunWriteModes: ldd r16, Y+UART_HW_IFACE_OFFS_WRITEMODE ; handle write functions cpi r16, UART_HW_WRITEMODE_IDLE breq comOnUart0RunWriteIdle cpi r16, UART_HW_WRITEMODE_WRITING breq comOnUart0RunWriting cpi r16, UART_HW_WRITEMODE_WAITBUFFEREMPTY breq comOnUart0RunWaitBufferEmpty cpi r16, UART_HW_WRITEMODE_WRITEBUFFEREMPTY breq comOnUart0RunWriteBufferEmpty ret ; @end ; --------------------------------------------------------------------------- ; @routine comOnUart0RunIdle ; ; @clobbers comOnUart0RunWriteIdle: ldd r16, Y+NET_IFACE_OFFS_WRITETIMER cpi r16, TTYONUART1_MSG_INTERVAL ; wait a bit between messages brcs comOnUart0RunWriteIdle_end rcall NET_Interface_GetNextOutgoingMsgNum ; (R17, R18, X) brcc comOnUart0RunWriteIdle_end rcall NET_Buffer_Locate ; (R17) brcc comOnUart0RunWriteIdle_end rcall ComOnUart0_SendBuffer ; (R16, R17) comOnUart0RunWriteIdle_end: ret ; --------------------------------------------------------------------------- ; @routine comOnUart0RunWriting ; ; @clobbers comOnUart0RunWriting: ; TODO: check for timeout etc. ret ; @end ; --------------------------------------------------------------------------- ; @routine comOnUart0RunWaitBufferEmpty ; ; @clobbers none comOnUart0RunWaitBufferEmpty: ; TODO: check for timeout etc. ret ; @end ; --------------------------------------------------------------------------- ; @routine comOnUart0RunWriteBufferEmpty ; ; @clobbers R16, R17, X comOnUart0RunWriteBufferEmpty: ldd r16, Y+UART_HW_IFACE_OFFS_WRITEBUFNUM ldi r17, 0xff cp r16, r17 breq comOnUart0RunWriteBufferEmpty_setIdle std Y+UART_HW_IFACE_OFFS_WRITEBUFNUM, r17 rcall NET_Buffer_ReleaseByNum ; (R16, X) comOnUart0RunWriteBufferEmpty_setIdle: rcall UART_HW_Uart0_StopTx ; disable transceiver and interrupts (R16) ldi r16, UART_HW_WRITEMODE_IDLE std Y+UART_HW_IFACE_OFFS_WRITEMODE, r16 ldi r16, NET_IFACE_OFFS_PACKETSOUT_LOW ; increment packets counter rcall NET_Interface_IncCounter16 ; (R24, R25) ret ; @end ; --------------------------------------------------------------------------- ; @routine comOnUart0RunReadModes ; ; @clobbers all, !Y comOnUart0RunReadModes: ldd r16, Y+UART_HW_IFACE_OFFS_READMODE ; handle read functions cpi r16, UART_HW_READMODE_IDLE breq comOnUart0RunReadIdle ; (R16, R17, R24, R25, X) cpi r16, UART_HW_READMODE_READING breq comOnUart0RunReading ; (none) cpi r16, UART_HW_READMODE_SKIPPING breq comOnUart0RunSkipping ; (R16) cpi r16, UART_HW_READMODE_MSGRECEIVED breq comOnUart0RunMsgReceived ; (R16, R17, R18, R24, R25) ret ; @end ; --------------------------------------------------------------------------- ; @routine comOnUart0RunReadIdle ; ; @clobbers R16 (R17, R24, R25, X) comOnUart0RunReadIdle: ldd r16, Y+UART_HW_IFACE_OFFS_READBUFNUM cpi r16, 0xff brne comOnUart0RunReadIdle_enterReading rcall NET_Buffer_Alloc ; (R16, R17, X) brcc comOnUart0RunReadIdle_noBuf rcall UART_HW_Interface_SetReadBuffer ; (R17) comOnUart0RunReadIdle_enterReading: ldi r16, UART_HW_READMODE_READING std Y+UART_HW_IFACE_OFFS_READMODE, r16 rcall UART_HW_Uart0_StartRx ; R16 ret comOnUart0RunReadIdle_noBuf: ldi r16, NET_IFACE_OFFS_ERR_NOBUF_LOW rcall NET_Interface_IncCounter16 ; (R24, R25) ret ; @end ; --------------------------------------------------------------------------- ; @routine comOnUart0RunReading ; ; @clobbers none comOnUart0RunReading: ret ; @end ; --------------------------------------------------------------------------- ; @routine comOnUart0RunSkipping ; ; @clobbers R16 comOnUart0RunSkipping: sbis COM_ATTN_INPUT, COM_ATTN_PIN ; ATTN low? rjmp comOnUart0RunSkipping_end ; yes, jmp ; ATTN ishigh, skipped message finished ldi r16, UART_HW_READMODE_IDLE std Y+UART_HW_IFACE_OFFS_READMODE, r16 comOnUart0RunSkipping_end: ret ; @end ; --------------------------------------------------------------------------- ; @routine comOnUart0RunMsgReceived ; ; @clobbers R16 (R17, R18, R24, R25) comOnUart0RunMsgReceived: ldd r16, Y+UART_HW_IFACE_OFFS_READBUFNUM cpi r16, 0xff breq comOnUart0RunMsgReceived_end rcall NET_AddIncomingMsgNum ; (R17, R18, X) brcs comOnUart0RunMsgReceived_enterIdle comOnUart0RunMsgReceived_overrun: ; reset/reuse current buffer rcall NET_Buffer_Locate rcall UART_HW_Interface_SetReadBuffer ; (R17) ldi r16, NET_IFACE_OFFS_ERR_NOBUF_LOW rcall NET_Interface_IncCounter16 ; (R24, R25) comOnUart0RunMsgReceived_enterIdle: ldi r16, 0xff std Y+UART_HW_IFACE_OFFS_READBUFNUM, r16 ldi r16, UART_HW_READMODE_IDLE std Y+UART_HW_IFACE_OFFS_READMODE, r16 comOnUart0RunMsgReceived_end: ret ; @end