OpenEdv-开源电子网

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

请教关于SDADC+DMA的问题

[复制链接]

7

主题

28

帖子

0

精华

初级会员

Rank: 2

积分
86
金钱
86
注册时间
2014-7-27
在线时间
8 小时
发表于 2014-8-3 14:25:19 | 显示全部楼层 |阅读模式
5金钱
平台:STM32F373

我用SDADC+DMA采集外部电压,采集到的数值特别小。如果配置为SDADC+中断读取数值的方式,数值就正常。
请教高手可能的原因?


SDADC+DMA,采集多个数据,数值特别小


用SDADC中断的方式,采集到的数据是正常的。

请教高手这个问题可能的原因!
谢谢!

最佳答案

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

不好意思。打扰了。 问题解决。 DMA_InitStructure.DMA_PeripheralDataSize = DMA_MemoryDataSize_Word; //这句跑偏了。
正点原子逻辑分析仪DL16劲爆上市
回复

使用道具 举报

7

主题

28

帖子

0

精华

初级会员

Rank: 2

积分
86
金钱
86
注册时间
2014-7-27
在线时间
8 小时
 楼主| 发表于 2014-8-3 14:25:20 | 显示全部楼层
不好意思。打扰了。
问题解决。
DMA_InitStructure.DMA_PeripheralDataSize = DMA_MemoryDataSize_Word; //这句跑偏了。
回复

使用道具 举报

7

主题

28

帖子

0

精华

初级会员

Rank: 2

积分
86
金钱
86
注册时间
2014-7-27
在线时间
8 小时
 楼主| 发表于 2014-8-3 14:27:20 | 显示全部楼层
代码基本参考自ST的官方固件
uint32_t SDADC1_Config(void)
{
  SDADC_AINStructTypeDef SDADC_AINStructure;
  GPIO_InitTypeDef   GPIO_InitStructure;
  NVIC_InitTypeDef NVIC_InitStructure;
  uint32_t SDADCTimeout = 0;
  
  /* MPX2102_SDADC APB2 interface clock enable */
  RCC_APB2PeriphClockCmd(MPX2102_SDADC_CLK, ENABLE);

  /* WR APB1 interface clock enable */
  RCC_APB1PeriphClockCmd(RCC_APB1Periph_PWR, ENABLE);
  /* Enable MPX2102_SDADC analog interface */
  WR_SDADCAnalogCmd(MPX2102_SDADC_PWR, ENABLE);

  /* Set the SDADC divider: The SDADC should run @6MHz */
  /* If Sysclk is 72MHz, SDADC divider should be 12 */
  RCC_SDADCCLKConfig(RCC_SDADCCLK_SYSCLK_Div12);

  /* GPIOE eripheral clock enable */
  RCC_AHBPeriphClockCmd(RCC_AHBPeriph_GPIOB, ENABLE);

  /* MPX2102_SDADC channel 8P (PE8)  and channel 8N (PE9) */
  GPIO_InitStructure.GPIO_Mode  = GPIO_Mode_AN;
  GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_NOPULL;
  GPIO_InitStructure.GPIO_Pin   = MPX2102_GPIO_PIN_P | MPX2102_GPIO_PIN_N;
  GPIO_Init(MPX2102_SDADC_GPIO_PORT, &GPIO_InitStructure);

  /* Select External reference: The reference voltage selection is available
     only in SDADC1 and therefore to select the VREF for SDADC2/SDADC3, SDADC1
     clock must be already enabled */
  SDADC_VREFSelect(MPX2102_SDADC_VREF);
  /* Insert delay equal to ~5 ms */
  Delay(5000);
  
  /* Enable MPX2102_SDADC */
  SDADC_Cmd(MPX2102_SDADC, ENABLE);

  /* Enter initialization mode */
  SDADC_InitModeCmd(MPX2102_SDADC, ENABLE);
  SDADCTimeout = SDADC_INIT_TIMEOUT;
  /* wait for INITRDY flag to be set */
  while((SDADC_GetFlagStatus(MPX2102_SDADC, SDADC_FLAG_INITRDY) == RESET) && (--SDADCTimeout != 0));

  if(SDADCTimeout == 0)
  {
    /* INITRDY flag is not set */
    return 1;
  }

  /* Analog Input configuration conf0: use differential mode and gain = 4 */
  SDADC_AINStructure.SDADC_InputMode = SDADC_InputMode_Diff;
  SDADC_AINStructure.SDADC_Gain = MPX2102_SDADC_GAIN;
  SDADC_AINStructure.SDADC_CommonMode = SDADC_CommonMode_VSSA;
  SDADC_AINStructure.SDADC_Offset = 0;
  SDADC_AINInit(MPX2102_SDADC, SDADC_Conf_0, &SDADC_AINStructure);

  /* select MPX2102_SDADC channel 8 to use conf0 */
  SDADC_ChannelConfig(MPX2102_SDADC, MPX2102_SDADC_CHANNEL, SDADC_Conf_0);

  /* select channel 8 */
  SDADC_InjectedChannelSelect(MPX2102_SDADC, MPX2102_SDADC_CHANNEL);
  /* Select an external trigger */
  SDADC_ExternalTrigInjectedConvConfig(MPX2102_SDADC, SDADC_ExternalTrigInjecConv_T19_CC2);
  /* Select rising edge */
  SDADC_ExternalTrigInjectedConvEdgeConfig(MPX2102_SDADC, SDADC_ExternalTrigInjecConvEdge_Rising);

  /* Exit initialization mode */
  SDADC_InitModeCmd(MPX2102_SDADC, DISABLE);
SDADC_DMAConfig(SDADC1, SDADC_DMATransfer_Injected, ENABLE);
  /* Enable end of injected conversion interrupt */
//  SDADC_ITConfig(MPX2102_SDADC, SDADC_IT_JEOC, ENABLE);

//  /* NVIC Configuration */
//  NVIC_InitStructure.NVIC_IRQChannel = SDADC1_IRQn;
//  NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0;
//  NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0;
//  NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
//  NVIC_Init(&NVIC_InitStructure);

  /* configure calibration to be performed on conf0 */
  SDADC_CalibrationSequenceConfig(MPX2102_SDADC, SDADC_CalibrationSequence_1);
  /* start MPX2102_SDADC Calibration */
  SDADC_StartCalibration(MPX2102_SDADC);
  /* Set calibration timeout: 5.12 ms at 6 MHz in a single calibration sequence */
  SDADCTimeout = SDADC_CAL_TIMEOUT;
  /* wait for MPX2102_SDADC Calibration process to end */
  while((SDADC_GetFlagStatus(MPX2102_SDADC, SDADC_FLAG_EOCAL) == RESET) && (--SDADCTimeout != 0));

  if(SDADCTimeout == 0)
  {
    /* EOCAL flag can not set */
    return 2;
  }

  return 0;
}

void DMA2_Config(void)
{

DMA_InitTypeDef DMA_InitStructure;
NVIC_InitTypeDef NVIC_InitStructure;
/* DMA2 clock enable */
  RCC_AHBPeriphClockCmd(RCC_AHBPeriph_DMA2,ENABLE);


  /* DMA2 Channel3 Config */
  DMA_DeInit(DMA2_Channel3);
  DMA_InitStructure.DMA_PeripheralBaseAddr = (uint32_t)SDADC1_JDATAR;
  DMA_InitStructure.DMA_MemoryBaseAddr = (uint32_t)InjectedConvData;
  DMA_InitStructure.DMA_DIR = DMA_DIR_PeripheralSRC;
  DMA_InitStructure.DMA_BufferSize = ADCConvertNum;
  DMA_InitStructure.DMA_PeripheralInc = DMA_PeripheralInc_Disable;
  DMA_InitStructure.DMA_MemoryInc = DMA_MemoryInc_Enable;
  DMA_InitStructure.DMA_PeripheralDataSize = DMA_MemoryDataSize_Word;
  DMA_InitStructure.DMA_MemoryDataSize = DMA_MemoryDataSize_Word;
  DMA_InitStructure.DMA_Mode = DMA_Mode_Circular;
  DMA_InitStructure.DMA_Priority = DMA_Priority_VeryHigh;
  DMA_InitStructure.DMA_M2M = DMA_M2M_Disable;
  DMA_Init(DMA2_Channel3, &DMA_InitStructure);

  /* DMA2 Channel3 enable */

  //DMA_ITConfig(DMA2_Channel3, DMA_IT_TC, DISABLE);
NVIC_InitStructure.NVIC_IRQChannel = DMA2_Channel3_IRQn;
 NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 4;
 NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0;
 NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
 NVIC_Init(&NVIC_InitStructure);
 DMA_ITConfig(DMA2_Channel3, DMA_IT_TC, ENABLE);
DMA_Cmd(DMA2_Channel3, ENABLE);
回复

使用道具 举报

7

主题

28

帖子

0

精华

初级会员

Rank: 2

积分
86
金钱
86
注册时间
2014-7-27
在线时间
8 小时
 楼主| 发表于 2014-8-3 15:10:48 | 显示全部楼层
 DMA_CCR3 寄存器的PSIZE位为0x00,也就是说是8bit数据。不知道为什么会这样?

回复

使用道具 举报

530

主题

11万

帖子

34

精华

管理员

Rank: 12Rank: 12Rank: 12

积分
165538
金钱
165538
注册时间
2010-12-1
在线时间
2117 小时
发表于 2014-8-4 00:07:08 | 显示全部楼层
回复【4楼】txmsszd:
---------------------------------
谢谢分享
我是开源电子网www.openedv.com站长,有关站务问题请与我联系。
正点原子STM32开发板购买店铺http://openedv.taobao.com
正点原子官方微信公众平台,点击这里关注“正点原子”
回复

使用道具 举报

1

主题

3

帖子

0

精华

新手入门

积分
27
金钱
27
注册时间
2014-8-7
在线时间
0 小时
发表于 2014-8-7 10:10:14 | 显示全部楼层
回复【4楼】txmsszd:
---------------------------------
请问楼主,你这里说的是什么意思,跑偏?不能用Word吗?@txmsszd
回复

使用道具 举报

7

主题

28

帖子

0

精华

初级会员

Rank: 2

积分
86
金钱
86
注册时间
2014-7-27
在线时间
8 小时
 楼主| 发表于 2014-8-26 22:25:14 | 显示全部楼层
回复【6楼】深枭:
---------------------------------
DMA_InitStructure.DMA_PeripheralDataSize = DMA_MemoryDataSize_Word; 
这句把Memory的参数用在了peripheral了。应该是这样的
DMA_InitStructure.DMA_PeripheralDataSize = DMA_PeripheralDataSize_Word;
回复

使用道具 举报

1

主题

3

帖子

0

精华

新手入门

积分
27
金钱
27
注册时间
2014-8-7
在线时间
0 小时
发表于 2014-8-26 23:56:59 | 显示全部楼层
回复【7楼】txmsszd:
---------------------------------
嗯,看了一下相应的定义,在CCR中,DMA_MemoryDataSize_Word是((uint32_t)0x00000800),
DMA_PeripheralDataSize_Word是((uint32_t)0x00000200),之前没注意看你的程序,故有此疑问。
回复

使用道具 举报

13

主题

57

帖子

0

精华

初级会员

Rank: 2

积分
193
金钱
193
注册时间
2014-9-11
在线时间
15 小时
发表于 2015-5-22 13:58:07 | 显示全部楼层
楼主,你参考的固件库是STM32cubef3下的STM32373C_EVAL文件下的Examples下sdadc下的例程吗?我怎么看着这下面的例程调用的都是封装好的函数
回复

使用道具 举报

0

主题

6

帖子

0

精华

新手上路

积分
29
金钱
29
注册时间
2016-3-29
在线时间
7 小时
发表于 2016-4-3 11:09:26 | 显示全部楼层

自己编写的程序,SDADC使用的方式,集中不同的方式
回复

使用道具 举报

0

主题

6

帖子

0

精华

新手上路

积分
29
金钱
29
注册时间
2016-3-29
在线时间
7 小时
发表于 2016-4-3 11:10:10 | 显示全部楼层
可以在21ic网站上下载。
回复

使用道具 举报

2

主题

23

帖子

0

精华

初级会员

Rank: 2

积分
95
金钱
95
注册时间
2020-3-24
在线时间
19 小时
发表于 2020-11-19 13:29:57 | 显示全部楼层
楼主做过SDADC+DMA多通道的采集没,最近在这里遇到问题了,希望能交流下。
回复

使用道具 举报

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

本版积分规则



关闭

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

正点原子公众号

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

GMT+8, 2025-6-15 15:03

Powered by OpenEdv-开源电子网

© 2001-2030 OpenEdv-开源电子网

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