OpenEdv-开源电子网

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

STM32F030F4 adc采集出现神奇异常,求围观解决

[复制链接]

1

主题

7

帖子

0

精华

新手上路

积分
29
金钱
29
注册时间
2019-1-12
在线时间
6 小时
发表于 2019-3-20 23:19:24 | 显示全部楼层 |阅读模式
file:///C:\Users\Irreplaceable\AppData\Roaming\Tencent\Users\2434268681\TIM\WinTemp\RichOle\ZOFK5%9PF_7XJIKZAHFM_J3.png单片机型号:STM32F030F4P6
问题:

做ADC采集时,如果不调用LED_Init()函数,ADC的读数最大值就会变成1024,只有10位精度,而且如果把LED 的初始化函数放在ADC初始化函数后面,读数也时最大1024,把LED 初始化函数放在ADC 初始化函数之前,读数就正常,精度变为12位,经排查,时钟源无异常,LED 初始化函数中,必须有GPIO_Init,其他的都可以没有,如果没有这个函数,ADC读数也会异常,求大神帮忙分析原因,感谢[mw_shl_code=c,true]#include "ALL_Includes.h"//包含所需的头文件


/************************
函数功能:总初始化
输入参数:无
输出参数:无
备    注:无
************************/
void ALL_Config(void)
{
        
        USART1_Init(115200);
        Delay_Init(72);
        LED_Init();
        Adc_Init();
}

int main(void)
{        
        ALL_Config();
        while(1)
        {
               
                printf("PA1_IN1 = %d",Get_Adc1(1));
                printf("        PA2_IN2 = %d",Get_Adc1(2));
               
                delay_ms(50);
                printf("\r\n");
        }
}
[/mw_shl_code]

[mw_shl_code=c,true]#include "ADC.h"

//初始化ADC                                                                                                                           
void  Adc_Init(void)
{   
  GPIO_InitTypeDef  GPIO_InitStructure;
        ADC_InitTypeDef       ADC_InitStructure;
                                
  RCC_AHBPeriphClockCmd(RCC_AHBPeriph_GPIOA, ENABLE);//使能GPIOA时钟
        
  RCC_APB2PeriphClockCmd(RCC_APB2Periph_ADC1, ENABLE); //使能ADC时钟

  //先初始化ADC1通道1 IO口
  GPIO_InitStructure.GPIO_Pin = GPIO_Pin_1;//PA1 通道1
  GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AN;//模拟输入
  GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_NOPULL ;//不带上下拉
  GPIO_Init(GPIOA, &GPIO_InitStructure);//初始化  
        
  //先初始化ADC1通道1 IO口
  GPIO_InitStructure.GPIO_Pin = GPIO_Pin_2;//PA2 通道2
  GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AN;//模拟输入
  GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_NOPULL ;//不带上下拉
  GPIO_Init(GPIOA, &GPIO_InitStructure);//初始化  
         
        RCC_APB2PeriphResetCmd(RCC_APB2Periph_ADC1,ENABLE);          //ADC1复位
        RCC_APB2PeriphResetCmd(RCC_APB2Periph_ADC1,DISABLE);        //复位结束         

        
  ADC_InitStructure.ADC_Resolution = ADC_Resolution_12b;//12位模式
  ADC_InitStructure.ADC_ContinuousConvMode = ENABLE;//连续转换
  ADC_InitStructure.ADC_ExternalTrigConvEdge = ADC_ExternalTrigConvEdge_None;//禁止触发检测,使用软件触发
  ADC_InitStructure.ADC_DataAlign = ADC_DataAlign_Right;//右对齐        
  ADC_InitStructure.ADC_ScanDirection = ADC_ScanDirection_Backward;
  ADC_Init(ADC1, &ADC_InitStructure);//ADC初始化        

  ADC_GetCalibrationFactor(ADC1);
        
        ADC_TempSensorCmd(ENABLE);        
        
  ADC_Cmd(ADC1, ENABLE);//开启AD转换器        
        
        while(!ADC_GetFlagStatus(ADC1, ADC_FLAG_ADEN ));
        
}        

u16 Get_Adc1(u8 ch)   
{
  ADC_ChannelConfig(ADC1,1<<ch,ADC_SampleTime_239_5Cycles);
        ADC1->CHSELR = (u32)1<<ch;
        
        ADC_StopOfConversion(ADC1);//停止转换
        ADC_ClearFlag(ADC1, ADC_FLAG_EOC);  //此处至关重要,一定要清除完成转换标志
        
        while (ADC_GetFlagStatus(ADC1, ADC_FLAG_ADRDY) == RESET)
                ;
  ADC_StartOfConversion(ADC1);        
        
        while(!ADC_GetFlagStatus(ADC1, ADC_FLAG_EOC ));//等待转换结束
        
        return ADC_GetConversionValue(ADC1);        
}


[/mw_shl_code]

无标题.png

STM32F030_ADC.zip

4.46 MB, 下载次数: 635

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

使用道具 举报

0

主题

1

帖子

0

精华

新手入门

积分
3
金钱
3
注册时间
2019-3-21
在线时间
1 小时
发表于 2019-3-21 10:01:03 | 显示全部楼层
会不会跟你这个IO口初始化有关系,AD采样这个用到的IO口是不是也需要初始化以下才行?我其实也是猜测,你可以试一试
回复 支持 反对

使用道具 举报

1

主题

7

帖子

0

精华

新手上路

积分
29
金钱
29
注册时间
2019-1-12
在线时间
6 小时
 楼主| 发表于 2019-3-21 12:51:33 | 显示全部楼层
迷你工程师 发表于 2019-3-21 10:01
会不会跟你这个IO口初始化有关系,AD采样这个用到的IO口是不是也需要初始化以下才行?我其实也是猜测,你可 ...

ADC通道IO初始化没问题,就是如果没有调用那个LED初始化,采样精度会变低,其他的没有异常,而且LED初始化的IO和ADC也没有冲突。
回复 支持 反对

使用道具 举报

1

主题

29

帖子

0

精华

初级会员

Rank: 2

积分
175
金钱
175
注册时间
2018-11-13
在线时间
26 小时
发表于 2019-3-21 15:35:29 | 显示全部楼层
楼主,你的

ADC_InitStructure.ADC_ScanDirection = ADC_ScanDirection_Backward;

这句话算是开扫描模式了么?
回复 支持 反对

使用道具 举报

1

主题

7

帖子

0

精华

新手上路

积分
29
金钱
29
注册时间
2019-1-12
在线时间
6 小时
 楼主| 发表于 2019-3-21 18:10:56 | 显示全部楼层
2018Dog 发表于 2019-3-21 15:35
楼主,你的

ADC_InitStructure.ADC_ScanDirection = ADC_ScanDirection_Backward;

这句话是设置扫描方向
回复 支持 反对

使用道具 举报

1

主题

7

帖子

0

精华

新手上路

积分
29
金钱
29
注册时间
2019-1-12
在线时间
6 小时
 楼主| 发表于 2019-3-22 12:10:34 | 显示全部楼层
求指教啊,有大佬帮帮忙吗
回复 支持 反对

使用道具 举报

1

主题

7

帖子

0

精华

新手上路

积分
29
金钱
29
注册时间
2019-1-12
在线时间
6 小时
 楼主| 发表于 2019-3-23 20:37:17 | 显示全部楼层
zxcv123 发表于 2019-3-22 12:10
求指教啊,有大佬帮帮忙吗

人工置顶
回复 支持 反对

使用道具 举报

2

主题

65

帖子

0

精华

金牌会员

Rank: 6Rank: 6

积分
2106
金钱
2106
注册时间
2016-5-21
在线时间
238 小时
发表于 2019-6-7 01:13:46 | 显示全部楼层
把程序中的这两行
// ADC_ChannelConfig(ADC1,1<<ch,ADC_SampleTime_239_5Cycles);
        //ADC1->CHSELR = (u32)1<<ch;
改成下面这一行就好了               
ADC_ChannelConfig(ADC1, ADC_Channel_1 , ADC_SampleTime_239_5Cycles);//PA1
回复 支持 反对

使用道具 举报

2

主题

474

帖子

0

精华

论坛元老

Rank: 8Rank: 8

积分
6456
金钱
6456
注册时间
2018-6-27
在线时间
546 小时
发表于 2019-12-19 18:42:25 | 显示全部楼层
学习学习,学习学习。
回复 支持 反对

使用道具 举报

37

主题

596

帖子

0

精华

金牌会员

Rank: 6Rank: 6

积分
1574
金钱
1574
注册时间
2017-7-17
在线时间
308 小时
发表于 2019-12-20 17:10:34 | 显示全部楼层
有没有用开启优化编译啊,关掉试试看。
回复 支持 反对

使用道具 举报

0

主题

1

帖子

0

精华

高级会员

Rank: 4

积分
739
金钱
739
注册时间
2019-5-23
在线时间
138 小时
发表于 2020-3-3 14:42:06 | 显示全部楼层
本帖最后由 杨泽锐 于 2020-3-3 14:44 编辑

在adc复位结束后面加个adc初始化函数就正常了
回复 支持 反对

使用道具 举报

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

本版积分规则



关闭

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

正点原子公众号

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

GMT+8, 2025-5-21 11:37

Powered by OpenEdv-开源电子网

© 2001-2030 OpenEdv-开源电子网

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