OpenEdv-开源电子网

 找回密码
 立即注册
正点原子全套STM32/Linux/FPGA开发资料,上千讲STM32视频教程免费下载...
查看: 3222|回复: 4

H743dfsdm输出的数据通过dma传输数据错误(Cache不一致)

[复制链接]

2

主题

6

帖子

0

精华

新手入门

积分
6
金钱
6
注册时间
2020-2-23
在线时间
5 小时
发表于 2020-8-10 16:32:00 | 显示全部楼层 |阅读模式
13金钱
dfsdm产生的数据通过循环模式dma储存到内存,因为想要开启DCache,所以尝试添加SCB_CleanDCache();这句话,但是无论添加在那里任然输出不了正确数据,所以想请教一下该如何处理



#include "sys.h"
#include "delay.h"
#include "usart.h"
#include "led.h"
#include "key.h"
#include "stm32h7xx_hal.h"
#include <string.h>
#include "arm_math.h"

DFSDM_Filter_HandleTypeDef hdfsdm1_filter0;
DFSDM_Channel_HandleTypeDef hdfsdm1_channel1;
DMA_HandleTypeDef hdma_dfsdm1_flt0;

#define SAMPLE_FREQ 7972
#define BYTE_PER_SAMPLE 2
#define MICROPHEN_NUMBER 1
#define FRAME_NUMBER 2

#define BUF_LENGTH 1024
#define RESULT_LENGTH (BUF_LENGTH/2)
#define FREQ_STEP (1.0*SAMPLE_FREQ/BUF_LENGTH)

#define OFFSET 0

arm_rfft_fast_instance_f32 fft_s;

#define FFT_FLAG 0

int16_t Buf_Mic0[BUF_LENGTH];
float32_t fft_input[BUF_LENGTH];
float32_t fft_output[BUF_LENGTH];
float32_t mag_output[RESULT_LENGTH];

float32_t fft_max_result;
uint32_t fft_max_index;

static void MX_GPIO_Init(void);
static void MX_DMA_Init(void);
static void MX_DFSDM1_Init(void);

void Error_Handler(void)
{
    while(1)
    {
        printf("------error------\n");
        delay_ms(500);
    }
}


void SystemClock_Config(void)
{
  RCC_OscInitTypeDef RCC_OscInitStruct = {0};
  RCC_ClkInitTypeDef RCC_ClkInitStruct = {0};
  RCC_PeriphCLKInitTypeDef PeriphClkInitStruct = {0};

  /** Supply configuration update enable
  */
  HAL_PWREx_ConfigSupply(PWR_LDO_SUPPLY);
  /** Configure the main internal regulator output voltage
  */
  __HAL_PWR_VOLTAGESCALING_CONFIG(PWR_REGULATOR_VOLTAGE_SCALE1);

  while(!__HAL_PWR_GET_FLAG(PWR_FLAG_VOSRDY)) {}
  /** Initializes the RCC Oscillators according to the specified parameters
  * in the RCC_OscInitTypeDef structure.
  */
  RCC_OscInitStruct.OscillatorType = RCC_OSCILLATORTYPE_HSE;
  RCC_OscInitStruct.HSEState = RCC_HSE_ON;
  RCC_OscInitStruct.PLL.PLLState = RCC_PLL_ON;
  RCC_OscInitStruct.PLL.PLLSource = RCC_PLLSOURCE_HSE;
  RCC_OscInitStruct.PLL.PLLM = 5;
  RCC_OscInitStruct.PLL.PLLN = 160;
  RCC_OscInitStruct.PLL.PLLP = 2;
  RCC_OscInitStruct.PLL.PLLQ = 2;
  RCC_OscInitStruct.PLL.PLLR = 2;
  RCC_OscInitStruct.PLL.PLLRGE = RCC_PLL1VCIRANGE_2;
  RCC_OscInitStruct.PLL.PLLVCOSEL = RCC_PLL1VCOWIDE;
  RCC_OscInitStruct.PLL.PLLFRACN = 0;
  if (HAL_RCC_OscConfig(&RCC_OscInitStruct) != HAL_OK)
  {
    Error_Handler();
  }
  /** Initializes the CPU, AHB and APB buses clocks
  */
  RCC_ClkInitStruct.ClockType = RCC_CLOCKTYPE_HCLK|RCC_CLOCKTYPE_SYSCLK
                              |RCC_CLOCKTYPE_PCLK1|RCC_CLOCKTYPE_PCLK2
                              |RCC_CLOCKTYPE_D3PCLK1|RCC_CLOCKTYPE_D1PCLK1;
  RCC_ClkInitStruct.SYSCLKSource = RCC_SYSCLKSOURCE_PLLCLK;
  RCC_ClkInitStruct.SYSCLKDivider = RCC_SYSCLK_DIV1;
  RCC_ClkInitStruct.AHBCLKDivider = RCC_HCLK_DIV2;
  RCC_ClkInitStruct.APB3CLKDivider = RCC_APB3_DIV2;
  RCC_ClkInitStruct.APB1CLKDivider = RCC_APB1_DIV2;
  RCC_ClkInitStruct.APB2CLKDivider = RCC_APB2_DIV2;
  RCC_ClkInitStruct.APB4CLKDivider = RCC_APB4_DIV2;

  if (HAL_RCC_ClockConfig(&RCC_ClkInitStruct, FLASH_LATENCY_2) != HAL_OK)
  {
    Error_Handler();
  }
  PeriphClkInitStruct.PeriphClockSelection = RCC_PERIPHCLK_DFSDM1;
  PeriphClkInitStruct.Dfsdm1ClockSelection = RCC_DFSDM1CLKSOURCE_D2PCLK1;
  if (HAL_RCCEx_PeriphCLKConfig(&PeriphClkInitStruct) != HAL_OK)
  {
    Error_Handler();
  }
}

int main(void)
{     
    Cache_Enable();                 //打开L1-Cache
    HAL_Init();                        //初始化HAL库
    SystemClock_Config();
    delay_init(400);                //延时初始化
    uart_init(115200);                //串口初始化
    MX_GPIO_Init();
  MX_DMA_Init();
  MX_DFSDM1_Init();
   
    arm_rfft_fast_init_f32(&fft_s, BUF_LENGTH);
    SCB_CleanDCache();
    HAL_DFSDM_FilterRegularMsbStart_DMA(&hdfsdm1_filter0,Buf_Mic0,BUF_LENGTH);
    while(1)
    {            

    }
}

void HAL_DFSDM_FilterRegConvCpltCallback(DFSDM_Filter_HandleTypeDef *hdfsdm_filter)
{
    int i;
    if(HAL_DFSDM_FilterRegularStop_DMA(&hdfsdm1_filter0)==HAL_ERROR)
    {
        Error_Handler();
    }
    for(i = 0; i < BUF_LENGTH; i++)
    {
        fft_input[i] = Buf_Mic0[i] - OFFSET;
    }
   
    arm_rfft_fast_f32(&fft_s, fft_input, fft_output, FFT_FLAG);   
    arm_cmplx_mag_f32(fft_output, mag_output, RESULT_LENGTH);     
    arm_max_f32(mag_output, RESULT_LENGTH, &fft_max_result, &fft_max_index);
   
//    for(i = 0; i < RESULT_LENGTH; i++)
//    {
//        printf("%30f\n", mag_output[i]);
//    }
    printf("\nmax magnitude:\t%f\nindex:\t\t%d\nfrequency:\t%f\n\n", fft_max_result, fft_max_index, (float32_t)fft_max_index*FREQ_STEP);

    delay_ms(500);
    SCB_CleanDCache();
    if(HAL_DFSDM_FilterRegularMsbStart_DMA(&hdfsdm1_filter0,Buf_Mic0,BUF_LENGTH)==HAL_ERROR)
    {
        Error_Handler();
    }

}




static void MX_DFSDM1_Init(void)
{
   
    hdfsdm1_filter0.Instance = DFSDM1_Filter0;
  hdfsdm1_filter0.Init.RegularParam.Trigger = DFSDM_FILTER_SW_TRIGGER;
  hdfsdm1_filter0.Init.RegularParam.FastMode = ENABLE;
  hdfsdm1_filter0.Init.RegularParam.DmaMode = ENABLE;
  hdfsdm1_filter0.Init.FilterParam.SincOrder = DFSDM_FILTER_SINC4_ORDER;
  hdfsdm1_filter0.Init.FilterParam.Oversampling = 128;
  hdfsdm1_filter0.Init.FilterParam.IntOversampling = 1;
   
    HAL_DFSDM_FilterInit(&hdfsdm1_filter0);
   
  hdfsdm1_channel1.Instance = DFSDM1_Channel1;
  hdfsdm1_channel1.Init.OutputClock.Activation = ENABLE;
  hdfsdm1_channel1.Init.OutputClock.Selection = DFSDM_CHANNEL_OUTPUT_CLOCK_SYSTEM;
  hdfsdm1_channel1.Init.OutputClock.Divider = 98;                             
  hdfsdm1_channel1.Init.Input.Multiplexer = DFSDM_CHANNEL_EXTERNAL_INPUTS;
  hdfsdm1_channel1.Init.Input.DataPacking = DFSDM_CHANNEL_STANDARD_MODE;
  hdfsdm1_channel1.Init.Input.Pins = DFSDM_CHANNEL_SAME_CHANNEL_PINS;
  hdfsdm1_channel1.Init.SerialInterface.Type = DFSDM_CHANNEL_SPI_RISING;
  hdfsdm1_channel1.Init.SerialInterface.SpiClock = DFSDM_CHANNEL_SPI_CLOCK_INTERNAL;
  hdfsdm1_channel1.Init.Awd.FilterOrder = DFSDM_CHANNEL_FASTSINC_ORDER;
  hdfsdm1_channel1.Init.Awd.Oversampling = 1;
  hdfsdm1_channel1.Init.Offset = 0;
  hdfsdm1_channel1.Init.RightBitShift = 0x05;
   
    HAL_DFSDM_ChannelInit(&hdfsdm1_channel1);
    HAL_DFSDM_FilterConfigRegChannel(&hdfsdm1_filter0, DFSDM_CHANNEL_1, DFSDM_CONTINUOUS_CONV_ON);
}



static void MX_DMA_Init(void)
{
  /* DMA controller clock enable */
  __HAL_RCC_DMA1_CLK_ENABLE();

  /* DMA interrupt init */
  /* DMA1_Stream0_IRQn interrupt configuration */
  HAL_NVIC_SetPriority(DMA1_Stream0_IRQn, 0, 0);
  HAL_NVIC_EnableIRQ(DMA1_Stream0_IRQn);

}

/** Configure pins as
        * Analog
        * Input
        * Output
        * EVENT_OUT
        * EXTI
*/
static void MX_GPIO_Init(void)
{

  /* GPIO Ports Clock Enable */
  __HAL_RCC_GPIOH_CLK_ENABLE();
  __HAL_RCC_GPIOB_CLK_ENABLE();

}


void _Error_Handler(char * file, int line)
{
  /* USER CODE BEGIN Error_Handler_Debug */
  /* User can add his own implementation to report the HAL error return state */
  while(1)
  {
  }
  /* USER CODE END Error_Handler_Debug */
}








正点原子逻辑分析仪DL16劲爆上市
回复

使用道具 举报

2

主题

6

帖子

0

精华

新手入门

积分
6
金钱
6
注册时间
2020-2-23
在线时间
5 小时
 楼主| 发表于 2020-8-10 16:33:17 | 显示全部楼层
关闭了Cache能够正常工作
回复

使用道具 举报

2

主题

6

帖子

0

精华

新手入门

积分
6
金钱
6
注册时间
2020-2-23
在线时间
5 小时
 楼主| 发表于 2020-8-10 16:41:08 | 显示全部楼层
void Cache_Enable(void)
{
    SCB_EnableICache();//使能I-Cache
    SCB_EnableDCache();//使能D-Cache   
        SCB->CACR|=1<<2;   //强制D-Cache透写,如不开启,实际使用中可能遇到各种问题       
}
而且也是直写模式
回复

使用道具 举报

2

主题

6

帖子

0

精华

新手入门

积分
6
金钱
6
注册时间
2020-2-23
在线时间
5 小时
 楼主| 发表于 2020-8-10 22:02:49 | 显示全部楼层
不对,好像是只要贴的足够近就可以有正确数据(即使开启了Cache,不做任何Cache的操作),为什么会这样,真诚希望大佬解答
回复

使用道具 举报

530

主题

11万

帖子

34

精华

管理员

Rank: 12Rank: 12Rank: 12

积分
165475
金钱
165475
注册时间
2010-12-1
在线时间
2115 小时
发表于 2020-8-11 00:59:11 | 显示全部楼层
DMA传输一定要考虑清cache,不然很容易出错。
我是开源电子网www.openedv.com站长,有关站务问题请与我联系。
正点原子STM32开发板购买店铺http://openedv.taobao.com
正点原子官方微信公众平台,点击这里关注“正点原子”
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则



关闭

原子哥极力推荐上一条 /2 下一条

正点原子公众号

QQ|手机版|OpenEdv-开源电子网 ( 粤ICP备12000418号-1 )

GMT+8, 2025-4-30 16:57

Powered by OpenEdv-开源电子网

© 2001-2030 OpenEdv-开源电子网

快速回复 返回顶部 返回列表