This file defines a useful set of functions for DACIFB on AVR32 devices.
Definition in file dacifb.c.
#include <avr32/io.h>
#include "compiler.h"
#include "dacifb.h"
Go to the source code of this file.
Defines | |
#define | dacifb_us_delay(us, hsb_mhz_up) dacifb_ck_delay((us) * (hsb_mhz_up)) |
Waits during at least the specified delay before returning. | |
Functions | |
Bool | dacifb_check_eoc (volatile avr32_dacifb_t *dacifb, U8 channel) |
Check channel conversion status. | |
static void | dacifb_ck_delay (unsigned long ck) |
Waits during at least the specified delay before returning. | |
U8 | dacifb_configure (volatile avr32_dacifb_t *dacifb, dacifb_opt_t *p_dacifb_opt, U32 pb_hz) |
Configure DACIFB. Mandatory to call. If not called, DACIFB channels will have side effects. | |
U8 | dacifb_configure_channel (volatile avr32_dacifb_t *dacifb, U8 channel, dacifb_channel_opt_t *p_dacifb_channel_opt, U32 prescaler_clock_hz) |
Configure DACIFB specific channel.
| |
void | dacifb_get_calibration_data (volatile avr32_dacifb_t *dacifb, dacifb_opt_t *p_dacifb_opt, U8 instance) |
Get DACIFB Calibration Data. Mandatory to call if factory calibration data are wanted to be used. If not called, Calibration Data should be set by the application. | |
void | dacifb_reload_timer (volatile avr32_dacifb_t *dacifb, U8 channel, U8 timer_us, U32 prescaler_clock_hz) |
Reload Timer for Automatic Trigger on DAC. | |
void | dacifb_set_value (volatile avr32_dacifb_t *dacifb, U8 channel, Bool dual, U32 value) |
Set channel value. | |
void | dacifb_start_channel (volatile avr32_dacifb_t *dacifb, U8 channel, U32 cpu_hz) |
Start analog to digital conversion. |
#define dacifb_us_delay | ( | us, | |||
hsb_mhz_up | ) | dacifb_ck_delay((us) * (hsb_mhz_up)) |
Waits during at least the specified delay before returning.
us | Number of microseconds to wait. | |
hsb_mhz_up | Rounded-up HSB frequency in MHz. |
Definition at line 76 of file dacifb.c.
Referenced by dacifb_start_channel().
Bool dacifb_check_eoc | ( | volatile avr32_dacifb_t * | dacifb, | |
U8 | channel | |||
) |
Check channel conversion status.
*dacifb | Base address of the DACIFB | |
channel | channel to check (0 to 1) |
Definition at line 317 of file dacifb.c.
References DACIFB_STATUS_COMPLETED, and DACIFB_STATUS_NOT_COMPLETED.
00319 { 00320 Assert( dacifb!=NULL ); 00321 00322 // get SR register : EOC bit for channel 00323 return ((((dacifb->sr)&(channel<<AVR32_DACIFB_SR_DEA_OFFSET))==(channel<<AVR32_DACIFB_SR_DEA_OFFSET))? DACIFB_STATUS_COMPLETED : DACIFB_STATUS_NOT_COMPLETED); 00324 }
static void dacifb_ck_delay | ( | unsigned long | ck | ) | [static] |
Waits during at least the specified delay before returning.
ck | Number of HSB clock cycles to wait. |
Definition at line 56 of file dacifb.c.
00057 { 00058 // Use the CPU cycle counter (CPU and HSB clocks are the same). 00059 unsigned long delay_start_cycle = Get_system_register(AVR32_COUNT); 00060 unsigned long delay_end_cycle = delay_start_cycle + ck; 00061 00062 // To be safer, the end of wait is based on an inequality test, so CPU cycle 00063 // counter wrap around is checked. 00064 if (delay_start_cycle > delay_end_cycle) 00065 { 00066 while ((unsigned long)Get_system_register(AVR32_COUNT) > delay_end_cycle); 00067 } 00068 while ((unsigned long)Get_system_register(AVR32_COUNT) < delay_end_cycle); 00069 }
U8 dacifb_configure | ( | volatile avr32_dacifb_t * | dacifb, | |
dacifb_opt_t * | p_dacifb_opt, | |||
U32 | pb_hz | |||
) |
Configure DACIFB. Mandatory to call. If not called, DACIFB channels will have side effects.
*dacifb | Base address of the DACIFB | |
*p_dacifb_opt | Structure for the DACIFB core configuration | |
pb_hz | Periphal Bus frequency |
Definition at line 95 of file dacifb.c.
References dacifb_opt_t::channel_selection, DACIFB_CHI_MIN_VALUE, DACIFB_CONFIGURATION_ACCEPTED, DACIFB_CONFIGURATION_REFUSED, dacifb_opt_t::dual, dacifb_opt_t::gain_calibration_value, dacifb_opt_t::low_power, dacifb_opt_t::offset_calibration_value, dacifb_opt_t::prescaler_clock_hz, and dacifb_opt_t::reference.
Referenced by main().
00098 { 00099 U32 prescaler = 0; 00100 U32 counter = 0; 00101 00102 Assert( dacifb!=NULL ); 00103 00104 // Calibration of DAC 00105 dacifb->goc = (((p_dacifb_opt->offset_calibration_value<<AVR32_DACIFB_GOC_OCR_OFFSET)&AVR32_DACIFB_GOC_OCR_MASK)| 00106 ((p_dacifb_opt->gain_calibration_value<<AVR32_DACIFB_GOC_GCR_OFFSET)&AVR32_DACIFB_GOC_GCR_MASK)); 00107 00108 // Compute PRESC field 00109 prescaler = 31 - clz(pb_hz/p_dacifb_opt->prescaler_clock_hz); 00110 00111 // Check PRESC value 00112 if (prescaler > (1<<AVR32_DACIFB_TCR_PRESC_SIZE)) 00113 return DACIFB_CONFIGURATION_REFUSED; 00114 00115 // Update prescaler_clock_hz value 00116 p_dacifb_opt->prescaler_clock_hz = pb_hz / (1<<prescaler); 00117 00118 // Compute CHI field ( minimum value of 2us) 00119 counter = (p_dacifb_opt->prescaler_clock_hz/DACIFB_CHI_MIN_VALUE); 00120 00121 // Check CHI value 00122 if (counter > (1<<AVR32_DACIFB_TCR_CHI_SIZE)) 00123 return DACIFB_CONFIGURATION_REFUSED; 00124 00125 00126 // Sampling Rate Frequency 00127 dacifb->tcr |= ( ((prescaler<<AVR32_DACIFB_TCR_PRESC_OFFSET)&AVR32_DACIFB_TCR_PRESC_MASK)| 00128 ((counter<<AVR32_DACIFB_TCR_CHI_OFFSET)&AVR32_DACIFB_TCR_CHI_MASK) ); 00129 00130 // Channel Selection 00131 dacifb->cfr |= ((p_dacifb_opt->channel_selection<<AVR32_DACIFB_CFR_CHC_OFFSET)&AVR32_DACIFB_CFR_CHC_MASK); 00132 00133 // Reference Selection 00134 dacifb->cfr |= ((p_dacifb_opt->reference <<AVR32_DACIFB_CFR_REF_OFFSET)&AVR32_DACIFB_CFR_REF_MASK); 00135 00136 // Dual Data 00137 dacifb->cfr |= ((p_dacifb_opt->dual<<AVR32_DACIFB_CFR_DDA_OFFSET)&AVR32_DACIFB_CFR_DDA_MASK); 00138 00139 // Low Power Mode 00140 dacifb->cfr |= ((p_dacifb_opt->low_power <<AVR32_DACIFB_CFR_LP_OFFSET)&AVR32_DACIFB_CFR_LP_MASK); 00141 00142 // Enable DAC 00143 dacifb->cr |= AVR32_DACIFB_CR_EN_MASK; 00144 00145 return DACIFB_CONFIGURATION_ACCEPTED; 00146 }
U8 dacifb_configure_channel | ( | volatile avr32_dacifb_t * | dacifb, | |
U8 | channel, | |||
dacifb_channel_opt_t * | p_dacifb_channel_opt, | |||
U32 | prescaler_clock_hz | |||
) |
Configure DACIFB specific channel.
*dacifb | Base address of the ADCIFA | |
channel | DACIFB_CHANNEL_SELECTION_NONE / DACIFB_CHANNEL_SELECTION_A / DACIFB_CHANNEL_SELECTION_B / DACIFB_CHANNEL_SELECTION_AB | |
p_dacifb_channel_opt | Structure for the sequencer configuration | |
prescaler_clock_hz | Prescaler Clock in Hertz (should be > 500000Hz) |
Definition at line 148 of file dacifb.c.
References dacifb_channel_opt_t::auto_refresh_mode, DACIFB_CHANNEL_SELECTION_A, DACIFB_CHANNEL_SELECTION_AB, DACIFB_CHANNEL_SELECTION_B, DACIFB_CHRx_MAX_VALUE, DACIFB_CHRx_MIN_VALUE, DACIFB_CONFIGURATION_ACCEPTED, DACIFB_CONFIGURATION_REFUSED, DACIFB_TRIGGER_MODE_EVENT, DACIFB_TRIGGER_MODE_MANUAL, DACIFB_TRIGGER_MODE_TIMER, dacifb_channel_opt_t::data_round_enable, dacifb_channel_opt_t::data_shift, dacifb_channel_opt_t::left_adjustment, and dacifb_channel_opt_t::trigger_mode.
Referenced by main().
00152 { 00153 U32 prescaler_min = 0; 00154 U32 prescaler_max = 0; 00155 U32 prescaler = 0; 00156 00157 Assert( dacifb!=NULL ); 00158 00159 // Auto-refresh Mode 00160 if (p_dacifb_channel_opt->auto_refresh_mode == TRUE) 00161 { 00162 switch(channel) 00163 { 00164 case DACIFB_CHANNEL_SELECTION_A: 00165 dacifb->cr |= (AVR32_DACIFB_CR_ARAE_MASK); 00166 break; 00167 case DACIFB_CHANNEL_SELECTION_B: 00168 dacifb->cr |= (AVR32_DACIFB_CR_ARBE_MASK ); 00169 break; 00170 case DACIFB_CHANNEL_SELECTION_AB: 00171 dacifb->cr |= (AVR32_DACIFB_CR_ARAE_MASK)|(AVR32_DACIFB_CR_ARBE_MASK ); 00172 break; 00173 } 00174 } 00175 00176 // Compute CHRA/CHRB fields ( min value of 25us) 00177 prescaler_min = 31 - clz(prescaler_clock_hz/DACIFB_CHRx_MIN_VALUE); 00178 if (prescaler_min > 0) prescaler_min --; 00179 00180 // Check CHRA/CHRB fields 00181 if ( (prescaler_min > (1<<AVR32_DACIFB_TCR_CHRA_SIZE)) || 00182 (prescaler_min > (1<<AVR32_DACIFB_TCR_CHRB_SIZE)) ) 00183 return DACIFB_CONFIGURATION_REFUSED; 00184 00185 // Compute CHRA/CHRB fields ( max value of 35us) 00186 prescaler_max = 31 - clz(prescaler_clock_hz/DACIFB_CHRx_MAX_VALUE); 00187 if (prescaler_max > 0) prescaler_max --; 00188 00189 // Check CHRA/CHRB fields 00190 if ( (prescaler_max > (1<<AVR32_DACIFB_TCR_CHRA_SIZE)) || 00191 (prescaler_max > (1<<AVR32_DACIFB_TCR_CHRB_SIZE)) ) 00192 return DACIFB_CONFIGURATION_REFUSED; 00193 00194 // Find value for CHRA/CHRB in the range min/max values 25us/35us and stop if it is not possible. 00195 prescaler = 0; 00196 while ((prescaler<<1) < prescaler_min) 00197 { 00198 prescaler++; 00199 } 00200 // If value found is out of range, configuration refused 00201 if ((prescaler<<1) > prescaler_max) 00202 return DACIFB_CONFIGURATION_REFUSED; 00203 00204 // Refresh Time 00205 switch(channel) 00206 { 00207 case DACIFB_CHANNEL_SELECTION_A: 00208 dacifb->tcr |= ((prescaler<<AVR32_DACIFB_TCR_CHRA_OFFSET)&AVR32_DACIFB_TCR_CHRA_MASK); 00209 break; 00210 case DACIFB_CHANNEL_SELECTION_B: 00211 dacifb->tcr |= ((prescaler<<AVR32_DACIFB_TCR_CHRB_OFFSET)&AVR32_DACIFB_TCR_CHRB_MASK); 00212 break; 00213 case DACIFB_CHANNEL_SELECTION_AB: 00214 dacifb->tcr |= ( ((prescaler<<AVR32_DACIFB_TCR_CHRA_OFFSET)&AVR32_DACIFB_TCR_CHRA_MASK) | 00215 ((prescaler<<AVR32_DACIFB_TCR_CHRB_OFFSET)&AVR32_DACIFB_TCR_CHRB_MASK) ); 00216 break; 00217 } 00218 00219 // Trigger Mode 00220 switch(channel) 00221 { 00222 case DACIFB_CHANNEL_SELECTION_A: 00223 if (p_dacifb_channel_opt->trigger_mode!=DACIFB_TRIGGER_MODE_MANUAL) 00224 { 00225 dacifb->cfr |= (AVR32_DACIFB_CFR_AAE_MASK); 00226 } 00227 if (p_dacifb_channel_opt->trigger_mode==DACIFB_TRIGGER_MODE_EVENT) 00228 { 00229 dacifb->ecr |= (AVR32_DACIFB_ECR_ESLA_MASK); 00230 } 00231 else if (p_dacifb_channel_opt->trigger_mode==DACIFB_TRIGGER_MODE_TIMER) 00232 { 00233 dacifb->cr |= (AVR32_DACIFB_CR_TRAE_MASK); 00234 } 00235 break; 00236 case DACIFB_CHANNEL_SELECTION_B: 00237 if (p_dacifb_channel_opt->trigger_mode!=DACIFB_TRIGGER_MODE_MANUAL) 00238 { 00239 dacifb->cfr |= (AVR32_DACIFB_CFR_ABE_MASK); 00240 } 00241 if (p_dacifb_channel_opt->trigger_mode==DACIFB_TRIGGER_MODE_EVENT) 00242 { 00243 dacifb->ecr |= (AVR32_DACIFB_ECR_ESLB_MASK); 00244 } 00245 else if (p_dacifb_channel_opt->trigger_mode==DACIFB_TRIGGER_MODE_TIMER) 00246 { 00247 dacifb->cr |= (AVR32_DACIFB_CR_TRBE_MASK); 00248 } 00249 break; 00250 case DACIFB_CHANNEL_SELECTION_AB: 00251 if (p_dacifb_channel_opt->trigger_mode!=DACIFB_TRIGGER_MODE_MANUAL) 00252 { 00253 dacifb->cfr |= (AVR32_DACIFB_CFR_AAE_MASK)|(AVR32_DACIFB_CFR_ABE_MASK); 00254 } 00255 if (p_dacifb_channel_opt->trigger_mode==DACIFB_TRIGGER_MODE_EVENT) 00256 { 00257 dacifb->ecr |= (AVR32_DACIFB_ECR_ESLA_MASK)|(AVR32_DACIFB_ECR_ESLB_MASK); 00258 } 00259 else if (p_dacifb_channel_opt->trigger_mode==DACIFB_TRIGGER_MODE_TIMER) 00260 { 00261 dacifb->cr |= (AVR32_DACIFB_CR_TRAE_MASK)|(AVR32_DACIFB_CR_TRBE_MASK); 00262 } 00263 break; 00264 } 00265 00266 00267 // Left Adjust/ Shift Value / Data Rounding 00268 switch(channel) 00269 { 00270 case DACIFB_CHANNEL_SELECTION_A: 00271 dacifb->drca |= (((p_dacifb_channel_opt->left_adjustment<<AVR32_DACIFB_DRCA_DSD_OFFSET)&AVR32_DACIFB_DRCA_DSD_MASK) | 00272 ((p_dacifb_channel_opt->data_shift<<AVR32_DACIFB_DRCA_DSV_OFFSET)&AVR32_DACIFB_DRCA_DSV_MASK) | 00273 ((p_dacifb_channel_opt->data_round_enable<<AVR32_DACIFB_DRCA_DRN_OFFSET)&AVR32_DACIFB_DRCA_DRN_MASK)); 00274 break; 00275 case DACIFB_CHANNEL_SELECTION_B: 00276 dacifb->drcb |= (((p_dacifb_channel_opt->left_adjustment<<AVR32_DACIFB_DRCB_DSD_OFFSET)&AVR32_DACIFB_DRCB_DSD_MASK) | 00277 ((p_dacifb_channel_opt->data_shift<<AVR32_DACIFB_DRCB_DSV_OFFSET)&AVR32_DACIFB_DRCB_DSV_MASK) | 00278 ((p_dacifb_channel_opt->data_round_enable<<AVR32_DACIFB_DRCB_DRN_OFFSET)&AVR32_DACIFB_DRCB_DRN_MASK)); 00279 break; 00280 case DACIFB_CHANNEL_SELECTION_AB: 00281 dacifb->drca |= (((p_dacifb_channel_opt->left_adjustment<<AVR32_DACIFB_DRCA_DSD_OFFSET)&AVR32_DACIFB_DRCA_DSD_MASK) | 00282 ((p_dacifb_channel_opt->data_shift<<AVR32_DACIFB_DRCA_DSV_OFFSET)&AVR32_DACIFB_DRCA_DSV_MASK) | 00283 ((p_dacifb_channel_opt->data_round_enable<<AVR32_DACIFB_DRCA_DRN_OFFSET)&AVR32_DACIFB_DRCA_DRN_MASK)); 00284 dacifb->drcb |= (((p_dacifb_channel_opt->left_adjustment<<AVR32_DACIFB_DRCB_DSD_OFFSET)&AVR32_DACIFB_DRCB_DSD_MASK) | 00285 ((p_dacifb_channel_opt->data_shift<<AVR32_DACIFB_DRCB_DSV_OFFSET)&AVR32_DACIFB_DRCB_DSV_MASK) | 00286 ((p_dacifb_channel_opt->data_round_enable<<AVR32_DACIFB_DRCB_DRN_OFFSET)&AVR32_DACIFB_DRCB_DRN_MASK)); 00287 break; 00288 } 00289 return DACIFB_CONFIGURATION_ACCEPTED; 00290 }
void dacifb_get_calibration_data | ( | volatile avr32_dacifb_t * | dacifb, | |
dacifb_opt_t * | p_dacifb_opt, | |||
U8 | instance | |||
) |
Get DACIFB Calibration Data. Mandatory to call if factory calibration data are wanted to be used. If not called, Calibration Data should be set by the application.
*dacifb | Base address of the DACIFB | |
*p_dacifb_opt | Structure for the DACIFB core configuration | |
instance | DACIFB core instance 0 for DACIFB0 or 1 for DACIFB1 |
Definition at line 78 of file dacifb.c.
References dacifb_opt_t::gain_calibration_value, and dacifb_opt_t::offset_calibration_value.
Referenced by main().
00081 { 00082 unsigned int* calibration_data = (unsigned int*)AVR32_FLASHC_CALIBRATION_FOURTH_WORD_ADDRESS; 00083 if (instance == 0) 00084 { 00085 p_dacifb_opt->offset_calibration_value = (*calibration_data >> 6); 00086 p_dacifb_opt->gain_calibration_value = ((*calibration_data >> 14)&0x3F); 00087 } 00088 else 00089 { 00090 p_dacifb_opt->offset_calibration_value = ((*calibration_data >> 22)&0x3F); 00091 p_dacifb_opt->gain_calibration_value = ((*calibration_data >> 30)&0x3F); 00092 } 00093 }
void dacifb_reload_timer | ( | volatile avr32_dacifb_t * | dacifb, | |
U8 | channel, | |||
U8 | timer_us, | |||
U32 | prescaler_clock_hz | |||
) |
Reload Timer for Automatic Trigger on DAC.
*dacifb | Base address of the DACIFB | |
channel | DACIFB_CHANNEL_SELECTION_NONE / DACIFB_CHANNEL_SELECTION_A / DACIFB_CHANNEL_SELECTION_B / DACIFB_CHANNEL_SELECTION_AB | |
timer_us | Timer Value in Microsecondes | |
prescaler_clock_hz | Prescaler Clock in Hertz (should be > 500000Hz) |
Definition at line 356 of file dacifb.c.
References DACIFB_CHANNEL_SELECTION_A, DACIFB_CHANNEL_SELECTION_AB, and DACIFB_CHANNEL_SELECTION_B.
Referenced by main().
00360 { 00361 U32 timer; 00362 00363 Assert( dacifb != NULL ); 00364 00365 timer = ( (timer_us * prescaler_clock_hz)/500000); 00366 // Reload Timer Valuie 00367 switch(channel) 00368 { 00369 case DACIFB_CHANNEL_SELECTION_A: 00370 dacifb->tra = (AVR32_DACIFB_TRA_TRL_MASK)|((timer<<AVR32_DACIFB_TRA_TCD_OFFSET)&AVR32_DACIFB_TRA_TCD_MASK); 00371 break; 00372 case DACIFB_CHANNEL_SELECTION_B: 00373 dacifb->trb = (AVR32_DACIFB_TRB_TRL_MASK)|((timer<<AVR32_DACIFB_TRB_TCD_OFFSET)&AVR32_DACIFB_TRB_TCD_MASK); 00374 break; 00375 case DACIFB_CHANNEL_SELECTION_AB: 00376 dacifb->tra = (AVR32_DACIFB_TRA_TRL_MASK)|((timer<<AVR32_DACIFB_TRA_TCD_OFFSET)&AVR32_DACIFB_TRA_TCD_MASK); 00377 dacifb->trb = (AVR32_DACIFB_TRB_TRL_MASK)|((timer<<AVR32_DACIFB_TRB_TCD_OFFSET)&AVR32_DACIFB_TRB_TCD_MASK); 00378 break; 00379 } 00380 }
void dacifb_set_value | ( | volatile avr32_dacifb_t * | dacifb, | |
U8 | channel, | |||
Bool | dual, | |||
U32 | value | |||
) |
Set channel value.
*dacifb | Base address of the DACIFB | |
channel | channel to handle (0 to 1) | |
dual | Dual Mode Selection | |
value | Value to be converted |
Definition at line 327 of file dacifb.c.
References DACIFB_CHANNEL_SELECTION_A, DACIFB_CHANNEL_SELECTION_AB, and DACIFB_CHANNEL_SELECTION_B.
00331 { 00332 Assert( dacifb != NULL ); 00333 00334 // Set new conversion value 00335 switch(channel) 00336 { 00337 case DACIFB_CHANNEL_SELECTION_A: 00338 dacifb->dr0 = (value); 00339 break; 00340 case DACIFB_CHANNEL_SELECTION_B: 00341 dacifb->dr1 = (value); 00342 break; 00343 case DACIFB_CHANNEL_SELECTION_AB: 00344 if(dual==TRUE) 00345 { 00346 dacifb->dr0 = value; 00347 } 00348 else 00349 { 00350 dacifb->dr0 = ((value&0x00FF) | ( (value&0xFF00>>16)<<16)); 00351 } 00352 break; 00353 } 00354 }
void dacifb_start_channel | ( | volatile avr32_dacifb_t * | dacifb, | |
U8 | channel, | |||
U32 | cpu_hz | |||
) |
Start analog to digital conversion.
*dacifb | Base address of the DACIFB | |
channel | DACIFB_CHANNEL_SELECTION_NONE / DACIFB_CHANNEL_SELECTION_A / DACIFB_CHANNEL_SELECTION_B / DACIFB_CHANNEL_SELECTION_AB | |
cpu_hz | CPU Clock frequency |
Definition at line 292 of file dacifb.c.
References DACIFB_CHANNEL_SELECTION_A, DACIFB_CHANNEL_SELECTION_AB, DACIFB_CHANNEL_SELECTION_B, and dacifb_us_delay.
Referenced by main().
00295 { 00296 Assert( dacifb!=NULL ); 00297 00298 // Wait 2us 00299 dacifb_us_delay(2,cpu_hz); 00300 00301 switch(channel) 00302 { 00303 case DACIFB_CHANNEL_SELECTION_A: 00304 dacifb->cr |= (AVR32_DACIFB_CR_AOE_MASK); 00305 break; 00306 case DACIFB_CHANNEL_SELECTION_B: 00307 dacifb->cr |= (AVR32_DACIFB_CR_BOE_MASK ); 00308 break; 00309 case DACIFB_CHANNEL_SELECTION_AB: 00310 dacifb->cr |= (AVR32_DACIFB_CR_AOE_MASK | AVR32_DACIFB_CR_BOE_MASK ); 00311 break; 00312 } 00313 00314 }