Beispiel #1
0
/**
 * @brief Compute UxBRG and set BRGH if needed.
 *
 * @param[in] uart_num
 * @param[in] baudrate
 * @return -1 if the baudrate error is greater than 3%, 0 otherwise
 */
static int compute_divisor(unsigned int uart_num, uint32_t baudrate)
{
    uint32_t divisor0, divisor1;
    uint32_t baudrate0, baudrate1;
    uint32_t error0, error1;
    int use_brgh = 0;
    const uint32_t pclk = mcu_get_system_clock() >> 1;

    /* Compute divisor with BRGH=0 */
    divisor0 = (pclk / (16 * baudrate)) - 1;
    if (divisor0 > UINT16_MAX)
        divisor0 = UINT16_MAX;

    /* Compute divisor with BRGH=1 */
    divisor1 = (pclk / (4 * baudrate)) - 1;
    if (divisor1 > UINT16_MAX)
        divisor1 = UINT16_MAX;

    /* Compute error */
    baudrate0 = pclk / (16 * (divisor0 + 1));
    baudrate1 = pclk / (4 * (divisor1 + 1));
    if (baudrate > baudrate0)
        error0 = baudrate - baudrate0;
    else
        error0 = baudrate0 - baudrate;

    if (baudrate > baudrate1)
        error1 = baudrate - baudrate1;
    else
        error1 = baudrate1 - baudrate;

    use_brgh = error1 < error0;

    /* Check if error is less than 3%. This uses the fact that 1/32 ~ 3% */
    if (use_brgh) {
        if ((error1 << 5) >= baudrate)
            return -1;
    } else if ((error0 << 5) >= baudrate) {
        return -1;
    }

    /* Configure UART module */
    if (use_brgh) {
        UxMODE(uart_num) |= _U1MODE_BRGH_MASK;
        UxBRG(uart_num) = divisor1;
    } else {
        UxBRG(uart_num) = divisor0;
    }

    return 0;
}
Beispiel #2
0
Datei: uart.c Projekt: adjih/RIOT
int uart_init(uart_t uart, uint32_t baudrate, uart_rx_cb_t rx_cb, void *arg)
{
    assert(uart <= UART_NUMOF && uart != 0); /*No uart 0 on pic32*/

    /* Pin Mux should be setup in board file */

    pic_uart[uart].regs =
        (volatile uint32_t *)(_UART1_BASE_ADDRESS + (uart - 1) * REGS_SPACING);
    pic_uart[uart].clock = PERIPHERAL_CLOCK;

    UxBRG(pic_uart[uart])= (pic_uart[uart].clock / (16 * baudrate)) - 1;
    UxSTA(pic_uart[uart])= 0;
    UxMODE(pic_uart[uart])= _U1MODE_ON_MASK;
    UxSTASET(pic_uart[uart])= _U1STA_URXEN_MASK;
    UxSTASET(pic_uart[uart])= _U1STA_UTXEN_MASK;

    return 0;
}