Example #1
0
/**
 * @brief   Low level ADC driver initialization.
 *
 * @notapi
 */
void adc_lld_init(void) {

#if STM32_ADC_USE_ADC1
    /* Driver initialization.*/
    adcObjectInit(&ADCD1);
    ADCD1.adc = ADC1;
    ADCD1.dmastp  = STM32_DMA1_STREAM1;
    ADCD1.dmamode = STM32_DMA_CR_PL(STM32_ADC_ADC1_DMA_PRIORITY) |
                    STM32_DMA_CR_DIR_P2M |
                    STM32_DMA_CR_MSIZE_HWORD | STM32_DMA_CR_PSIZE_HWORD |
                    STM32_DMA_CR_MINC        | STM32_DMA_CR_TCIE        |
                    STM32_DMA_CR_DMEIE       | STM32_DMA_CR_TEIE;
#endif

    /* The shared vector is initialized on driver initialization and never
       disabled.*/
    nvicEnableVector(12, STM32_ADC_IRQ_PRIORITY);

    /* Calibration procedure.*/
    rccEnableADC1(FALSE);
    osalDbgAssert(ADC1->CR == 0, "invalid register state");
    ADC1->CR |= ADC_CR_ADCAL;
    while (ADC1->CR & ADC_CR_ADCAL)
        ;
    rccDisableADC1(FALSE);
}
Example #2
0
/**
 * @brief   Configures and activates the ADC peripheral.
 *
 * @param[in] adcp      pointer to the @p ADCDriver object
 *
 * @notapi
 */
void adc_lld_start(ADCDriver *adcp) {

    /* If in stopped state then enables the ADC and DMA clocks.*/
    if (adcp->state == ADC_STOP) {
#if STM32_ADC_USE_ADC1
        if (&ADCD1 == adcp) {
            bool b;
            b = dmaStreamAllocate(adcp->dmastp,
                                  STM32_ADC_ADC1_DMA_IRQ_PRIORITY,
                                  (stm32_dmaisr_t)adc_lld_serve_rx_interrupt,
                                  (void *)adcp);
            osalDbgAssert(!b, "stream already allocated");
            dmaStreamSetPeripheral(adcp->dmastp, &ADC1->DR);
            rccEnableADC1(FALSE);
#if STM32_ADCSW == STM32_ADCSW_HSI14
            /* Clock from HSI14, no need for jitter removal.*/
            ADC1->CFGR2 = 0x00001000;
#else
#if STM32_ADCPRE == STM32_ADCPRE_DIV2
            ADC1->CFGR2 = 0x00001000 | ADC_CFGR2_JITOFFDIV2;
#else
            ADC1->CFGR2 = 0x00001000 | ADC_CFGR2_JITOFFDIV4;
#endif
#endif
        }
#endif /* STM32_ADC_USE_ADC1 */

        /* ADC initial setup, starting the analog part here in order to reduce
           the latency when starting a conversion.*/
        adcp->adc->CR = ADC_CR_ADEN;
        while (!(adcp->adc->ISR & ADC_ISR_ADRDY))
            ;
    }
}
Example #3
0
/**
 * @brief   Low level ADC driver initialization.
 *
 * @notapi
 */
void adc_lld_init(void) {

#if STM32_ADC_USE_ADC1
  /* Driver initialization.*/
  adcObjectInit(&ADCD1);
  ADCD1.adc = ADC1;
  ADCD1.dmastp  = STM32_DMA1_STREAM1;
  ADCD1.dmamode = STM32_DMA_CR_PL(STM32_ADC_ADC1_DMA_PRIORITY) |
                  STM32_DMA_CR_MSIZE_HWORD | STM32_DMA_CR_PSIZE_HWORD |
                  STM32_DMA_CR_MINC        | STM32_DMA_CR_TCIE        |
                  STM32_DMA_CR_TEIE;

  /* Temporary activation.*/
  rccEnableADC1(FALSE);
  ADC1->CR1 = 0;
  ADC1->CR2 = ADC_CR2_ADON;

  /* Reset calibration just to be safe.*/
  ADC1->CR2 = ADC_CR2_ADON | ADC_CR2_RSTCAL;
  while ((ADC1->CR2 & ADC_CR2_RSTCAL) != 0)
    ;

  /* Calibration.*/
  ADC1->CR2 = ADC_CR2_ADON | ADC_CR2_CAL;
  while ((ADC1->CR2 & ADC_CR2_CAL) != 0)
    ;

  /* Return the ADC in low power mode.*/
  ADC1->CR2 = 0;
  rccDisableADC1(FALSE);
#endif
}
Example #4
0
/**
 * @brief   Configures and activates the ADC peripheral.
 *
 * @param[in] adcp      pointer to the @p ADCDriver object
 *
 * @notapi
 */
void adc_lld_start(ADCDriver *adcp) {

  /* If in stopped state then enables the ADC and DMA clocks.*/
  if (adcp->state == ADC_STOP) {
#if STM32_ADC_USE_ADC1
    if (&ADCD1 == adcp) {
      bool b;
      b = dmaStreamAllocate(adcp->dmastp,
                            STM32_ADC_ADC1_DMA_IRQ_PRIORITY,
                            (stm32_dmaisr_t)adc_lld_serve_rx_interrupt,
                            (void *)adcp);
      osalDbgAssert(!b, "stream already allocated");
      dmaStreamSetPeripheral(adcp->dmastp, &ADC1->DR);
      rccEnableADC1(FALSE);

      /* Clock settings.*/
      adcp->adc->CFGR2 = STM32_ADC_CKMODE;
    }
#endif /* STM32_ADC_USE_ADC1 */

    /* ADC initial setup, starting the analog part here in order to reduce
       the latency when starting a conversion.*/
    adcp->adc->CR = ADC_CR_ADEN;
    while (!(adcp->adc->ISR & ADC_ISR_ADRDY))
      ;
  }
}
Example #5
0
/**
 * @brief   Configures and activates the ADC peripheral.
 *
 * @param[in] adcp      pointer to the @p ADCDriver object
 *
 * @notapi
 */
void adc_lld_start(ADCDriver *adcp) {

  /* If in stopped state then enables the ADC and DMA clocks.*/
  if (adcp->state == ADC_STOP) {
#if STM32_ADC_USE_ADC1
    if (&ADCD1 == adcp) {
      bool b;
      b = dmaStreamAllocate(adcp->dmastp,
                            STM32_ADC_ADC1_DMA_IRQ_PRIORITY,
                            (stm32_dmaisr_t)adc_lld_serve_rx_interrupt,
                            (void *)adcp);
      osalDbgAssert(!b, "stream already allocated");
      dmaStreamSetPeripheral(adcp->dmastp, &ADC1->DR);
      rccEnableADC1(FALSE);
    }
#endif /* STM32_ADC_USE_ADC1 */

#if STM32_ADC_USE_ADC2
    if (&ADCD2 == adcp) {
      bool b;
      b = dmaStreamAllocate(adcp->dmastp,
                            STM32_ADC_ADC2_DMA_IRQ_PRIORITY,
                            (stm32_dmaisr_t)adc_lld_serve_rx_interrupt,
                            (void *)adcp);
      osalDbgAssert(!b, "stream already allocated");
      dmaStreamSetPeripheral(adcp->dmastp, &ADC2->DR);
      rccEnableADC2(FALSE);
    }
#endif /* STM32_ADC_USE_ADC2 */

#if STM32_ADC_USE_ADC3
    if (&ADCD3 == adcp) {
      bool b;
      b = dmaStreamAllocate(adcp->dmastp,
                            STM32_ADC_ADC3_DMA_IRQ_PRIORITY,
                            (stm32_dmaisr_t)adc_lld_serve_rx_interrupt,
                            (void *)adcp);
      osalDbgAssert(!b, "stream already allocated");
      dmaStreamSetPeripheral(adcp->dmastp, &ADC3->DR);
      rccEnableADC3(FALSE);
    }
#endif /* STM32_ADC_USE_ADC3 */

    /* This is a common register but apparently it requires that at least one
       of the ADCs is clocked in order to allow writing, see bug 3575297.*/
    ADC->CCR = (ADC->CCR & (ADC_CCR_TSVREFE | ADC_CCR_VBATE)) |
               (STM32_ADC_ADCPRE << 16);

    /* ADC initial setup, starting the analog part here in order to reduce
       the latency when starting a conversion.*/
    adcp->adc->CR1 = 0;
    adcp->adc->CR2 = 0;
    adcp->adc->CR2 = ADC_CR2_ADON;
  }
}
Example #6
0
void Adc_t::Init() {
    rccEnableADC1(FALSE);   // Enable digital clock
    SetupClk(adcDiv4);      // Setup ADCCLK
    SetChannelCount(ADC_CHANNEL_CNT);
    for(uint8_t i = 0; i < ADC_CHANNEL_CNT; i++) ChannelConfig(AdcChannels[i]);
    // ==== DMA ====
    // Here only unchanged parameters of the DMA are configured.
    dmaStreamAllocate     (ADC_DMA, IRQ_PRIO_LOW, AdcTxIrq, NULL);
    dmaStreamSetPeripheral(ADC_DMA, &ADC1->DR);
    dmaStreamSetMode      (ADC_DMA, ADC_DMA_MODE);
}
Example #7
0
/*
  initialise ADC capture
 */
void adc_init(void)
{
    adc_lld_init();
    rccEnableADC1(true);

    /* set channels 4 and 5 for 28.5us sample time */
    ADC1->SMPR2 = ADC_SMPR2_SMP_AN4(ADC_SAMPLE_28P5) | ADC_SMPR2_SMP_AN5(ADC_SAMPLE_28P5);

    /* capture a single sample at a time */
    ADC1->SQR1 = 0;
    ADC1->SQR2 = 0;
}
Example #8
0
/**
 * @brief   Configures and activates the ADC peripheral.
 *
 * @param[in] adcp      pointer to the @p ADCDriver object
 *
 * @notapi
 */
void adc_lld_start(ADCDriver *adcp) {

  /* If in stopped state then enables the ADC and DMA clocks.*/
  if (adcp->state == ADC_STOP) {
#if STM32_ADC_USE_ADC1
    if (&ADCD1 == adcp) {
      bool_t b;
      b = dmaStreamAllocate(adcp->dmastp,
                            STM32_ADC_ADC1_DMA_IRQ_PRIORITY,
                            (stm32_dmaisr_t)adc_lld_serve_rx_interrupt,
                            (void *)adcp);
      chDbgAssert(!b, "adc_lld_start(), #1", "stream already allocated");
      dmaStreamSetPeripheral(adcp->dmastp, &ADC1->DR);
      rccEnableADC1(FALSE);
    }
#endif /* STM32_ADC_USE_ADC1 */

#if STM32_ADC_USE_ADC2
    if (&ADCD2 == adcp) {
      bool_t b;
      b = dmaStreamAllocate(adcp->dmastp,
                            STM32_ADC_ADC2_DMA_IRQ_PRIORITY,
                            (stm32_dmaisr_t)adc_lld_serve_rx_interrupt,
                            (void *)adcp);
      chDbgAssert(!b, "adc_lld_start(), #2", "stream already allocated");
      dmaStreamSetPeripheral(adcp->dmastp, &ADC2->DR);
      rccEnableADC2(FALSE);
    }
#endif /* STM32_ADC_USE_ADC2 */

#if STM32_ADC_USE_ADC3
    if (&ADCD3 == adcp) {
      bool_t b;
      b = dmaStreamAllocate(adcp->dmastp,
                            STM32_ADC_ADC3_DMA_IRQ_PRIORITY,
                            (stm32_dmaisr_t)adc_lld_serve_rx_interrupt,
                            (void *)adcp);
      chDbgAssert(!b, "adc_lld_start(), #3", "stream already allocated");
      dmaStreamSetPeripheral(adcp->dmastp, &ADC3->DR);
      rccEnableADC3(FALSE);
    }
#endif /* STM32_ADC_USE_ADC3 */

    /* ADC initial setup, starting the analog part here in order to reduce
       the latency when starting a conversion.*/
    adcp->adc->CR1 = 0;
    adcp->adc->CR2 = 0;
    adcp->adc->CR2 = ADC_CR2_ADON;
  }
}
Example #9
0
void Adc_t::Init() {
    rccEnableADC1(FALSE);   	// Enable digital clock
    SetupClk(ADC_CLK_DIVIDER);  // Setup ADCCLK
    // Setup channels
    SetSequenceLength(ADC_SEQ_LEN);
    uint8_t SeqIndx = 1;    // First sequence item is 1, not 0
    for(uint8_t i=0; i < ADC_CHANNEL_CNT; i++) {
		SetChannelSampleTime(AdcChannels[i], ADC_SAMPLE_TIME);
		for(uint8_t j=0; j<ADC_SAMPLE_CNT; j++) SetSequenceItem(SeqIndx++, AdcChannels[i]);
	}
    // ==== DMA ====
    dmaStreamAllocate     (ADC_DMA, IRQ_PRIO_LOW, AdcTxIrq, NULL);
    dmaStreamSetPeripheral(ADC_DMA, &ADC1->DR);
    dmaStreamSetMode      (ADC_DMA, ADC_DMA_MODE);
}
Example #10
0
/**
 * @brief   Configures and activates the ADC peripheral.
 *
 * @param[in] adcp      pointer to the @p ADCDriver object
 *
 * @notapi
 */
void adc_lld_start(ADCDriver *adcp) {

  /* If in stopped state then enables the ADC and DMA clocks.*/
  if (adcp->state == ADC_STOP) {
#if STM32_ADC_USE_ADC1
    if (&ADCD1 == adcp) {
      bool b;
      b = dmaStreamAllocate(adcp->dmastp,
                            STM32_ADC_ADC1_IRQ_PRIORITY,
                            (stm32_dmaisr_t)adc_lld_serve_rx_interrupt,
                            (void *)adcp);
      osalDbgAssert(!b, "stream already allocated");
      dmaStreamSetPeripheral(adcp->dmastp, &ADC1->DR);
      rccEnableADC1(FALSE);
    }
#endif

    /* ADC setup, the calibration procedure has already been performed
       during initialization.*/
    adcp->adc->CR1 = 0;
    adcp->adc->CR2 = 0;
  }
}
Example #11
0
/**
 * @brief   Configures and activates the ADC peripheral.
 *
 * @param[in] adcp      pointer to the @p ADCDriver object
 *
 * @notapi
 */
void adc_lld_start(ADCDriver *adcp) {

  if (adcp->config == NULL)
    adcp->config = &adc_lld_default_config;

  /* If in stopped state then enables the ADC and DMA clocks.*/
  if (adcp->state == ADC_STOP) {
#if STM32_ADC_USE_ADC1
    if (&ADCD1 == adcp) {
      bool_t b;
      b = dmaStreamAllocate(adcp->dmastp,
                            STM32_ADC_ADC1_DMA_IRQ_PRIORITY,
                            (stm32_dmaisr_t)adc_lld_serve_dma_interrupt,
                            (void *)adcp);
      chDbgAssert(!b, "adc_lld_start(), #1", "stream already allocated");
      dmaStreamSetPeripheral(adcp->dmastp, &ADC1->DR);
      rccEnableADC1(FALSE);
    }
#endif /* STM32_ADC_USE_ADC1 */

#if STM32_ADC_USE_SDADC1
    if (&SDADCD1 == adcp) {
      bool_t b = dmaStreamAllocate(adcp->dmastp,
                                   STM32_ADC_SDADC1_DMA_IRQ_PRIORITY,
                                   (stm32_dmaisr_t)adc_lld_serve_dma_interrupt,
                                   (void *)adcp);
      chDbgAssert(!b, "adc_lld_start(), #2", "stream already allocated");
      dmaStreamSetPeripheral(adcp->dmastp, &SDADC1->JDATAR);
      rccEnableSDADC1(FALSE);
      PWR->CR |= PWR_CR_SDADC1EN;
      adcp->sdadc->CR2 = 0;
      adcp->sdadc->CR1 = (adcp->config->cr1 | SDADC_ENFORCED_CR1_FLAGS) &
                         ~SDADC_FORBIDDEN_CR1_FLAGS;
      adcp->sdadc->CR2 = SDADC_CR2_ADON;
    }
#endif /* STM32_ADC_USE_SDADC1 */

#if STM32_ADC_USE_SDADC2
    if (&SDADCD2 == adcp) {
      bool_t b = dmaStreamAllocate(adcp->dmastp,
                                   STM32_ADC_SDADC2_DMA_IRQ_PRIORITY,
                                   (stm32_dmaisr_t)adc_lld_serve_dma_interrupt,
                                   (void *)adcp);
      chDbgAssert(!b, "adc_lld_start(), #3", "stream already allocated");
      dmaStreamSetPeripheral(adcp->dmastp, &SDADC2->JDATAR);
      rccEnableSDADC2(FALSE);
      PWR->CR |= PWR_CR_SDADC2EN;
      adcp->sdadc->CR2 = 0;
      adcp->sdadc->CR1 = (adcp->config->cr1 | SDADC_ENFORCED_CR1_FLAGS) &
                         ~SDADC_FORBIDDEN_CR1_FLAGS;
      adcp->sdadc->CR2 = SDADC_CR2_ADON;
    }
#endif /* STM32_ADC_USE_SDADC2 */

#if STM32_ADC_USE_SDADC3
    if (&SDADCD3 == adcp) {
      bool_t b = dmaStreamAllocate(adcp->dmastp,
                                   STM32_ADC_SDADC3_DMA_IRQ_PRIORITY,
                                   (stm32_dmaisr_t)adc_lld_serve_dma_interrupt,
                                   (void *)adcp);
      chDbgAssert(!b, "adc_lld_start(), #4", "stream already allocated");
      dmaStreamSetPeripheral(adcp->dmastp, &SDADC3->JDATAR);
      rccEnableSDADC3(FALSE);
      PWR->CR |= PWR_CR_SDADC3EN;
      adcp->sdadc->CR2 = 0;
      adcp->sdadc->CR1 = (adcp->config->cr1 | SDADC_ENFORCED_CR1_FLAGS) &
                         ~SDADC_FORBIDDEN_CR1_FLAGS;
      adcp->sdadc->CR2 = SDADC_CR2_ADON;
    }
#endif /* STM32_ADC_USE_SDADC3 */
  }

  adc_lld_reconfig(adcp);
}