1 /***************************************************************************//**
2 * @file
3 * @brief Device initialization for DPLL.
4 *******************************************************************************
5 * # License
6 * <b>Copyright 2019 Silicon Laboratories Inc. www.silabs.com</b>
7 *******************************************************************************
8 *
9 * SPDX-License-Identifier: Zlib
10 *
11 * The licensor of this software is Silicon Laboratories Inc.
12 *
13 * This software is provided 'as-is', without any express or implied
14 * warranty. In no event will the authors be held liable for any damages
15 * arising from the use of this software.
16 *
17 * Permission is granted to anyone to use this software for any purpose,
18 * including commercial applications, and to alter it and redistribute it
19 * freely, subject to the following restrictions:
20 *
21 * 1. The origin of this software must not be misrepresented; you must not
22 * claim that you wrote the original software. If you use this software
23 * in a product, an acknowledgment in the product documentation would be
24 * appreciated but is not required.
25 * 2. Altered source versions must be plainly marked as such, and must not be
26 * misrepresented as being the original software.
27 * 3. This notice may not be removed or altered from any source distribution.
28 *
29 ******************************************************************************/
30 #include "sl_device_init_dpll.h"
31 #include "sl_device_init_dpll_config.h"
32
33 #include "em_cmu.h"
34
sl_device_init_dpll(void)35 sl_status_t sl_device_init_dpll(void)
36 {
37 CMU_DPLLInit_TypeDef dpll_init = {
38 .frequency = SL_DEVICE_INIT_DPLL_FREQ,
39 .n = SL_DEVICE_INIT_DPLL_N,
40 .m = SL_DEVICE_INIT_DPLL_M,
41 .refClk = SL_DEVICE_INIT_DPLL_REFCLK,
42 .edgeSel = SL_DEVICE_INIT_DPLL_EDGE,
43 .lockMode = SL_DEVICE_INIT_DPLL_LOCKMODE,
44 .autoRecover = SL_DEVICE_INIT_DPLL_AUTORECOVER,
45 .ditherEn = SL_DEVICE_INIT_DPLL_DITHER
46 };
47
48 CMU_Select_TypeDef selected_sysclk = CMU_ClockSelectGet(cmuClock_SYSCLK);
49
50 if (selected_sysclk == cmuSelect_HFRCODPLL) {
51 // From Reference Manual:
52 // The CMU should not be running from the HFRCO. If necessary, the CMU
53 // should switch to the FSRCO until after the DPLL has locked to avoid
54 // over-clocking due to overshoot.
55 CMU_ClockSelectSet(cmuClock_SYSCLK, cmuSelect_FSRCO);
56 }
57
58 #if (_SILICON_LABS_32B_SERIES_2_CONFIG > 1)
59 CMU_ClockEnable(cmuClock_DPLL0, true);
60 #endif
61
62 bool success = CMU_DPLLLock(&dpll_init);
63
64 if (selected_sysclk == cmuSelect_HFRCODPLL) {
65 CMU_ClockSelectSet(cmuClock_SYSCLK, selected_sysclk);
66 }
67
68 if (success) {
69 return SL_STATUS_OK;
70 } else {
71 return SL_STATUS_FAIL;
72 }
73 }
74