BCTU ADC FIFO conversion time

キャンセル
次の結果を表示 
表示  限定  | 次の代わりに検索 
もしかして: 

BCTU ADC FIFO conversion time

1,353件の閲覧回数
not_a_duck
Contributor III

I have some adc conversions that are being triggered from a bctu hw trigger. 
i have emios 1 ch0 set up as my timebase with 5000 ticks and a system clock of 160mhz so my timer period is 31.25 us (32khz).
I have my bctu fifo set up to sample all three adcs for three channels.
so my conversion time should be 2.8 us.

i added an breakpoint in Bctu_Ip_Bctu0Fifo1DmaComplete(void) to see the value of emios 1 ch0 CNT to get an understanding of when the adc values are being processed.

emios 1 ch4 is being used as the trigger for the adc conversion. which i have set to trigger at 4500 ticks. 
now what i'm seeing is that the value of emios1ch0 CNT is always around 460. which means it's taking 960 ticks from the adc trigger to the dma complete trigger.
what i don't understand is where the additional ~500ticks are coming from.
i also moved the adc conversion trigger from 4500 to 4998 and then the value of cnt was 960 so the duration seems to be consistent, but i am wondering how much delay there is between the start of first adc sample and the adc conversion trigger? 
i also understand that there would be some delay between conversion completion and bctuFIFOdma interrupt being triggered but how much that delay should be I can't clearly reason out for myself.

my dma interrupt is already the highest priority interrupt in the system so i doubt there is delay there but are there any settings i can or should configure to ensure this timeline is as tight as possible.






Conversion time math:
Total_conversion_time = ( [(PST + ST + CT + DP) × chain_length] + TPT) × TAD_clk

Example:
The ADC controller clock is equal to the module clock (80 MHz, clock cyle = 12.5 ns)
• ADC resolution 12 bit + 1 bit for a special capacitor (CS)
• Three channels are programmed in NCMRn , so a chain of three is to be converted
• Default sample time (22 cycles) is specified
• No presampling
• Conversion time (4 cycles per bit)
The total time for the three conversions = [(0 + 22 + (4×13) + 2) × 3] + 1 = 229 cycles ~= 2.862 µs

タグ(5)
0 件の賞賛
返信
3 返答(返信)

1,303件の閲覧回数
PetrS
NXP TechSupport
NXP TechSupport

Hi,

hard to say without knowledge of actual setting you have. Can you share your project?
Calculation looks correct, but do you really have AD_clock 80Mhz?
There should be minimum SW overhead when DMA is reading FIFO.

BR, Petr 

0 件の賞賛
返信

1,255件の閲覧回数
not_a_duck
Contributor III

Hey @PetrS ,

I think there may be a bug in the ADC HW access for setting HSEN and CMPCTRL0.

I just collected some data on this.
So i checked the ADC<0,1,2>_CLK before the system_clock config runs, after the adc_init is called and after calibration.

adc0_clk[0] = Clock_Ip_GetClockFrequency(ADC0_CLK);
adc1_clk[0] = Clock_Ip_GetClockFrequency(ADC1_CLK);
adc2_clk[0] = Clock_Ip_GetClockFrequency(ADC2_CLK);

Clock_Ip_StatusType eClockStatus = Clock_Ip_Init(&Clock_Ip_aClockConfig[0]);
bool bClockInitSuccess = ( eClockStatus == CLOCK_IP_SUCCESS );

Adc_Sar_Ip_StatusType adc0_status = Adc_Sar_Ip_Init(ADCHWUNIT_0_INSTANCE, &AdcHwUnit_0);
Adc_Sar_Ip_StatusType adc1_status = Adc_Sar_Ip_Init(ADCHWUNIT_1_INSTANCE, &AdcHwUnit_1);
Adc_Sar_Ip_StatusType adc2_status = Adc_Sar_Ip_Init(ADCHWUNIT_2_INSTANCE, &AdcHwUnit_2);
PANIC_ASSERT( adc0_status == ADC_SAR_IP_STATUS_SUCCESS );
PANIC_ASSERT( adc1_status == ADC_SAR_IP_STATUS_SUCCESS );
PANIC_ASSERT( adc2_status == ADC_SAR_IP_STATUS_SUCCESS );

// ...

adc0_clk[1] = Clock_Ip_GetClockFrequency(ADC0_CLK);
adc1_clk[1] = Clock_Ip_GetClockFrequency(ADC1_CLK);
adc2_clk[1] = Clock_Ip_GetClockFrequency(ADC2_CLK);

/* Call Calibration function multiple times, to mitigate instability of board source */
for (int i = 0; i <= kBSP_ADC_CalibrationAttemptCount; i++)
{
    if ( Adc_Sar_Ip_DoCalibration(ADCHWUNIT_0_INSTANCE) == E_OK)
    {
        break;
    }
}

/* Call Calibration function multiple times, to mitigate instability of board source */
for (int i = 0; i <= kBSP_ADC_CalibrationAttemptCount; i++)
{
    if ( Adc_Sar_Ip_DoCalibration(ADCHWUNIT_1_INSTANCE) == E_OK)
    {
        break;
    }
}

/* Call Calibration function multiple times, to mitigate instability of board source */
for (int i = 0; i <= kBSP_ADC_CalibrationAttemptCount; i++)
{
    if ( Adc_Sar_Ip_DoCalibration(ADCHWUNIT_2_INSTANCE) == E_OK)
    {
        break;
    }
}

adc0_clk[2] = Clock_Ip_GetClockFrequency(ADC0_CLK);
adc1_clk[2] = Clock_Ip_GetClockFrequency(ADC1_CLK);
adc2_clk[2] = Clock_Ip_GetClockFrequency(ADC2_CLK);

 

and i'm seeing 160,000,000 for all of them. 
Screenshot 2024-11-08 at 9.08.15 AM.png


Screenshot 2024-11-08 at 9.07.16 AM.png
next i checked MCR and AMSIO to check that they match what is described in table 317 in the reference manual.

Screenshot 2024-11-08 at 9.09.25 AM.png
Screenshot 2024-11-08 at 9.09.47 AM.png


MCR[ADCLKSEL] is set to 1 which seems correct. meaning that the ADC_CLK is 80mhz.

AMSIO[HSEN] is set to 2. that doesn’t seem right. it should be set to 0.
AMSIO[CMPCTRL0] is set to 0.


Is this a bug in the ADC_HW access function then?

Adc_Sar_Ip_StatusType Adc_Sar_Ip_SetClockMode(const uint32 u32Instance,
                                              const Adc_Sar_Ip_ClockConfigType * const pConfig)
// ...
#if FEATURE_ADC_HAS_HIGH_SPEED_ENABLE
            SchM_Enter_Adc_ADC_EXCLUSIVE_AREA_51();
            /* Enables high speed conversion or calibration */
            Adc_Sar_EnableHighSpeed(AdcBasePtr, pConfig->HighSpeedConvEn);
            SchM_Exit_Adc_ADC_EXCLUSIVE_AREA_51();
#endif /* FEATURE_ADC_HAS_HIGH_SPEED_ENABLE */
// ...
}

 

#if FEATURE_ADC_HAS_HIGH_SPEED_ENABLE
/*FUNCTION*********************************************************************
 *
 * Function Name : Adc_Sar_EnableHighSpeed
 * Description   : Enable a high-speed calibration or a high-speed conversion
 *
 *END*************************************************************************/
static inline void Adc_Sar_EnableHighSpeed(ADC_Type * const Base,
                                           boolean Enable)
{
    uint32 Amsio = Base->AMSIO;
    Amsio &= ~(ADC_AMSIO_HSEN_MASK);
    Amsio |= ADC_AMSIO_HSEN(Enable ? 3u : 0u);
    Base->AMSIO = Amsio;
}
#endif /* FEATURE_ADC_HAS_HIGH_SPEED_ENABLE */

 

If EnableHighSpeed is set to true. this function writes 3 to HSEN. but setting HSEN to 3 does not seem to be a valid option as describe in the table. it should instead be writing 1 to HSEN and 1 to CMPCTRL0. but that is not what this function is doing.

but regardless of this bug it seems that i should have high speed enable set to false in my configuration.


タグ(1)
0 件の賞賛
返信

1,124件の閲覧回数
PetrS
NXP TechSupport
NXP TechSupport

Hi,

not sure of the RTD you have but e.g. in RTD400 I see correct assignment for HSEN and CMPCTRL0, following the RM

PetrS_0-1732281249104.png

BR, Petr

 

0 件の賞賛
返信