打印
[STM32]

基于AT32F403的ADC学习(STM32F103类似)

[复制链接]
345|0
手机看帖
扫描二维码
随时随地手机跟帖
跳转到指定楼层
楼主
林堪堪|  楼主 | 2020-12-9 18:40 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
使用ADC的基础配置步骤包括:开启时钟,配置ADC相关的GPIO口,配置和使能ADC对应的DMA通道,配置和使能ADC,ADC校准,开始触发。
1)使能ADC对应时钟,对应DMA的时钟,对应GPIO时钟:
   RCC_AHBPeriphClockCmd(RCC_AHBPERIPH_DMA1, ENABLE);
   RCC_APB2PeriphClockCmd(RCC_APB2PERIPH_ADC1, ENABLE);
   RCC_APB2PeriphClockCmd(RCC_APB2PERIPH_GPIOA, ENABLE);
2)配置对应GPIO为模拟输入模式:
    GPIO_InitStructure.GPIO_Pins = GPIO_Pins_0 | GPIO_Pins_1| GPIO_Pins_2 | GPIO_Pins_3 ;
    GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN_ANALOG;
    GPIO_Init(GPIOA, &GPIO_InitStructure);
3)配置ADC对应的DMA:需要先在DMA章节查找ADC对应的DMA通道(示例里就是DMA1_Channel1)。需要使用DMA是因为规则组的多通道ADC共用一个数据寄存器,所以多通道转化时需要开启DMA,否则数据会丢失。开启对应DMA后,每转换完一个通道的数据,DMA都会自动将数据寄存器里的数据搬运到用户预先设置好的数组里,这个搬运过程不需要用户关注/操作。
    DMA_InitStructure.DMA_PeripheralBaseAddr = ADC1_DR_Address;//外设地址—即ADC1数据寄存器地址
    DMA_InitStructure.DMA_MemoryBaseAddr= (uint32_t)&ADC_RegularConvertedValueTab;//内存地址—用户需要存储ADC转换数据的数组首地址
    DMA_InitStructure.DMA_Direction = DMA_DIR_PERIPHERALSRC;//DMA传输方向—这里是外设到内存
    DMA_InitStructure.DMA_BufferSize = 4;//DMA传输数据量—这里是4,与ADC通道数量一样
    DMA_InitStructure.DMA_PeripheralInc = DMA_PERIPHERALINC_DISABLE;//外设地址自增--不自增,一直都是ADC1的数据寄存器
    DMA_InitStructure.DMA_MemoryInc = DMA_MEMORYINC_ENABLE; //内存地址自增--自增,每传输完一次数据,内存地址就加一。例如:DMA第一次搬运的数据放在ADC_RegularConvertedValueTab[0],下一次搬运的数据就放在ADC_RegularConvertedValueTab[1]了,依次增加。直到达到DMA设置的BufferSize,这里时4。
    DMA_InitStructure.DMA_PeripheralDataWidth= DMA_PERIPHERALDATAWIDTH_HALFWORD; //外设数据格式--16bit,AT32F403的ADC有效数据是12bit,这里选择16bit的数据格式就可以。
    DMA_InitStructure.DMA_MemoryDataWidth = DMA_PERIPHERALDATAWIDTH_HALFWORD; //内存数据格式--16bit,注意对应的ADC_RegularConvertedValueTab数组定义的时候需要定义为16bit格式。
    DMA_InitStructure.DMA_Mode = DMA_MODE_CIRCULAR; //传输模式--循环模式,循环模式即DMA搬运完4次之后,内存地址又从ADC_RegularConvertedValueTab[0]开始。
    DMA_InitStructure.DMA_Priority = DMA_PRIORITY_HIGH; //传输优先级--高
    DMA_InitStructure.DMA_MTOM = DMA_MEMTOMEM_DISABLE; //内存到内存--关闭
    DMA_Init(DMA1_Channel1, &DMA_InitStructure);
    DMA_ChannelEnable(DMA1_Channel1, ENABLE); //DMA通道使能
4)配置ADC:
    ADC_InitStructure.ADC_Mode = ADC_Mode_Independent; //ADC模式--独立模式
    ADC_InitStructure.ADC_ScanMode = ENABLE; //扫描模式--使能,多通道转换的时候,需要开启扫描模式,否则会一直转换第一个通道。
    ADC_InitStructure.ADC_ContinuousMode = DISABLE; //连续模式--失能
    ADC_InitStructure.ADC_ExternalTrig = ADC_ExternalTrig_None; //外部触发—选择软件触发(触发方式还可以使用定时器触发/外部中断触发等方式,这里选择最基础的软件触发)
    ADC_InitStructure.ADC_DataAlign = ADC_DataAlign_Right; //数据对齐--右对齐
    ADC_InitStructure.ADC_NumOfChannel = 4; //转换通道数--4
    ADC_Init(ADC1, &ADC_InitStructure);       
5)使能ADC的DMA功能:
   ADC_DMACtrl(ADC1, ENABLE);
6)ADC通道配置(通道顺序,采样时间):
   ADC_RegularChannelConfig(ADC1, ADC_Channel_0, 1, ADC_SampleTime_41_5); //ADC1的通道0(对应GPIO口为PA0),转化顺序为1,采样时间为41.5个ADCCLK
   ADC_RegularChannelConfig(ADC1, ADC_Channel_1, 2, ADC_SampleTime_41_5); //ADC1的通道1(对应GPIO口为PA1),转化顺序为2,采样时间为41.5个ADCCLK
   ADC_RegularChannelConfig(ADC1, ADC_Channel_2, 3, ADC_SampleTime_41_5); //ADC1的通道2(对应GPIO口为PA2),转化顺序为3,采样时间为41.5个ADCCLK
   ADC_RegularChannelConfig(ADC1, ADC_Channel_3, 4, ADC_SampleTime_41_5); //ADC1的通道3(对应GPIO口为PA3),转化顺序为4,采样时间为41.5个ADCCLK
7)ADC外部触发使能、配置:
   ADC_ExternalTrigConvCtrl(ADC1, ENABLE);//外部触发使能—注意,软触发也算外部触发,也需要使能外部触发。
8)ADC使能/唤醒:
   ADC_Ctrl(ADC1, ENABLE);
9)ADC校准:
   ADC_RstCalibration(ADC1);
   while(ADC_GetResetCalibrationStatus(ADC1));
   ADC_StartCalibration(ADC1);
   while(ADC_GetCalibrationStatus(ADC1));
   delay_ms(10);
10)ADC软触发--开始转换:
ADC_SoftwareStartConvCtrl(ADC1, ENABLE);

使用特权

评论回复

相关帖子

发新帖 我要提问
您需要登录后才可以回帖 登录 | 注册

本版积分规则

69

主题

119

帖子

5

粉丝