问小白 wenxiaobai
资讯
历史
科技
环境与自然
成长
游戏
财经
文学与艺术
美食
健康
家居
文化
情感
汽车
三农
军事
旅行
运动
教育
生活
星座命理

基于STM32F4和MATLAB的FIR数字低通滤波器实现

创作时间:
作者:
@小白创作中心

基于STM32F4和MATLAB的FIR数字低通滤波器实现

引用
CSDN
1.
https://blog.csdn.net/m0_74408701/article/details/144581825

本文将介绍如何使用STM32F4微控制器和MATLAB实现FIR数字低通滤波器。通过HAL库和CubeMX工具,我们将完成从理论概念到实际硬件实现的全过程。

FIR滤波器基本概念

FIR(Finite Impulse Response)滤波器是一种有限冲激响应滤波器,其输出仅取决于当前及之前的输入值。与IIR(Infinite Impulse Response)滤波器不同,FIR滤波器不依赖于过去的输出值,因此具有线性相位特性,适用于需要保持信号相位一致性的场合。

FIR滤波器的关键在于其抽头系数(h(n)),这些系数决定了滤波器的频率响应特性。通过合理设置这些系数,可以实现低通、高通、带通或带阻等不同类型的滤波效果。

实践过程

MATLAB配置

在MATLAB中,我们可以使用信号处理工具箱来计算FIR滤波器的抽头系数。通过设置通带频率(Fpass)和阻带频率(Fstop),可以生成满足特定频率响应要求的滤波器系数。

导出的抽头系数如下:

uint16_t BL = 24;
float32_t TB[24] = {
    0.0013  ,
    0.0056    ,
    -0.0086   ,
    -0.0048   ,
    0.0218    ,
    -0.0093   ,
    -0.0332   ,
    0.0456    ,
    0.0245    ,
   -0.1186  ,
   0.0638   ,
   0.5119   , 
   0.5119   , 
   0.0638   ,
   -0.1186  ,  
   0.0245   ,
   0.0456   ,
   -0.0332  ,
   -0.0093  ,
   0.0218   ,
   -0.0048  ,
   -0.0086  , 
   0.0056   ,
   0.0013
     };

STM32F4配置

使用STM32CubeMX工具,我们可以方便地配置STM32F4的时钟、ADC和DMA等外设。关键配置包括:

  • 时钟树配置:确保系统时钟满足采样频率要求
  • ADC配置:使用定时器触发ADC采样,确保采样频率稳定
  • DMA配置:使用DMA传输ADC采样数据,提高数据处理效率

代码实现

在Keil中,我们需要引入STM32的DSP库,并配置相应的头文件。关键代码包括:

  • 初始化FIR滤波器实例
  • 读取ADC采样数据
  • 调用FIR滤波函数处理数据
  • 通过串口输出处理结果
#include "arm_math.h"
#include "arm_const_structs.h"
#include "stdio.h"
#include <stdlib.h>

int fputc(int ch, FILE *fp)
{
  HAL_UART_Transmit(&huart1, (uint8_t *)&ch, 1, 0xffff);
  return ch;
}

int fgetc(FILE *fp)
{
  uint8_t ch = 0;
  HAL_UART_Receive(&huart1, &ch, 1, 0xffff);
  return ch;
}

int main(void)
{
  /* 初始化HAL库 */
  HAL_Init();
  /* 配置系统时钟 */
  SystemClock_Config();
  /* 初始化外设 */
  MX_GPIO_Init();
  MX_DMA_Init();
  MX_ADC1_Init();
  MX_TIM3_Init();
  MX_USART1_UART_Init();

  /* 开始ADC采样 */
  HAL_TIM_Base_Start(&htim3);
  HAL_ADC_Start_DMA(&hadc1, (uint32_t*)ADC1_ConvertedValue, ADC1_DMA_Size);
  printf("init_ok\r\n");

  /* 初始化FIR滤波器 */
  arm_fir_instance_f32 *S = (arm_fir_instance_f32 *)malloc(sizeof(arm_fir_instance_f32));
  arm_fir_init_f32(S, BL, TB, pState, blockSize);

  while (1)
  {
    if (flag == 1)
    {
      flag = 0;
      HAL_Delay(1000);
      printf("/**************************************/\r\n");

      for (i = 0; i < FFT_LENGTH; i++)
      {
        fir_inputbuf[i] = (float)ADC1_ConvertedValue[i] * 3.3 / 4096;
      }

      arm_fir_f32(S, fir_inputbuf, fir_outputbuf, blockSize);

      for (i = 0; i < FFT_LENGTH; i++)
      {
        printf("%f,%f\r\n", (float)ADC1_ConvertedValue[i] * 3.3 / 4096, fir_outputbuf[i]);
      }
    }
    HAL_ADC_Start_DMA(&hadc1, (uint32_t*)ADC1_ConvertedValue, ADC1_DMA_Size);
  }
}

实验验证

通过波形发生器产生不同频率的正弦波信号,并加入直流偏置。STM32采集信号后进行FIR滤波处理,最后通过串口将原始信号和滤波后的信号发送至上位机进行分析。

测试结果显示,对于高频信号(如4KHz正弦波),滤波后的信号振幅趋近于0,验证了低通滤波器的有效性。



© 2023 北京元石科技有限公司 ◎ 京公网安备 11010802042949号