📄 mcfuart.c
字号:
{ umr2 |= MCF5206E_UMR2_SB5_1; } else { umr2 |= MCF5206E_UMR2_SB_1; } } /* Set parity mode */ if ((t->c_cflag & PARENB) != 0) { if ((t->c_cflag & PARODD) != 0) { umr1 |= MCF5206E_UMR1_PM_ODD; } else { umr1 |= MCF5206E_UMR1_PM_EVEN; } } else { umr1 |= MCF5206E_UMR1_PM_NO_PARITY; } rtems_interrupt_disable(level); *MCF5206E_UCR(MBAR,uart->chn) = MCF5206E_UCR_TC_DISABLE | MCF5206E_UCR_RC_DISABLE; mcfuart_set_baudrate(uart, baud); *MCF5206E_UCR(MBAR,uart->chn) = MCF5206E_UCR_MISC_RESET_MR; *MCF5206E_UMR(MBAR,uart->chn) = umr1; *MCF5206E_UMR(MBAR,uart->chn) = umr2; if ((t->c_cflag & CREAD) != 0) { *MCF5206E_UCR(MBAR,uart->chn) = MCF5206E_UCR_TC_ENABLE | MCF5206E_UCR_RC_ENABLE; } else { *MCF5206E_UCR(MBAR,uart->chn) = MCF5206E_UCR_TC_ENABLE; } rtems_interrupt_enable(level); return RTEMS_SUCCESSFUL;}/* * mcfuart_poll_read -- * This function tried to read character from MCF UART and perform * error handling. When parity or framing error occured, return * value dependent on termios input mode flags: * - received character, if IGNPAR == 1 * - 0, if IGNPAR == 0 and PARMRK == 0 * - 0xff and 0x00 on next poll_read invocation, if IGNPAR == 0 and * PARMRK == 1 * * PARAMETERS: * uart - pointer to UART descriptor structure * * RETURNS: * code of received character or -1 if no characters received. */intmcfuart_poll_read(mcfuart *uart){ rtems_unsigned8 usr; int ch; if (uart->parerr_mark_flag == 1) { uart->parerr_mark_flag = 0; return 0; } usr = *MCF5206E_USR(MBAR,uart->chn); if ((usr & MCF5206E_USR_RXRDY) != 0) { if (((usr & (MCF5206E_USR_FE | MCF5206E_USR_PE)) != 0) && !(uart->c_iflag & IGNPAR)) { ch = *MCF5206E_URB(MBAR,uart->chn); /* Clear error bits */ if (uart->c_iflag & PARMRK) { uart->parerr_mark_flag = 1; ch = 0xff; } else { ch = 0; } } else { ch = *MCF5206E_URB(MBAR,uart->chn); } } else ch = -1; return ch;}/* * mcfuart_poll_write -- * This function transmit buffer byte-by-byte in polling mode. * * PARAMETERS: * uart - pointer to the UART descriptor structure * buf - pointer to transmit buffer * len - transmit buffer length * * RETURNS: * 0 */intmcfuart_poll_write(mcfuart *uart, const char *buf, int len){ while (len--) { while ((*MCF5206E_USR(MBAR, uart->chn) & MCF5206E_USR_TXRDY) == 0); *MCF5206E_UTB(MBAR, uart->chn) = *buf++; } return 0;}/* mcfuart_interrupt_handler -- * UART interrupt handler routine * * PARAMETERS: * vec - interrupt vector number * * RETURNS: * none */static rtems_isrmcfuart_interrupt_handler(rtems_vector_number vec){ mcfuart *uart; register rtems_unsigned8 usr; register rtems_unsigned8 uisr; register int chn; register int bp = 0; /* Find UART descriptor from vector number */ if (int_driven_uart[0].vec == vec) uart = int_driven_uart[0].uart; else if (int_driven_uart[1].vec == vec) uart = int_driven_uart[1].uart; else return; chn = uart->chn; uisr = *MCF5206E_UISR(MBAR, chn); if (uisr & MCF5206E_UISR_DB) { *MCF5206E_UCR(MBAR, chn) = MCF5206E_UCR_MISC_RESET_BRK; } /* Receiving */ while (1) { char buf[32]; usr = *MCF5206E_USR(MBAR,chn); if ((bp < sizeof(buf) - 1) && ((usr & MCF5206E_USR_RXRDY) != 0)) { /* Receive character and handle frame/parity errors */ if (((usr & (MCF5206E_USR_FE | MCF5206E_USR_PE)) != 0) && !(uart->c_iflag & IGNPAR)) { if (uart->c_iflag & PARMRK) { buf[bp++] = 0xff; buf[bp++] = 0x00; } else { buf[bp++] = 0x00; } } else { buf[bp++] = *MCF5206E_URB(MBAR, chn); } /* Reset error condition if any errors has been detected */ if (usr & (MCF5206E_USR_RB | MCF5206E_USR_FE | MCF5206E_USR_PE | MCF5206E_USR_OE)) { *MCF5206E_UCR(MBAR, chn) = MCF5206E_UCR_MISC_RESET_ERR; } } else { if (bp != 0) rtems_termios_enqueue_raw_characters(uart->tty, buf, bp); break; } } /* Transmitting */ while (1) { if ((*MCF5206E_USR(MBAR, chn) & MCF5206E_USR_TXRDY) == 0) break; if (uart->tx_buf != NULL) { if (uart->tx_ptr >= uart->tx_buf_len) { register int dequeue = uart->tx_buf_len; *MCF5206E_UIMR(MBAR, uart->chn) = MCF5206E_UIMR_FFULL; uart->tx_buf = NULL; uart->tx_ptr = uart->tx_buf_len = 0; rtems_termios_dequeue_characters(uart->tty, dequeue); } else { *MCF5206E_UTB(MBAR, chn) = uart->tx_buf[uart->tx_ptr++]; } } else break; }}/* mcfuart_interrupt_write -- * This function initiate transmitting of the buffer in interrupt mode. * * PARAMETERS: * uart - pointer to the UART descriptor structure * buf - pointer to transmit buffer * len - transmit buffer length * * RETURNS: * 0 */intmcfuart_interrupt_write(mcfuart *uart, const char *buf, int len){ int level; rtems_interrupt_disable(level); uart->tx_buf = buf; uart->tx_buf_len = len; uart->tx_ptr = 0; *MCF5206E_UIMR(MBAR, uart->chn) = MCF5206E_UIMR_FFULL | MCF5206E_UIMR_TXRDY; while (((*MCF5206E_USR(MBAR,uart->chn) & MCF5206E_USR_TXRDY) != 0) && (uart->tx_ptr < uart->tx_buf_len)) { *MCF5206E_UTB(MBAR,uart->chn) = uart->tx_buf[uart->tx_ptr++]; } rtems_interrupt_enable(level); return 0;}/* mcfuart_stop_remote_tx -- * This function stop data flow from remote device. * * PARAMETERS: * uart - pointer to the UART descriptor structure * * RETURNS: * RTEMS_SUCCESSFUL */intmcfuart_stop_remote_tx(mcfuart *uart){ *MCF5206E_UOP0(MBAR, uart->chn) = 1; return RTEMS_SUCCESSFUL;}/* mcfuart_start_remote_tx -- * This function resume data flow from remote device. * * PARAMETERS: * uart - pointer to the UART descriptor structure * * RETURNS: * RTEMS_SUCCESSFUL */intmcfuart_start_remote_tx(mcfuart *uart){ *MCF5206E_UOP1(MBAR, uart->chn) = 1; return RTEMS_SUCCESSFUL;}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -