Fix the initialisation and operation of the PX4IO ADC - now RSSI and VSERVO voltages should be read correctly.

This commit is contained in:
px4dev 2014-01-22 23:51:53 -08:00
parent 1ac8501d95
commit 0994412cca
2 changed files with 26 additions and 30 deletions

View File

@ -83,6 +83,14 @@ adc_init(void)
{ {
adc_perf = perf_alloc(PC_ELAPSED, "adc"); adc_perf = perf_alloc(PC_ELAPSED, "adc");
/* put the ADC into power-down mode */
rCR2 &= ~ADC_CR2_ADON;
up_udelay(10);
/* bring the ADC out of power-down mode */
rCR2 |= ADC_CR2_ADON;
up_udelay(10);
/* do calibration if supported */ /* do calibration if supported */
#ifdef ADC_CR2_CAL #ifdef ADC_CR2_CAL
rCR2 |= ADC_CR2_RSTCAL; rCR2 |= ADC_CR2_RSTCAL;
@ -96,41 +104,25 @@ adc_init(void)
if (rCR2 & ADC_CR2_CAL) if (rCR2 & ADC_CR2_CAL)
return -1; return -1;
#endif #endif
/* arbitrarily configure all channels for 55 cycle sample time */ /*
rSMPR1 = 0b00000011011011011011011011011011; * Configure sampling time.
*
* For electrical protection reasons, we want to be able to have
* 10K in series with ADC inputs that leave the board. At 12MHz this
* means we need 28.5 cycles of sampling time (per table 43 in the
* datasheet).
*/
rSMPR1 = 0b00000000011011011011011011011011;
rSMPR2 = 0b00011011011011011011011011011011; rSMPR2 = 0b00011011011011011011011011011011;
/* XXX for F2/4, might want to select 12-bit mode? */ rCR2 |= ADC_CR2_TSVREFE; /* enable the temperature sensor / Vrefint channel */
rCR1 = 0;
/* enable the temperature sensor / Vrefint channel if supported*/
rCR2 =
#ifdef ADC_CR2_TSVREFE
/* enable the temperature sensor in CR2 */
ADC_CR2_TSVREFE |
#endif
0;
#ifdef ADC_CCR_TSVREFE
/* enable temperature sensor in CCR */
rCCR = ADC_CCR_TSVREFE;
#endif
/* configure for a single-channel sequence */ /* configure for a single-channel sequence */
rSQR1 = 0; rSQR1 = 0;
rSQR2 = 0; rSQR2 = 0;
rSQR3 = 0; /* will be updated with the channel each tick */ rSQR3 = 0; /* will be updated with the channel at conversion time */
/* power-cycle the ADC and turn it on */
rCR2 &= ~ADC_CR2_ADON;
up_udelay(10);
rCR2 |= ADC_CR2_ADON;
up_udelay(10);
rCR2 |= ADC_CR2_ADON;
up_udelay(10);
return 0; return 0;
} }
@ -141,11 +133,12 @@ adc_init(void)
uint16_t uint16_t
adc_measure(unsigned channel) adc_measure(unsigned channel)
{ {
perf_begin(adc_perf); perf_begin(adc_perf);
/* clear any previous EOC */ /* clear any previous EOC */
if (rSR & ADC_SR_EOC) rSR = 0;
rSR &= ~ADC_SR_EOC; (void)rDR;
/* run a single conversion right now - should take about 60 cycles (a few microseconds) max */ /* run a single conversion right now - should take about 60 cycles (a few microseconds) max */
rSQR3 = channel; rSQR3 = channel;
@ -158,7 +151,6 @@ adc_measure(unsigned channel)
/* never spin forever - this will give a bogus result though */ /* never spin forever - this will give a bogus result though */
if (hrt_elapsed_time(&now) > 100) { if (hrt_elapsed_time(&now) > 100) {
debug("adc timeout");
perf_end(adc_perf); perf_end(adc_perf);
return 0xffff; return 0xffff;
} }
@ -166,6 +158,7 @@ adc_measure(unsigned channel)
/* read the result and clear EOC */ /* read the result and clear EOC */
uint16_t result = rDR; uint16_t result = rDR;
rSR = 0;
perf_end(adc_perf); perf_end(adc_perf);
return result; return result;

View File

@ -210,6 +210,9 @@ user_start(int argc, char *argv[])
/* initialise the control inputs */ /* initialise the control inputs */
controls_init(); controls_init();
/* set up the ADC */
adc_init();
/* start the FMU interface */ /* start the FMU interface */
interface_init(); interface_init();