OpenEdv-开源电子网

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

stm32改用内部时钟后 adc+dma 读取的 adc值错位

[复制链接]

1

主题

2

帖子

0

精华

新手上路

积分
22
金钱
22
注册时间
2020-3-13
在线时间
5 小时
发表于 2020-4-6 15:33:10 | 显示全部楼层 |阅读模式
2金钱
之前用外部时钟读取dma 中 的四个ADC值,数据规整,换做内部时钟源作为系统时钟后 ,数据读取出来错位~一下是两种时钟的配置:

//#define PLL_SOURCE_HSE
static void SetSysClock(void)
{
#if defined (PLL_SOURCE_HSE)
  __IO uint32_t StartUpCounter = 0, HSEStatus = 0;

  /* SYSCLK, HCLK, PCLK configuration ----------------------------------------*/
  /* Enable HSE */   
  RCC->CR |= ((uint32_t)RCC_CR_HSEON);

  /* Wait till HSE is ready and if Time out is reached exit */
  do
  {
    HSEStatus = RCC->CR & RCC_CR_HSERDY;
    StartUpCounter++;  
  } while((HSEStatus == 0) && (StartUpCounter != HSE_STARTUP_TIMEOUT));

  if ((RCC->CR & RCC_CR_HSERDY) != RESET)
  {
    HSEStatus = (uint32_t)0x01;
  }
  else
  {
    HSEStatus = (uint32_t)0x00;
  }  

  if (HSEStatus == (uint32_t)0x01)
  {
    /* Enable Prefetch Buffer and set Flash Latency */
    FLASH->ACR = FLASH_ACR_PRFTBE | FLASH_ACR_LATENCY;

    /* HCLK = SYSCLK */
    RCC->CFGR |= (uint32_t)RCC_CFGR_HPRE_DIV1;

    /* PCLK = HCLK */
    RCC->CFGR |= (uint32_t)RCC_CFGR_PPRE_DIV1;

    /* PLL configuration = HSE * 6 = 48 MHz */
    RCC->CFGR &= (uint32_t)((uint32_t)~(RCC_CFGR_PLLSRC | RCC_CFGR_PLLXTPRE | RCC_CFGR_PLLMULL));
    RCC->CFGR |= (uint32_t)(RCC_CFGR_PLLSRC_PREDIV1 | RCC_CFGR_PLLXTPRE_PREDIV1 | RCC_CFGR_PLLMULL6);

    /* Enable PLL */
    RCC->CR |= RCC_CR_PLLON;

    /* Wait till PLL is ready */
    while((RCC->CR & RCC_CR_PLLRDY) == 0)
    {
    }

    /* Select PLL as system clock source */
    RCC->CFGR &= (uint32_t)((uint32_t)~(RCC_CFGR_SW));
    RCC->CFGR |= (uint32_t)RCC_CFGR_SW_PLL;   

    /* Wait till PLL is used as system clock source */
    while ((RCC->CFGR & (uint32_t)RCC_CFGR_SWS) != (uint32_t)RCC_CFGR_SWS_PLL)
    {
    }
  }
  else
  { /* If HSE fails to start-up, the application will have wrong clock
         configuration. User can add here some code to deal with this error */
  }  
#else
        __IO uint32_t StartUpCounter = 0, HSIStatus = 0;
/*关闭外部时钟*/
        RCC->CR &= ~((uint32_t)RCC_CR_HSEON);                                    
        RCC->CR |= ((uint32_t)RCC_CR_HSION);               //使能内部时钟 HSI
        do                                                                                    //等待内部时钟起振
        {
                HSIStatus = RCC->CR & RCC_CR_HSIRDY;                                              // 设置RCC
                StartUpCounter++;                                                                 //启动计数器
        }
        while((HSIStatus== 0) && (StartUpCounter != HSI_STARTUP_TIMEOUT));                    // 等待 HSE 启动稳定

        if ((RCC->CR & RCC_CR_HSIRDY) != RESET)                                               //判断启动状态
        {
                HSIStatus = (uint32_t)0x01;
        }
        else
        {
                HSIStatus = (uint32_t)0x00;                                                       //启动不成功
        }

        if (HSIStatus == (uint32_t)0x01) //启动成功
        {
                /* Enable Prefetch Buffer and set Flash Latency */
                FLASH->ACR = FLASH_ACR_PRFTBE | FLASH_ACR_LATENCY;      //flash总线时钟使能

                /* HCLK = SYSCLK */      //AHB总线时钟HCLK(是系统时钟SYSCLK经过AHB分频器分频后得到的时钟,

                //一般设置1分频,HCLK=SYSSCLK=48MHz;

                RCC->CFGR |= (uint32_t)RCC_CFGR_HPRE_DIV1;    //AHB总线时钟  HCLK = SYSCLK/1=48MHz

                /* PCLK = HCLK */         //APB总线时钟PCLK等于AHB总线时钟/1   PCLK=HCLK/1
                RCC->CFGR |= (uint32_t)RCC_CFGR_PPRE_DIV1;                    // PCLK=HCLK/1=48M/1=48M

                /* PLL configuration = HSI/2 * 12= 48 MHz */
                RCC->CFGR &= (uint32_t)((uint32_t)~(RCC_CFGR_PLLSRC | RCC_CFGR_PLLSRC | RCC_CFGR_PLLMULL));
                RCC->CFGR |= (uint32_t)(RCC_CFGR_PLLSRC_HSI_Div2 | RCC_CFGR_PLLMULL12);   

                //RC时钟2分频后 进行12倍频
                //=8M/2*12=48M
                RCC->CR |= RCC_CR_PLLON;                                             //使能锁相环倍频开关 /* Enable PLL */

                while((RCC->CR & RCC_CR_PLLRDY) == 0)                                //等待锁相环就绪
                { }

                /* Select PLL as system clock source */                              //选择锁相环输出时钟作为系统时钟
                RCC->CFGR &= (uint32_t)((uint32_t)~(RCC_CFGR_SW));
                RCC->CFGR |= (uint32_t)RCC_CFGR_SW_PLL;

                while ((RCC->CFGR & (uint32_t)RCC_CFGR_SWS) != (uint32_t)RCC_CFGR_SWS_PLL)
                {
                }                                                                   //等待锁相环输出时钟已经成为系统时钟
        }
        else
        {
       
        }   
#endif
}




最佳答案

查看完整内容[请看2#楼]

已经解决了 ,之前用的2.5V系统,换用3.3后 读取dma是没有问题的
正点原子逻辑分析仪DL16劲爆上市
回复

使用道具 举报

1

主题

2

帖子

0

精华

新手上路

积分
22
金钱
22
注册时间
2020-3-13
在线时间
5 小时
 楼主| 发表于 2020-4-6 15:33:11 | 显示全部楼层
已经解决了 ,之前用的2.5V系统,换用3.3后 读取dma是没有问题的
回复

使用道具 举报

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

本版积分规则



关闭

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

正点原子公众号

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

GMT+8, 2025-5-24 21:25

Powered by OpenEdv-开源电子网

© 2001-2030 OpenEdv-开源电子网

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