0
  • 聊天消息
  • 系统消息
  • 评论与回复
登录后你可以
  • 下载海量资料
  • 学习在线课程
  • 观看技术视频
  • 写文章/发帖/加入社区
会员中心
创作中心

完善资料让更多小伙伴认识你,还能领取20积分哦,立即完善>

3天内不再提示

【GD32 MCU 入门教程】GD32 MCU 常见外设介绍 (6) ADC 模块介绍

聚沃科技 2024-08-15 09:46 次阅读

6.1.ADC 基础知识

12 位逐次逼近式模数转换器模块(ADC),可以采样来自于外部输入通道、内部输入通道的模拟信号,采样转换后,转换结果可以按照最低有效位对齐或最高有效位对齐的方式保存在相应的数据寄存器中。

6.2.GD32 ADC 外设原理

GD32 ADC 主要特性

◼ 高性能:

– ADC采样分辨率: 12位、 10位、 8位、或者6位分辨率;

– 前置校准功能;

– 可编程采样时间;

– 数据存储模式:最高有效位对齐和最低有效位对齐;

– 支持规则数据转换的DMA请求。

◼ 模拟输入通道:

– 16个外部模拟输入通道;

– 1个内部温度传感器输入通道(VSENSE);

– 1个内部参考电压输入通道(VREFINT)。

◼ 转换开始的发起:

– 软件触发;

硬件触发。

◼ 转换模式:

– 转换单个通道,或者扫描一序列的通道;

– 单次运行模式,每次触发转换一次选择的输入通道;

– 连续运行模式,连续转换所选择的输入通道;

– 间断运行模式;

– 同步模式(适用于具有两个或多个ADC的设备)。

◼ 转换结果阈值监测器功能: 模拟看门狗。

◼ 中断的产生:

– 常规序列转换结束;

– 模拟看门狗事件。

◼ 过采样:

– 16位的数据寄存器;

– 可调整的过采样率,从2x到256x;

– 高达8位的可编程数据移位。

◼ ADC供电要求:

– 2.4V到3.6V,一般供电电压为3.3V。

◼ ADC输入范围: VREF- ≤VIN ≤VREF+。

– VREF- : ADC 负参考电压, VREF- = VSSA

– VREF+ : ADC 正参考电压, 2.6 V ≤ VREF+ ≤ VDDA

ADC 结构框图介绍

输入图片说明

6.3.硬件连接说明

输入图片说明

ADC的检测需要将输入阻抗和采样周期保持一定的关系,下表列出了以GD32E103为例子

输入图片说明

6.4.软件配置说明

查询法

查询法采用的是转换单个通道,或者扫描一序列的通道,通过不断切换通道的方式去读取对应通道的ADC数值。我们介绍使用库函数来设置 ADC0 的通道来进行 AD 转换的步骤,下面讲解其详细设置步骤:

开启 GPIO口时钟和 ADC0 时钟,设置GPIO口为模拟输入。

rcu_periph_clock_enable(RCU_GPIOA); /* enable GPIOB clock */ rcu_periph_clock_enable(RCU_GPIOB); /* enable ADC0 clock */ rcu_periph_clock_enable(RCU_ADC0); /* config ADC clock */ rcu_adc_clock_config(RCU_CKADC_CKAPB2_DIV4); /* enable alternate function clock */ rcu_periph_clock_enable(RCU_AF); //使能 GPIO 口复用

这里需要说明一下, ADC 的通道与引脚的对应关系在数据手册可以查到

输入图片说明

(1)配置 ADC 输入时钟分频,模式为独立模式,转换长度以及触发方式等

/* reset ADC */ adc_deinit(ADC0); /* ADC mode config */ adc_mode_config(ADC_MODE_FREE); //独立模式 /* ADC continous function enable */ adc_special_function_config(ADC0, ADC_SCAN_MODE, ENABLE) /* ADC data alignment config */ adc_data_alignment_config(ADC0, ADC_DATAALIGN_RIGHT); //ADC 数据右对齐 adc_special_function_config(ADC0,ADC_CONTINUOUS_MODE,DISABLE); /* ADC channel length config */ adc_channel_length_config(ADC0, ADC_REGULAR_CHANNEL, 1);//设置 ADC 转换的通道数量 /* ADC trigger config */ adc_external_trigger_source_config(ADC0,ADC_REGULAR_CHANNEL,ADC0_1_EXTTRIG_REGULAR_NONE); //通过软件触发 ADC 转换 adc_external_trigger_config(ADC0, ADC_REGULAR_CHANNEL, ENABLE);

(2)开启 AD 转换器

在设置完了以上信息后,我们就开启 AD 转换器了

/* enable ADC interface */ adc_enable(ADC0); delay_1ms(1);//延迟 等待稳定 /* ADC calibration and reset calibration */ adc_calibration_enable(ADC0);//使能 ADC 校准

(3)读取 ADC 值 在上面的步骤完成后, ADC 就算准备好了。所谓的查询法就是不断地进行通道切换

unsigned short adc0_transfer(unsigned char adc_channel) { uint16_t ADC_temp; /* ADC regular channel config */ adc_regular_channel_config(ADC0, 0, adc_channel, ADC_SAMPLETIME_55POINT5); adc_software_trigger_enable(ADC0,ADC_REGULAR_CHANNEL); while(!adc_flag_get(ADC0, ADC_FLAG_EOC));//等待转换完成 /* clear the end of conversion flag */ adc_flag_clear(ADC0, ADC_FLAG_EOC); ADC_temp=adc_regular_data_read(ADC0); return ADC_temp; }

这里还需要说明一下ADC的参考电压,是以Vref作为参考电压。

常规通道转换 DMA 搬运

通过ADC转换,在ADC 转换完成后 触发DMA 进行数据搬运。

DMA 请求,可以通过设置 ADC_CTL1 寄存器的 DMA 位来使能,它用于规则组多个通道的转换结果。 ADC 在规则组一个通道转换结束后产生一个 DMA 请求, DMA 接受到请求后可以将转换的数据从 ADC_RDATA 寄存器传输到用户指定的目的地址。

在和查询法一节的差别,主要在于ADC 的配置方面和DMA的配置

(1)ADC 的配置

/* ADC channel length config */ adc_channel_length_config(ADC0, ADC_REGULAR_CHANNEL, 4);//常规通道长度配置 /* ADC regular channel config */ adc_regular_channel_config(ADC0, 0, ADC_CHANNEL_4, ADC_SAMPLETIME_55POINT5); adc_regular_channel_config(ADC0, 1, ADC_CHANNEL_5, ADC_SAMPLETIME_55POINT5); adc_regular_channel_config(ADC0, 2, ADC_CHANNEL_6, ADC_SAMPLETIME_55POINT5); adc_regular_channel_config(ADC0, 3, ADC_CHANNEL_7, ADC_SAMPLETIME_55POINT5); /* ADC trigger config */ adc_external_trigger_source_config(ADC0,ADC_REGULAR_CHANNEL, ADC0_1_EXTTRIG_REGULAR_NONE); adc_external_trigger_config(ADC0, ADC_REGULAR_CHANNEL, ENABLE); /* ADC DMA function enable */ adc_dma_mode_enable(ADC0);//使能 DMA 模式 /* enable ADC interface */ adc_enable(ADC0); delay_1ms(1); /* ADC calibration and reset calibration */ adc_calibration_enable(ADC0);

(2)DMA的配置

/* ADC_DMA_channel configuration */ dma_parameter_struct dma_data_parameter; /* ADC DMA_channel configuration */ dma_deinit(DMA0, DMA_CH0); /* initialize DMA single data mode */ dma_data_parameter.periph_addr = (uint32_t)(&ADC_RDATA(ADC0)); //外设地址 dma_data_parameter.periph_inc = DMA_PERIPH_INCREASE_DISABLE; dma_data_parameter.memory_addr = (uint32_t)(&adc_value); //搬运目标地址 dma_data_parameter.memory_inc = DMA_MEMORY_INCREASE_ENABLE; dma_data_parameter.periph_width = DMA_PERIPHERAL_WIDTH_16BIT; dma_data_parameter.memory_width = DMA_MEMORY_WIDTH_16BIT; dma_data_parameter.direction = DMA_PERIPHERAL_TO_MEMORY; dma_data_parameter.number = 4; dma_data_parameter.priority = DMA_PRIORITY_HIGH; dma_init(DMA0, DMA_CH0, &dma_data_parameter); /* enable DMA circulation mode */ dma_circulation_enable(DMA0, DMA_CH0); /* enable DMA channel */ dma_channel_enable(DMA0, DMA_CH0);

(3)触发ADC 转换

adc_software_trigger_enable(ADC0,ADC_REGULAR_CHANNEL);

注入通道-中断

在和查询法一节的差别,主要在于ADC 的配置方面和注入通道会产生中断

(1)ADC 的配置

/* reset ADC */ adc_deinit(ADC0); /* ADC mode config */ adc_mode_config(ADC_MODE_FREE); /* ADC continous function enable */ adc_special_function_config(ADC0, ADC_SCAN_MODE, ENABLE); /* ADC data alignment config */ adc_data_alignment_config(ADC0, ADC_DATAALIGN_RIGHT); /* ADC channel length config *//注入通道配置 adc_channel_length_config(ADC0, ADC_INSERTED_CHANNEL, 4);//注入通道长度配置 /* ADC inserted channel config */ adc_inserted_channel_config(ADC0, 0, ADC_CHANNEL_0, ADC_SAMPLETIME_55POINT5); adc_inserted_channel_config(ADC0, 1, ADC_CHANNEL_1, ADC_SAMPLETIME_55POINT5); adc_inserted_channel_config(ADC0, 2, ADC_CHANNEL_2, ADC_SAMPLETIME_55POINT5); adc_inserted_channel_config(ADC0, 3, ADC_CHANNEL_3, ADC_SAMPLETIME_55POINT5); /* ADC trigger config */ //通过 EXTI 15 进行触发 adc_external_trigger_source_config(ADC0,ADC_INSERTED_CHANNEL,ADC0_1_EXTTRIG_INSERTED_EXTI_15); /* ADC external trigger enable */ adc_external_trigger_config(ADC0, ADC_INSERTED_CHANNEL, ENABLE); /* clear the ADC flag */ adc_interrupt_flag_clear(ADC0, ADC_INT_FLAG_EOC); adc_interrupt_flag_clear(ADC0, ADC_INT_FLAG_EOIC); /* enable ADC interrupt */ adc_interrupt_enable(ADC0, ADC_INT_EOIC);//使能注入通道的中断 /* enable ADC */ adc_enable(ADC0); delay_1ms(1); /* ADC calibration and reset calibration */ adc_calibration_enable(ADC0);

(2)ADC 注入通道转换完成服务函数

void ADC0_1_IRQHandler(void) { /* clear the ADC flag */ adc_interrupt_flag_clear(ADC0, ADC_INT_FLAG_EOIC);//清除注入通道转换完成标志位 /* read ADC inserted group data register */ inserted_data[0] = adc_inserted_data_read(ADC0, ADC_INSERTED_CHANNEL_0); inserted_data[1] = adc_inserted_data_read(ADC0, ADC_INSERTED_CHANNEL_1); inserted_data[2] = adc_inserted_data_read(ADC0, ADC_INSERTED_CHANNEL_2); inserted_data[3] = adc_inserted_data_read(ADC0, ADC_INSERTED_CHANNEL_3); }

6.5.ADC 使用注意事项

1、ADC通道的采集引脚未配置为模拟输入,GD32要求通道IO口必须配置为模拟输入;

2、ADC时钟过高,ADC采样时钟高于ADC最高采样时钟获取到的数据不具有参考意义,需要手动分频到合适的ADC 要求的频率;

3、ADC采样值偏小或不稳定,应该适当的降低ADC时钟,加大采样周期的值;

4、ADC的查询法在获取ADC数值的时候,不允许重入,即不允许在同一时间调用ADC的数据读取函数;

5、ADC在使能之后需要进行短暂的延时,时间周期约为2毫秒左右,以保证ADC能正常启动。

教程GD32 MCU方案商聚沃科技原创发布,了解更多GD32 MCU教程,关注聚沃科技官网

声明:本文内容及配图由入驻作者撰写或者入驻合作网站授权转载。文章观点仅代表作者本人,不代表电子发烧友网立场。文章及其配图仅供工程师学习之用,如有内容侵权或者其他违规问题,请联系本站处理。 举报投诉
  • 单片机
    +关注

    关注

    6030

    文章

    44482

    浏览量

    631706
  • mcu
    mcu
    +关注

    关注

    146

    文章

    16846

    浏览量

    349785
  • 嵌入式
    +关注

    关注

    5056

    文章

    18953

    浏览量

    301638
  • adc
    adc
    +关注

    关注

    97

    文章

    6381

    浏览量

    543654
  • 开发板
    +关注

    关注

    25

    文章

    4880

    浏览量

    96998
收藏 人收藏

    评论

    相关推荐

    GD32 MCU 入门教程GD32 MCU 常见外设介绍(12)FMC 模块介绍

    闪存控制器(FMC),提供了片上闪存需要的所有功能。FMC 也提供了页擦除,整片擦除,以及32 位整字或 16 位半字编程闪存等操作。 GD32 MCU 支持不同类型编程的具体说明如下表 GD32
    的头像 发表于 08-21 09:56 898次阅读
    <b class='flag-5'>GD32</b> <b class='flag-5'>MCU</b> <b class='flag-5'>入门教程</b>】<b class='flag-5'>GD32</b> <b class='flag-5'>MCU</b> <b class='flag-5'>常见外设</b><b class='flag-5'>介绍</b>(12)FMC <b class='flag-5'>模块</b><b class='flag-5'>介绍</b>

    GD32MCU介绍

    其实兆芯的MCU为了兼容ST,外设的寄存器设计与ST保持一致了。比如GD32VF103或者GD32E103系列的USBFS这个外设,基本等同
    发表于 11-01 06:03

    GD32 MCU原理及固件库开发指南》 + 初读感悟

    GD32 MCU原理固件库开发指南这本书内容丰富,囊括了GD32中的所有外设,书中首先介绍了如何使用MDK或IAR软件搭建
    发表于 03-31 22:11

    GD32 MCU原理及固件库开发指南》+读后感

    GD32 MCU的电源管理系统及复位、时钟系统。 第5章介绍GD32 MCU的基础外设,包括GP
    发表于 06-06 21:52

    兆易创新GD32 MCU选型手册,适用于GD32全系列MCU

    兆易创新GD32MCU选型手册,适用于GD32全系列MCUGD32MCU选型手册,适用于GD32全系列MCU
    发表于 10-19 17:26 49次下载

    你了解GD32 MCU的命名规则吗

    下面为大家介绍GD32 MCU的通用命名规则,以GD32F303ZGT6为例,其中,GD32代表GD32
    的头像 发表于 01-13 09:38 3342次阅读
    你了解<b class='flag-5'>GD32</b> <b class='flag-5'>MCU</b>的命名规则吗

    GD32 MCU的选项字节是什么?

    GD32 MCU的选项字节是什么,有什么功能呢?选项字节被误篡改如何回复?
    的头像 发表于 01-17 09:42 1158次阅读
    <b class='flag-5'>GD32</b> <b class='flag-5'>MCU</b>的选项字节是什么?

    不同型号的GD32 MCU如何区分?

    大家是否碰到过以下应用场景:同一套软件代码希望跑在不同型号的GD32 MCU中,但有些地方需要根据MCU型号进行调整?或者上位机或其他MCUGD3
    的头像 发表于 01-27 09:32 906次阅读
    不同型号的<b class='flag-5'>GD32</b> <b class='flag-5'>MCU</b>如何区分?

    GD32 MCU 入门教程】一、GD32 MCU 开发环境搭建(1)使用Keil开发GD32

    GD32系列为通用型MCU,所以开发环境也可以使用通用型的IDE,目前使用较多的是KEIL、IAR、 GCC和Embedded Builder,客户可以根据个人喜好来选择相应的开发环境。
    的头像 发表于 08-08 15:01 886次阅读
    【<b class='flag-5'>GD32</b> <b class='flag-5'>MCU</b> <b class='flag-5'>入门教程</b>】一、<b class='flag-5'>GD32</b> <b class='flag-5'>MCU</b> 开发环境搭建(1)使用Keil开发<b class='flag-5'>GD32</b>

    GD32 MCU 入门教程】一、GD32 MCU 开发环境搭建(2)使用 IAR 开发 GD32

    GD32系列为通用型MCU,所以开发环境也可以使用通用型的IDE,目前使用较多的是KEIL、IAR、 GCC和Embedded Builder,客户可以根据个人喜好来选择相应的开发环境。
    的头像 发表于 08-08 15:40 526次阅读
    【<b class='flag-5'>GD32</b> <b class='flag-5'>MCU</b> <b class='flag-5'>入门教程</b>】一、<b class='flag-5'>GD32</b> <b class='flag-5'>MCU</b> 开发环境搭建(2)使用 IAR 开发 <b class='flag-5'>GD32</b>

    GD32 MCU 入门教程】一、GD32 MCU 开发环境搭建(3)使用 Embedded Builder 开发 GD32

    GD32系列为通用型MCU,所以开发环境也可以使用通用型的IDE,目前使用较多的是KEIL、IAR、 GCC和Embedded Builder,客户可以根据个人喜好来选择相应的开发环境。
    的头像 发表于 08-08 16:03 729次阅读
    【<b class='flag-5'>GD32</b> <b class='flag-5'>MCU</b> <b class='flag-5'>入门教程</b>】一、<b class='flag-5'>GD32</b> <b class='flag-5'>MCU</b> 开发环境搭建(3)使用 Embedded Builder 开发 <b class='flag-5'>GD32</b>

    GD32 MCU 入门教程】二、GD32 MCU 烧录说明(1)ISP 烧录

    ISP:In System Programing,在系统编程,通过MCU片内的引导程序进行Flash编程。 GD32片内有一个只读信息块,用于存放引导装载程序,引导程序在MCU出厂前就会提前烧录好
    的头像 发表于 08-08 16:20 652次阅读
    【<b class='flag-5'>GD32</b> <b class='flag-5'>MCU</b> <b class='flag-5'>入门教程</b>】二、<b class='flag-5'>GD32</b> <b class='flag-5'>MCU</b> 烧录说明(1)ISP 烧录

    GD32 MCU 入门教程GD32 MCU 常见外设介绍(14)RTC 模块介绍

    GD32 MCU内部提供了一个RTC(实时时钟)模块,通过RTC可以实现日历时钟、闹钟等功能。RTC也可以用于深度睡眠或待机模式的低功耗唤醒。不同系列的GD32
    的头像 发表于 08-23 09:18 337次阅读
    【<b class='flag-5'>GD32</b> <b class='flag-5'>MCU</b> <b class='flag-5'>入门教程</b>】<b class='flag-5'>GD32</b> <b class='flag-5'>MCU</b> <b class='flag-5'>常见外设</b><b class='flag-5'>介绍</b>(14)RTC <b class='flag-5'>模块</b><b class='flag-5'>介绍</b>

    GD32 MCU 入门教程GD32 MCU FPU 使用方法

    GD32 MCU FPU 使用方法
    的头像 发表于 08-25 09:24 394次阅读
    【<b class='flag-5'>GD32</b> <b class='flag-5'>MCU</b> <b class='flag-5'>入门教程</b>】<b class='flag-5'>GD32</b> <b class='flag-5'>MCU</b> FPU 使用方法

    GD32 MCU入门教程GD32 MCU GPIO 结构与使用注意事项

    本文是专门为基于GD32 MCU开发的工程设计人员提供,主要介绍了GPIO的功能配置、内部结构以及在不同场景使用时的注意事项,旨在帮助GD32 MC
    的头像 发表于 09-07 10:34 489次阅读
    【<b class='flag-5'>GD32</b> <b class='flag-5'>MCU</b><b class='flag-5'>入门教程</b>】<b class='flag-5'>GD32</b> <b class='flag-5'>MCU</b> GPIO 结构与使用注意事项