]> git.gir.st - tmk_keyboard.git/blob - tmk_core/tool/mbed/mbed-sdk/libraries/mbed/targets/cmsis/TARGET_Freescale/TARGET_K20XX/TARGET_TEENSY3_1/system_MK20DX256.c
Merge commit '1fe4406f374291ab2e86e95a97341fd9c475fcb8'
[tmk_keyboard.git] / tmk_core / tool / mbed / mbed-sdk / libraries / mbed / targets / cmsis / TARGET_Freescale / TARGET_K20XX / TARGET_TEENSY3_1 / system_MK20DX256.c
1 /*
2 ** ###################################################################
3 ** Compilers: ARM Compiler
4 ** Freescale C/C++ for Embedded ARM
5 ** GNU C Compiler
6 ** IAR ANSI C/C++ Compiler for ARM
7 **
8 **
9 **
10 ** Version: rev. 1.0, 2011-12-15
11 **
12 ** Abstract:
13 ** Provides a system configuration function and a global variable that
14 ** contains the system frequency. It configures the device and initializes
15 ** the oscillator (PLL) that is part of the microcontroller device.
16 **
17 ** Copyright: 2015 Freescale Semiconductor, Inc. All Rights Reserved.
18 **
19 ** http: www.freescale.com
20 ** mail: support@freescale.com
21 **
22 ** Revisions:
23 ** - rev. 1.0 (2011-12-15)
24 ** Initial version
25 **
26 ** ###################################################################
27 */
28
29 /**
30 * @file MK20DX256
31 * @version 1.0
32 * @date 2011-12-15
33 * @brief Device specific configuration file for MK20DX256 (implementation file)
34 *
35 * Provides a system configuration function and a global variable that contains
36 * the system frequency. It configures the device and initializes the oscillator
37 * (PLL) that is part of the microcontroller device.
38 */
39
40 #include <stdint.h>
41 #include "MK20DX256.h"
42
43 #define DISABLE_WDOG 1
44
45 #define CLOCK_SETUP 3
46 /* Predefined clock setups
47 0 ... Multipurpose Clock Generator (MCG) in FLL Engaged Internal (FEI) mode
48 Reference clock source for MCG module is the slow internal clock source 32.768kHz
49 Core clock = 41.94MHz, BusClock = 41.94MHz
50 This works on Teensy3.1
51 1 ... Multipurpose Clock Generator (MCG) in PLL Engaged External (PEE) mode
52 Reference clock source for MCG module is an external crystal 8MHz
53 Core clock = 48MHz, BusClock = 48MHz
54 2 ... Multipurpose Clock Generator (MCG) in Bypassed Low Power External (BLPE) mode
55 Core clock/Bus clock derived directly from an external crystal 8MHz with no multiplication
56 Core clock = 8MHz, BusClock = 8MHz
57 3 ... Multipurpose Clock Generator (MCG) in PLL Engaged External (PEE) mode
58 Reference clock source for MCG module is an external crystal 16MHz
59 Core clock = 72MHz, BusClock = 48MHz
60 This is the default Teensy3.1 72Mhz set up
61 */
62
63 /*----------------------------------------------------------------------------
64 Define clock source values
65 *----------------------------------------------------------------------------*/
66 #if (CLOCK_SETUP == 0)
67 #define CPU_XTAL_CLK_HZ 8000000u /* Value of the external crystal or oscillator clock frequency in Hz */
68 #define CPU_XTAL32k_CLK_HZ 32768u /* Value of the external 32k crystal or oscillator clock frequency in Hz */
69 #define CPU_INT_SLOW_CLK_HZ 32768u /* Value of the slow internal oscillator clock frequency in Hz */
70 #define CPU_INT_FAST_CLK_HZ 4000000u /* Value of the fast internal oscillator clock frequency in Hz */
71 #define DEFAULT_SYSTEM_CLOCK 41943040u /* Default System clock value */
72 #elif (CLOCK_SETUP == 1)
73 #define CPU_XTAL_CLK_HZ 8000000u /* Value of the external crystal or oscillator clock frequency in Hz */
74 #define CPU_XTAL32k_CLK_HZ 32768u /* Value of the external 32k crystal or oscillator clock frequency in Hz */
75 #define CPU_INT_SLOW_CLK_HZ 32768u /* Value of the slow internal oscillator clock frequency in Hz */
76 #define CPU_INT_FAST_CLK_HZ 4000000u /* Value of the fast internal oscillator clock frequency in Hz */
77 #define DEFAULT_SYSTEM_CLOCK 48000000u /* Default System clock value */
78 #elif (CLOCK_SETUP == 2)
79 #define CPU_XTAL_CLK_HZ 8000000u /* Value of the external crystal or oscillator clock frequency in Hz */
80 #define CPU_XTAL32k_CLK_HZ 32768u /* Value of the external 32k crystal or oscillator clock frequency in Hz */
81 #define CPU_INT_SLOW_CLK_HZ 32768u /* Value of the slow internal oscillator clock frequency in Hz */
82 #define CPU_INT_FAST_CLK_HZ 4000000u /* Value of the fast internal oscillator clock frequency in Hz */
83 #define DEFAULT_SYSTEM_CLOCK 8000000u /* Default System clock value */
84 #elif (CLOCK_SETUP == 3)
85 #define CPU_XTAL_CLK_HZ 16000000u /* Value of the external crystal or oscillator clock frequency in Hz */
86 #define CPU_XTAL32k_CLK_HZ 32768u /* Value of the external 32k crystal or oscillator clock frequency in Hz */
87 #define CPU_INT_SLOW_CLK_HZ 32768u /* Value of the slow internal oscillator clock frequency in Hz */
88 #define CPU_INT_FAST_CLK_HZ 4000000u /* Value of the fast internal oscillator clock frequency in Hz */
89 #define DEFAULT_SYSTEM_CLOCK 72000000u /* Default System clock value */
90 #endif /* (CLOCK_SETUP == 2) */
91
92
93 /* ----------------------------------------------------------------------------
94 -- Core clock
95 ---------------------------------------------------------------------------- */
96
97 uint32_t SystemCoreClock = DEFAULT_SYSTEM_CLOCK;
98
99 /* ----------------------------------------------------------------------------
100 -- SystemInit()
101 ---------------------------------------------------------------------------- */
102 void SystemInit (void) {
103 /* SystemInit MUST NOT use any variables from the .data section, as this section is not loaded yet! */
104
105 #if (DISABLE_WDOG)
106 /* Disable the WDOG module */
107 /* WDOG_UNLOCK: WDOGUNLOCK=0xC520 */
108 WDOG->UNLOCK = (uint16_t)0xC520u; /* Key 1 */
109 /* WDOG_UNLOCK : WDOGUNLOCK=0xD928 */
110 WDOG->UNLOCK = (uint16_t)0xD928u; /* Key 2 */
111 /* WDOG_STCTRLH: DISTESTWDOG=0,BYTESEL=0,TESTSEL=0,TESTWDOG=0,STNDBYEN=1,WAITEN=1,STOPEN=1,DBGEN=0,ALLOWUPDATE=1,WINEN=0,IRQRSTEN=0,CLKSRC=1,WDOGEN=0 */
112 WDOG->STCTRLH = (uint16_t)0x01D2u;
113 #endif /* (DISABLE_WDOG) */
114
115 #if (CLOCK_SETUP == 0)
116 /* SIM->CLKDIV1: OUTDIV1=0,OUTDIV2=0,OUTDIV4=1 Set Prescalers 41.94MHz cpu, 41.94MHz system, 20.97MHz flash*/
117 SIM->CLKDIV1 = SIM_CLKDIV1_OUTDIV4(1);
118 /* Switch to FEI Mode */
119 /* MCG->C1: CLKS=0,FRDIV=0,IREFS=1,IRCLKEN=1,IREFSTEN=0 */
120 MCG->C1 = MCG_C1_IREFS_MASK | MCG_C1_IRCLKEN_MASK;
121 /* MCG->C2: LOCKRE0=0,RANGE0=0,HGO=0,EREFS=0,LP=0,IRCS=0 */
122 MCG->C2 = (uint8_t)0x00u;
123 /* MCG_C4: DMX32=0,DRST_DRS=1 */
124 MCG->C4 = (uint8_t)((MCG->C4 & (uint8_t)~(uint8_t)0xC0u) | (uint8_t)0x20u);
125 /* MCG->C5: PLLCLKEN=0,PLLSTEN=0,PRDIV0=0 */
126 MCG->C5 = (uint8_t)0x00u;
127 /* MCG->C6: LOLIE=0,PLLS=0,CME=0,VDIV0=0 */
128 MCG->C6 = (uint8_t)0x00u;
129 while((MCG->S & MCG_S_IREFST_MASK) == 0u) { } /* Check that the source of the FLL reference clock is the internal reference clock. */
130 while((MCG->S & 0x0Cu) != 0x00u) { } /* Wait until output of the FLL is selected */
131
132 #elif (CLOCK_SETUP == 1)
133 /* SIM->CLKDIV1: OUTDIV1=0,OUTDIV2=0,OUTDIV4=1 Set Prescalers 48MHz cpu, 48MHz system, 24MHz flash*/
134 SIM->CLKDIV1 = SIM_CLKDIV1_OUTDIV4(1);
135 /* Switch to FBE Mode */
136 /* OSC0->CR: ERCLKEN=0,EREFSTEN=0,SC2P=0,SC4P=0,SC8P=0,SC16P=0 */
137 OSC0->CR = (uint8_t)0x00u;
138 /* MCG->C7: OSCSEL=0 */
139 MCG->C7 = (uint8_t)0x00u;
140 /* MCG->C2: LOCKRE0=0,RANGE0=2,HGO=0,EREFS=1,LP=0,IRCS=0 */
141 MCG->C2 = MCG_C2_RANGE0(2);
142 /* MCG->C1: CLKS=2,FRDIV=3,IREFS=0,IRCLKEN=1,IREFSTEN=0 */
143 MCG->C1 = MCG_C1_CLKS(2) | MCG_C1_FRDIV(3) | MCG_C1_IRCLKEN_MASK;
144 /* MCG->C4: DMX32=0,DRST_DRS=0 */
145 MCG->C4 &= (uint8_t)~(uint8_t)0xE0u;
146 /* MCG->C5: PLLCLKEN=0,PLLSTEN=0,PRDIV0=3 */
147 MCG->C5 = MCG_C5_PRDIV0(3);
148 /* MCG->C6: LOLIE=0,PLLS=0,CME=0,VDIV0=0 */
149 MCG->C6 = (uint8_t)0x00u;
150 while((MCG->S & MCG_S_OSCINIT0_MASK) == 0u) { } /* Check that the oscillator is running */
151 while((MCG->S & 0x0Cu) != 0x08u) { } /* Wait until external reference clock is selected as MCG output */
152 /* Switch to PBE Mode */
153 /* MCG_C5: PLLCLKEN=0,PLLSTEN=0,PRDIV0=3 */
154 MCG->C5 = MCG_C5_PRDIV0(3);
155 /* MCG->C6: LOLIE=0,PLLS=1,CME=0,VDIV0=0 */
156 MCG->C6 = MCG_C6_PLLS_MASK;
157 while((MCG->S & MCG_S_PLLST_MASK) == 0u) { } /* Wait until the source of the PLLS clock has switched to the PLL */
158 while((MCG->S & MCG_S_LOCK0_MASK) == 0u) { } /* Wait until locked */
159 /* Switch to PEE Mode */
160 /* MCG->C1: CLKS=0,FRDIV=3,IREFS=0,IRCLKEN=1,IREFSTEN=0 */
161 MCG->C1 = MCG_C1_FRDIV(3) | MCG_C1_IRCLKEN_MASK;
162 while((MCG->S & 0x0Cu) != 0x0Cu) { } /* Wait until output of the PLL is selected */
163 while((MCG->S & MCG_S_LOCK0_MASK) == 0u) { } /* Wait until locked */
164
165 #elif (CLOCK_SETUP == 2)
166 /* SIM->CLKDIV1: OUTDIV1=0,OUTDIV2=0,OUTDIV4=1 Set Prescalers 8MHz cpu, 8MHz system, 8MHz flash*/
167 SIM->CLKDIV1 = SIM_CLKDIV1_OUTDIV4(1);
168 /* Switch to FBE Mode */
169 /* OSC0->CR: ERCLKEN=0,EREFSTEN=0,SC2P=0,SC4P=0,SC8P=0,SC16P=0 */
170 OSC0->CR = (uint8_t)0x00u;
171 /* MCG->C7: OSCSEL=0 */
172 MCG->C7 = (uint8_t)0x00u;
173 /* MCG->C2: LOCKRE0=0,RANGE0=2,HGO=0,EREFS=1,LP=0,IRCS=0 */
174 MCG->C2 = MCG_C2_RANGE0(2) | MCG_C2_EREFS0_MASK;
175 /* MCG->C1: CLKS=2,FRDIV=3,IREFS=0,IRCLKEN=1,IREFSTEN=0 */
176 MCG->C1 = MCG_C1_CLKS(2) | MCG_C1_FRDIV(3) | MCG_C1_IRCLKEN_MASK;
177 /* MCG->C4: DMX32=0,DRST_DRS=0 */
178 MCG->C4 &= (uint8_t)~(uint8_t)0xE0u;
179 /* MCG->C5: PLLCLKEN=0,PLLSTEN=0,PRDIV0=0 */
180 MCG->C5 = (uint8_t)0x00u;
181 /* MCG->C6: LOLIE=0,PLLS=0,CME=0,VDIV0=0 */
182 MCG->C6 = (uint8_t)0x00u;
183 while((MCG->S & MCG_S_OSCINIT0_MASK) == 0u) { } /* Check that the oscillator is running */
184 while((MCG->S & 0x0CU) != 0x08u) { } /* Wait until external reference clock is selected as MCG output */
185 /* Switch to BLPE Mode */
186 /* MCG->C2: LOCKRE0=0,RANGE0=2,HGO=0,EREFS=1,LP=0,IRCS=0 */
187 MCG->C2 = MCG_C2_RANGE0(2) | MCG_C2_EREFS0_MASK;
188
189 #elif (CLOCK_SETUP == 3)
190 /* SIM->CLKDIV1: OUTDIV1=0,OUTDIV2=0,OUTDIV4=1 Set Prescalers 72MHz cpu, 72MHz system, 36MHz flash*/
191 SIM->CLKDIV1 = SIM_CLKDIV1_OUTDIV4(1);
192 /* SIM->CLKDIV2: USBDIV=2,USBFRAC=1 Divide 72MHz system clock for USB 48MHz */
193 SIM->CLKDIV2 = SIM_CLKDIV2_USBDIV(2) | SIM_CLKDIV2_USBFRAC_MASK;
194 /* OSC0->CR: ERCLKEN=0,EREFSTEN=0,SC2P=1,SC4P=0,SC8P=1,SC16P=0 10pF loading capacitors for 16MHz system oscillator*/
195 OSC0->CR = OSC_CR_SC8P_MASK | OSC_CR_SC2P_MASK;
196 /* Switch to FBE Mode */
197 /* MCG->C7: OSCSEL=0 */
198 MCG->C7 = (uint8_t)0x00u;
199 /* MCG->C2: LOCKRE0=0,RANGE0=2,HGO=0,EREFS=1,LP=0,IRCS=0 */
200 MCG->C2 = MCG_C2_RANGE0(2) | MCG_C2_EREFS0_MASK;
201 //MCG->C2 = (uint8_t)0x24u;
202 /* MCG->C1: CLKS=2,FRDIV=3,IREFS=0,IRCLKEN=1,IREFSTEN=0 */
203 MCG->C1 = MCG_C1_CLKS(2) | MCG_C1_FRDIV(3) | MCG_C1_IRCLKEN_MASK;
204 /* MCG->C4: DMX32=0,DRST_DRS=0,FCTRIM=0,SCFTRIM=0 */
205 MCG->C4 &= (uint8_t)~(uint8_t)0xE0u;
206 /* MCG->C5: PLLCLKEN=0,PLLSTEN=0,PRDIV0=7 */
207 MCG->C5 = MCG_C5_PRDIV0(7);
208 /* MCG->C6: LOLIE=0,PLLS=0,CME=0,VDIV0=0 */
209 MCG->C6 = (uint8_t)0x00u;
210 while((MCG->S & MCG_S_OSCINIT0_MASK) == 0u) { } /* Check that the oscillator is running */
211 while((MCG->S & 0x0Cu) != 0x08u) { } /* Wait until external reference clock is selected as MCG output */
212 /* Switch to PBE Mode */
213 /* MCG_C5: PLLCLKEN=0,PLLSTEN=0,PRDIV0=5 */
214 MCG->C5 = MCG_C5_PRDIV0(5);
215 /* MCG->C6: LOLIE=0,PLLS=1,CME=0,VDIV0=3 */
216 MCG->C6 = MCG_C6_PLLS_MASK | MCG_C6_VDIV0(3);
217 while((MCG->S & MCG_S_PLLST_MASK) == 0u) { } /* Wait until the source of the PLLS clock has switched to the PLL */
218 while((MCG->S & MCG_S_LOCK0_MASK) == 0u) { } /* Wait until locked */
219 /* Switch to PEE Mode */
220 /* MCG->C1: CLKS=0,FRDIV=2,IREFS=0,IRCLKEN=1,IREFSTEN=0 */
221 MCG->C1 = MCG_C1_FRDIV(2) | MCG_C1_IRCLKEN_MASK;
222 while((MCG->S & 0x0Cu) != 0x0Cu) { } /* Wait until output of the PLL is selected */
223 while((MCG->S & MCG_S_LOCK0_MASK) == 0u) { } /* Wait until locked */
224 #endif /* (CLOCK_SETUP) */
225 }
226
227 /* ----------------------------------------------------------------------------
228 -- SystemCoreClockUpdate()
229 ---------------------------------------------------------------------------- */
230
231 void SystemCoreClockUpdate (void) {
232 uint32_t MCGOUTClock; /* Variable to store output clock frequency of the MCG module */
233 uint8_t Divider;
234
235 if ((MCG->C1 & MCG_C1_CLKS_MASK) == 0x0u) {
236 /* Output of FLL or PLL is selected */
237 if ((MCG->C6 & MCG_C6_PLLS_MASK) == 0x0u) {
238 /* FLL is selected */
239 if ((MCG->C1 & MCG_C1_IREFS_MASK) == 0x0u) {
240 /* External reference clock is selected */
241 if ((MCG->C7 & MCG_C7_OSCSEL_MASK) == 0x0u) {
242 MCGOUTClock = CPU_XTAL_CLK_HZ; /* System oscillator drives MCG clock */
243 } else { /* (!((MCG->C7 & MCG_C7_OSCSEL_MASK) == 0x0u)) */
244 MCGOUTClock = CPU_XTAL32k_CLK_HZ; /* RTC 32 kHz oscillator drives MCG clock */
245 } /* (!((MCG->C7 & MCG_C7_OSCSEL_MASK) == 0x0u)) */
246 Divider = (uint8_t)(1u << ((MCG->C1 & MCG_C1_FRDIV_MASK) >> MCG_C1_FRDIV_SHIFT));
247 MCGOUTClock = (MCGOUTClock / Divider); /* Calculate the divided FLL reference clock */
248 if ((MCG->C2 & MCG_C2_RANGE0_MASK) != 0x0u) {
249 MCGOUTClock /= 32u; /* If high range is enabled, additional 32 divider is active */
250 } /* ((MCG->C2 & MCG_C2_RANGE0_MASK) != 0x0u) */
251 } else { /* (!((MCG->C1 & MCG_C1_IREFS_MASK) == 0x0u)) */
252 MCGOUTClock = CPU_INT_SLOW_CLK_HZ; /* The slow internal reference clock is selected */
253 } /* (!((MCG->C1 & MCG_C1_IREFS_MASK) == 0x0u)) */
254 /* Select correct multiplier to calculate the MCG output clock */
255 switch (MCG->C4 & (MCG_C4_DMX32_MASK | MCG_C4_DRST_DRS_MASK)) {
256 case 0x0u:
257 MCGOUTClock *= 640u;
258 break;
259 case 0x20u:
260 MCGOUTClock *= 1280u;
261 break;
262 case 0x40u:
263 MCGOUTClock *= 1920u;
264 break;
265 case 0x60u:
266 MCGOUTClock *= 2560u;
267 break;
268 case 0x80u:
269 MCGOUTClock *= 732u;
270 break;
271 case 0xA0u:
272 MCGOUTClock *= 1464u;
273 break;
274 case 0xC0u:
275 MCGOUTClock *= 2197u;
276 break;
277 case 0xE0u:
278 MCGOUTClock *= 2929u;
279 break;
280 default:
281 break;
282 }
283 } else { /* (!((MCG->C6 & MCG_C6_PLLS_MASK) == 0x0u)) */
284 /* PLL is selected */
285 Divider = (1u + (MCG->C5 & MCG_C5_PRDIV0_MASK));
286 MCGOUTClock = (uint32_t)(CPU_XTAL_CLK_HZ / Divider); /* Calculate the PLL reference clock */
287 Divider = ((MCG->C6 & MCG_C6_VDIV0_MASK) + 24u);
288 MCGOUTClock *= Divider; /* Calculate the MCG output clock */
289 } /* (!((MCG->C6 & MCG_C6_PLLS_MASK) == 0x0u)) */
290 } else if ((MCG->C1 & MCG_C1_CLKS_MASK) == 0x40u) {
291 /* Internal reference clock is selected */
292 if ((MCG->C2 & MCG_C2_IRCS_MASK) == 0x0u) {
293 MCGOUTClock = CPU_INT_SLOW_CLK_HZ; /* Slow internal reference clock selected */
294 } else { /* (!((MCG->C2 & MCG_C2_IRCS_MASK) == 0x0u)) */
295 MCGOUTClock = CPU_INT_FAST_CLK_HZ / (1 << ((MCG->SC & MCG_SC_FCRDIV_MASK) >> MCG_SC_FCRDIV_SHIFT)); /* Fast internal reference clock selected */
296 } /* (!((MCG->C2 & MCG_C2_IRCS_MASK) == 0x0u)) */
297 } else if ((MCG->C1 & MCG_C1_CLKS_MASK) == 0x80u) {
298 /* External reference clock is selected */
299 if ((MCG->C7 & MCG_C7_OSCSEL_MASK) == 0x0u) {
300 MCGOUTClock = CPU_XTAL_CLK_HZ; /* System oscillator drives MCG clock */
301 } else { /* (!((MCG->C7 & MCG_C7_OSCSEL_MASK) == 0x0u)) */
302 MCGOUTClock = CPU_XTAL32k_CLK_HZ; /* RTC 32 kHz oscillator drives MCG clock */
303 } /* (!((MCG->C7 & MCG_C7_OSCSEL_MASK) == 0x0u)) */
304 } else { /* (!((MCG->C1 & MCG_C1_CLKS_MASK) == 0x80u)) */
305 /* Reserved value */
306 return;
307 } /* (!((MCG->C1 & MCG_C1_CLKS_MASK) == 0x80u)) */
308 SystemCoreClock = (MCGOUTClock / (1u + ((SIM->CLKDIV1 & SIM_CLKDIV1_OUTDIV1_MASK) >> SIM_CLKDIV1_OUTDIV1_SHIFT)));
309 }
Imprint / Impressum