00001
00067 #include "clksys_driver.h"
00068
00077 void CCPWrite( volatile uint8_t * address, uint8_t value )
00078 {
00079 AVR_ENTER_CRITICAL_REGION( );
00080 #ifdef __ICCAVR__
00081
00082 asm("movw r30, r16");
00083 #ifdef RAMPZ
00084 RAMPZ = 0;
00085 #endif
00086 asm("ldi r16, 0xD8 \n"
00087 "out 0x34, r16 \n"
00088 #if (__MEMORY_MODEL__ == 1)
00089 "st Z, r17 \n");
00090 #elif (__MEMORY_MODEL__ == 2)
00091 "st Z, r18 \n");
00092 #else
00093 "st Z, r19 \n");
00094 #endif
00095
00096 #elif defined __GNUC__
00097 volatile uint8_t * tmpAddr = address;
00098 #ifdef RAMPZ
00099 RAMPZ = 0;
00100 #endif
00101 asm volatile(
00102 "movw r30, %0" "\n\t"
00103 "ldi r16, %2" "\n\t"
00104 "out %3, r16" "\n\t"
00105 "st Z, %1" "\n\t"
00106 :
00107 : "r" (tmpAddr), "r" (value), "M" (CCP_IOREG_gc), "i" (&CCP)
00108 : "r16", "r30", "r31"
00109 );
00110
00111 #endif
00112 AVR_LEAVE_CRITICAL_REGION( );
00113 }
00114
00129 void CLKSYS_XOSC_Config( OSC_FRQRANGE_t freqRange,
00130 bool lowPower32kHz,
00131 OSC_XOSCSEL_t xoscModeSelection )
00132 {
00133 OSC.XOSCCTRL = (uint8_t) freqRange |
00134 ( lowPower32kHz ? OSC_X32KLPM_bm : 0 ) |
00135 xoscModeSelection;
00136 }
00137
00138
00155 void CLKSYS_PLL_Config( OSC_PLLSRC_t clockSource, uint8_t factor )
00156 {
00157 factor &= OSC_PLLFAC_gm;
00158 OSC.PLLCTRL = (uint8_t) clockSource | ( factor << OSC_PLLFAC_gp );
00159 }
00160
00161
00175 uint8_t CLKSYS_Disable( uint8_t oscSel )
00176 {
00177 OSC.CTRL &= ~oscSel;
00178 uint8_t clkEnabled = OSC.CTRL & oscSel;
00179 return clkEnabled;
00180 }
00181
00182
00194 void CLKSYS_Prescalers_Config( CLK_PSADIV_t PSAfactor,
00195 CLK_PSBCDIV_t PSBCfactor )
00196 {
00197 uint8_t PSconfig = (uint8_t) PSAfactor | PSBCfactor;
00198 CCPWrite( &CLK.PSCTRL, PSconfig );
00199 }
00200
00201
00213 uint8_t CLKSYS_Main_ClockSource_Select( CLK_SCLKSEL_t clockSource )
00214 {
00215 uint8_t clkCtrl = ( CLK.CTRL & ~CLK_SCLKSEL_gm ) | clockSource;
00216 CCPWrite( &CLK.CTRL, clkCtrl );
00217 clkCtrl = ( CLK.CTRL & clockSource );
00218 return clkCtrl;
00219 }
00220
00221
00229 void CLKSYS_RTC_ClockSource_Enable( CLK_RTCSRC_t clockSource )
00230 {
00231 CLK.RTCCTRL = ( CLK.RTCCTRL & ~CLK_RTCSRC_gm ) |
00232 clockSource |
00233 CLK_RTCEN_bm;
00234 }
00235
00236
00248 void CLKSYS_AutoCalibration_Enable( uint8_t clkSource, bool extReference )
00249 {
00250 OSC.DFLLCTRL = ( OSC.DFLLCTRL & ~clkSource ) |
00251 ( extReference ? clkSource : 0 );
00252 if (clkSource == OSC_RC2MCREF_bm) {
00253 DFLLRC2M.CTRL |= DFLL_ENABLE_bm;
00254 } else if (clkSource == OSC_RC32MCREF_bm) {
00255 DFLLRC32M.CTRL |= DFLL_ENABLE_bm;
00256 }
00257 }
00258
00259
00268 void CLKSYS_XOSC_FailureDetection_Enable( void )
00269 {
00270 CCPWrite( &OSC.XOSCFAIL, ( OSC_XOSCFDIF_bm | OSC_XOSCFDEN_bm ) );
00271 }
00272
00273
00280 void CLKSYS_Configuration_Lock( void )
00281 {
00282 CCPWrite( &CLK.LOCK, CLK_LOCK_bm );
00283 }
00284