ST意法半导体
直播中

王树林

8年用户 1751经验值
私信 关注
[问答]

手册描述LPUart1可以工作在APB clock domain,请问用HAL库如何设置?

你好,看到手册描述LPUart1可以工作在APB clock domain,请问用HAL库如何设置,谢谢!

下面代码应该为independent clock设置,对吧?
void HAL_UART_MspInit(UART_HandleTypeDef huart){GPIO_InitTypeDef GPIO_InitStruct = {0};RCC_PeriphCLKInitTypeDef PeriphClkInit = {0};if(huart->Instance==LPUART1){/ USER CODE BEGIN LPUART1_MspInit 0 */
/ USER CODE END LPUART1_MspInit 0 /
/ Initializes the peripherals clock***/*PeriphClkInit.PeriphClockSelection = RCC_PERIPHCLK_LPUART1;PeriphClkInit.Lpuart1ClockSelection = RCC_LPUART1CLKSOURCE_HSI;if (HAL_RCCEx_PeriphCLKConfig(&PeriphClkInit) != HAL_OK)**{Error_Handler();}
/ Peripheral clock enable /__HAL_RCC_LPUART1_CLK_ENABLE();
__HAL_RCC_GPIOB_CLK_ENABLE();/*LPUART1 GPIO ConfigurationPB10     ------> LPUART1_RXPB11     ------> LPUART1_TX/

回帖(3)

孟竹

2025-3-11 16:37:54
看来我这里需要稍微补充下。
数据手册这个地方的写法稍微有点乱。我们简单点,对于很多外设往往涉及2种时钟,
一个是外设总线时钟,一个是外设工作时钟。前者是给CPU或DMA访问外设寄存器用的
,实现对外设的控制和状态获取,后者是外设工作时用到的时钟,以UART为例就是
它通信时使用的时钟,以TIMER为例就是它计数的时钟。


我们不扯多了,重点聊聊你现在关于LPUART的时钟。它有两个时钟:
Usart_pclk 和 lpuart_ker_ck,且后者独立于前者,你可以把后者理解成这里说的独立时钟。


Usart_pclk就是我上面说的外设总线时钟,没得选,外设挂在什么总线就走什么总线来访问
它的寄存器。 lpuart_ker_ck是UART通讯时用到的时钟,比方波特率的是基于该时钟和寄存器配置
得到。它是可选的,在CubeMx那里有好几个选项就是针对lpuart_ker_ck的。


不过,在基于CubeMx生成的代码里,相应变量写法跟手册描述并未对应。假设我们在Cubemx
选择lpuart_ker_ck来自HSI.


我们可以看到工程里的配置代码是这样的:


PeriphClkInit.PeriphClockSelection = RCC_PERIPHCLK_LPUART1;
xa0xa0PeriphClkInit.Lpuart1ClockSelection = RCC_LPUART1CLKSOURCE_HSI;


第一项配置就是指配置UART的外设总线时钟,下方是它的工作时钟配置,也就是你
提到的独立时钟。


这样设计的好处,一是让外设工作时钟有更多的选择自由度;具体到这里,还有个好处,
即使外设总线时钟因低功耗模式停了,还可以基于外设工作时钟继续工作,比方我将
上面的工作时钟改成LSI或LSE. 
举报

张锐

2025-3-11 16:37:58
你使用cubeMx配置,相应外设的时钟使能在创建工程后的初始化代码里 都有做了使能操作。


另外,不建议使用L5系列做产品开发了,可以看看U5 H5 等系列。
举报

岳臻俊

2025-3-11 18:13:57

是的,你提到的代码片段是用来配置LPUART1的时钟源的。根据你的描述,你希望将LPUART1配置为工作在APB时钟域(APB clock domain),而不是独立的时钟源。


在HAL库中,你可以通过配置RCC_PeriphCLKInitTypeDef结构体来设置外设的时钟源。对于LPUART1,你可以选择使用APB时钟作为其时钟源。以下是如何设置LPUART1使用APB时钟的示例代码:


void HAL_UART_MspInit(UART_HandleTypeDef *huart)
{
    GPIO_InitTypeDef GPIO_InitStruct = {0};
    RCC_PeriphCLKInitTypeDef PeriphClkInit = {0};

    if(huart->Instance == LPUART1)
    {
        /* USER CODE BEGIN LPUART1_MspInit 0 */

        /* USER CODE END LPUART1_MspInit 0 */

        // Initializes the peripherals clock
        PeriphClkInit.PeriphClockSelection = RCC_PERIPHCLK_LPUART1;
        PeriphClkInit.Lpuart1ClockSelection = RCC_LPUART1CLKSOURCE_PCLK1; // 使用APB1时钟作为LPUART1的时钟源

        if (HAL_RCCEx_PeriphCLKConfig(&PeriphClkInit) != HAL_OK)
        {
            // 错误处理
            Error_Handler();
        }

        // 使能LPUART1时钟
        __HAL_RCC_LPUART1_CLK_ENABLE();

        // 配置GPIO引脚
        GPIO_InitStruct.Pin = GPIO_PIN_2 | GPIO_PIN_3; // 假设LPUART1使用GPIO_PIN_2和GPIO_PIN_3
        GPIO_InitStruct.Mode = GPIO_MODE_AF_PP;
        GPIO_InitStruct.Pull = GPIO_NOPULL;
        GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_VERY_HIGH;
        GPIO_InitStruct.Alternate = GPIO_AF8_LPUART1; // 根据实际情况选择合适的Alternate Function
        HAL_GPIO_Init(GPIOA, &GPIO_InitStruct); // 假设LPUART1使用GPIOA

        /* USER CODE BEGIN LPUART1_MspInit 1 */

        /* USER CODE END LPUART1_MspInit 1 */
    }
}

关键点:



  1. 时钟源选择:通过PeriphClkInit.Lpuart1ClockSelection设置为RCC_LPUART1CLKSOURCE_PCLK1,表示LPUART1使用APB1时钟作为时钟源。

  2. GPIO配置:根据实际硬件连接,配置LPUART1的TX和RX引脚。


注意:



  • RCC_LPUART1CLKSOURCE_PCLK1表示使用APB1时钟作为LPUART1的时钟源。如果你的微控制器有多个APB总线,确保选择正确的APB时钟源。

  • GPIO_InitStruct.Alternate需要根据实际硬件连接的GPIO引脚和Alternate Function进行配置。


通过以上设置,LPUART1将工作在APB时钟域中。

举报

更多回帖

×
20
完善资料,
赚取积分