You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@mynewt.apache.org by je...@apache.org on 2022/02/16 14:48:48 UTC

[mynewt-core] branch master updated: hw/mcu/dialog: Increase UART maximum baudrate

This is an automated email from the ASF dual-hosted git repository.

jerzy pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/mynewt-core.git


The following commit(s) were added to refs/heads/master by this push:
     new 83663e1  hw/mcu/dialog: Increase UART maximum baudrate
83663e1 is described below

commit 83663e1efa951535b1baf5c2e8adffa2f24a36b7
Author: Jerzy Kasenberg <je...@codecoup.pl>
AuthorDate: Mon Feb 14 13:26:41 2022 +0100

    hw/mcu/dialog: Increase UART maximum baudrate
    
    Now 2MHz can be used for all UARTs.
    For UART_1(UART2) UART2(UART3) two additional baudrates
    are added 3MHz and 6MHz.
    For those to work PLL96 must be selected as system clock source (syscfg MCU_SYSCLK_SOURCE: 1).
    
    Code updates both hal_uart and uart_da1469x
---
 hw/drivers/uart/uart_da1469x/src/uart_da1469x.c | 44 +++++++++++++++++++------
 hw/mcu/dialog/da1469x/src/hal_uart.c            | 35 +++++++++++++++-----
 2 files changed, 61 insertions(+), 18 deletions(-)

diff --git a/hw/drivers/uart/uart_da1469x/src/uart_da1469x.c b/hw/drivers/uart/uart_da1469x/src/uart_da1469x.c
index c40686a..2d5345f 100644
--- a/hw/drivers/uart/uart_da1469x/src/uart_da1469x.c
+++ b/hw/drivers/uart/uart_da1469x/src/uart_da1469x.c
@@ -37,8 +37,10 @@ struct da1469x_uart_hw_data {
     mcu_gpio_func tx_pin_func;
     mcu_gpio_func rts_pin_func;
     mcu_gpio_func cts_pin_func;
-    /* Mask for (RE)SET_CLK_COM_REG */
-    uint8_t clk_com_mask;
+    /* Mask for (RE)SET_CLK_COM_REG clock enable */
+    uint8_t clk_com_enable_mask;
+    /* Mask for (RE)SET_CLK_COM_REG clock selection */
+    uint8_t clk_com_clk_sel_mask;
     void (*isr)(void);
 };
 
@@ -49,7 +51,8 @@ static const struct da1469x_uart_hw_data da1469x_uart0_hw = {
     .tx_pin_func = MCU_GPIO_FUNC_UART_TX,
     .rts_pin_func = MCU_GPIO_FUNC_GPIO,
     .cts_pin_func = MCU_GPIO_FUNC_GPIO,
-    .clk_com_mask = CRG_COM_RESET_CLK_COM_REG_UART_ENABLE_Msk,
+    .clk_com_enable_mask = CRG_COM_RESET_CLK_COM_REG_UART_ENABLE_Msk,
+    .clk_com_clk_sel_mask = 0,
     .isr = da1469x_uart_uart_isr,
 };
 
@@ -60,7 +63,8 @@ static const struct da1469x_uart_hw_data da1469x_uart1_hw = {
     .tx_pin_func = MCU_GPIO_FUNC_UART2_TX,
     .rts_pin_func = MCU_GPIO_FUNC_UART2_RTSN,
     .cts_pin_func = MCU_GPIO_FUNC_UART2_CTSN,
-    .clk_com_mask = CRG_COM_RESET_CLK_COM_REG_UART2_ENABLE_Msk,
+    .clk_com_enable_mask = CRG_COM_RESET_CLK_COM_REG_UART2_ENABLE_Msk,
+    .clk_com_clk_sel_mask = CRG_COM_RESET_CLK_COM_REG_UART2_CLK_SEL_Msk,
     .isr = da1469x_uart_uart2_isr,
 };
 
@@ -71,7 +75,8 @@ static const struct da1469x_uart_hw_data da1469x_uart2_hw = {
     .tx_pin_func = MCU_GPIO_FUNC_UART3_TX,
     .rts_pin_func = MCU_GPIO_FUNC_UART3_RTSN,
     .cts_pin_func = MCU_GPIO_FUNC_UART3_CTSN,
-    .clk_com_mask = CRG_COM_RESET_CLK_COM_REG_UART3_ENABLE_Msk,
+    .clk_com_enable_mask = CRG_COM_RESET_CLK_COM_REG_UART3_ENABLE_Msk,
+    .clk_com_clk_sel_mask = CRG_COM_RESET_CLK_COM_REG_UART3_CLK_SEL_Msk,
     .isr = da1469x_uart_uart3_isr,
 };
 
@@ -258,6 +263,7 @@ da1469x_uart_uart_configure(struct da1469x_uart_dev *dev)
     uint32_t reg;
     UART2_Type *uart = dev->hw->regs;
     IRQn_Type irqn = dev->hw->irqn;
+    uint32_t uart_clock = 32000000;
 
     da1469x_pd_acquire(MCU_PD_DOMAIN_COM);
 
@@ -270,14 +276,31 @@ da1469x_uart_uart_configure(struct da1469x_uart_dev *dev)
     }
 
     /* Reset UART */
-    CRG_COM->RESET_CLK_COM_REG = dev->hw->clk_com_mask;
-    CRG_COM->SET_CLK_COM_REG = dev->hw->clk_com_mask;
+    CRG_COM->RESET_CLK_COM_REG = dev->hw->clk_com_enable_mask;
+    CRG_COM->SET_CLK_COM_REG = dev->hw->clk_com_enable_mask;
+    if (uc->uc_speed > 2000000) {
+        /* System core clock should be 96 MHz */
+        if (!MYNEWT_VAL_CHOICE(MCU_SYSCLK_SOURCE, PLL96)) {
+            assert(0);
+        }
+        uart_clock = 96000000;
+        /* Select DIV1 */
+        CRG_COM->SET_CLK_COM_REG = dev->hw->clk_com_clk_sel_mask;
+    } else {
+        /* Select DIVN, always 32MHz */
+        CRG_COM->RESET_CLK_COM_REG = dev->hw->clk_com_clk_sel_mask;
+    }
     uart->UART2_SRR_REG = UART2_UART2_SRR_REG_UART_UR_Msk |
                           UART2_UART2_SRR_REG_UART_RFR_Msk |
                           UART2_UART2_SRR_REG_UART_XFR_Msk;
 
     /* Configure baudrate */
-    baudrate_cfg = (32000000 - 1 + (uc->uc_speed / 2)) / uc->uc_speed;
+    baudrate_cfg = (uart_clock - 1 + (uc->uc_speed / 2)) / uc->uc_speed;
+
+    /* If requested clock exceeds limit, set maximum baudrate */
+    if (baudrate_cfg < 16) {
+        baudrate_cfg = 16;
+    }
     uart->UART2_LCR_REG |= UART2_UART2_LCR_REG_UART_DLAB_Msk;
     uart->UART2_IER_DLH_REG = (baudrate_cfg >> 12) & 0xff;
     uart->UART2_RBR_THR_DLL_REG = (baudrate_cfg >> 4) & 0xff;
@@ -355,7 +378,7 @@ da1469x_uart_uart_shutdown(struct da1469x_uart_dev *dev)
     NVIC_DisableIRQ(dev->hw->irqn);
     NVIC_ClearPendingIRQ(dev->hw->irqn);
 
-    CRG_COM->RESET_CLK_COM_REG = dev->hw->clk_com_mask;
+    CRG_COM->RESET_CLK_COM_REG = dev->hw->clk_com_enable_mask;
 
     da1469x_pd_release(MCU_PD_DOMAIN_COM);
 }
@@ -377,7 +400,8 @@ da1469x_uart_open(struct os_dev *odev, uint32_t wait, void *arg)
 
     dev->uc = *uc;
 
-    if (uc->uc_speed < 1200 || uc->uc_speed > 1000000) {
+    if (uc->uc_speed < 1200 ||
+        uc->uc_speed > ((dev->hw->regs == (UART2_Type *)UART) ? 2000000 : 6000000)) {
         return OS_INVALID_PARM;
     }
 
diff --git a/hw/mcu/dialog/da1469x/src/hal_uart.c b/hw/mcu/dialog/da1469x/src/hal_uart.c
index 0f09f97..2a374e0 100644
--- a/hw/mcu/dialog/da1469x/src/hal_uart.c
+++ b/hw/mcu/dialog/da1469x/src/hal_uart.c
@@ -90,6 +90,13 @@ struct da1469x_uart_baudrate {
 };
 
 static const struct da1469x_uart_baudrate da1469x_uart_baudrates[] = {
+#if MYNEWT_VAL_CHOICE(MCU_SYSCLK_SOURCE, PLL96)
+#if MYNEWT_VAL(UART_1) || MYNEWT_VAL(UART_2)
+    { 6000000, 0x00000100 },
+    { 3000000, 0x00000200 },
+#endif
+#endif
+    { 2000000, 0x00000100 },
     { 1000000, 0x00000200 },
     {  921600, 0x00000203 },
     {  500000, 0x00000400 },
@@ -523,29 +530,41 @@ hal_uart_config(int port, int32_t baudrate, uint8_t databits, uint8_t stopbits,
         return SYS_EINVAL;
     }
 
+    /* Check baudrate */
+    baudrate_cfg = da1469x_uart_find_baudrate_cfg(baudrate);
+    if (!baudrate_cfg || ((port == 0) && (baudrate > 2000000))) {
+        return SYS_ENOTSUP;
+    }
+
     switch (port) {
     case 0:
         CRG_COM->SET_CLK_COM_REG = CRG_COM_SET_CLK_COM_REG_UART_ENABLE_Msk;
         break;
     case 1:
         CRG_COM->SET_CLK_COM_REG = CRG_COM_SET_CLK_COM_REG_UART2_ENABLE_Msk;
-        CRG_COM->RESET_CLK_COM_REG = CRG_COM_SET_CLK_COM_REG_UART2_CLK_SEL_Msk;
+        if (baudrate <= 2000000) {
+            /* Use DIVN as clock source */
+            CRG_COM->RESET_CLK_COM_REG = CRG_COM_SET_CLK_COM_REG_UART2_CLK_SEL_Msk;
+        } else {
+            /* Use DIV1 as clock source */
+            CRG_COM->SET_CLK_COM_REG = CRG_COM_SET_CLK_COM_REG_UART2_CLK_SEL_Msk;
+        }
         break;
     case 2:
         CRG_COM->SET_CLK_COM_REG = CRG_COM_SET_CLK_COM_REG_UART3_ENABLE_Msk;
-        CRG_COM->RESET_CLK_COM_REG = CRG_COM_SET_CLK_COM_REG_UART3_CLK_SEL_Msk;
+        if (baudrate <= 2000000) {
+            /* Use DIVN as clock source */
+            CRG_COM->RESET_CLK_COM_REG = CRG_COM_SET_CLK_COM_REG_UART3_CLK_SEL_Msk;
+        } else {
+            /* Use DIV1 as clock source */
+            CRG_COM->SET_CLK_COM_REG = CRG_COM_SET_CLK_COM_REG_UART3_CLK_SEL_Msk;
+        }
         break;
     default:
         assert(0);
         break;
     }
 
-    /* Set baudrate */
-    baudrate_cfg = da1469x_uart_find_baudrate_cfg(baudrate);
-    if (!baudrate_cfg) {
-        return SYS_ENOTSUP;
-    }
-
     if (uart->cfg->pin_rx >= 0) {
         /*
          * Switch to GPIO during configuration to prevent landing up in