diff options
author | inmarket <andrewh@inmarket.com.au> | 2014-03-20 23:41:27 +1000 |
---|---|---|
committer | inmarket <andrewh@inmarket.com.au> | 2014-03-20 23:41:27 +1000 |
commit | 271f0c743f31d3ae21ede35909e1f14845c6d338 (patch) | |
tree | 03541486e35fd48b3dd76db6c0470a8d860cd964 /drivers | |
parent | 712ff73f77763eeee798d6913f57e5577adcef3f (diff) | |
download | uGFX-271f0c743f31d3ae21ede35909e1f14845c6d338.tar.gz uGFX-271f0c743f31d3ae21ede35909e1f14845c6d338.tar.bz2 uGFX-271f0c743f31d3ae21ede35909e1f14845c6d338.zip |
Updates to GADC to use new simpler gfx queued bufferring.
NOTE: code is still buggy (or the one and only driver is buggy).
Diffstat (limited to 'drivers')
-rw-r--r-- | drivers/gadc/AT91SAM7/gadc_lld.c | 72 | ||||
-rw-r--r-- | drivers/gadc/AT91SAM7/gadc_lld_config.h | 7 | ||||
-rw-r--r-- | drivers/gaudio/gadc/gaudio_record_board_template.h | 8 | ||||
-rw-r--r-- | drivers/gaudio/gadc/gaudio_record_config.h | 18 | ||||
-rw-r--r-- | drivers/gaudio/gadc/gaudio_record_lld.c | 34 |
5 files changed, 82 insertions, 57 deletions
diff --git a/drivers/gadc/AT91SAM7/gadc_lld.c b/drivers/gadc/AT91SAM7/gadc_lld.c index f18f2717..52b06539 100644 --- a/drivers/gadc/AT91SAM7/gadc_lld.c +++ b/drivers/gadc/AT91SAM7/gadc_lld.c @@ -8,10 +8,6 @@ /** * @file drivers/gadc/AT91SAM7/gadc_lld.c * @brief GADC - Periodic ADC driver source file for the AT91SAM7 cpu. - * - * @defgroup Driver Driver - * @ingroup GADC - * @{ */ #include "gfx.h" @@ -20,44 +16,76 @@ #include "src/gadc/driver.h" +static GDataBuffer *pData; +static size_t bytesperconversion; + +static void ISR_CompleteI(ADCDriver *adcp, adcsample_t *buffer, size_t n); +static void ISR_ErrorI(ADCDriver *adcp, adcerror_t err); + + static ADCConversionGroup acg = { FALSE, // circular 1, // num_channels - GADC_ISR_CompleteI, // end_cb - GADC_ISR_ErrorI, // error_cb + ISR_CompleteI, // end_cb + ISR_ErrorI, // error_cb 0, // channelselects 0, // trigger 0, // frequency }; +static void ISR_CompleteI(ADCDriver *adcp, adcsample_t *buffer, size_t n) { + (void) adcp; + (void) buffer; + + if (pData) { + // A set of timer base conversions is complete + pData->len += n * bytesperconversion; + + // Are we finished yet? + // In ChibiOS we (may) get a half-buffer complete. In this situation the conversions + // are really not complete and so we just wait for the next lot of data. + if (pData->len + bytesperconversion > pData->size) + gadcDataReadyI(); + + } else { + // A single non-timer conversion is complete + gadcDataReadyI(); + } +} + +static void ISR_ErrorI(ADCDriver *adcp, adcerror_t err) { + (void) adcp; + (void) err; + + gadcDataFailI(); +} + void gadc_lld_init(void) { adcStart(&ADCD1, 0); } -size_t gadc_lld_samples_per_conversion(uint32_t physdev) { - size_t cnt; - int i; +void gadc_lld_start_timer(GadcLldTimerData *pgtd) { + int phys; + /* Calculate the bytes per conversion from physdev */ /* The AT91SAM7 has AD0..7 - physdev is a bitmap of those channels */ - for(cnt = 0, i = 0; i < 8; i++, physdev >>= 1) - if (physdev & 0x01) - cnt++; - return cnt; -} + phys = pgtd->physdev; + for(bytesperconversion = 0; phys; phys >>= 1) + if (phys & 0x01) + bytesperconversion++; + bytesperconversion *= (gfxSampleFormatBits(GADC_SAMPLE_FORMAT)+7)/8; -void gadc_lld_start_timer(uint32_t physdev, uint32_t frequency) { - (void) physdev; /** * The AT91SAM7 ADC driver supports triggering the ADC using a timer without having to implement * an interrupt handler for the timer. The driver also initialises the timer correctly for us. * Because we aren't trapping the interrupt ourselves we can't increment GADC_Timer_Missed if an * interrupt is missed. */ - acg.frequency = frequency; + acg.frequency = pgtd->frequency; } -void gadc_lld_stop_timer(uint32_t physdev) { - (void) physdev; +void gadc_lld_stop_timer(GadcLldTimerData *pgtd) { + (void) pgtd; if ((acg.trigger & ~ADC_TRIGGER_SOFTWARE) == ADC_TRIGGER_TIMER) adcStop(&ADCD1); } @@ -69,7 +97,8 @@ void gadc_lld_adc_timerI(GadcLldTimerData *pgtd) { acg.channelselects = pgtd->physdev; acg.trigger = pgtd->now ? (ADC_TRIGGER_TIMER|ADC_TRIGGER_SOFTWARE) : ADC_TRIGGER_TIMER; - adcStartConversionI(&ADCD1, &acg, pgtd->buffer, pgtd->count); + pData = pgtd->pdata; + adcStartConversionI(&ADCD1, &acg, (adcsample_t *)(pgtd->pdata+1), pData->size/bytesperconversion); /* Next time assume the same (still running) timer */ acg.frequency = 0; @@ -81,8 +110,9 @@ void gadc_lld_adc_nontimerI(GadcLldNonTimerData *pgntd) { */ acg.channelselects = pgntd->physdev; acg.trigger = ADC_TRIGGER_SOFTWARE; + + pData = 0; adcStartConversionI(&ADCD1, &acg, pgntd->buffer, 1); } #endif /* GFX_USE_GADC */ -/** @} */ diff --git a/drivers/gadc/AT91SAM7/gadc_lld_config.h b/drivers/gadc/AT91SAM7/gadc_lld_config.h index ba6cbda2..de5af3d3 100644 --- a/drivers/gadc/AT91SAM7/gadc_lld_config.h +++ b/drivers/gadc/AT91SAM7/gadc_lld_config.h @@ -35,7 +35,7 @@ * @note For the AT91SAM7 ADC driver, it post-dates the finding of the bug so we safely * say that the bug doesn't exist for this driver. */ -#define ADC_ISR_FULL_CODE_BUG FALSE +#define CHIBIOS_ADC_ISR_FULL_CODE_BUG FALSE /** * @brief The maximum sample frequency supported by this CPU @@ -43,11 +43,6 @@ #define GADC_MAX_SAMPLE_FREQUENCY 132000 /** - * @brief The number of bits in a sample - */ -#define GADC_BITS_PER_SAMPLE AT91_ADC1_RESOLUTION - -/** * @brief The sample format */ #define GADC_SAMPLE_FORMAT ARRAY_DATA_10BITUNSIGNED diff --git a/drivers/gaudio/gadc/gaudio_record_board_template.h b/drivers/gaudio/gadc/gaudio_record_board_template.h index 26e87d88..59168be1 100644 --- a/drivers/gaudio/gadc/gaudio_record_board_template.h +++ b/drivers/gaudio/gadc/gaudio_record_board_template.h @@ -27,6 +27,12 @@ #define GAUDIO_RECORD_NUM_CHANNELS 1 /** + * @brief Whether each channel is mono or stereo + * @note This is an example + */ +#define GAUDIO_RECORD_CHANNEL0_IS_STEREO FALSE + +/** * @brief The list of audio channels and their uses * @note This is an example * @{ @@ -40,7 +46,7 @@ * @{ */ #ifdef GAUDIO_RECORD_LLD_IMPLEMENTATION - static uint32_t gaudin_lld_physdevs[GAUDIO_RECORD_NUM_CHANNELS] = { + static uint32_t gaudio_gadc_physdevs[GAUDIO_RECORD_NUM_CHANNELS] = { GADC_PHYSDEV_MICROPHONE, }; #endif diff --git a/drivers/gaudio/gadc/gaudio_record_config.h b/drivers/gaudio/gadc/gaudio_record_config.h index 22d8750f..88092a63 100644 --- a/drivers/gaudio/gadc/gaudio_record_config.h +++ b/drivers/gaudio/gadc/gaudio_record_config.h @@ -23,28 +23,20 @@ /*===========================================================================*/ /** - * @brief The audio record sample type - * @details For this driver it matches the cpu sample type - */ -typedef adcsample_t audio_record_sample_t; - -/** * @brief The maximum sample frequency supported by this audio device * @details For this driver it matches the GADC maximum high speed sample rate */ -#define GAUDIO_RECORD_MAX_SAMPLE_FREQUENCY GADC_MAX_HIGH_SPEED_SAMPLERATE +#define GAUDIO_RECORD_MAX_SAMPLE_FREQUENCY GADC_MAX_HIGH_SPEED_SAMPLERATE /** - * @brief The number of bits in a sample - * @details For this driver it matches the cpu sample bits + * @brief The number of audio formats supported by this driver */ -#define GAUDIO_RECORD_BITS_PER_SAMPLE GADC_BITS_PER_SAMPLE +#define GAUDIO_RECORD_NUM_FORMATS 1 /** - * @brief The format of an audio sample - * @details For this driver it matches the cpu sample format + * @brief The available audio sample formats in order of preference */ -#define GAUDIO_RECORD_SAMPLE_FORMAT GADC_SAMPLE_FORMAT +#define GAUDIO_RECORD_FORMAT1 GADC_SAMPLE_FORMAT /** * For the GAUDIO driver that uses GADC - all the remaining config definitions are specific diff --git a/drivers/gaudio/gadc/gaudio_record_lld.c b/drivers/gaudio/gadc/gaudio_record_lld.c index ee994dc1..6f4cb2de 100644 --- a/drivers/gaudio/gadc/gaudio_record_lld.c +++ b/drivers/gaudio/gadc/gaudio_record_lld.c @@ -8,10 +8,6 @@ /** * @file drivers/gaudio/gadc/gaudio_record_lld.c * @brief GAUDIO - Record Driver file for using the cpu ADC (via GADC). - * - * @addtogroup GAUDIO - * - * @{ */ /** @@ -19,8 +15,6 @@ * from the board definitions. */ #define GAUDIO_RECORD_IMPLEMENTATION - - #include "gfx.h" #if GFX_USE_GAUDIO && GAUDIO_NEED_RECORD @@ -33,30 +27,38 @@ /* Include the driver defines */ #include "src/gaudio/driver_record.h" +static void gadcCallbackI(void) { + GDataBuffer *pd; + + pd = gadcHighSpeedGetDataI(); + if (pd) + gaudioRecordSaveDataBlockI(pd); +} + /*===========================================================================*/ /* External declarations. */ /*===========================================================================*/ -void gaudin_lld_init(const gaudin_params *paud) { +bool_t gaudio_record_lld_init(uint16_t channel, uint32_t frequency, ArrayDataFormat format) { + /* Check the parameters */ + if (channel >= GAUDIO_RECORD_NUM_CHANNELS || frequency > GAUDIO_RECORD_MAX_SAMPLE_FREQUENCY || format != GAUDIO_RECORD_FORMAT1) + return FALSE; + /* Setup the high speed GADC */ - gadcHighSpeedInit(gaudin_lld_physdevs[paud->channel], paud->frequency, paud->buffer, paud->bufcount, paud->samplesPerEvent); + gadcHighSpeedInit(gaudio_gadc_physdevs[channel], frequency); /* Register ourselves for ISR callbacks */ - gadcHighSpeedSetISRCallback(GAUDIN_ISR_CompleteI); + gadcHighSpeedSetISRCallback(gadcCallbackI); - /** - * The gadc driver handles any errors for us by restarting the transaction so there is - * no need for us to setup anything for GAUDIN_ISR_ErrorI() - */ + return TRUE; } -void gaudin_lld_start(void) { +void gaudio_record_lld_start(void) { gadcHighSpeedStart(); } -void gaudin_lld_stop(void) { +void gaudio_record_lld_stop(void) { gadcHighSpeedStop(); } #endif /* GFX_USE_GAUDIO && GAUDIO_NEED_RECORD */ -/** @} */ |