signal-processing - 通过 UART 流式传输 ADC 数据
问题描述
我正在尝试通过 STM32 核板上的 UART 从 8 位 ADC 流式传输采样值。
我使用带有 DMA 的 ADC。采样率约为 6kHz,用 100 个转换值填充缓冲区需要大约 17 毫秒。
之后,我想通过波特率 115200 的 UART 发送这些值。由于 ADC 转换值是HALF_WORD
100 个转换值,我必须发送 1600 位。这意味着我可以在不覆盖数据的情况下将它们发送 14 毫秒。
这是我在代码中的尝试:
/* Private variables*/
#define ADC_BUF_LEN 100
uint16_t adc_buf[ADC_BUF_LEN];
uint8_t flag = 0;
/* USER CODE BEGIN 2 */
HAL_ADC_Start_DMA(&hadc, (uint32_t*)adc_buf, ADC_BUF_LEN);
HAL_TIM_Base_Start(&htim2);
while (1)
{
if (flag==1)
{
HAL_UART_Transmit(&huart4,(uint8_t*)adc_buf,100,1);
flag = 0;
HAL_GPIO_TogglePin(GPIOA,GPIO_PIN_9);
}
else
{}
}
void HAL_ADC_ConvCpltCallback(ADC_HandleTypeDef* hadc)
{
HAL_GPIO_TogglePin(GPIOA,LED_GREEN_Pin);
flag = 1;
}
我已将带有传输数据的图片附加到终端。对于输入,ADC 满足 1 kHz 正弦波 2 V p-pk。我可以用肉眼看到我的系统无法正常工作。
如果我绘制该数据,它将不是正弦波。
该项目用于 EMG 信号处理:我需要对信号进行采样,然后在 Python 中进行处理。
解决方案
将 的Timeout
参数设置HAL_UART_Transmit
为 1 是不正确的。您已经计算出需要 14 毫秒!这意味着该函数将在仅传输一小部分数据后放弃并返回。
要在没有数据间隙的情况下多次执行此操作,您需要同时在 ADC 和 UART 上使用 DMA。
启用 ADC DMA 的半传输中断,或轮询半传输标志。当您收到它时,在缓冲区的前半部分以 DMA 模式启动 UART。它应该在 7 毫秒内完成,即 ADC DMA 开始覆盖其包含的数据之前的 1.5 毫秒。当您获得 ADC DMA 完成中断或标志时,在缓冲区的后半部分启动 UART DMA。
或者,大多数 STM32 上的 DMA 也支持“双缓冲区”模式,其工作方式或多或少相同,但您只使用完整的中断,并且您有两个单独的数据指针,而不是计算半个缓冲区的偏移量。
推荐阅读
- android - React native android fontFamily 无法更改或不影响
- reactjs - 自定义钩子卡在递归循环中
- c++ - VS2010-VS2015下编译时如何使用decltype作为较大类型表达式的LHS
- mobile - 使用 Katalon 运行移动自动化测试
- google-tag-manager - 如何缩小谷歌标签管理器
- javascript - 我可以在 node.js 中使用异步函数作为回调吗?
- delphi - eBay Trading API - Delphi 中的调用结构
- javascript - Babel 没有将导入的 node_modules 转换为 ES5 - 包括 ES2015 语法
- javascript - 在我的脚本中重命名 PDF 以包含 Google 表格中当前行的值(创建 pdf 的地方)
- reactjs - componentWillMount 中不需要的页面刷新的可能原因