1 /*******************************************************************************
4 * Provides Functions to Initialize the UCS/FLL and clock sources
7 * Copyright (C) 2010 Texas Instruments Incorporated - http://www.ti.com/
10 * Redistribution and use in source and binary forms, with or without
11 * modification, are permitted provided that the following conditions
14 * Redistributions of source code must retain the above copyright
15 * notice, this list of conditions and the following disclaimer.
17 * Redistributions in binary form must reproduce the above copyright
18 * notice, this list of conditions and the following disclaimer in the
19 * documentation and/or other materials provided with the
22 * Neither the name of Texas Instruments Incorporated nor the names of
23 * its contributors may be used to endorse or promote products derived
24 * from this software without specific prior written permission.
26 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
27 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
28 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
29 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
30 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
31 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
32 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
33 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
34 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
35 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
36 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
38 * Created: Version 1.0 11/24/2009
39 * Updated: Version 2.0 12/15/2010
40 * Added Functions: XT2_Stop() and XT1_Stop()
41 * Modified all functions to preserve drive settings
43 ******************************************************************************/
47 // #include "hal_calibration.h"
49 /*******************************************************************************
50 * Check and define required Defines
51 ******************************************************************************/
52 #ifndef XT1LFOFFG // Defines if not available in header file
56 #ifndef XT1HFOFFG // Defines if not available in header file
60 #ifndef XT2OFFG // Defines if not available in header file
64 #ifndef XTS // Defines if not available in header file
68 #ifndef XT2DRIVE_3 // Defines if not available in header file
73 /*******************************************************************************
74 * \brief Initializes FLL of the UCS
76 * \param fsystem Required system frequency (MCLK) in kHz
77 * \param ratio Ratio between fsystem and FLLREFCLK
78 ******************************************************************************/
79 static void Init_FLL(unsigned int fsystem, unsigned int ratio);
83 void LFXT_Start(unsigned int xtdrive)
85 // If the drive setting is not already set to maximum
86 // Set it to max for LFXT startup
87 if ((UCSCTL6 & XT1DRIVE_3)!= XT1DRIVE_3) {
88 UCSCTL6_L |= XT1DRIVE1_L + XT1DRIVE0_L; // Highest drive setting for XT1startup
91 while (SFRIFG1 & OFIFG) { // Check OFIFG fault flag
92 UCSCTL7 &= ~(DCOFFG+XT1LFOFFG+XT1HFOFFG+XT2OFFG); // Clear OSC flaut Flags fault flags
93 SFRIFG1 &= ~OFIFG; // Clear OFIFG fault flag
96 UCSCTL6 = (UCSCTL6 & ~(XT1DRIVE_3)) | (xtdrive); // set requested Drive mode
100 unsigned int LFXT_Start_Timeout(unsigned int xtdrive, unsigned int timeout)
102 // add in capacitor setting
103 //SetOscillatorCapacitorValues();
105 // If the drive setting is not already set to maximum
106 // Set it to max for LFXT startup
107 if ((UCSCTL6 & XT1DRIVE_3)!= XT1DRIVE_3) {
108 UCSCTL6_L |= XT1DRIVE1_L+XT1DRIVE0_L; // Highest drive setting for XT1startup
111 while ((SFRIFG1 & OFIFG) && timeout--){ // Check OFIFG fault flag
112 UCSCTL7 &= ~(DCOFFG+XT1LFOFFG+XT1HFOFFG+XT2OFFG); // Clear OSC flaut Flags fault flags
113 SFRIFG1 &= ~OFIFG; // Clear OFIFG fault flag
116 UCSCTL6 = (UCSCTL6 & ~(XT1DRIVE_3)) |(xtdrive); // set Drive mode
118 // add in capacitor setting
119 //SetOscillatorCapacitorValues();
122 return (UCS_STATUS_OK);
124 return (UCS_STATUS_ERROR);
128 void XT1_Start(unsigned int xtdrive)
130 // Check if drive value is the expected one
131 if ((UCSCTL6 & XT1DRIVE_3) != xtdrive) {
132 UCSCTL6 &= ~XT1DRIVE_3; // Clear XT1drive field
133 UCSCTL6 |= xtdrive; // Set requested value
136 UCSCTL6 &= ~XT1OFF; // Enable XT1
137 UCSCTL6 |= XTS; // Enable HF mode
139 while (SFRIFG1 & OFIFG) { // Check OFIFG fault flag
140 UCSCTL7 &= ~(DCOFFG+XT1LFOFFG+XT1HFOFFG+XT2OFFG); // Clear OSC flaut Flags
141 SFRIFG1 &= ~OFIFG; // Clear OFIFG fault flag
145 unsigned int XT1_Start_Timeout(unsigned int xtdrive, unsigned int timeout)
147 // Check if drive value is the expected one
148 if ((UCSCTL6 & XT1DRIVE_3) != xtdrive) {
149 UCSCTL6 &= ~XT1DRIVE_3; // Clear XT1drive field
150 UCSCTL6 |= xtdrive; // Set requested value
153 UCSCTL6 &= ~XT1OFF; // Enable XT1
154 UCSCTL6 |= XTS; // Enable HF mode
156 while ((SFRIFG1 & OFIFG) && timeout--) { // Check OFIFG fault flag
157 UCSCTL7 &= ~(DCOFFG+XT1LFOFFG+XT1HFOFFG+XT2OFFG); // Clear OSC flaut Flags
158 SFRIFG1 &= ~OFIFG; // Clear OFIFG fault flag
162 return UCS_STATUS_OK;
165 return UCS_STATUS_ERROR;
169 void XT1_Bypass(void)
171 UCSCTL6 |= XT1BYPASS;
173 while (SFRIFG1 & OFIFG) { // Check OFIFG fault flag
174 UCSCTL7 &= ~(DCOFFG+XT1LFOFFG+XT1HFOFFG+XT2OFFG); // Clear OSC flaut Flags
175 SFRIFG1 &= ~OFIFG; // Clear OFIFG fault flag
182 UCSCTL6 |= XT1OFF; // Switch off XT1 oscillator
186 void XT2_Start(unsigned int xtdrive)
188 // Check if drive value is the expected one
189 if ((UCSCTL6 & XT2DRIVE_3) != xtdrive) {
190 UCSCTL6 &= ~XT2DRIVE_3; // Clear XT2drive field
191 UCSCTL6 |= xtdrive; // Set requested value
196 while (SFRIFG1 & OFIFG) { // Check OFIFG fault flag
197 UCSCTL7 &= ~(DCOFFG+XT1LFOFFG+XT1HFOFFG+XT2OFFG); // Clear OSC flaut Flags
198 SFRIFG1 &= ~OFIFG; // Clear OFIFG fault flag
202 unsigned int XT2_Start_Timeout(unsigned int xtdrive, unsigned int timeout)
204 // Check if drive value is the expected one
205 if ((UCSCTL6 & XT2DRIVE_3) != xtdrive) {
206 UCSCTL6 &= ~XT2DRIVE_3; // Clear XT2drive field
207 UCSCTL6 |= xtdrive; // Set requested value
212 while ((SFRIFG1 & OFIFG) && timeout--) { // Check OFIFG fault flag
213 UCSCTL7 &= ~(DCOFFG+XT1LFOFFG+XT1HFOFFG+XT2OFFG); // Clear OSC flaut Flags
214 SFRIFG1 &= ~OFIFG; // Clear OFIFG fault flag
218 return UCS_STATUS_OK;
221 return UCS_STATUS_ERROR;
225 void XT2_Bypass(void)
227 #ifdef XT2BYPASS // On devices without XT2 this function will be empty
228 UCSCTL6 |= XT2BYPASS;
230 while (SFRIFG1 & OFIFG) { // Check OFIFG fault flag
231 UCSCTL7 &= ~(DCOFFG+XT1LFOFFG+XT1HFOFFG+XT2OFFG); // Clear OSC flaut Flags
232 SFRIFG1 &= ~OFIFG; // Clear OFIFG fault flag
239 UCSCTL6 |= XT2OFF; // Switch off XT2 oscillator
243 void Init_FLL_Settle(unsigned int fsystem, unsigned int ratio)
245 volatile unsigned int x;
249 Init_FLL(fsystem, ratio);
251 /* from changes in Init_FLL we know that fll is now enabled */
257 static void Init_FLL(unsigned int fsystem, unsigned int ratio)
259 unsigned int d, dco_div_bits;
263 unsigned int srRegisterState;
268 /* we only run this at startup and we want the fll enabled on exit */
270 // Save actual state of FLL loop control, then disable it. This is needed to
271 // prevent the FLL from acting as we are making fundamental modifications to
273 srRegisterState = __get_SR_register() & SCG0;
277 dco_div_bits = FLLD__2; // Have at least a divider of 2
279 if (fsystem > 16000) {
284 fsystem <<= 1; // fsystem = fsystem * 2
288 dco_div_bits = dco_div_bits + FLLD0; // Set next higher div level
293 __bis_SR_register(SCG0);
295 UCSCTL0 = 0x0000; // Set DCO to lowest Tap
297 UCSCTL2 &= ~(0x03FF); // Reset FN bits
298 UCSCTL2 = dco_div_bits | (d - 1);
300 if (fsystem <= 630) // fsystem < 0.63MHz
302 else if (fsystem < 1250) // 0.63MHz < fsystem < 1.25MHz
304 else if (fsystem < 2500) // 1.25MHz < fsystem < 2.5MHz
306 else if (fsystem < 5000) // 2.5MHz < fsystem < 5MHz
308 else if (fsystem < 10000) // 5MHz < fsystem < 10MHz
310 else if (fsystem < 20000) // 10MHz < fsystem < 20MHz
312 else if (fsystem < 40000) // 20MHz < fsystem < 40MHz
318 __bic_SR_register(SCG0);
320 while (SFRIFG1 & OFIFG) { // Check OFIFG fault flag
321 UCSCTL7 &= ~(DCOFFG+XT1LFOFFG+XT1HFOFFG+XT2OFFG); // Clear OSC flaut Flags
322 SFRIFG1 &= ~OFIFG; // Clear OFIFG fault flag
325 /* Init fll is only run at startup - We want the fll enabled when
326 * this function is complete (so don't save a restore setting)
329 // Restore previous SCG0
330 __bis_SR_register(srRegisterState);
333 if (mode == 1) { // fsystem > 16000
334 SELECT_MCLK_SMCLK(SELM__DCOCLK + SELS__DCOCLK); // Select DCOCLK
337 SELECT_MCLK_SMCLK(SELM__DCOCLKDIV + SELS__DCOCLKDIV); // Select DCODIVCLK