AnsweredAssumed Answered

ADC/DMA out of sync

Question asked by ebommer on Dec 18, 2014
Latest reply on Dec 19, 2014 by ebommer
I am having an issue where my index from the ADC to Memory is being shifted.  The data being copied to my array is off by "-1".  I have looked at my code and not seeing anything there that could cause such an issue.  I have an other example that used the exact same routine and it works correctly on the same HW, so I know its something in my project but I am not sure what else other then setting up the rank position that would affect the placement of the data.  I have used beyond compare to review my 2 ADC files(working and file with data offset by "-1") both "C" and "H" and there are no differences.  All I can assume is there is something that is affecting the DMA transfer, but I am not sure what I should be looking at for a clue.  The values are correct but in the wrong spot.  This has worked correct on my project for the last month and stopped today, but I was not modify anything to do with the ADC.  

Thanks 

/* Private variables ---------------------------------------------------------*/
 
#define ADC1_DR_Address    ((uint32_t)0x50000040)
#define ADC2_DR_Address    ((uint32_t)0x50001040)
 
uint16_t ADC1_Buffer[7];
uint16_t ADC2_Buffer[4];
 
uint16_t PrevADC_Read[11];
uint16_t CurrentADC_Read[11];
const float ADC_Constant = 0.25;
 
 
 
void ADC2_Read(void);
void MX_ADC1_Init(void);
void MX_ADC2_Init(void);
 
ADC_HandleTypeDef hadc1;
ADC_HandleTypeDef hadc2;
DMA_HandleTypeDef hdma_adc1;
DMA_HandleTypeDef hdma_adc2;
/* USER CODE END 0 */
 
void ADC_Read(void)
{
    CurrentADC_Read[LH_TRANS_TEMP] = PrevADC_Read[LH_TRANS_TEMP] + (( ADC1_Buffer[LH_TRANS_TEMP]-PrevADC_Read[LH_TRANS_TEMP] )* ADC_Constant);
    PrevADC_Read[LH_TRANS_TEMP] = CurrentADC_Read[LH_TRANS_TEMP];
     
    CurrentADC_Read[RH_TRANS_TEMP] = PrevADC_Read[RH_TRANS_TEMP] + (( ADC1_Buffer[RH_TRANS_TEMP]-PrevADC_Read[RH_TRANS_TEMP] )* ADC_Constant);
    PrevADC_Read[RH_TRANS_TEMP] = CurrentADC_Read[RH_TRANS_TEMP];
  
   CurrentADC_Read[ENG_TEMP] = PrevADC_Read[ENG_TEMP] + (( ADC1_Buffer[ENG_TEMP]-PrevADC_Read[ENG_TEMP] )* ADC_Constant);
    PrevADC_Read[ENG_TEMP] = CurrentADC_Read[ENG_TEMP];
  
   CurrentADC_Read[CUTTING_CLUTCH_CURRENT] = PrevADC_Read[CUTTING_CLUTCH_CURRENT] + (( ADC1_Buffer[CUTTING_CLUTCH_CURRENT]-PrevADC_Read[CUTTING_CLUTCH_CURRENT] )* ADC_Constant);
    PrevADC_Read[CUTTING_CLUTCH_CURRENT] = CurrentADC_Read[CUTTING_CLUTCH_CURRENT];
  
   CurrentADC_Read[GOVERNOR] = PrevADC_Read[GOVERNOR] + (( ADC1_Buffer[GOVERNOR]-PrevADC_Read[GOVERNOR] )* ADC_Constant);
    PrevADC_Read[GOVERNOR] = CurrentADC_Read[GOVERNOR];
  
   CurrentADC_Read[SUPPLY_VOLTAGE] = PrevADC_Read[SUPPLY_VOLTAGE] + (( ADC1_Buffer[SUPPLY_VOLTAGE]-PrevADC_Read[SUPPLY_VOLTAGE] )* ADC_Constant);
    PrevADC_Read[SUPPLY_VOLTAGE] = CurrentADC_Read[SUPPLY_VOLTAGE];
  
   CurrentADC_Read[FUEL_SENDER] = PrevADC_Read[FUEL_SENDER] + (( ADC1_Buffer[FUEL_SENDER]-PrevADC_Read[FUEL_SENDER] )* ADC_Constant);
    PrevADC_Read[FUEL_SENDER] = CurrentADC_Read[FUEL_SENDER];
 /*         ADC2                */
   CurrentADC_Read[CUTTING_CLUTCH] = PrevADC_Read[CUTTING_CLUTCH] + (( ADC2_Buffer[0]-PrevADC_Read[CUTTING_CLUTCH] )* ADC_Constant);
    PrevADC_Read[CUTTING_CLUTCH] = CurrentADC_Read[CUTTING_CLUTCH];
  
  
}
/* ADC1 init function */
void MX_ADC1_Init(void)
{
 
  ADC_ChannelConfTypeDef sConfig;
 
    /**Common config     */
  hadc1.Instance = ADC1;
  hadc1.Init.ClockPrescaler = ADC_CLOCK_ASYNC;
  hadc1.Init.Resolution = ADC_RESOLUTION12b;
  hadc1.Init.ScanConvMode = ENABLE;
  hadc1.Init.ContinuousConvMode = ENABLE;
  hadc1.Init.DiscontinuousConvMode = DISABLE;
  hadc1.Init.NbrOfDiscConversion = 1;
  hadc1.Init.ExternalTrigConvEdge = ADC_EXTERNALTRIGCONVEDGE_NONE;
  hadc1.Init.DataAlign = ADC_DATAALIGN_RIGHT;
  hadc1.Init.NbrOfConversion = 7;
  hadc1.Init.DMAContinuousRequests = ENABLE;
  hadc1.Init.EOCSelection = EOC_SINGLE_CONV;
  hadc1.Init.LowPowerAutoWait = DISABLE;
  hadc1.Init.Overrun = OVR_DATA_OVERWRITTEN;
  HAL_ADC_Init(&hadc1);
 
    /**Configure Regular Channel
    */
  sConfig.SingleDiff = ADC_SINGLE_ENDED;
  sConfig.SamplingTime = ADC_SAMPLETIME_1CYCLE_5;
  sConfig.OffsetNumber = ADC_OFFSET_NONE;
  sConfig.Offset = 0;
 
  sConfig.Channel = ADC_CHANNEL_1;
  sConfig.Rank = 1;
  HAL_ADC_ConfigChannel(&hadc1, &sConfig);
 
    /**Configure Regular Channel
    */
  sConfig.Channel = ADC_CHANNEL_2;
  sConfig.Rank = 2;
  HAL_ADC_ConfigChannel(&hadc1, &sConfig);
 
    /**Configure Regular Channel
    */
  sConfig.Channel = ADC_CHANNEL_3;
  sConfig.Rank = 3;
  HAL_ADC_ConfigChannel(&hadc1, &sConfig);
 
    /**Configure Regular Channel
    */
  sConfig.Channel = ADC_CHANNEL_4;
  sConfig.Rank = 4;
  HAL_ADC_ConfigChannel(&hadc1, &sConfig);
 
    /**Configure Regular Channel
    */
  sConfig.Channel = ADC_CHANNEL_5;
  sConfig.Rank = 5;
  HAL_ADC_ConfigChannel(&hadc1, &sConfig);
 
    /**Configure Regular Channel
    */
  sConfig.Channel = ADC_CHANNEL_6;
  sConfig.Rank = 6;
  HAL_ADC_ConfigChannel(&hadc1, &sConfig);
 
    /**Configure Regular Channel
    */
  sConfig.Channel = ADC_CHANNEL_8;
  sConfig.Rank = 7;
  HAL_ADC_ConfigChannel(&hadc1, &sConfig);
   
  HAL_ADC_Start_DMA(&hadc1, (uint32_t*)(&ADC1_Buffer[0]), 7);
 
}
/* ADC2 init function */
void MX_ADC2_Init(void)
{
 
  ADC_ChannelConfTypeDef sConfig;
 
    /**Common config
    */
  hadc2.Instance = ADC2;
  hadc2.Init.ClockPrescaler = ADC_CLOCK_ASYNC;
  hadc2.Init.Resolution = ADC_RESOLUTION12b;
  hadc2.Init.ScanConvMode = ENABLE;
  hadc2.Init.ContinuousConvMode = ENABLE;
  hadc2.Init.DiscontinuousConvMode = DISABLE;
  hadc2.Init.NbrOfDiscConversion = 1;
  hadc2.Init.ExternalTrigConvEdge = ADC_EXTERNALTRIGCONVEDGE_NONE;
  hadc2.Init.DataAlign = ADC_DATAALIGN_RIGHT;
  hadc2.Init.NbrOfConversion = 4;
  hadc2.Init.DMAContinuousRequests = ENABLE;
  hadc2.Init.EOCSelection = EOC_SINGLE_CONV;
  hadc2.Init.LowPowerAutoWait = DISABLE;
  hadc2.Init.Overrun = OVR_DATA_OVERWRITTEN;
  HAL_ADC_Init(&hadc2);
 
    /**Configure Regular Channel
    */
  sConfig.Channel = ADC_CHANNEL_7;
  sConfig.Rank = 1;
  sConfig.SingleDiff = ADC_SINGLE_ENDED;
  sConfig.SamplingTime = ADC_SAMPLETIME_1CYCLE_5;
  sConfig.OffsetNumber = ADC_OFFSET_NONE;
  sConfig.Offset = 0;
  HAL_ADC_ConfigChannel(&hadc2, &sConfig);
 
    /**Configure Regular Channel
    */
  sConfig.Channel = ADC_CHANNEL_9;
  sConfig.Rank = 2;
  HAL_ADC_ConfigChannel(&hadc2, &sConfig);
 
    /**Configure Regular Channel
    */
  sConfig.Channel = ADC_CHANNEL_10;
  sConfig.Rank = 3;
  HAL_ADC_ConfigChannel(&hadc2, &sConfig);
 
    /**Configure Regular Channel
    */
  sConfig.Channel = ADC_CHANNEL_11;
  sConfig.Rank = 4;
  HAL_ADC_ConfigChannel(&hadc2, &sConfig);
   
  HAL_ADC_Start_DMA(&hadc2, (uint32_t*)(&ADC2_Buffer[0]), 4);
 
}
 
static int ADC12_CLK_ENABLED=0;
 
void HAL_ADC_MspInit(ADC_HandleTypeDef* hadc)
{
 
  GPIO_InitTypeDef GPIO_InitStruct;
  if(hadc->Instance==ADC1)
  {
    /* Peripheral clock enable */
    ADC12_CLK_ENABLED++;
    if(ADC12_CLK_ENABLED==1){
      __ADC12_CLK_ENABLE();
    }
   
    /**ADC1 GPIO Configuration   
    PC0     ------> ADC1_IN6
    PC2     ------> ADC1_IN8
    PA0     ------> ADC1_IN1
    PA1     ------> ADC1_IN2
    PA2     ------> ADC1_IN3
    PA3     ------> ADC1_IN4
    PF4     ------> ADC1_IN5
    */
    GPIO_InitStruct.Pin = GPIO_PIN_0|GPIO_PIN_2;
    GPIO_InitStruct.Mode = GPIO_MODE_ANALOG;
    GPIO_InitStruct.Pull = GPIO_NOPULL;
    HAL_GPIO_Init(GPIOC, &GPIO_InitStruct);
 
    GPIO_InitStruct.Pin = GPIO_PIN_0|GPIO_PIN_1|GPIO_PIN_2;
    GPIO_InitStruct.Mode = GPIO_MODE_ANALOG;
    GPIO_InitStruct.Pull = GPIO_NOPULL;
    HAL_GPIO_Init(GPIOA, &GPIO_InitStruct);
 
    GPIO_InitStruct.Pin = GPIO_PIN_4;
    GPIO_InitStruct.Mode = GPIO_MODE_ANALOG;
    GPIO_InitStruct.Pull = GPIO_NOPULL;
    HAL_GPIO_Init(GPIOF, &GPIO_InitStruct);
 
    /* Peripheral DMA init*/
   
    hdma_adc1.Instance = DMA1_Channel1;
    hdma_adc1.Init.Direction = DMA_PERIPH_TO_MEMORY;
    hdma_adc1.Init.PeriphInc = DMA_PINC_DISABLE;
    hdma_adc1.Init.MemInc = DMA_MINC_ENABLE;
    hdma_adc1.Init.PeriphDataAlignment = DMA_PDATAALIGN_HALFWORD;
    hdma_adc1.Init.MemDataAlignment = DMA_MDATAALIGN_HALFWORD;
    hdma_adc1.Init.Mode = DMA_CIRCULAR;
    hdma_adc1.Init.Priority = DMA_PRIORITY_LOW;
    HAL_DMA_Init(&hdma_adc1);
 
    __HAL_LINKDMA(hadc,DMA_Handle,hdma_adc1);
 
  }
  else if(hadc->Instance==ADC2)
  {
    /* Peripheral clock enable */
    ADC12_CLK_ENABLED++;
    if(ADC12_CLK_ENABLED==1){
      __ADC12_CLK_ENABLE();
    }
   
    /**ADC2 GPIO Configuration   
    PC1     ------> ADC2_IN7
    PC3     ------> ADC2_IN9
    PF2     ------> ADC2_IN10
    PC5     ------> ADC2_IN11
    */
    GPIO_InitStruct.Pin = GPIO_PIN_1|GPIO_PIN_3|GPIO_PIN_5;
    GPIO_InitStruct.Mode = GPIO_MODE_ANALOG;
    GPIO_InitStruct.Pull = GPIO_NOPULL;
    HAL_GPIO_Init(GPIOC, &GPIO_InitStruct);
 
    GPIO_InitStruct.Pin = GPIO_PIN_2;
    GPIO_InitStruct.Mode = GPIO_MODE_ANALOG;
    GPIO_InitStruct.Pull = GPIO_NOPULL;
    HAL_GPIO_Init(GPIOF, &GPIO_InitStruct);
 
    /* Peripheral DMA init*/
   
    hdma_adc2.Instance = DMA2_Channel1;
    hdma_adc2.Init.Direction = DMA_PERIPH_TO_MEMORY;
    hdma_adc2.Init.PeriphInc = DMA_PINC_DISABLE;
    hdma_adc2.Init.MemInc = DMA_MINC_ENABLE;
    hdma_adc2.Init.PeriphDataAlignment = DMA_PDATAALIGN_HALFWORD;
    hdma_adc2.Init.MemDataAlignment = DMA_MDATAALIGN_HALFWORD;
    hdma_adc2.Init.Mode = DMA_CIRCULAR;
    hdma_adc2.Init.Priority = DMA_PRIORITY_LOW;
    HAL_DMA_Init(&hdma_adc2);
 
    __HAL_LINKDMA(hadc,DMA_Handle,hdma_adc2);
 
  }
 
}
 
void HAL_ADC_MspDeInit(ADC_HandleTypeDef* hadc)
{
 
  if(hadc->Instance==ADC1)
  {
    /* Peripheral clock disable */
    ADC12_CLK_ENABLED--;
    if(ADC12_CLK_ENABLED==0){
      __ADC12_CLK_DISABLE();
    }
   
    /**ADC1 GPIO Configuration   
    PC0     ------> ADC1_IN6
    PC2     ------> ADC1_IN8
    PA0     ------> ADC1_IN1
    PA1     ------> ADC1_IN2
    PA2     ------> ADC1_IN3
    PA3     ------> ADC1_IN4
    PF4     ------> ADC1_IN5
    */
    HAL_GPIO_DeInit(GPIOC, GPIO_PIN_0|GPIO_PIN_2);
 
    HAL_GPIO_DeInit(GPIOA, GPIO_PIN_0|GPIO_PIN_1|GPIO_PIN_2|GPIO_PIN_3);
 
    HAL_GPIO_DeInit(GPIOF, GPIO_PIN_4);
 
    /* Peripheral DMA DeInit*/
    HAL_DMA_DeInit(hadc->DMA_Handle);
  }
  else if(hadc->Instance==ADC2)
  {
    /* Peripheral clock disable */
    ADC12_CLK_ENABLED--;
    if(ADC12_CLK_ENABLED==0){
      __ADC12_CLK_DISABLE();
    }
   
    /**ADC2 GPIO Configuration   
    PC1     ------> ADC2_IN7
    PC3     ------> ADC2_IN9
    PF2     ------> ADC2_IN10
    PC5     ------> ADC2_IN11
    */
    HAL_GPIO_DeInit(GPIOC, GPIO_PIN_1|GPIO_PIN_3|GPIO_PIN_5);
 
    HAL_GPIO_DeInit(GPIOF, GPIO_PIN_2);
 
    /* Peripheral DMA DeInit*/
    HAL_DMA_DeInit(hadc->DMA_Handle);
  }
}

Outcomes