STM32 ADC单/多通道采样+DMA搬运

这篇具有很好参考价值的文章主要介绍了STM32 ADC单/多通道采样+DMA搬运。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

一、ADC介绍

adc多通道采样,stm32,单片机,嵌入式硬件
通过介绍我们可以了解到,ADC是12位的转换器,所以采样值范围是0~4095。18个通道可同时进行转换,也可以单独转换某个通道。

二、单通道单次ADC采样

使用ADC的流程应为:

  1. 初始化IO口。
    我这里使用的是PA1进行采样,也就是ADC1的通道1
void ADC_GPIO_Init(void)
{
	
	GPIO_InitTypeDef GPIO_InitStructure;
	RCC_APB2PeriphClockCmd( RCC_APB2Periph_GPIOA, ENABLE);//打开IO时钟
	
	//配置ADC对应的IO为模拟输入
	GPIO_InitStructure.GPIO_Pin = GPIO_Pin_1;
	GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AIN ;
	GPIO_Init(GPIOA,&GPIO_InitStructure);//初始化结构体
}
  1. 初始化ADC。
void ADC1_Init(void)
{	
	

	ADC_InitTypeDef ADC_InitStructure; 
	
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_ADC1,ENABLE);
	RCC_ADCCLKConfig(RCC_PCLK2_Div6);
	
	ADC_DeInit(ADC1);
	ADC_InitStructure.ADC_Mode = ADC_Mode_Independent;//ADC1工作在独立模式
	ADC_InitStructure.ADC_ScanConvMode = DISABLE;//单通道模式
	ADC_InitStructure.ADC_ContinuousConvMode =DISABLE;//单次转换
	ADC_InitStructure.ADC_ExternalTrigConv = ADC_ExternalTrigConv_None;//软件触发转换
	ADC_InitStructure.ADC_DataAlign=ADC_DataAlign_Right;//数据右对齐

	ADC_InitStructure.ADC_NbrOfChannel=1;//顺序转化的ADC通道数量


	ADC_Init(ADC1,&ADC_InitStructure);
	
	//耗时 1/14KHz*239 ≈ 17.07us
	ADC_RegularChannelConfig(ADC1,ADC_Channel_1,1,ADC_SampleTime_239Cycles5);

	
	ADC_Cmd(ADC1,ENABLE);

	/*ADC校准*/
	ADC_ResetCalibration(ADC1);
	while(ADC_GetResetCalibrationStatus(ADC1));
	ADC_StartCalibration(ADC1);
	while(ADC_GetCalibrationStatus(ADC1));
}
  1. 转换、获取采样值。
uint16_t ReadADC(void)
{
  ADC_SoftwareStartConvCmd(ADC1, ENABLE);		//启用ADC软件转换
  while(!ADC_GetFlagStatus(ADC1, ADC_FLAG_EOC));//等待转换结束
  return ADC_GetConversionValue(ADC1);	//返回最近一次ADC1的转换结果
}

三、多通道采样+DMA搬运

多通道的时候我们一般用DMA来搬运数据,与单通道不同的是,ADC配置时有些变化,DMA需要进行配置。

void ADC1_Init(void)
{	
	

	ADC_InitTypeDef ADC_InitStructure; 
	DMA_InitTypeDef DMA_InitStructure;
	
	RCC_AHBPeriphClockCmd(RCC_AHBPeriph_DMA1, ENABLE);
	
	/*使能DMA通道1*/
	DMA_DeInit(DMA1_Channel1);
	DMA_InitStructure.DMA_PeripheralBaseAddr = (uint32_t)(&(ADC1->DR));
	DMA_InitStructure.DMA_MemoryBaseAddr = (uint32_t) &DMA_Getvalue;//DMA_Getvalue[10]; 搬运数据的存放地址
	DMA_InitStructure.DMA_DIR = DMA_DIR_PeripheralSRC;
	DMA_InitStructure.DMA_BufferSize = 10; // 每次传输10个通道的值,就停止
	DMA_InitStructure.DMA_PeripheralInc = DMA_PeripheralInc_Disable;//存储地址固定
	DMA_InitStructure.DMA_MemoryInc = DMA_MemoryInc_Enable;//递增模式,可将上面的数组填充完整,否则永远是第一个
	DMA_InitStructure.DMA_PeripheralDataSize=DMA_PeripheralDataSize_HalfWord;
	DMA_InitStructure.DMA_MemoryDataSize = DMA_MemoryDataSize_HalfWord;
	DMA_InitStructure.DMA_Mode = DMA_Mode_Circular;
	DMA_InitStructure.DMA_Priority = DMA_Priority_High;
	DMA_InitStructure.DMA_M2M = DMA_M2M_Disable;
	DMA_Init(DMA1_Channel1,&DMA_InitStructure);
	
	DMA_Cmd(DMA1_Channel1,ENABLE);	
	
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_ADC1,ENABLE);
	RCC_ADCCLKConfig(RCC_PCLK2_Div6);
	
	/*ADC1工作模式为扫描模式、单次转换、14个通道、数据右对齐,*/
	ADC_DeInit(ADC1);
	ADC_InitStructure.ADC_Mode = ADC_Mode_Independent;
	ADC_InitStructure.ADC_ScanConvMode = ENABLE;
	ADC_InitStructure.ADC_ContinuousConvMode =DISABLE;
	ADC_InitStructure.ADC_ExternalTrigConv = ADC_ExternalTrigConv_None;
	ADC_InitStructure.ADC_DataAlign=ADC_DataAlign_Right;

	ADC_InitStructure.ADC_NbrOfChannel=SixChannelMax;


	ADC_Init(ADC1,&ADC_InitStructure);
	
	//排列好各通道的顺序,此顺序对应DMA数组内数据的顺序
	ADC_RegularChannelConfig(ADC1,ADC_Channel_1,1,ADC_SampleTime_239Cycles5);
	ADC_RegularChannelConfig(ADC1,ADC_Channel_2,2,ADC_SampleTime_239Cycles5);
	ADC_RegularChannelConfig(ADC1,ADC_Channel_3,3,ADC_SampleTime_239Cycles5);
	ADC_RegularChannelConfig(ADC1,ADC_Channel_4,4,ADC_SampleTime_239Cycles5);
	ADC_RegularChannelConfig(ADC1,ADC_Channel_5,5,ADC_SampleTime_239Cycles5);
	ADC_RegularChannelConfig(ADC1,ADC_Channel_6,6,ADC_SampleTime_239Cycles5);
	ADC_RegularChannelConfig(ADC1,ADC_Channel_7,7,ADC_SampleTime_239Cycles5);
	ADC_RegularChannelConfig(ADC1,ADC_Channel_8,8,ADC_SampleTime_239Cycles5);
	ADC_RegularChannelConfig(ADC1,ADC_Channel_9,9,ADC_SampleTime_239Cycles5);
	ADC_RegularChannelConfig(ADC1,ADC_Channel_10,10,ADC_SampleTime_239Cycles5);

	
	ADC_DMACmd(ADC1,ENABLE);
	
	ADC_Cmd(ADC1,ENABLE);

	/*ADC校准*/
	ADC_ResetCalibration(ADC1);
	while(ADC_GetResetCalibrationStatus(ADC1));
	ADC_StartCalibration(ADC1);
	while(ADC_GetCalibrationStatus(ADC1));
	
	/*启用ADC软件转换*/
	ADC_SoftwareStartConvCmd(ADC1,ENABLE);
}

然后获取转化值函数也发生相应的改变,此函数可以放在一个定时中断或定时任务中,固定多少间隔去读取

void Read_ADCValue(void)
{
	uint32_t Value[10];
	ADC_Cmd(ADC1,DISABLE);//先失能ADC
	int i = 0;

	//将读取到的值保存
	for(i =0; i < 10; i++)
	{
		Value[i] += DMA_Getvalue[i];//将搬运的数据取出
	}
	memset(DMA_Getvalue,0,sizeof(DMA_Getvalue));		//每次读取数据后清空DMA存储空间
	
	ADC_Cmd(ADC1,ENABLE);//使能ADC
	ADC_SoftwareStartConvCmd(ADC1, ENABLE);//开始转换
}

读取函数也可以使用DMA中断,进行配置然后在中断内取出数据即可。文章来源地址https://www.toymoban.com/news/detail-634962.html

到了这里,关于STM32 ADC单/多通道采样+DMA搬运的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • STM32CubeMX配置ADC采样(轮询、中断、DMA)

    STM32CubeMX能够极大减小STM32外设配置的工作量,因此作者也借助空闲时间对STM32CubeMX相关配置进行了学习,本文介绍如何利用STM32CubeMX配置ADC采样,记录了作者学习过程中遇到的问题及解决办法,使大家少走弯路,并方便以后复习 先选择所使用的MCU,这里我使用的是STM32F407ZGT系

    2024年02月03日
    浏览(44)
  • STM32-单通道ADC采集(DMA读取)实验

    关于ADC的一些原理和实验我们已经有了2篇笔记,链接如下: 关于ADC的笔记1_Mr_rustylake的博客-CSDN博客 STM32-ADC单通道采集实验_Mr_rustylake的博客-CSDN博客 实验要求:通过ADC1通道1(PA1)采集电位器的电压,并显示ADC转换的数字量和换算后的电压值。 我们通过下表可以知道DMA1通道

    2024年02月16日
    浏览(42)
  • STM32F103采用DMA方式多路ADC采样

    stm32采用DMA方式进行ADC采样可以高效的进行数据采集,不用cpu实时参与,以节省单片机资源,让单片机可以在同一时间里干更多事,STM32F103 ADC为12位ADC的,是一种逐次逼近型模拟数字转换器,它有多达18个通道,可测量16个外部和2个内部信号源。各通道的A/D转换可以单次、连续

    2024年02月06日
    浏览(40)
  • STM32CubeMX配置-ADC多通道配置(DMA) (STM32G070)

    一、写在前面         ADC通道采集数据的两种方式:         1)ADC轮询采集数据直接放到数组中;         2)采用中断方式,ADC采集完成进入中断,中断关闭ADC采集,取数据之后再打开ADC采集。 以下按第一种方式实现: 二、ADC多通道配置 1)配置通道及参数     如果要控

    2024年02月05日
    浏览(41)
  • STM32-微项目10-ADC多通道采集+DMA数据转移

    一、微项目实现目标: 由于ADC多通道采集在规则组中只有一个寄存器CR,实际上在多通道采集时刻,需要把每一个同都的数据及时传出,否则上一个通道的数据会被当前通道的数据给覆盖掉。 二、微项目硬件配置需求:  stm32F103C8T6核心板一块 0.96寸OLED显示,用于显示计数 三

    2024年02月16日
    浏览(49)
  • STM32F103:ADC采样——定时器触发+DMA传输

    实现ADC多通道采样,采用DMA传输,采样由定时器触发 初始化代码:

    2024年02月14日
    浏览(35)
  • 定时器(PWM输出)触发ADC采样(DMA)——STM32CubeMX

    我用的单片机是STM32F103CBTX 定时器:使用PWM输出的模式 ADC:使用DMA的模式 (在不使用DMA的情况下,定时器控制ADC进行数据采集只能是单通道!如果开启了多通道,读取到的ADC采集值只会是最后一个通道的值!所以,要想使用定时器控制ADC采集 多通道 , 必须使用DMA !)  看

    2024年04月10日
    浏览(46)
  • STM32CubeMx实现ADC多通道+DMA读取(HAL库)

    目录 一、实验结果  二、STM32CubeMx配置 三、main.c测试代码 1、RCC配置 (外部晶振选择8MHz。设置相应的分频器M=8,倍频器倍频系数N=336,分频器分频系数P=2,那么主PLL生成的第一个输出高速时钟PLLP为:168MHz)  2、SYS配置  3、ADC(规则)通道配置(独立模式,预分频4分频,1

    2024年02月15日
    浏览(44)
  • STM32 hal库使用笔记(五)ADC—单通道/双通道DMA传输

    实现目的:利用ADC采集光敏传感器/烟雾传感器的值,并利用串口打印 实验平台:正点原子精英版 一、简介 1.DMA的介绍 参考:STM32 hal库使用笔记(四)DMA—内存到内存/内存到外设_乱码小伙的博客-CSDN博客 2.ADC简介      ADC(Analog-Digital Converter)模拟-数字转换器 ADC可以将引脚

    2024年02月03日
    浏览(49)
  • STM32F407 ADC+DMA+定时器 定时采样模拟量

    项目中需要对多个通道的电压进行一定频率的AD采样,由于采样过程贯穿整个任务,为了使采样过程尽可能不占用CPU资源,采用定时器触发的多通道ADC扫描采样,且采样数据由DMA传到RAM中的缓存。 这样做有以下几个好处:1、由定时器触发ADC采样,这样采样的频率可控,且定时

    2024年02月14日
    浏览(43)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包