Hi All
Has anyone worked with the KL28's ADC but not using its internal asynchronous clock source?
The NXP examples that I have seen all use the ADC's internal clock rather than a PCC selected clock source but I haven't been able to get the ADC to calibrate when connecting other sources (bus clock, fast IRC, etc.) although I believe that they should be correctly in range. When I use the internal clock source it does operate.
The KL28 is one of the first with a PCC and SCG to control clocks and peripheral clock sources, whereas I never had issues with using the bus clock in many other parts.
Anyone know the trick needed!
Regards
Mark
Hi, Mark,
I think this is the clock tree of Kl28.
ADCx_CFG1[ADICLK]=00; //bus clock
=01; //bus clock/2
=10; //ADC clock is from PCC
=11; //Asynchronous clock
I do not test calibration, but if I select ADCx_CFG1[ADICLK]=10; PCC_ADC0=0x42000000; //select SCGIRCLK - Slow IRC Clock, the ADC can convert analog channel. The Slow IRC Clock is always enabled.
As you said that the KL28 is a new product, I am not familiar with it, but i have one FRDM-Kl28 board, I can have a test.
Hope it can help you
BR
Xiangjun Rong
Hi Xiangjun
Thanks - if I use the alternative clock (rather than bus) I can control the clock via the PCC.
I wonder whether you could find out details to the following because it is possibly missing from the user's manual, as is the fact that selecting the clock source for the alternative clock is the PCC module (ALTCLK is not defined anywhere in the manual)
This is the general ADC block diagram showing the 4 clock sources that can (normally) be selected:
- ADACK (the internal asynchronous clock that works)
- ALTCLK, which we now know is the ADC's PCC source
- Bus clock and Bus clock/2. This is the source that I haven't been able to get to work. Is it possible that it is not connected in the KL28? Note that the bus clock is DIVSLOW_CLK in the KL28 (also the flash clock).
The only reference in the user's manual is:
3.7.1.5 ADC clock source
The ADC module clock is sourced from the Peripheral Clock Control (PCC) module.
which I initially understood to mean that the ADC's bus clock input may be from there. I now believe that it means that the ALTCLK input is sourced from the PCC. Further, I have the feeling that the bus clock inputs are not connected at all based on the fact that when I use this (24MHz), divided by 16 at the ADC input to get a 1.5MHz clock for calibration, the calibration never takes place/completes although there is also no calibration error flagged.
Can this be confirmed?
Regards
Mark
Hi, Mark,
I have tested based on KSDK, I just change the ADC clock to bus clock and set the ADC clock divider as 8, the ADC clock will be 24MHz/8=3MHz.
I can pass the calibration, this is the code:
You can have a test after you download KSDK based on Kl28, I use KDS tools.
BR
Xiangjun Rong
int main(void)
{
adc16_config_t adc16ConfigStruct;
adc16_channel_config_t adc16ChannelConfigStruct;
BOARD_InitPins();
BOARD_BootClockRUN();
BOARD_InitDebugConsole();
PRINTF("\r\nADC16 polling Example.\r\n");
/*
* adc16ConfigStruct.referenceVoltageSource = kADC16_ReferenceVoltageSourceVref;
* adc16ConfigStruct.clockSource = kADC16_ClockSourceAsynchronousClock;
* adc16ConfigStruct.enableAsynchronousClock = true;
* adc16ConfigStruct.clockDivider = kADC16_ClockDivider8;
* adc16ConfigStruct.resolution = kADC16_ResolutionSE12Bit;
* adc16ConfigStruct.longSampleMode = kADC16_LongSampleDisabled;
* adc16ConfigStruct.enableHighSpeed = false;
* adc16ConfigStruct.enableLowPower = false;
* adc16ConfigStruct.enableContinuousConversion = false;
*/
ADC16_GetDefaultConfig(&adc16ConfigStruct);
adc16ConfigStruct.clockSource=kADC16_ClockSourceAlt0; //bus clock 24MHz, kADC16_ClockSourceAlt2;
//PCC_ADC0=0x42000000;
#ifdef BOARD_ADC_USE_ALT_VREF
adc16ConfigStruct.referenceVoltageSource = kADC16_ReferenceVoltageSourceValt;
#endif
ADC16_Init(DEMO_ADC16_BASE, &adc16ConfigStruct);
ADC16_EnableHardwareTrigger(DEMO_ADC16_BASE, false); /* Make sure the software trigger is used. */
#if defined(FSL_FEATURE_ADC16_HAS_CALIBRATION) && FSL_FEATURE_ADC16_HAS_CALIBRATION
if (kStatus_Success == ADC16_DoAutoCalibration(DEMO_ADC16_BASE))
{
PRINTF("ADC16_DoAutoCalibration() Done.\r\n");
}
else
{
PRINTF("ADC16_DoAutoCalibration() Failed.\r\n");
}
#endif /* FSL_FEATURE_ADC16_HAS_CALIBRATION */
PRINTF("Press any key to get user channel's ADC value ...\r\n");
adc16ChannelConfigStruct.channelNumber = DEMO_ADC16_USER_CHANNEL;
adc16ChannelConfigStruct.enableInterruptOnConversionCompleted = false;
#if defined(FSL_FEATURE_ADC16_HAS_DIFF_MODE) && FSL_FEATURE_ADC16_HAS_DIFF_MODE
adc16ChannelConfigStruct.enableDifferentialConversion = false;
#endif /* FSL_FEATURE_ADC16_HAS_DIFF_MODE */
while (1)
{
GETCHAR();
/*
When in software trigger mode, each conversion would be launched once calling the "ADC16_ChannelConfigure()"
function, which works like writing a conversion command and executing it. For another channel's conversion,
just to change the "channelNumber" field in channel's configuration structure, and call the
"ADC16_ChannelConfigure() again.
*/
ADC16_SetChannelConfig(DEMO_ADC16_BASE, DEMO_ADC16_CHANNEL_GROUP, &adc16ChannelConfigStruct);
while (0U == (kADC16_ChannelConversionDoneFlag &
ADC16_GetChannelStatusFlags(DEMO_ADC16_BASE, DEMO_ADC16_CHANNEL_GROUP)))
{
}
PRINTF("ADC Value: %d\r\n", ADC16_GetChannelConversionValue(DEMO_ADC16_BASE, DEMO_ADC16_CHANNEL_GROUP));
}
}
Hi Xiangjun
Yes, you are correct that the bus clock directly works - try however the kADC16_ClockSourceAlt1 instead (this is BUS_CLOCK / 2). With kADC16_ClockDivider4 it should be equivalent but you will see that also the KSDK code will hang in the calibration routine.
Regards
Mark
Hi, Mark,
you are right, if I use BUS_CLOCK / 2 as clock alternative, the ADC flag can not be set. I suppose that the BUS clock/2 signal is NOT connected to ADC module.
I will ask application team and hope they can give a confirmation.
BR
Xiangjun Rong
Hi Xiangjun
Many thanks for the confirmation!
It is strange that the BUS_CLOCK/2 source doesn't work (I tend to use that as default and have used/tested it on about 60 different K, KL, KE, KEA, KV, KM, KW derivatives and this is the first time that it hasn't worked).
Maybe be its a (new) errata? In any case it would be great to have an official technical response/explanation.
Regards
Mark
Hi Xiangjun
Note that the KE15's (another SCG + PCC based processor) user's manual is very clear on the ADC clocking:
[This has neither bus nor synchronous support].
In comparison, the KL28's description leaves one guessing!
Regards
Mark