AnsweredAssumed Answered

Kinnetis K22 using PIT triggered ADC with Compare

Question asked by Ashley Duncan on Sep 15, 2016
Latest reply on Sep 28, 2016 by Lawrence Archard



I am stuck here.  I have a FRDMK22F dev kit.  I started by using the SDK example for PIT triggered ADC.  I changed it to 16 bit differential and set the PIT rate as I desired.  Works mint!


BUT...  When I enable the compare function in the ADC, I get only one ADC conversion complete interrupt if the compare conditions are met on the very first sample, otherwise I never get an interrupt.


My intention is to wait until a sample is measured outside of a range, then switch the compare function off and continue sampling at a fixed interval.  Any ideas on this, I am stuck and burning time away...


Relevant Code, the rest is as per the PIt hardware triggered ADC example:


* @brief ADC channel0 callback for fetching sample data.

static void adc_chn0_isr_callback(void)
    gCurChan = 0;
    gAdcDone = true;

#define ACCEL_ADC_CHANNEL (kAdc16Chn0d)

adc16_status_t res;
* @brief Initialize the ADCx for HW trigger.
* @param instance The ADC instance number

static int32_t init_adc(uint32_t instance)
     // Initiaslise ADC to default
     adc16_converter_config_t adcUserConfig;
    ADC16_DRV_Init(instance, &adcUserConfig);

    // Initialise ADC for calibration process
    // Note this enables the ADC Async Clock which is within the correct frequency range for calibration
    // Set hardware averaging to maximum
    adc16_hw_average_config_t adcAverageConfig =
      .hwAverageEnable = true,
      .hwAverageCountMode = kAdc16HwAverageCountOf32
    ADC16_DRV_ConfigHwAverage(instance, &adcAverageConfig);

    adc16_chn_config_t adcCalibrationChnConfig;
    adcCalibrationChnConfig.diffConvEnable = true;
    adcCalibrationChnConfig.convCompletedIntEnable = false;
    // Configure channel 0
    ADC16_DRV_ConfigConvChn(instance, 0U, &adcCalibrationChnConfig);
    // Auto calibration.
    adc16_calibration_param_t adcCalibrationParam;
    ADC16_DRV_GetAutoCalibrationParam(instance, &adcCalibrationParam);
    ADC16_DRV_SetCalibrationParam(instance, &adcCalibrationParam);

    // Initialise ADC for
    // Bus Clock (5MHz RUN mode, 7.5MHz HSRUN mode), async clock disabled
    adcUserConfig.clkSrc = kAdc16ClkSrcOfBusClk;
    adcUserConfig.clkDividerMode = kAdc16ClkDividerOf8;
    adcUserConfig.lowPowerEnable = false;
    // 16 bit resolution, differential.  VREFH/L as reference
    adcUserConfig.resolution = kAdc16ResolutionBitOfDiffModeAs16;
    adcUserConfig.refVoltSrc = kAdc16RefVoltSrcOfVref;
    // Sampling: Gives 14.925us (67 kHz max) conversion time in RUN mode or 11.616us in HSRUN mode
    adcUserConfig.asyncClkEnable = false;
    adcUserConfig.longSampleTimeEnable = true;
     adcUserConfig.longSampleCycleMode = kAdc16LongSampleCycleOf16; // 12 extra cycles, 16 in total
     adcUserConfig.highSpeedEnable = false;
    // Interrupt mode, HW trigger enabled, disable continuous convert mode.
    adcUserConfig.hwTriggerEnable = true;
    adcUserConfig.continuousConvEnable = false;
    adcUserConfig.dmaEnable = false;
    ADC16_DRV_Init(instance, &adcUserConfig);
    // Disable averaging
    adcAverageConfig.hwAverageEnable = false;
    ADC16_DRV_ConfigConvChn(instance, 0U, &adcCalibrationChnConfig);

    // Install Callback function into ISR
    ADC_TEST_InstallCallback(instance, 0U, adc_chn0_isr_callback);

    adc16_hw_cmp_config_t compareVals =
         .hwCmpEnable = true,
          .hwCmpRangeEnable = false,//true,
          .hwCmpGreaterThanEnable = true,
          .cmpValue1 = 10000//,
         //.cmpValue2 = (uint16_t)-10000
    res = ADC16_DRV_ConfigHwCompare(instance, &compareVals);

    // Setup channel 0
    adc16_chn_config_t adcChnConfig;
    adcChnConfig.chnIdx = ACCEL_ADC_CHANNEL;
    adcChnConfig.diffConvEnable = true;
    adcChnConfig.convCompletedIntEnable = true;

    // Configure channel 0
    ADC16_DRV_ConfigConvChn(instance, 0U, &adcChnConfig);

    return 0;