1 | /* This source file is part of the ATMEL AVR-UC3-SoftwareFramework-1.7.0 Release */ |
---|
2 | |
---|
3 | /*This file has been prepared for Doxygen automatic documentation generation.*/ |
---|
4 | /*! \file ********************************************************************* |
---|
5 | * |
---|
6 | * \brief High-level library abstracting features such as oscillators/pll/dfll |
---|
7 | * configuration, clock configuration, System-sensible parameters |
---|
8 | * configuration, buses clocks configuration, sleep mode, reset. |
---|
9 | * |
---|
10 | * |
---|
11 | * - Compiler: IAR EWAVR32 and GNU GCC for AVR32 |
---|
12 | * - Supported devices: All AVR32 devices. |
---|
13 | * - AppNote: |
---|
14 | * |
---|
15 | * \author Atmel Corporation: http://www.atmel.com \n |
---|
16 | * Support and FAQ: http://support.atmel.no/ |
---|
17 | * |
---|
18 | *****************************************************************************/ |
---|
19 | |
---|
20 | /* Copyright (c) 2009 Atmel Corporation. All rights reserved. |
---|
21 | * |
---|
22 | * Redistribution and use in source and binary forms, with or without |
---|
23 | * modification, are permitted provided that the following conditions are met: |
---|
24 | * |
---|
25 | * 1. Redistributions of source code must retain the above copyright notice, this |
---|
26 | * list of conditions and the following disclaimer. |
---|
27 | * |
---|
28 | * 2. Redistributions in binary form must reproduce the above copyright notice, |
---|
29 | * this list of conditions and the following disclaimer in the documentation |
---|
30 | * and/or other materials provided with the distribution. |
---|
31 | * |
---|
32 | * 3. The name of Atmel may not be used to endorse or promote products derived |
---|
33 | * from this software without specific prior written permission. |
---|
34 | * |
---|
35 | * 4. This software may only be redistributed and used in connection with an Atmel |
---|
36 | * AVR product. |
---|
37 | * |
---|
38 | * THIS SOFTWARE IS PROVIDED BY ATMEL "AS IS" AND ANY EXPRESS OR IMPLIED |
---|
39 | * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF |
---|
40 | * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT ARE |
---|
41 | * EXPRESSLY AND SPECIFICALLY DISCLAIMED. IN NO EVENT SHALL ATMEL BE LIABLE FOR |
---|
42 | * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES |
---|
43 | * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; |
---|
44 | * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND |
---|
45 | * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT |
---|
46 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS |
---|
47 | * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE |
---|
48 | * |
---|
49 | */ |
---|
50 | #include "power_clocks_lib.h" |
---|
51 | |
---|
52 | |
---|
53 | //! Device-specific data |
---|
54 | #if UC3L |
---|
55 | static long int pcl_configure_clocks_uc3l(pcl_freq_param_t *param); // FORWARD declaration |
---|
56 | #endif |
---|
57 | |
---|
58 | #if UC3C |
---|
59 | static long int pcl_configure_clocks_uc3c(pcl_freq_param_t *param); // FORWARD declaration |
---|
60 | #endif |
---|
61 | |
---|
62 | long int pcl_configure_clocks(pcl_freq_param_t *param) |
---|
63 | { |
---|
64 | #ifndef AVR32_PM_VERSION_RESETVALUE |
---|
65 | // Implementation for UC3A, UC3A3, UC3B parts. |
---|
66 | return(pm_configure_clocks(param)); |
---|
67 | #else |
---|
68 | #ifdef AVR32_PM_410_H_INCLUDED |
---|
69 | // Implementation for UC3C parts. |
---|
70 | return(pcl_configure_clocks_uc3c(param)); |
---|
71 | #else |
---|
72 | // Implementation for UC3L parts. |
---|
73 | return(pcl_configure_clocks_uc3l(param)); |
---|
74 | #endif |
---|
75 | #endif |
---|
76 | } |
---|
77 | |
---|
78 | |
---|
79 | //! Device-specific implementation |
---|
80 | #if UC3L |
---|
81 | // FORWARD declaration |
---|
82 | static long int pcl_configure_synchronous_clocks( pm_clk_src_t main_clk_src, |
---|
83 | unsigned long main_clock_freq_hz, |
---|
84 | pcl_freq_param_t *param); |
---|
85 | |
---|
86 | long int pcl_configure_clocks_rcsys(pcl_freq_param_t *param) |
---|
87 | { |
---|
88 | // Supported main clock sources: PCL_MC_RCSYS |
---|
89 | |
---|
90 | // Supported synchronous clocks frequencies if RCSYS is the main clock source: |
---|
91 | // 115200Hz, 57600Hz, 28800Hz, 14400Hz, 7200Hz, 3600Hz, 1800Hz, 900Hz, 450Hz. |
---|
92 | |
---|
93 | // NOTE: by default, this implementation doesn't perform thorough checks on the |
---|
94 | // input parameters. To enable the checks, define AVR32SFW_INPUT_CHECK. |
---|
95 | |
---|
96 | #ifdef AVR32SFW_INPUT_CHECK |
---|
97 | // Verify that fCPU >= fPBx |
---|
98 | if((param->cpu_f < param->pba_f) || (param->cpu_f < param->pbb_f)) |
---|
99 | return(-1); |
---|
100 | #endif |
---|
101 | |
---|
102 | #ifdef AVR32SFW_INPUT_CHECK |
---|
103 | // Verify that the target frequencies are reachable. |
---|
104 | if((param->cpu_f > SCIF_SLOWCLOCK_FREQ_HZ) || (param->pba_f > SCIF_SLOWCLOCK_FREQ_HZ) |
---|
105 | || (param->pbb_f > SCIF_SLOWCLOCK_FREQ_HZ)) |
---|
106 | return(-1); |
---|
107 | #endif |
---|
108 | |
---|
109 | return(pcl_configure_synchronous_clocks(PM_CLK_SRC_SLOW, SCIF_SLOWCLOCK_FREQ_HZ, param)); |
---|
110 | } |
---|
111 | |
---|
112 | |
---|
113 | long int pcl_configure_clocks_rc120m(pcl_freq_param_t *param) |
---|
114 | { |
---|
115 | // Supported main clock sources: PCL_MC_RC120M |
---|
116 | |
---|
117 | // Supported synchronous clocks frequencies if RC120M is the main clock source: |
---|
118 | // 30MHz, 15MHz, 7.5MHz, 3.75MHz, 1.875MHz, 937.5kHz, 468.75kHz. |
---|
119 | |
---|
120 | // NOTE: by default, this implementation doesn't perform thorough checks on the |
---|
121 | // input parameters. To enable the checks, define AVR32SFW_INPUT_CHECK. |
---|
122 | |
---|
123 | #ifdef AVR32SFW_INPUT_CHECK |
---|
124 | // Verify that fCPU >= fPBx |
---|
125 | if((param->cpu_f < param->pba_f) || (param->cpu_f < param->pbb_f)) |
---|
126 | return(-1); |
---|
127 | #endif |
---|
128 | |
---|
129 | #ifdef AVR32SFW_INPUT_CHECK |
---|
130 | // Verify that the target frequencies are reachable. |
---|
131 | if((param->cpu_f > SCIF_RC120M_FREQ_HZ) || (param->pba_f > SCIF_RC120M_FREQ_HZ) |
---|
132 | || (param->pbb_f > SCIF_RC120M_FREQ_HZ)) |
---|
133 | return(-1); |
---|
134 | #endif |
---|
135 | |
---|
136 | // Start the 120MHz internal RCosc (RC120M) clock |
---|
137 | scif_start_rc120M(); |
---|
138 | |
---|
139 | return(pcl_configure_synchronous_clocks(PM_CLK_SRC_RC120M, SCIF_RC120M_FREQ_HZ, param)); |
---|
140 | } |
---|
141 | |
---|
142 | |
---|
143 | long int pcl_configure_clocks_osc0(pcl_freq_param_t *param) |
---|
144 | { |
---|
145 | // Supported main clock sources: PCL_MC_OSC0 |
---|
146 | |
---|
147 | // Supported synchronous clocks frequencies if OSC0 is the main clock source: |
---|
148 | // (these obviously depend on the OSC0 frequency; we'll take 16MHz as an example) |
---|
149 | // 16MHz, 8MHz, 4MHz, 2MHz, 1MHz, 500kHz, 250kHz, 125kHz, 62.5kHz. |
---|
150 | |
---|
151 | // NOTE: by default, this implementation doesn't perform thorough checks on the |
---|
152 | // input parameters. To enable the checks, define AVR32SFW_INPUT_CHECK. |
---|
153 | |
---|
154 | unsigned long main_clock_freq; |
---|
155 | |
---|
156 | |
---|
157 | #ifdef AVR32SFW_INPUT_CHECK |
---|
158 | // Verify that fCPU >= fPBx |
---|
159 | if((param->cpu_f < param->pba_f) || (param->cpu_f < param->pbb_f)) |
---|
160 | return(-1); |
---|
161 | #endif |
---|
162 | |
---|
163 | main_clock_freq = param->osc0_f; |
---|
164 | #ifdef AVR32SFW_INPUT_CHECK |
---|
165 | // Verify that the target frequencies are reachable. |
---|
166 | if((param->cpu_f > main_clock_freq) || (param->pba_f > main_clock_freq) |
---|
167 | || (param->pbb_f > main_clock_freq)) |
---|
168 | return(-1); |
---|
169 | #endif |
---|
170 | // Configure OSC0 in crystal mode, external crystal with a fcrystal Hz frequency. |
---|
171 | scif_configure_osc_crystalmode(SCIF_OSC0, main_clock_freq); |
---|
172 | // Enable the OSC0 |
---|
173 | scif_enable_osc(SCIF_OSC0, param->osc0_startup, true); |
---|
174 | |
---|
175 | return(pcl_configure_synchronous_clocks(PM_CLK_SRC_OSC0, main_clock_freq, param)); |
---|
176 | } |
---|
177 | |
---|
178 | |
---|
179 | long int pcl_configure_clocks_dfll0(pcl_freq_param_t *param) |
---|
180 | { |
---|
181 | // Supported main clock sources: PCL_MC_DFLL |
---|
182 | |
---|
183 | // Supported synchronous clocks frequencies if DFLL is the main clock source: |
---|
184 | // (these obviously depend on the DFLL target frequency; we'll take 100MHz as an example) |
---|
185 | // 50MHz, 25MHz, 12.5MHz, 6.25MHz, 3.125MHz, 1562.5kHz, 781.25kHz, 390.625kHz. |
---|
186 | |
---|
187 | // NOTE: by default, this implementation doesn't perform thorough checks on the |
---|
188 | // input parameters. To enable the checks, define AVR32SFW_INPUT_CHECK. |
---|
189 | |
---|
190 | unsigned long main_clock_freq; |
---|
191 | scif_gclk_opt_t *pgc_dfllif_ref_opt; |
---|
192 | |
---|
193 | |
---|
194 | #ifdef AVR32SFW_INPUT_CHECK |
---|
195 | // Verify that fCPU >= fPBx |
---|
196 | if((param->cpu_f < param->pba_f) || (param->cpu_f < param->pbb_f)) |
---|
197 | return(-1); |
---|
198 | #endif |
---|
199 | |
---|
200 | main_clock_freq = param->dfll_f; |
---|
201 | #ifdef AVR32SFW_INPUT_CHECK |
---|
202 | // Verify that the target DFLL output frequency is in the correct range. |
---|
203 | if((main_clock_freq > SCIF_DFLL_MAXFREQ_HZ) || (main_clock_freq < SCIF_DFLL_MINFREQ_HZ)) |
---|
204 | return(-1); |
---|
205 | // Verify that the target frequencies are reachable. |
---|
206 | if((param->cpu_f > main_clock_freq) || (param->pba_f > main_clock_freq) |
---|
207 | || (param->pbb_f > main_clock_freq)) |
---|
208 | return(-1); |
---|
209 | #endif |
---|
210 | pgc_dfllif_ref_opt = (scif_gclk_opt_t *)param->pextra_params; |
---|
211 | // Implementation note: this implementation configures the DFLL in closed-loop |
---|
212 | // mode (because it gives the best accuracy) which enables the generic clock CLK_DFLLIF_REF |
---|
213 | // as a reference (RCSYS being used as the generic clock source, undivided). |
---|
214 | scif_dfll0_closedloop_configure_and_start(pgc_dfllif_ref_opt, main_clock_freq, TRUE); |
---|
215 | |
---|
216 | return(pcl_configure_synchronous_clocks(PM_CLK_SRC_DFLL0, main_clock_freq, param)); |
---|
217 | } |
---|
218 | |
---|
219 | |
---|
220 | static long int pcl_configure_clocks_uc3l(pcl_freq_param_t *param) |
---|
221 | { |
---|
222 | // Supported main clock sources: PCL_MC_RCSYS, PCL_MC_OSC0, PCL_MC_DFLL0, PCL_MC_RC120M |
---|
223 | |
---|
224 | // Supported synchronous clocks frequencies if RCSYS is the main clock source: |
---|
225 | // 115200Hz, 57600Hz, 28800Hz, 14400Hz, 7200Hz, 3600Hz, 1800Hz, 900Hz, 450Hz. |
---|
226 | |
---|
227 | // Supported synchronous clocks frequencies if RC120M is the main clock source: |
---|
228 | // 30MHz, 15MHz, 7.5MHz, 3.75MHz, 1.875MHz, 937.5kHz, 468.75kHz. |
---|
229 | |
---|
230 | // Supported synchronous clocks frequencies if OSC0 is the main clock source: |
---|
231 | // (these obviously depend on the OSC0 frequency; we'll take 16MHz as an example) |
---|
232 | // 16MHz, 8MHz, 4MHz, 2MHz, 1MHz, 500kHz, 250kHz, 125kHz, 62.5kHz. |
---|
233 | |
---|
234 | // Supported synchronous clocks frequencies if DFLL is the main clock source: |
---|
235 | // (these obviously depend on the DFLL target frequency; we'll take 100MHz as an example) |
---|
236 | // 50MHz, 25MHz, 12.5MHz, 6.25MHz, 3.125MHz, 1562.5kHz, 781.25kHz, 390.625kHz. |
---|
237 | |
---|
238 | // NOTE: by default, this implementation doesn't perform thorough checks on the |
---|
239 | // input parameters. To enable the checks, define AVR32SFW_INPUT_CHECK. |
---|
240 | |
---|
241 | |
---|
242 | #ifdef AVR32SFW_INPUT_CHECK |
---|
243 | // Verify that fCPU >= fPBx |
---|
244 | if((param->cpu_f < param->pba_f) || (param->cpu_f < param->pbb_f)) |
---|
245 | return(-1); |
---|
246 | #endif |
---|
247 | |
---|
248 | if(PCL_MC_RCSYS == param->main_clk_src) |
---|
249 | { |
---|
250 | return(pcl_configure_clocks_rcsys(param)); |
---|
251 | } |
---|
252 | else if(PCL_MC_RC120M == param->main_clk_src) |
---|
253 | { |
---|
254 | return(pcl_configure_clocks_rc120m(param)); |
---|
255 | } |
---|
256 | else if(PCL_MC_OSC0 == param->main_clk_src) |
---|
257 | { |
---|
258 | return(pcl_configure_clocks_osc0(param)); |
---|
259 | } |
---|
260 | else // PCL_MC_DFLL0 == param->main_clk_src |
---|
261 | { |
---|
262 | return(pcl_configure_clocks_dfll0(param)); |
---|
263 | } |
---|
264 | } |
---|
265 | |
---|
266 | static long int pcl_configure_synchronous_clocks(pm_clk_src_t main_clk_src, unsigned long main_clock_freq_hz, pcl_freq_param_t *param) |
---|
267 | { |
---|
268 | //# |
---|
269 | //# Set the Synchronous clock division ratio for each clock domain |
---|
270 | //# |
---|
271 | pm_set_all_cksel(main_clock_freq_hz, param->cpu_f, param->pba_f, param->pbb_f); |
---|
272 | |
---|
273 | //# |
---|
274 | //# Set the Flash wait state and the speed read mode (depending on the target CPU frequency). |
---|
275 | //# |
---|
276 | #if UC3L |
---|
277 | flashcdw_set_flash_waitstate_and_readmode(param->cpu_f); |
---|
278 | #elif UC3C |
---|
279 | flashc_set_flash_waitstate_and_readmode(param->cpu_f); |
---|
280 | #endif |
---|
281 | |
---|
282 | |
---|
283 | //# |
---|
284 | //# Switch the main clock source to the selected clock. |
---|
285 | //# |
---|
286 | pm_set_mclk_source(main_clk_src); |
---|
287 | |
---|
288 | return PASS; |
---|
289 | } |
---|
290 | |
---|
291 | #endif // UC3L device-specific implementation |
---|
292 | |
---|
293 | //! UC3C Device-specific implementation |
---|
294 | #if UC3C |
---|
295 | static long int pcl_configure_clocks_uc3c(pcl_freq_param_t *param) |
---|
296 | { |
---|
297 | #define PM_MAX_MUL ((1 << AVR32_SCIF_PLLMUL_SIZE) - 1) |
---|
298 | #define AVR32_PM_PBA_MAX_FREQ 66000000 |
---|
299 | #define AVR32_PM_PLL_VCO_RANGE0_MAX_FREQ 240000000 |
---|
300 | #define AVR32_PM_PLL_VCO_RANGE0_MIN_FREQ 160000000 |
---|
301 | |
---|
302 | // Implementation for UC3C parts. |
---|
303 | // Supported frequencies: |
---|
304 | // Fosc0 mul div PLL div2_en cpu_f pba_f Comment |
---|
305 | // 12 15 1 192 1 12 12 |
---|
306 | // 12 9 3 40 1 20 20 PLL out of spec |
---|
307 | // 12 15 1 192 1 24 12 |
---|
308 | // 12 9 1 120 1 30 15 |
---|
309 | // 12 9 3 40 0 40 20 PLL out of spec |
---|
310 | // 12 15 1 192 1 48 12 |
---|
311 | // 12 15 1 192 1 48 24 |
---|
312 | // 12 8 1 108 1 54 27 |
---|
313 | // 12 9 1 120 1 60 15 |
---|
314 | // 12 9 1 120 1 60 30 |
---|
315 | // 12 10 1 132 1 66 16.5 |
---|
316 | // |
---|
317 | unsigned long in_cpu_f = param->cpu_f; |
---|
318 | unsigned long in_osc0_f = param->osc0_f; |
---|
319 | unsigned long mul, div, div2_en = 0, div2_cpu = 0, div2_pba = 0; |
---|
320 | unsigned long pll_freq, rest; |
---|
321 | Bool b_div2_pba, b_div2_cpu; |
---|
322 | |
---|
323 | // Configure OSC0 in crystal mode, external crystal with a FOSC0 Hz frequency. |
---|
324 | scif_configure_osc_crystalmode(SCIF_OSC0, in_osc0_f); |
---|
325 | // Enable the OSC0 |
---|
326 | scif_enable_osc(SCIF_OSC0, param->osc0_startup, true); |
---|
327 | // Set the main clock source as being OSC0. |
---|
328 | pm_set_mclk_source(PM_CLK_SRC_OSC0); |
---|
329 | |
---|
330 | // Start with CPU freq config |
---|
331 | if (in_cpu_f == in_osc0_f) |
---|
332 | { |
---|
333 | param->cpu_f = in_osc0_f; |
---|
334 | param->pba_f = in_osc0_f; |
---|
335 | return PASS; |
---|
336 | } |
---|
337 | else if (in_cpu_f < in_osc0_f) |
---|
338 | { |
---|
339 | // TBD |
---|
340 | } |
---|
341 | |
---|
342 | rest = in_cpu_f % in_osc0_f; |
---|
343 | |
---|
344 | for (div = 1; div < 32; div++) |
---|
345 | { |
---|
346 | if ((div * rest) % in_osc0_f == 0) |
---|
347 | break; |
---|
348 | } |
---|
349 | if (div == 32) |
---|
350 | return FAIL; |
---|
351 | |
---|
352 | mul = (in_cpu_f * div) / in_osc0_f; |
---|
353 | |
---|
354 | if (mul > PM_MAX_MUL) |
---|
355 | return FAIL; |
---|
356 | |
---|
357 | // export 2power from PLL div to div2_cpu |
---|
358 | while (!(div % 2)) |
---|
359 | { |
---|
360 | div /= 2; |
---|
361 | div2_cpu++; |
---|
362 | } |
---|
363 | |
---|
364 | // Here we know the mul and div parameter of the PLL config. |
---|
365 | // . Check out if the PLL has a valid in_cpu_f. |
---|
366 | // . Try to have for the PLL frequency (VCO output) the highest possible value |
---|
367 | // to reduce jitter. |
---|
368 | while (in_osc0_f * 2 * mul / div < AVR32_PM_PLL_VCO_RANGE0_MAX_FREQ) |
---|
369 | { |
---|
370 | if (2 * mul > PM_MAX_MUL) |
---|
371 | break; |
---|
372 | mul *= 2; |
---|
373 | div2_cpu++; |
---|
374 | } |
---|
375 | |
---|
376 | if (div2_cpu != 0) |
---|
377 | { |
---|
378 | div2_cpu--; |
---|
379 | div2_en = 1; |
---|
380 | } |
---|
381 | |
---|
382 | pll_freq = in_osc0_f * mul / (div * (1 << div2_en)); |
---|
383 | |
---|
384 | // Update real CPU Frequency |
---|
385 | param->cpu_f = pll_freq / (1 << div2_cpu); |
---|
386 | mul--; |
---|
387 | |
---|
388 | scif_pll_opt_t opt; |
---|
389 | |
---|
390 | opt.osc = SCIF_OSC0, // Sel Osc0 or Osc1 |
---|
391 | opt.lockcount = 16, // lockcount in main clock for the PLL wait lock |
---|
392 | opt.div = div, // DIV=1 in the formula |
---|
393 | opt.mul = mul, // MUL=7 in the formula |
---|
394 | opt.pll_div2 = div2_en, // pll_div2 Divide the PLL output frequency by 2 (this settings does not change the FVCO value) |
---|
395 | opt.pll_wbwdisable = 0, //pll_wbwdisable 1 Disable the Wide-Bandith Mode (Wide-Bandwith mode allow a faster startup time and out-of-lock time). 0 to enable the Wide-Bandith Mode. |
---|
396 | opt.pll_freq = (pll_freq < AVR32_PM_PLL_VCO_RANGE0_MIN_FREQ) ? 1 : 0, // Set to 1 for VCO frequency range 80-180MHz, set to 0 for VCO frequency range 160-240Mhz. |
---|
397 | |
---|
398 | |
---|
399 | scif_pll_setup(SCIF_PLL0, opt); // lockcount in main clock for the PLL wait lock |
---|
400 | |
---|
401 | /* Enable PLL0 */ |
---|
402 | scif_pll_enable(SCIF_PLL0); |
---|
403 | |
---|
404 | /* Wait for PLL0 locked */ |
---|
405 | scif_wait_for_pll_locked(SCIF_PLL0) ; |
---|
406 | |
---|
407 | rest = pll_freq; |
---|
408 | while (rest > AVR32_PM_PBA_MAX_FREQ || |
---|
409 | rest != param->pba_f) |
---|
410 | { |
---|
411 | div2_pba++; |
---|
412 | rest = pll_freq / (1 << div2_pba); |
---|
413 | if (rest < param->pba_f) |
---|
414 | break; |
---|
415 | } |
---|
416 | |
---|
417 | // Update real PBA Frequency |
---|
418 | param->pba_f = pll_freq / (1 << div2_pba); |
---|
419 | |
---|
420 | |
---|
421 | if (div2_cpu) |
---|
422 | { |
---|
423 | b_div2_cpu = TRUE; |
---|
424 | div2_cpu--; |
---|
425 | } |
---|
426 | else |
---|
427 | b_div2_cpu = FALSE; |
---|
428 | |
---|
429 | if (div2_pba) |
---|
430 | { |
---|
431 | b_div2_pba = TRUE; |
---|
432 | div2_pba--; |
---|
433 | } |
---|
434 | else |
---|
435 | b_div2_pba = FALSE; |
---|
436 | |
---|
437 | if (b_div2_cpu == TRUE ) |
---|
438 | { |
---|
439 | pm_set_clk_domain_div(PM_CLK_DOMAIN_0, (pm_divratio_t) div2_cpu); // CPU |
---|
440 | pm_set_clk_domain_div(PM_CLK_DOMAIN_1, (pm_divratio_t) div2_cpu); // HSB |
---|
441 | pm_set_clk_domain_div(PM_CLK_DOMAIN_3, (pm_divratio_t) div2_cpu); // PBB |
---|
442 | } |
---|
443 | if (b_div2_pba == TRUE ) |
---|
444 | { |
---|
445 | pm_set_clk_domain_div(PM_CLK_DOMAIN_2, (pm_divratio_t) div2_pba); // PBA |
---|
446 | pm_set_clk_domain_div(PM_CLK_DOMAIN_4, (pm_divratio_t) div2_pba); // PBC |
---|
447 | } |
---|
448 | |
---|
449 | // Set Flashc Wait State |
---|
450 | flashc_set_flash_waitstate_and_readmode(param->cpu_f); |
---|
451 | |
---|
452 | // Set the main clock source as being PLL0. |
---|
453 | pm_set_mclk_source(PM_CLK_SRC_PLL0); |
---|
454 | |
---|
455 | return PASS; |
---|
456 | } |
---|
457 | #endif // UC3C device-specific implementation |
---|
458 | |
---|
459 | long int pcl_switch_to_osc(pcl_osc_t osc, unsigned int fcrystal, unsigned int startup) |
---|
460 | { |
---|
461 | #ifndef AVR32_PM_VERSION_RESETVALUE |
---|
462 | // Implementation for UC3A, UC3A3, UC3B parts. |
---|
463 | if(PCL_OSC0 == osc) |
---|
464 | { |
---|
465 | // Configure OSC0 in crystal mode, external crystal with a FOSC0 Hz frequency, |
---|
466 | // enable the OSC0, set the main clock source as being OSC0. |
---|
467 | pm_switch_to_osc0(&AVR32_PM, fcrystal, startup); |
---|
468 | } |
---|
469 | else |
---|
470 | { |
---|
471 | return PCL_NOT_SUPPORTED; |
---|
472 | } |
---|
473 | #else |
---|
474 | // Implementation for UC3C, UC3L parts. |
---|
475 | #if AVR32_PM_VERSION_RESETVALUE < 0x400 |
---|
476 | return PCL_NOT_SUPPORTED; |
---|
477 | #else |
---|
478 | if(PCL_OSC0 == osc) |
---|
479 | { |
---|
480 | // Configure OSC0 in crystal mode, external crystal with a fcrystal Hz frequency. |
---|
481 | scif_configure_osc_crystalmode(SCIF_OSC0, fcrystal); |
---|
482 | // Enable the OSC0 |
---|
483 | scif_enable_osc(SCIF_OSC0, startup, true); |
---|
484 | // Set the Flash wait state and the speed read mode (depending on the target CPU frequency). |
---|
485 | #if UC3L |
---|
486 | flashcdw_set_flash_waitstate_and_readmode(fcrystal); |
---|
487 | #elif UC3C |
---|
488 | flashc_set_flash_waitstate_and_readmode(fcrystal); |
---|
489 | #endif |
---|
490 | // Set the main clock source as being OSC0. |
---|
491 | pm_set_mclk_source(PM_CLK_SRC_OSC0); |
---|
492 | } |
---|
493 | else |
---|
494 | { |
---|
495 | return PCL_NOT_SUPPORTED; |
---|
496 | } |
---|
497 | #endif |
---|
498 | #endif |
---|
499 | return PASS; |
---|
500 | } |
---|
501 | |
---|
502 | long int pcl_configure_usb_clock(void) |
---|
503 | { |
---|
504 | #ifndef AVR32_PM_VERSION_RESETVALUE |
---|
505 | // Implementation for UC3A, UC3A3, UC3B parts. |
---|
506 | pm_configure_usb_clock(); |
---|
507 | return PASS; |
---|
508 | #else |
---|
509 | #ifdef AVR32_PM_410_H_INCLUDED |
---|
510 | const scif_pll_opt_t opt = { |
---|
511 | .osc = SCIF_OSC0, // Sel Osc0 or Osc1 |
---|
512 | .lockcount = 16, // lockcount in main clock for the PLL wait lock |
---|
513 | .div = 1, // DIV=1 in the formula |
---|
514 | .mul = 5, // MUL=7 in the formula |
---|
515 | .pll_div2 = 1, // pll_div2 Divide the PLL output frequency by 2 (this settings does not change the FVCO value) |
---|
516 | .pll_wbwdisable = 0, //pll_wbwdisable 1 Disable the Wide-Bandith Mode (Wide-Bandwith mode allow a faster startup time and out-of-lock time). 0 to enable the Wide-Bandith Mode. |
---|
517 | .pll_freq = 1, // Set to 1 for VCO frequency range 80-180MHz, set to 0 for VCO frequency range 160-240Mhz. |
---|
518 | }; |
---|
519 | |
---|
520 | /* Setup PLL1 on Osc0, mul=7 ,no divisor, lockcount=16, ie. 16Mhzx6 = 96MHz output */ |
---|
521 | scif_pll_setup(SCIF_PLL1, opt); // lockcount in main clock for the PLL wait lock |
---|
522 | |
---|
523 | /* Enable PLL1 */ |
---|
524 | scif_pll_enable(SCIF_PLL1); |
---|
525 | |
---|
526 | /* Wait for PLL1 locked */ |
---|
527 | scif_wait_for_pll_locked(SCIF_PLL1) ; |
---|
528 | |
---|
529 | // Implementation for UC3C parts. |
---|
530 | // Setup the generic clock for USB |
---|
531 | scif_gc_setup(AVR32_SCIF_GCLK_USB, |
---|
532 | SCIF_GCCTRL_PLL1, |
---|
533 | AVR32_SCIF_GC_NO_DIV_CLOCK, |
---|
534 | 0); |
---|
535 | // Now enable the generic clock |
---|
536 | scif_gc_enable(AVR32_SCIF_GCLK_USB); |
---|
537 | return PASS; |
---|
538 | #else |
---|
539 | return PCL_NOT_SUPPORTED; |
---|
540 | #endif |
---|
541 | #endif |
---|
542 | } |
---|
543 | |
---|
544 | |
---|
545 | #if UC3L |
---|
546 | #else |
---|
547 | void pcl_write_gplp(unsigned long gplp, unsigned long value) |
---|
548 | { |
---|
549 | #ifndef AVR32_PM_VERSION_RESETVALUE |
---|
550 | // Implementation for UC3A, UC3A3, UC3B parts. |
---|
551 | pm_write_gplp(&AVR32_PM,gplp,value); |
---|
552 | #else |
---|
553 | scif_write_gplp(gplp,value); |
---|
554 | #endif |
---|
555 | } |
---|
556 | |
---|
557 | unsigned long pcl_read_gplp(unsigned long gplp) |
---|
558 | { |
---|
559 | #ifndef AVR32_PM_VERSION_RESETVALUE |
---|
560 | // Implementation for UC3A, UC3A3, UC3B parts. |
---|
561 | return pm_read_gplp(&AVR32_PM,gplp); |
---|
562 | #else |
---|
563 | return scif_read_gplp(gplp); |
---|
564 | #endif |
---|
565 | } |
---|
566 | #endif |
---|