gpt4 book ai didi

c - STM32L0的自动波特率检测

转载 作者:太空狗 更新时间:2023-10-29 14:58:42 30 4
gpt4 key购买 nike

我无法让自动波特率检测在 STM32L0 上工作。我正在使用硬件抽象层 (HAL)。

我的初始化代码是:

/* USART1 init function */
void MX_USART1_UART_Init(void)
{

huart1.Instance = USART1;
huart1.Init.BaudRate = 300;
huart1.Init.WordLength = UART_WORDLENGTH_9B;
huart1.Init.StopBits = UART_STOPBITS_1;
huart1.Init.Parity = UART_PARITY_EVEN;
huart1.Init.Mode = UART_MODE_TX_RX;
huart1.Init.HwFlowCtl = UART_HWCONTROL_NONE;
huart1.Init.OverSampling = UART_OVERSAMPLING_16;
huart1.Init.OneBitSampling = UART_ONEBIT_SAMPLING_DISABLED;
huart1.AdvancedInit.AdvFeatureInit = UART_ADVFEATURE_AUTOBAUDRATE_INIT;
huart1.AdvancedInit.AutoBaudRateEnable = UART_ADVFEATURE_AUTOBAUDRATE_ENABLE;
huart1.AdvancedInit.AutoBaudRateMode = UART_ADVFEATURE_AUTOBAUDRATE_ONSTARTBIT;
HAL_UART_Init(&huart1);


}

我通过 UART1 发送的字节是:

        0   1   2   3   4   5   6   7   8   
000x 68 0B 0B 68 53 FD 52 FF FF .. etc.

0x68 = 0b01101000
0x0B = 0b00001011
0xFD = 0b11111101 <-- Character starting with 1, baudrate should be detected


0xFD :
start 1 1 .....
___ bit __________
¦______¦
...

为什么没有检测到波特率?我试过:

UART_ADVFEATURE_AUTOBAUDRATE_ONSTARTBITUART_ADVFEATURE_AUTOBAUDRATE_ONFALLINGEDGE

所以我调整了驱动程序中模式设置和启用的顺序:

  /* if required, configure auto Baud rate detection scheme */              
if(HAL_IS_BIT_SET(huart->AdvancedInit.AdvFeatureInit, UART_ADVFEATURE_AUTOBAUDRATE_INIT))
{
assert_param(IS_UART_ADVFEATURE_AUTOBAUDRATE(huart->AdvancedInit.AutoBaudRateEnable));
MODIFY_REG(huart->Instance->CR2, USART_CR2_ABREN, huart->AdvancedInit.AutoBaudRateEnable);
/* set auto Baudrate detection parameters if detection is enabled */
if(huart->AdvancedInit.AutoBaudRateEnable == UART_ADVFEATURE_AUTOBAUDRATE_ENABLE)
{
assert_param(IS_UART_ADVFEATURE_AUTOBAUDRATEMODE(huart->AdvancedInit.AutoBaudRateMode));
MODIFY_REG(huart->Instance->CR2, USART_CR2_ABRMODE, huart->AdvancedInit.AutoBaudRateMode);
}
}

  /* if required, configure auto Baud rate detection scheme */              
if(HAL_IS_BIT_SET(huart->AdvancedInit.AdvFeatureInit, UART_ADVFEATURE_AUTOBAUDRATE_INIT))
{
assert_param(IS_UART_ADVFEATURE_AUTOBAUDRATE(huart-
/* set auto Baudrate detection parameters if detection is enabled */
if(huart->AdvancedInit.AutoBaudRateEnable == UART_ADVFEATURE_AUTOBAUDRATE_ENABLE)
{
assert_param(IS_UART_ADVFEATURE_AUTOBAUDRATEMODE(huart->AdvancedInit.AutoBaudRateMode));
MODIFY_REG(huart->Instance->CR2, USART_CR2_ABRMODE, huart->AdvancedInit.AutoBaudRateMode);
}
MODIFY_REG(huart->Instance->CR2, USART_CR2_ABREN, huart->AdvancedInit.AutoBaudRateEnable);
}

什么都不做。

此外,以下内容似乎还不错:

The clock source frequency must be compatible with the expected communication speed(when oversampling by 16, the baud rate is between fCK/65535 and fCK/16. whenoversampling by 8, the baudrate is between fCK/65535 and fCK/8).

我过采样 16,所以

fCK= 16000000

fCK > 16000000 / 65535 = 244 = 244 Hz
fCK < 16000000 / 16 = 1000000 = 1 MHz

我选择的波特率是:19200/9600/2400/300

最佳答案

如果您无法指定要由 STM32L0 的自动波特率检测硬件检查的单个字节的精确内容,您仍然可以“推出自己的”自动波特率检测方案,前提是以下假设可以为您的系统制作:

  • 在自动波特率检测过程中允许丢弃任意数量的连续接收字符。

  • 在接收到多个字符的任意时间间隔内,可以假定位序列 010101是比较常见的现象。

  • 该设备有一个可用的通用定时器外设,可以映射到与 USART Rx 信号相同的设备引脚。

如果以上所有情况都成立,那么您可以使用芯片上通用定时器外设之一的输入捕获功能创建自己的自动波特率检测方案。这些定时器可以配置为使用内部 16 MHz 时钟作为它们的时钟源。每个定时器包含一个 16 位计数器。使用 16 MHz 时钟时,定时器具有 (1/16,000,000 Hz) = 62.5 nS 脉冲测量分辨率。

在您首选的波特率下,单个位的持续时间如下:

 Baud   Microseconds   62.5-nS Clocks
---- ------------ --------------
300 3,333.3 53,333
2400 416.7 6,667
9600 104.2 1,667
19200 52.1 833

您可以在输入捕获模式下设置定时器,并让它计算两个相邻边沿转换之间的时钟数。对相对较多的样本(例如 100)执行此操作。这些样本中的许多将表示两个或多个相邻零或两个或多个相邻零的宽度。但您正在寻找最短 样本。如果您找到一个介于 831 和 835 之间的计数,那么您可以有理由相信波特率为 19200。在 100 个样本之后,如果您找到的最短的计数介于 1665 和 1669 之间,那么您可以假设波特率为9600等等。

在此过程中,USART 被禁用,而定时器被分配给引脚。确定要使用的正确波特率后,重新配置引脚以将其分配给 USART Rx 外设功能。

关于c - STM32L0的自动波特率检测,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/34874020/

30 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com