Zeroday Hong / mbed-dev

Fork of mbed-dev by mbed official

Committer:
<>
Date:
Wed Jan 04 16:58:05 2017 +0000
Revision:
154:37f96f9d4de2
This updates the lib to the mbed lib v133

Who changed what in which revision?

UserRevisionLine numberNew contents of line
<> 154:37f96f9d4de2 1 /*
<> 154:37f96f9d4de2 2 * Copyright (c) 2015, Freescale Semiconductor, Inc.
<> 154:37f96f9d4de2 3 * All rights reserved.
<> 154:37f96f9d4de2 4 *
<> 154:37f96f9d4de2 5 * Redistribution and use in source and binary forms, with or without modification,
<> 154:37f96f9d4de2 6 * are permitted provided that the following conditions are met:
<> 154:37f96f9d4de2 7 *
<> 154:37f96f9d4de2 8 * o Redistributions of source code must retain the above copyright notice, this list
<> 154:37f96f9d4de2 9 * of conditions and the following disclaimer.
<> 154:37f96f9d4de2 10 *
<> 154:37f96f9d4de2 11 * o Redistributions in binary form must reproduce the above copyright notice, this
<> 154:37f96f9d4de2 12 * list of conditions and the following disclaimer in the documentation and/or
<> 154:37f96f9d4de2 13 * other materials provided with the distribution.
<> 154:37f96f9d4de2 14 *
<> 154:37f96f9d4de2 15 * o Neither the name of Freescale Semiconductor, Inc. nor the names of its
<> 154:37f96f9d4de2 16 * contributors may be used to endorse or promote products derived from this
<> 154:37f96f9d4de2 17 * software without specific prior written permission.
<> 154:37f96f9d4de2 18 *
<> 154:37f96f9d4de2 19 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
<> 154:37f96f9d4de2 20 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
<> 154:37f96f9d4de2 21 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
<> 154:37f96f9d4de2 22 * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
<> 154:37f96f9d4de2 23 * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
<> 154:37f96f9d4de2 24 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
<> 154:37f96f9d4de2 25 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
<> 154:37f96f9d4de2 26 * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
<> 154:37f96f9d4de2 27 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
<> 154:37f96f9d4de2 28 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
<> 154:37f96f9d4de2 29 */
<> 154:37f96f9d4de2 30
<> 154:37f96f9d4de2 31 #include "fsl_common.h"
<> 154:37f96f9d4de2 32 #include "fsl_clock.h"
<> 154:37f96f9d4de2 33
<> 154:37f96f9d4de2 34 /*******************************************************************************
<> 154:37f96f9d4de2 35 * Definitions
<> 154:37f96f9d4de2 36 ******************************************************************************/
<> 154:37f96f9d4de2 37
<> 154:37f96f9d4de2 38 /* Macro definition remap workaround. */
<> 154:37f96f9d4de2 39 #if (defined(MCG_C2_EREFS_MASK) && !(defined(MCG_C2_EREFS0_MASK)))
<> 154:37f96f9d4de2 40 #define MCG_C2_EREFS0_MASK MCG_C2_EREFS_MASK
<> 154:37f96f9d4de2 41 #endif
<> 154:37f96f9d4de2 42 #if (defined(MCG_C2_HGO_MASK) && !(defined(MCG_C2_HGO0_MASK)))
<> 154:37f96f9d4de2 43 #define MCG_C2_HGO0_MASK MCG_C2_HGO_MASK
<> 154:37f96f9d4de2 44 #endif
<> 154:37f96f9d4de2 45 #if (defined(MCG_C2_RANGE_MASK) && !(defined(MCG_C2_RANGE0_MASK)))
<> 154:37f96f9d4de2 46 #define MCG_C2_RANGE0_MASK MCG_C2_RANGE_MASK
<> 154:37f96f9d4de2 47 #endif
<> 154:37f96f9d4de2 48 #if (defined(MCG_C6_CME_MASK) && !(defined(MCG_C6_CME0_MASK)))
<> 154:37f96f9d4de2 49 #define MCG_C6_CME0_MASK MCG_C6_CME_MASK
<> 154:37f96f9d4de2 50 #endif
<> 154:37f96f9d4de2 51
<> 154:37f96f9d4de2 52 /* PLL fixed multiplier when there is not PRDIV and VDIV. */
<> 154:37f96f9d4de2 53 #define PLL_FIXED_MULT (375U)
<> 154:37f96f9d4de2 54 /* Max frequency of the reference clock used for internal clock trim. */
<> 154:37f96f9d4de2 55 #define TRIM_REF_CLK_MIN (8000000U)
<> 154:37f96f9d4de2 56 /* Min frequency of the reference clock used for internal clock trim. */
<> 154:37f96f9d4de2 57 #define TRIM_REF_CLK_MAX (16000000U)
<> 154:37f96f9d4de2 58 /* Max trim value of fast internal reference clock. */
<> 154:37f96f9d4de2 59 #define TRIM_FIRC_MAX (5000000U)
<> 154:37f96f9d4de2 60 /* Min trim value of fast internal reference clock. */
<> 154:37f96f9d4de2 61 #define TRIM_FIRC_MIN (3000000U)
<> 154:37f96f9d4de2 62 /* Max trim value of fast internal reference clock. */
<> 154:37f96f9d4de2 63 #define TRIM_SIRC_MAX (39063U)
<> 154:37f96f9d4de2 64 /* Min trim value of fast internal reference clock. */
<> 154:37f96f9d4de2 65 #define TRIM_SIRC_MIN (31250U)
<> 154:37f96f9d4de2 66
<> 154:37f96f9d4de2 67 #define MCG_S_IRCST_VAL ((MCG->S & MCG_S_IRCST_MASK) >> MCG_S_IRCST_SHIFT)
<> 154:37f96f9d4de2 68 #define MCG_S_CLKST_VAL ((MCG->S & MCG_S_CLKST_MASK) >> MCG_S_CLKST_SHIFT)
<> 154:37f96f9d4de2 69 #define MCG_S_IREFST_VAL ((MCG->S & MCG_S_IREFST_MASK) >> MCG_S_IREFST_SHIFT)
<> 154:37f96f9d4de2 70 #define MCG_S_PLLST_VAL ((MCG->S & MCG_S_PLLST_MASK) >> MCG_S_PLLST_SHIFT)
<> 154:37f96f9d4de2 71 #define MCG_C1_FRDIV_VAL ((MCG->C1 & MCG_C1_FRDIV_MASK) >> MCG_C1_FRDIV_SHIFT)
<> 154:37f96f9d4de2 72 #define MCG_C2_LP_VAL ((MCG->C2 & MCG_C2_LP_MASK) >> MCG_C2_LP_SHIFT)
<> 154:37f96f9d4de2 73 #define MCG_C2_RANGE_VAL ((MCG->C2 & MCG_C2_RANGE_MASK) >> MCG_C2_RANGE_SHIFT)
<> 154:37f96f9d4de2 74 #define MCG_SC_FCRDIV_VAL ((MCG->SC & MCG_SC_FCRDIV_MASK) >> MCG_SC_FCRDIV_SHIFT)
<> 154:37f96f9d4de2 75 #define MCG_S2_PLLCST_VAL ((MCG->S2 & MCG_S2_PLLCST_MASK) >> MCG_S2_PLLCST_SHIFT)
<> 154:37f96f9d4de2 76 #define MCG_C7_OSCSEL_VAL ((MCG->C7 & MCG_C7_OSCSEL_MASK) >> MCG_C7_OSCSEL_SHIFT)
<> 154:37f96f9d4de2 77 #define MCG_C4_DMX32_VAL ((MCG->C4 & MCG_C4_DMX32_MASK) >> MCG_C4_DMX32_SHIFT)
<> 154:37f96f9d4de2 78 #define MCG_C4_DRST_DRS_VAL ((MCG->C4 & MCG_C4_DRST_DRS_MASK) >> MCG_C4_DRST_DRS_SHIFT)
<> 154:37f96f9d4de2 79 #define MCG_C7_PLL32KREFSEL_VAL ((MCG->C7 & MCG_C7_PLL32KREFSEL_MASK) >> MCG_C7_PLL32KREFSEL_SHIFT)
<> 154:37f96f9d4de2 80 #define MCG_C5_PLLREFSEL0_VAL ((MCG->C5 & MCG_C5_PLLREFSEL0_MASK) >> MCG_C5_PLLREFSEL0_SHIFT)
<> 154:37f96f9d4de2 81 #define MCG_C11_PLLREFSEL1_VAL ((MCG->C11 & MCG_C11_PLLREFSEL1_MASK) >> MCG_C11_PLLREFSEL1_SHIFT)
<> 154:37f96f9d4de2 82 #define MCG_C11_PRDIV1_VAL ((MCG->C11 & MCG_C11_PRDIV1_MASK) >> MCG_C11_PRDIV1_SHIFT)
<> 154:37f96f9d4de2 83 #define MCG_C12_VDIV1_VAL ((MCG->C12 & MCG_C12_VDIV1_MASK) >> MCG_C12_VDIV1_SHIFT)
<> 154:37f96f9d4de2 84 #define MCG_C5_PRDIV0_VAL ((MCG->C5 & MCG_C5_PRDIV0_MASK) >> MCG_C5_PRDIV0_SHIFT)
<> 154:37f96f9d4de2 85 #define MCG_C6_VDIV0_VAL ((MCG->C6 & MCG_C6_VDIV0_MASK) >> MCG_C6_VDIV0_SHIFT)
<> 154:37f96f9d4de2 86
<> 154:37f96f9d4de2 87 #define OSC_MODE_MASK (MCG_C2_EREFS0_MASK | MCG_C2_HGO0_MASK | MCG_C2_RANGE0_MASK)
<> 154:37f96f9d4de2 88
<> 154:37f96f9d4de2 89 #define SIM_CLKDIV1_OUTDIV1_VAL ((SIM->CLKDIV1 & SIM_CLKDIV1_OUTDIV1_MASK) >> SIM_CLKDIV1_OUTDIV1_SHIFT)
<> 154:37f96f9d4de2 90 #define SIM_CLKDIV1_OUTDIV2_VAL ((SIM->CLKDIV1 & SIM_CLKDIV1_OUTDIV2_MASK) >> SIM_CLKDIV1_OUTDIV2_SHIFT)
<> 154:37f96f9d4de2 91 #define SIM_CLKDIV1_OUTDIV3_VAL ((SIM->CLKDIV1 & SIM_CLKDIV1_OUTDIV3_MASK) >> SIM_CLKDIV1_OUTDIV3_SHIFT)
<> 154:37f96f9d4de2 92 #define SIM_CLKDIV1_OUTDIV4_VAL ((SIM->CLKDIV1 & SIM_CLKDIV1_OUTDIV4_MASK) >> SIM_CLKDIV1_OUTDIV4_SHIFT)
<> 154:37f96f9d4de2 93 #define SIM_SOPT1_OSC32KSEL_VAL ((SIM->SOPT1 & SIM_SOPT1_OSC32KSEL_MASK) >> SIM_SOPT1_OSC32KSEL_SHIFT)
<> 154:37f96f9d4de2 94 #define SIM_SOPT2_PLLFLLSEL_VAL ((SIM->SOPT2 & SIM_SOPT2_PLLFLLSEL_MASK) >> SIM_SOPT2_PLLFLLSEL_SHIFT)
<> 154:37f96f9d4de2 95
<> 154:37f96f9d4de2 96 /* MCG_S_CLKST definition. */
<> 154:37f96f9d4de2 97 enum _mcg_clkout_stat
<> 154:37f96f9d4de2 98 {
<> 154:37f96f9d4de2 99 kMCG_ClkOutStatFll, /* FLL. */
<> 154:37f96f9d4de2 100 kMCG_ClkOutStatInt, /* Internal clock. */
<> 154:37f96f9d4de2 101 kMCG_ClkOutStatExt, /* External clock. */
<> 154:37f96f9d4de2 102 kMCG_ClkOutStatPll /* PLL. */
<> 154:37f96f9d4de2 103 };
<> 154:37f96f9d4de2 104
<> 154:37f96f9d4de2 105 /* MCG_S_PLLST definition. */
<> 154:37f96f9d4de2 106 enum _mcg_pllst
<> 154:37f96f9d4de2 107 {
<> 154:37f96f9d4de2 108 kMCG_PllstFll, /* FLL is used. */
<> 154:37f96f9d4de2 109 kMCG_PllstPll /* PLL is used. */
<> 154:37f96f9d4de2 110 };
<> 154:37f96f9d4de2 111
<> 154:37f96f9d4de2 112 /*******************************************************************************
<> 154:37f96f9d4de2 113 * Variables
<> 154:37f96f9d4de2 114 ******************************************************************************/
<> 154:37f96f9d4de2 115
<> 154:37f96f9d4de2 116 /* Slow internal reference clock frequency. */
<> 154:37f96f9d4de2 117 static uint32_t s_slowIrcFreq = 32768U;
<> 154:37f96f9d4de2 118 /* Fast internal reference clock frequency. */
<> 154:37f96f9d4de2 119 static uint32_t s_fastIrcFreq = 4000000U;
<> 154:37f96f9d4de2 120
<> 154:37f96f9d4de2 121 /* External XTAL0 (OSC0) clock frequency. */
<> 154:37f96f9d4de2 122 uint32_t g_xtal0Freq;
<> 154:37f96f9d4de2 123
<> 154:37f96f9d4de2 124 /* External XTAL32K clock frequency. */
<> 154:37f96f9d4de2 125 uint32_t g_xtal32Freq;
<> 154:37f96f9d4de2 126
<> 154:37f96f9d4de2 127 /*******************************************************************************
<> 154:37f96f9d4de2 128 * Prototypes
<> 154:37f96f9d4de2 129 ******************************************************************************/
<> 154:37f96f9d4de2 130
<> 154:37f96f9d4de2 131 /*!
<> 154:37f96f9d4de2 132 * @brief Get the MCG external reference clock frequency.
<> 154:37f96f9d4de2 133 *
<> 154:37f96f9d4de2 134 * Get the current MCG external reference clock frequency in Hz. It is
<> 154:37f96f9d4de2 135 * the frequency select by MCG_C7[OSCSEL]. This is an internal function.
<> 154:37f96f9d4de2 136 *
<> 154:37f96f9d4de2 137 * @return MCG external reference clock frequency in Hz.
<> 154:37f96f9d4de2 138 */
<> 154:37f96f9d4de2 139 static uint32_t CLOCK_GetMcgExtClkFreq(void);
<> 154:37f96f9d4de2 140
<> 154:37f96f9d4de2 141 /*!
<> 154:37f96f9d4de2 142 * @brief Get the MCG FLL external reference clock frequency.
<> 154:37f96f9d4de2 143 *
<> 154:37f96f9d4de2 144 * Get the current MCG FLL external reference clock frequency in Hz. It is
<> 154:37f96f9d4de2 145 * the frequency after by MCG_C1[FRDIV]. This is an internal function.
<> 154:37f96f9d4de2 146 *
<> 154:37f96f9d4de2 147 * @return MCG FLL external reference clock frequency in Hz.
<> 154:37f96f9d4de2 148 */
<> 154:37f96f9d4de2 149 static uint32_t CLOCK_GetFllExtRefClkFreq(void);
<> 154:37f96f9d4de2 150
<> 154:37f96f9d4de2 151 /*!
<> 154:37f96f9d4de2 152 * @brief Get the MCG FLL reference clock frequency.
<> 154:37f96f9d4de2 153 *
<> 154:37f96f9d4de2 154 * Get the current MCG FLL reference clock frequency in Hz. It is
<> 154:37f96f9d4de2 155 * the frequency select by MCG_C1[IREFS]. This is an internal function.
<> 154:37f96f9d4de2 156 *
<> 154:37f96f9d4de2 157 * @return MCG FLL reference clock frequency in Hz.
<> 154:37f96f9d4de2 158 */
<> 154:37f96f9d4de2 159 static uint32_t CLOCK_GetFllRefClkFreq(void);
<> 154:37f96f9d4de2 160
<> 154:37f96f9d4de2 161 /*!
<> 154:37f96f9d4de2 162 * @brief Get the frequency of clock selected by MCG_C2[IRCS].
<> 154:37f96f9d4de2 163 *
<> 154:37f96f9d4de2 164 * This clock's two output:
<> 154:37f96f9d4de2 165 * 1. MCGOUTCLK when MCG_S[CLKST]=0.
<> 154:37f96f9d4de2 166 * 2. MCGIRCLK when MCG_C1[IRCLKEN]=1.
<> 154:37f96f9d4de2 167 *
<> 154:37f96f9d4de2 168 * @return The frequency in Hz.
<> 154:37f96f9d4de2 169 */
<> 154:37f96f9d4de2 170 static uint32_t CLOCK_GetInternalRefClkSelectFreq(void);
<> 154:37f96f9d4de2 171
<> 154:37f96f9d4de2 172 /*!
<> 154:37f96f9d4de2 173 * @brief Get the MCG PLL/PLL0 reference clock frequency.
<> 154:37f96f9d4de2 174 *
<> 154:37f96f9d4de2 175 * Get the current MCG PLL/PLL0 reference clock frequency in Hz.
<> 154:37f96f9d4de2 176 * This is an internal function.
<> 154:37f96f9d4de2 177 *
<> 154:37f96f9d4de2 178 * @return MCG PLL/PLL0 reference clock frequency in Hz.
<> 154:37f96f9d4de2 179 */
<> 154:37f96f9d4de2 180 static uint32_t CLOCK_GetPll0RefFreq(void);
<> 154:37f96f9d4de2 181
<> 154:37f96f9d4de2 182 /*!
<> 154:37f96f9d4de2 183 * @brief Calculate the RANGE value base on crystal frequency.
<> 154:37f96f9d4de2 184 *
<> 154:37f96f9d4de2 185 * To setup external crystal oscillator, must set the register bits RANGE
<> 154:37f96f9d4de2 186 * base on the crystal frequency. This function returns the RANGE base on the
<> 154:37f96f9d4de2 187 * input frequency. This is an internal function.
<> 154:37f96f9d4de2 188 *
<> 154:37f96f9d4de2 189 * @param freq Crystal frequency in Hz.
<> 154:37f96f9d4de2 190 * @return The RANGE value.
<> 154:37f96f9d4de2 191 */
<> 154:37f96f9d4de2 192 static uint8_t CLOCK_GetOscRangeFromFreq(uint32_t freq);
<> 154:37f96f9d4de2 193
<> 154:37f96f9d4de2 194 /*!
<> 154:37f96f9d4de2 195 * @brief Delay function to wait FLL stable.
<> 154:37f96f9d4de2 196 *
<> 154:37f96f9d4de2 197 * Delay function to wait FLL stable in FEI mode or FEE mode, should wait at least
<> 154:37f96f9d4de2 198 * 1ms. Every time changes FLL setting, should wait this time for FLL stable.
<> 154:37f96f9d4de2 199 */
<> 154:37f96f9d4de2 200 static void CLOCK_FllStableDelay(void);
<> 154:37f96f9d4de2 201
<> 154:37f96f9d4de2 202 /*******************************************************************************
<> 154:37f96f9d4de2 203 * Code
<> 154:37f96f9d4de2 204 ******************************************************************************/
<> 154:37f96f9d4de2 205
<> 154:37f96f9d4de2 206 static uint32_t CLOCK_GetMcgExtClkFreq(void)
<> 154:37f96f9d4de2 207 {
<> 154:37f96f9d4de2 208 uint32_t freq;
<> 154:37f96f9d4de2 209
<> 154:37f96f9d4de2 210 switch (MCG_C7_OSCSEL_VAL)
<> 154:37f96f9d4de2 211 {
<> 154:37f96f9d4de2 212 case 0U:
<> 154:37f96f9d4de2 213 /* Please call CLOCK_SetXtal0Freq base on board setting before using OSC0 clock. */
<> 154:37f96f9d4de2 214 assert(g_xtal0Freq);
<> 154:37f96f9d4de2 215 freq = g_xtal0Freq;
<> 154:37f96f9d4de2 216 break;
<> 154:37f96f9d4de2 217 case 1U:
<> 154:37f96f9d4de2 218 /* Please call CLOCK_SetXtal32Freq base on board setting before using XTAL32K/RTC_CLKIN clock. */
<> 154:37f96f9d4de2 219 assert(g_xtal32Freq);
<> 154:37f96f9d4de2 220 freq = g_xtal32Freq;
<> 154:37f96f9d4de2 221 break;
<> 154:37f96f9d4de2 222 case 2U:
<> 154:37f96f9d4de2 223 freq = MCG_INTERNAL_IRC_48M;
<> 154:37f96f9d4de2 224 break;
<> 154:37f96f9d4de2 225 default:
<> 154:37f96f9d4de2 226 freq = 0U;
<> 154:37f96f9d4de2 227 break;
<> 154:37f96f9d4de2 228 }
<> 154:37f96f9d4de2 229
<> 154:37f96f9d4de2 230 return freq;
<> 154:37f96f9d4de2 231 }
<> 154:37f96f9d4de2 232
<> 154:37f96f9d4de2 233 static uint32_t CLOCK_GetFllExtRefClkFreq(void)
<> 154:37f96f9d4de2 234 {
<> 154:37f96f9d4de2 235 /* FllExtRef = McgExtRef / FllExtRefDiv */
<> 154:37f96f9d4de2 236 uint8_t frdiv;
<> 154:37f96f9d4de2 237 uint8_t range;
<> 154:37f96f9d4de2 238 uint8_t oscsel;
<> 154:37f96f9d4de2 239
<> 154:37f96f9d4de2 240 uint32_t freq = CLOCK_GetMcgExtClkFreq();
<> 154:37f96f9d4de2 241
<> 154:37f96f9d4de2 242 if (!freq)
<> 154:37f96f9d4de2 243 {
<> 154:37f96f9d4de2 244 return freq;
<> 154:37f96f9d4de2 245 }
<> 154:37f96f9d4de2 246
<> 154:37f96f9d4de2 247 frdiv = MCG_C1_FRDIV_VAL;
<> 154:37f96f9d4de2 248 freq >>= frdiv;
<> 154:37f96f9d4de2 249
<> 154:37f96f9d4de2 250 range = MCG_C2_RANGE_VAL;
<> 154:37f96f9d4de2 251 oscsel = MCG_C7_OSCSEL_VAL;
<> 154:37f96f9d4de2 252
<> 154:37f96f9d4de2 253 /*
<> 154:37f96f9d4de2 254 When should use divider 32, 64, 128, 256, 512, 1024, 1280, 1536.
<> 154:37f96f9d4de2 255 1. MCG_C7[OSCSEL] selects IRC48M.
<> 154:37f96f9d4de2 256 2. MCG_C7[OSCSEL] selects OSC0 and MCG_C2[RANGE] is not 0.
<> 154:37f96f9d4de2 257 */
<> 154:37f96f9d4de2 258 if (((0U != range) && (kMCG_OscselOsc == oscsel)) || (kMCG_OscselIrc == oscsel))
<> 154:37f96f9d4de2 259 {
<> 154:37f96f9d4de2 260 switch (frdiv)
<> 154:37f96f9d4de2 261 {
<> 154:37f96f9d4de2 262 case 0:
<> 154:37f96f9d4de2 263 case 1:
<> 154:37f96f9d4de2 264 case 2:
<> 154:37f96f9d4de2 265 case 3:
<> 154:37f96f9d4de2 266 case 4:
<> 154:37f96f9d4de2 267 case 5:
<> 154:37f96f9d4de2 268 freq >>= 5u;
<> 154:37f96f9d4de2 269 break;
<> 154:37f96f9d4de2 270 case 6:
<> 154:37f96f9d4de2 271 /* 64*20=1280 */
<> 154:37f96f9d4de2 272 freq /= 20u;
<> 154:37f96f9d4de2 273 break;
<> 154:37f96f9d4de2 274 case 7:
<> 154:37f96f9d4de2 275 /* 128*12=1536 */
<> 154:37f96f9d4de2 276 freq /= 12u;
<> 154:37f96f9d4de2 277 break;
<> 154:37f96f9d4de2 278 default:
<> 154:37f96f9d4de2 279 freq = 0u;
<> 154:37f96f9d4de2 280 break;
<> 154:37f96f9d4de2 281 }
<> 154:37f96f9d4de2 282 }
<> 154:37f96f9d4de2 283
<> 154:37f96f9d4de2 284 return freq;
<> 154:37f96f9d4de2 285 }
<> 154:37f96f9d4de2 286
<> 154:37f96f9d4de2 287 static uint32_t CLOCK_GetInternalRefClkSelectFreq(void)
<> 154:37f96f9d4de2 288 {
<> 154:37f96f9d4de2 289 if (kMCG_IrcSlow == MCG_S_IRCST_VAL)
<> 154:37f96f9d4de2 290 {
<> 154:37f96f9d4de2 291 /* Slow internal reference clock selected*/
<> 154:37f96f9d4de2 292 return s_slowIrcFreq;
<> 154:37f96f9d4de2 293 }
<> 154:37f96f9d4de2 294 else
<> 154:37f96f9d4de2 295 {
<> 154:37f96f9d4de2 296 /* Fast internal reference clock selected*/
<> 154:37f96f9d4de2 297 return s_fastIrcFreq >> MCG_SC_FCRDIV_VAL;
<> 154:37f96f9d4de2 298 }
<> 154:37f96f9d4de2 299 }
<> 154:37f96f9d4de2 300
<> 154:37f96f9d4de2 301 static uint32_t CLOCK_GetFllRefClkFreq(void)
<> 154:37f96f9d4de2 302 {
<> 154:37f96f9d4de2 303 /* If use external reference clock. */
<> 154:37f96f9d4de2 304 if (kMCG_FllSrcExternal == MCG_S_IREFST_VAL)
<> 154:37f96f9d4de2 305 {
<> 154:37f96f9d4de2 306 return CLOCK_GetFllExtRefClkFreq();
<> 154:37f96f9d4de2 307 }
<> 154:37f96f9d4de2 308 /* If use internal reference clock. */
<> 154:37f96f9d4de2 309 else
<> 154:37f96f9d4de2 310 {
<> 154:37f96f9d4de2 311 return s_slowIrcFreq;
<> 154:37f96f9d4de2 312 }
<> 154:37f96f9d4de2 313 }
<> 154:37f96f9d4de2 314
<> 154:37f96f9d4de2 315 static uint32_t CLOCK_GetPll0RefFreq(void)
<> 154:37f96f9d4de2 316 {
<> 154:37f96f9d4de2 317 /* MCG external reference clock. */
<> 154:37f96f9d4de2 318 return CLOCK_GetMcgExtClkFreq();
<> 154:37f96f9d4de2 319 }
<> 154:37f96f9d4de2 320
<> 154:37f96f9d4de2 321 static uint8_t CLOCK_GetOscRangeFromFreq(uint32_t freq)
<> 154:37f96f9d4de2 322 {
<> 154:37f96f9d4de2 323 uint8_t range;
<> 154:37f96f9d4de2 324
<> 154:37f96f9d4de2 325 if (freq <= 39063U)
<> 154:37f96f9d4de2 326 {
<> 154:37f96f9d4de2 327 range = 0U;
<> 154:37f96f9d4de2 328 }
<> 154:37f96f9d4de2 329 else if (freq <= 8000000U)
<> 154:37f96f9d4de2 330 {
<> 154:37f96f9d4de2 331 range = 1U;
<> 154:37f96f9d4de2 332 }
<> 154:37f96f9d4de2 333 else
<> 154:37f96f9d4de2 334 {
<> 154:37f96f9d4de2 335 range = 2U;
<> 154:37f96f9d4de2 336 }
<> 154:37f96f9d4de2 337
<> 154:37f96f9d4de2 338 return range;
<> 154:37f96f9d4de2 339 }
<> 154:37f96f9d4de2 340
<> 154:37f96f9d4de2 341 static void CLOCK_FllStableDelay(void)
<> 154:37f96f9d4de2 342 {
<> 154:37f96f9d4de2 343 /*
<> 154:37f96f9d4de2 344 Should wait at least 1ms. Because in these modes, the core clock is 100MHz
<> 154:37f96f9d4de2 345 at most, so this function could obtain the 1ms delay.
<> 154:37f96f9d4de2 346 */
<> 154:37f96f9d4de2 347 volatile uint32_t i = 30000U;
<> 154:37f96f9d4de2 348 while (i--)
<> 154:37f96f9d4de2 349 {
<> 154:37f96f9d4de2 350 __NOP();
<> 154:37f96f9d4de2 351 }
<> 154:37f96f9d4de2 352 }
<> 154:37f96f9d4de2 353
<> 154:37f96f9d4de2 354 uint32_t CLOCK_GetOsc0ErClkUndivFreq(void)
<> 154:37f96f9d4de2 355 {
<> 154:37f96f9d4de2 356 if (OSC0->CR & OSC_CR_ERCLKEN_MASK)
<> 154:37f96f9d4de2 357 {
<> 154:37f96f9d4de2 358 /* Please call CLOCK_SetXtal0Freq base on board setting before using OSC0 clock. */
<> 154:37f96f9d4de2 359 assert(g_xtal0Freq);
<> 154:37f96f9d4de2 360 return g_xtal0Freq;
<> 154:37f96f9d4de2 361 }
<> 154:37f96f9d4de2 362 else
<> 154:37f96f9d4de2 363 {
<> 154:37f96f9d4de2 364 return 0U;
<> 154:37f96f9d4de2 365 }
<> 154:37f96f9d4de2 366 }
<> 154:37f96f9d4de2 367
<> 154:37f96f9d4de2 368 uint32_t CLOCK_GetOsc0ErClkDivFreq(void)
<> 154:37f96f9d4de2 369 {
<> 154:37f96f9d4de2 370 if (OSC0->CR & OSC_CR_ERCLKEN_MASK)
<> 154:37f96f9d4de2 371 {
<> 154:37f96f9d4de2 372 /* Please call CLOCK_SetXtal0Freq base on board setting before using OSC0 clock. */
<> 154:37f96f9d4de2 373 assert(g_xtal0Freq);
<> 154:37f96f9d4de2 374 return g_xtal0Freq >> ((OSC0->DIV & OSC_DIV_ERPS_MASK) >> OSC_DIV_ERPS_SHIFT);
<> 154:37f96f9d4de2 375 }
<> 154:37f96f9d4de2 376 else
<> 154:37f96f9d4de2 377 {
<> 154:37f96f9d4de2 378 return 0U;
<> 154:37f96f9d4de2 379 }
<> 154:37f96f9d4de2 380 }
<> 154:37f96f9d4de2 381
<> 154:37f96f9d4de2 382 uint32_t CLOCK_GetEr32kClkFreq(void)
<> 154:37f96f9d4de2 383 {
<> 154:37f96f9d4de2 384 uint32_t freq;
<> 154:37f96f9d4de2 385
<> 154:37f96f9d4de2 386 switch (SIM_SOPT1_OSC32KSEL_VAL)
<> 154:37f96f9d4de2 387 {
<> 154:37f96f9d4de2 388 case 0U: /* OSC 32k clock */
<> 154:37f96f9d4de2 389 freq = (CLOCK_GetOsc0ErClkUndivFreq() == 32768U) ? 32768U : 0U;
<> 154:37f96f9d4de2 390 break;
<> 154:37f96f9d4de2 391 case 2U: /* RTC 32k clock */
<> 154:37f96f9d4de2 392 /* Please call CLOCK_SetXtal32Freq base on board setting before using XTAL32K/RTC_CLKIN clock. */
<> 154:37f96f9d4de2 393 assert(g_xtal32Freq);
<> 154:37f96f9d4de2 394 freq = g_xtal32Freq;
<> 154:37f96f9d4de2 395 break;
<> 154:37f96f9d4de2 396 case 3U: /* LPO clock */
<> 154:37f96f9d4de2 397 freq = LPO_CLK_FREQ;
<> 154:37f96f9d4de2 398 break;
<> 154:37f96f9d4de2 399 default:
<> 154:37f96f9d4de2 400 freq = 0U;
<> 154:37f96f9d4de2 401 break;
<> 154:37f96f9d4de2 402 }
<> 154:37f96f9d4de2 403 return freq;
<> 154:37f96f9d4de2 404 }
<> 154:37f96f9d4de2 405
<> 154:37f96f9d4de2 406 uint32_t CLOCK_GetPllFllSelClkFreq(void)
<> 154:37f96f9d4de2 407 {
<> 154:37f96f9d4de2 408 uint32_t freq;
<> 154:37f96f9d4de2 409
<> 154:37f96f9d4de2 410 switch (SIM_SOPT2_PLLFLLSEL_VAL)
<> 154:37f96f9d4de2 411 {
<> 154:37f96f9d4de2 412 case 0U: /* FLL. */
<> 154:37f96f9d4de2 413 freq = CLOCK_GetFllFreq();
<> 154:37f96f9d4de2 414 break;
<> 154:37f96f9d4de2 415 case 1U: /* PLL. */
<> 154:37f96f9d4de2 416 freq = CLOCK_GetPll0Freq();
<> 154:37f96f9d4de2 417 break;
<> 154:37f96f9d4de2 418 case 3U: /* MCG IRC48M. */
<> 154:37f96f9d4de2 419 freq = MCG_INTERNAL_IRC_48M;
<> 154:37f96f9d4de2 420 break;
<> 154:37f96f9d4de2 421 default:
<> 154:37f96f9d4de2 422 freq = 0U;
<> 154:37f96f9d4de2 423 break;
<> 154:37f96f9d4de2 424 }
<> 154:37f96f9d4de2 425
<> 154:37f96f9d4de2 426 return freq;
<> 154:37f96f9d4de2 427 }
<> 154:37f96f9d4de2 428
<> 154:37f96f9d4de2 429 uint32_t CLOCK_GetOsc0ErClkFreq(void)
<> 154:37f96f9d4de2 430 {
<> 154:37f96f9d4de2 431 return CLOCK_GetOsc0ErClkDivFreq();
<> 154:37f96f9d4de2 432 }
<> 154:37f96f9d4de2 433
<> 154:37f96f9d4de2 434 uint32_t CLOCK_GetPlatClkFreq(void)
<> 154:37f96f9d4de2 435 {
<> 154:37f96f9d4de2 436 return CLOCK_GetOutClkFreq() / (SIM_CLKDIV1_OUTDIV1_VAL + 1);
<> 154:37f96f9d4de2 437 }
<> 154:37f96f9d4de2 438
<> 154:37f96f9d4de2 439 uint32_t CLOCK_GetFlashClkFreq(void)
<> 154:37f96f9d4de2 440 {
<> 154:37f96f9d4de2 441 return CLOCK_GetOutClkFreq() / (SIM_CLKDIV1_OUTDIV4_VAL + 1);
<> 154:37f96f9d4de2 442 }
<> 154:37f96f9d4de2 443
<> 154:37f96f9d4de2 444 uint32_t CLOCK_GetFlexBusClkFreq(void)
<> 154:37f96f9d4de2 445 {
<> 154:37f96f9d4de2 446 return CLOCK_GetOutClkFreq() / (SIM_CLKDIV1_OUTDIV3_VAL + 1);
<> 154:37f96f9d4de2 447 }
<> 154:37f96f9d4de2 448
<> 154:37f96f9d4de2 449 uint32_t CLOCK_GetBusClkFreq(void)
<> 154:37f96f9d4de2 450 {
<> 154:37f96f9d4de2 451 return CLOCK_GetOutClkFreq() / (SIM_CLKDIV1_OUTDIV2_VAL + 1);
<> 154:37f96f9d4de2 452 }
<> 154:37f96f9d4de2 453
<> 154:37f96f9d4de2 454 uint32_t CLOCK_GetCoreSysClkFreq(void)
<> 154:37f96f9d4de2 455 {
<> 154:37f96f9d4de2 456 return CLOCK_GetOutClkFreq() / (SIM_CLKDIV1_OUTDIV1_VAL + 1);
<> 154:37f96f9d4de2 457 }
<> 154:37f96f9d4de2 458
<> 154:37f96f9d4de2 459 uint32_t CLOCK_GetFreq(clock_name_t clockName)
<> 154:37f96f9d4de2 460 {
<> 154:37f96f9d4de2 461 uint32_t freq;
<> 154:37f96f9d4de2 462
<> 154:37f96f9d4de2 463 switch (clockName)
<> 154:37f96f9d4de2 464 {
<> 154:37f96f9d4de2 465 case kCLOCK_CoreSysClk:
<> 154:37f96f9d4de2 466 case kCLOCK_PlatClk:
<> 154:37f96f9d4de2 467 freq = CLOCK_GetOutClkFreq() / (SIM_CLKDIV1_OUTDIV1_VAL + 1);
<> 154:37f96f9d4de2 468 break;
<> 154:37f96f9d4de2 469 case kCLOCK_BusClk:
<> 154:37f96f9d4de2 470 freq = CLOCK_GetOutClkFreq() / (SIM_CLKDIV1_OUTDIV2_VAL + 1);
<> 154:37f96f9d4de2 471 break;
<> 154:37f96f9d4de2 472 case kCLOCK_FlexBusClk:
<> 154:37f96f9d4de2 473 freq = CLOCK_GetOutClkFreq() / (SIM_CLKDIV1_OUTDIV3_VAL + 1);
<> 154:37f96f9d4de2 474 break;
<> 154:37f96f9d4de2 475 case kCLOCK_FlashClk:
<> 154:37f96f9d4de2 476 freq = CLOCK_GetOutClkFreq() / (SIM_CLKDIV1_OUTDIV4_VAL + 1);
<> 154:37f96f9d4de2 477 break;
<> 154:37f96f9d4de2 478 case kCLOCK_PllFllSelClk:
<> 154:37f96f9d4de2 479 freq = CLOCK_GetPllFllSelClkFreq();
<> 154:37f96f9d4de2 480 break;
<> 154:37f96f9d4de2 481 case kCLOCK_Er32kClk:
<> 154:37f96f9d4de2 482 freq = CLOCK_GetEr32kClkFreq();
<> 154:37f96f9d4de2 483 break;
<> 154:37f96f9d4de2 484 case kCLOCK_McgFixedFreqClk:
<> 154:37f96f9d4de2 485 freq = CLOCK_GetFixedFreqClkFreq();
<> 154:37f96f9d4de2 486 break;
<> 154:37f96f9d4de2 487 case kCLOCK_McgInternalRefClk:
<> 154:37f96f9d4de2 488 freq = CLOCK_GetInternalRefClkFreq();
<> 154:37f96f9d4de2 489 break;
<> 154:37f96f9d4de2 490 case kCLOCK_McgFllClk:
<> 154:37f96f9d4de2 491 freq = CLOCK_GetFllFreq();
<> 154:37f96f9d4de2 492 break;
<> 154:37f96f9d4de2 493 case kCLOCK_McgPll0Clk:
<> 154:37f96f9d4de2 494 freq = CLOCK_GetPll0Freq();
<> 154:37f96f9d4de2 495 break;
<> 154:37f96f9d4de2 496 case kCLOCK_McgIrc48MClk:
<> 154:37f96f9d4de2 497 freq = MCG_INTERNAL_IRC_48M;
<> 154:37f96f9d4de2 498 break;
<> 154:37f96f9d4de2 499 case kCLOCK_LpoClk:
<> 154:37f96f9d4de2 500 freq = LPO_CLK_FREQ;
<> 154:37f96f9d4de2 501 break;
<> 154:37f96f9d4de2 502 case kCLOCK_Osc0ErClkUndiv:
<> 154:37f96f9d4de2 503 freq = CLOCK_GetOsc0ErClkUndivFreq();
<> 154:37f96f9d4de2 504 break;
<> 154:37f96f9d4de2 505 case kCLOCK_Osc0ErClk:
<> 154:37f96f9d4de2 506 freq = CLOCK_GetOsc0ErClkDivFreq();
<> 154:37f96f9d4de2 507 break;
<> 154:37f96f9d4de2 508 default:
<> 154:37f96f9d4de2 509 freq = 0U;
<> 154:37f96f9d4de2 510 break;
<> 154:37f96f9d4de2 511 }
<> 154:37f96f9d4de2 512
<> 154:37f96f9d4de2 513 return freq;
<> 154:37f96f9d4de2 514 }
<> 154:37f96f9d4de2 515
<> 154:37f96f9d4de2 516 void CLOCK_SetSimConfig(sim_clock_config_t const *config)
<> 154:37f96f9d4de2 517 {
<> 154:37f96f9d4de2 518 SIM->CLKDIV1 = config->clkdiv1;
<> 154:37f96f9d4de2 519 CLOCK_SetPllFllSelClock(config->pllFllSel);
<> 154:37f96f9d4de2 520 CLOCK_SetEr32kClock(config->er32kSrc);
<> 154:37f96f9d4de2 521 }
<> 154:37f96f9d4de2 522
<> 154:37f96f9d4de2 523 bool CLOCK_EnableUsbfs0Clock(clock_usb_src_t src, uint32_t freq)
<> 154:37f96f9d4de2 524 {
<> 154:37f96f9d4de2 525 bool ret = true;
<> 154:37f96f9d4de2 526
<> 154:37f96f9d4de2 527 CLOCK_DisableClock(kCLOCK_Usbfs0);
<> 154:37f96f9d4de2 528
<> 154:37f96f9d4de2 529 if (kCLOCK_UsbSrcExt == src)
<> 154:37f96f9d4de2 530 {
<> 154:37f96f9d4de2 531 SIM->SOPT2 &= ~SIM_SOPT2_USBSRC_MASK;
<> 154:37f96f9d4de2 532 }
<> 154:37f96f9d4de2 533 else
<> 154:37f96f9d4de2 534 {
<> 154:37f96f9d4de2 535 switch (freq)
<> 154:37f96f9d4de2 536 {
<> 154:37f96f9d4de2 537 case 120000000U:
<> 154:37f96f9d4de2 538 SIM->CLKDIV2 = SIM_CLKDIV2_USBDIV(4) | SIM_CLKDIV2_USBFRAC(1);
<> 154:37f96f9d4de2 539 break;
<> 154:37f96f9d4de2 540 case 96000000U:
<> 154:37f96f9d4de2 541 SIM->CLKDIV2 = SIM_CLKDIV2_USBDIV(1) | SIM_CLKDIV2_USBFRAC(0);
<> 154:37f96f9d4de2 542 break;
<> 154:37f96f9d4de2 543 case 72000000U:
<> 154:37f96f9d4de2 544 SIM->CLKDIV2 = SIM_CLKDIV2_USBDIV(2) | SIM_CLKDIV2_USBFRAC(1);
<> 154:37f96f9d4de2 545 break;
<> 154:37f96f9d4de2 546 case 48000000U:
<> 154:37f96f9d4de2 547 SIM->CLKDIV2 = SIM_CLKDIV2_USBDIV(0) | SIM_CLKDIV2_USBFRAC(0);
<> 154:37f96f9d4de2 548 break;
<> 154:37f96f9d4de2 549 default:
<> 154:37f96f9d4de2 550 ret = false;
<> 154:37f96f9d4de2 551 break;
<> 154:37f96f9d4de2 552 }
<> 154:37f96f9d4de2 553
<> 154:37f96f9d4de2 554 SIM->SOPT2 = ((SIM->SOPT2 & ~(SIM_SOPT2_PLLFLLSEL_MASK | SIM_SOPT2_USBSRC_MASK)) | (uint32_t)src);
<> 154:37f96f9d4de2 555 }
<> 154:37f96f9d4de2 556
<> 154:37f96f9d4de2 557 CLOCK_EnableClock(kCLOCK_Usbfs0);
<> 154:37f96f9d4de2 558
<> 154:37f96f9d4de2 559 if (kCLOCK_UsbSrcIrc48M == src)
<> 154:37f96f9d4de2 560 {
<> 154:37f96f9d4de2 561 USB0->CLK_RECOVER_IRC_EN = 0x03U;
<> 154:37f96f9d4de2 562 USB0->CLK_RECOVER_CTRL |= USB_CLK_RECOVER_CTRL_CLOCK_RECOVER_EN_MASK;
<> 154:37f96f9d4de2 563 }
<> 154:37f96f9d4de2 564 return ret;
<> 154:37f96f9d4de2 565 }
<> 154:37f96f9d4de2 566
<> 154:37f96f9d4de2 567 uint32_t CLOCK_GetOutClkFreq(void)
<> 154:37f96f9d4de2 568 {
<> 154:37f96f9d4de2 569 uint32_t mcgoutclk;
<> 154:37f96f9d4de2 570 uint32_t clkst = MCG_S_CLKST_VAL;
<> 154:37f96f9d4de2 571
<> 154:37f96f9d4de2 572 switch (clkst)
<> 154:37f96f9d4de2 573 {
<> 154:37f96f9d4de2 574 case kMCG_ClkOutStatPll:
<> 154:37f96f9d4de2 575 mcgoutclk = CLOCK_GetPll0Freq();
<> 154:37f96f9d4de2 576 break;
<> 154:37f96f9d4de2 577 case kMCG_ClkOutStatFll:
<> 154:37f96f9d4de2 578 mcgoutclk = CLOCK_GetFllFreq();
<> 154:37f96f9d4de2 579 break;
<> 154:37f96f9d4de2 580 case kMCG_ClkOutStatInt:
<> 154:37f96f9d4de2 581 mcgoutclk = CLOCK_GetInternalRefClkSelectFreq();
<> 154:37f96f9d4de2 582 break;
<> 154:37f96f9d4de2 583 case kMCG_ClkOutStatExt:
<> 154:37f96f9d4de2 584 mcgoutclk = CLOCK_GetMcgExtClkFreq();
<> 154:37f96f9d4de2 585 break;
<> 154:37f96f9d4de2 586 default:
<> 154:37f96f9d4de2 587 mcgoutclk = 0U;
<> 154:37f96f9d4de2 588 break;
<> 154:37f96f9d4de2 589 }
<> 154:37f96f9d4de2 590 return mcgoutclk;
<> 154:37f96f9d4de2 591 }
<> 154:37f96f9d4de2 592
<> 154:37f96f9d4de2 593 uint32_t CLOCK_GetFllFreq(void)
<> 154:37f96f9d4de2 594 {
<> 154:37f96f9d4de2 595 static const uint16_t fllFactorTable[4][2] = {{640, 732}, {1280, 1464}, {1920, 2197}, {2560, 2929}};
<> 154:37f96f9d4de2 596
<> 154:37f96f9d4de2 597 uint8_t drs, dmx32;
<> 154:37f96f9d4de2 598 uint32_t freq;
<> 154:37f96f9d4de2 599
<> 154:37f96f9d4de2 600 /* If FLL is not enabled currently, then return 0U. */
<> 154:37f96f9d4de2 601 if ((MCG->C2 & MCG_C2_LP_MASK) || (MCG->S & MCG_S_PLLST_MASK))
<> 154:37f96f9d4de2 602 {
<> 154:37f96f9d4de2 603 return 0U;
<> 154:37f96f9d4de2 604 }
<> 154:37f96f9d4de2 605
<> 154:37f96f9d4de2 606 /* Get FLL reference clock frequency. */
<> 154:37f96f9d4de2 607 freq = CLOCK_GetFllRefClkFreq();
<> 154:37f96f9d4de2 608 if (!freq)
<> 154:37f96f9d4de2 609 {
<> 154:37f96f9d4de2 610 return freq;
<> 154:37f96f9d4de2 611 }
<> 154:37f96f9d4de2 612
<> 154:37f96f9d4de2 613 drs = MCG_C4_DRST_DRS_VAL;
<> 154:37f96f9d4de2 614 dmx32 = MCG_C4_DMX32_VAL;
<> 154:37f96f9d4de2 615
<> 154:37f96f9d4de2 616 return freq * fllFactorTable[drs][dmx32];
<> 154:37f96f9d4de2 617 }
<> 154:37f96f9d4de2 618
<> 154:37f96f9d4de2 619 uint32_t CLOCK_GetInternalRefClkFreq(void)
<> 154:37f96f9d4de2 620 {
<> 154:37f96f9d4de2 621 /* If MCGIRCLK is gated. */
<> 154:37f96f9d4de2 622 if (!(MCG->C1 & MCG_C1_IRCLKEN_MASK))
<> 154:37f96f9d4de2 623 {
<> 154:37f96f9d4de2 624 return 0U;
<> 154:37f96f9d4de2 625 }
<> 154:37f96f9d4de2 626
<> 154:37f96f9d4de2 627 return CLOCK_GetInternalRefClkSelectFreq();
<> 154:37f96f9d4de2 628 }
<> 154:37f96f9d4de2 629
<> 154:37f96f9d4de2 630 uint32_t CLOCK_GetFixedFreqClkFreq(void)
<> 154:37f96f9d4de2 631 {
<> 154:37f96f9d4de2 632 uint32_t freq = CLOCK_GetFllRefClkFreq();
<> 154:37f96f9d4de2 633
<> 154:37f96f9d4de2 634 /* MCGFFCLK must be no more than MCGOUTCLK/8. */
<> 154:37f96f9d4de2 635 if ((freq) && (freq <= (CLOCK_GetOutClkFreq() / 8U)))
<> 154:37f96f9d4de2 636 {
<> 154:37f96f9d4de2 637 return freq;
<> 154:37f96f9d4de2 638 }
<> 154:37f96f9d4de2 639 else
<> 154:37f96f9d4de2 640 {
<> 154:37f96f9d4de2 641 return 0U;
<> 154:37f96f9d4de2 642 }
<> 154:37f96f9d4de2 643 }
<> 154:37f96f9d4de2 644
<> 154:37f96f9d4de2 645 uint32_t CLOCK_GetPll0Freq(void)
<> 154:37f96f9d4de2 646 {
<> 154:37f96f9d4de2 647 uint32_t mcgpll0clk;
<> 154:37f96f9d4de2 648
<> 154:37f96f9d4de2 649 /* If PLL0 is not enabled, return 0. */
<> 154:37f96f9d4de2 650 if (!(MCG->S & MCG_S_LOCK0_MASK))
<> 154:37f96f9d4de2 651 {
<> 154:37f96f9d4de2 652 return 0U;
<> 154:37f96f9d4de2 653 }
<> 154:37f96f9d4de2 654
<> 154:37f96f9d4de2 655 mcgpll0clk = CLOCK_GetPll0RefFreq();
<> 154:37f96f9d4de2 656
<> 154:37f96f9d4de2 657 mcgpll0clk /= (FSL_FEATURE_MCG_PLL_PRDIV_BASE + MCG_C5_PRDIV0_VAL);
<> 154:37f96f9d4de2 658 mcgpll0clk *= (FSL_FEATURE_MCG_PLL_VDIV_BASE + MCG_C6_VDIV0_VAL);
<> 154:37f96f9d4de2 659
<> 154:37f96f9d4de2 660 return mcgpll0clk;
<> 154:37f96f9d4de2 661 }
<> 154:37f96f9d4de2 662
<> 154:37f96f9d4de2 663 status_t CLOCK_SetExternalRefClkConfig(mcg_oscsel_t oscsel)
<> 154:37f96f9d4de2 664 {
<> 154:37f96f9d4de2 665 bool needDelay;
<> 154:37f96f9d4de2 666 uint32_t i;
<> 154:37f96f9d4de2 667
<> 154:37f96f9d4de2 668 #if (defined(MCG_CONFIG_CHECK_PARAM) && MCG_CONFIG_CHECK_PARAM)
<> 154:37f96f9d4de2 669 /* If change MCG_C7[OSCSEL] and external reference clock is system clock source, return error. */
<> 154:37f96f9d4de2 670 if ((MCG_C7_OSCSEL_VAL != oscsel) && (!(MCG->S & MCG_S_IREFST_MASK)))
<> 154:37f96f9d4de2 671 {
<> 154:37f96f9d4de2 672 return kStatus_MCG_SourceUsed;
<> 154:37f96f9d4de2 673 }
<> 154:37f96f9d4de2 674 #endif /* MCG_CONFIG_CHECK_PARAM */
<> 154:37f96f9d4de2 675
<> 154:37f96f9d4de2 676 if (MCG_C7_OSCSEL_VAL != oscsel)
<> 154:37f96f9d4de2 677 {
<> 154:37f96f9d4de2 678 /* If change OSCSEL, need to delay, ERR009878. */
<> 154:37f96f9d4de2 679 needDelay = true;
<> 154:37f96f9d4de2 680 }
<> 154:37f96f9d4de2 681 else
<> 154:37f96f9d4de2 682 {
<> 154:37f96f9d4de2 683 needDelay = false;
<> 154:37f96f9d4de2 684 }
<> 154:37f96f9d4de2 685
<> 154:37f96f9d4de2 686 MCG->C7 = (MCG->C7 & ~MCG_C7_OSCSEL_MASK) | MCG_C7_OSCSEL(oscsel);
<> 154:37f96f9d4de2 687 if (kMCG_OscselOsc == oscsel)
<> 154:37f96f9d4de2 688 {
<> 154:37f96f9d4de2 689 if (MCG->C2 & MCG_C2_EREFS_MASK)
<> 154:37f96f9d4de2 690 {
<> 154:37f96f9d4de2 691 while (!(MCG->S & MCG_S_OSCINIT0_MASK))
<> 154:37f96f9d4de2 692 {
<> 154:37f96f9d4de2 693 }
<> 154:37f96f9d4de2 694 }
<> 154:37f96f9d4de2 695 }
<> 154:37f96f9d4de2 696
<> 154:37f96f9d4de2 697 if (needDelay)
<> 154:37f96f9d4de2 698 {
<> 154:37f96f9d4de2 699 /* ERR009878 Delay at least 50 micro-seconds for external clock change valid. */
<> 154:37f96f9d4de2 700 i = 1500U;
<> 154:37f96f9d4de2 701 while (i--)
<> 154:37f96f9d4de2 702 {
<> 154:37f96f9d4de2 703 __NOP();
<> 154:37f96f9d4de2 704 }
<> 154:37f96f9d4de2 705 }
<> 154:37f96f9d4de2 706
<> 154:37f96f9d4de2 707 return kStatus_Success;
<> 154:37f96f9d4de2 708 }
<> 154:37f96f9d4de2 709
<> 154:37f96f9d4de2 710 status_t CLOCK_SetInternalRefClkConfig(uint8_t enableMode, mcg_irc_mode_t ircs, uint8_t fcrdiv)
<> 154:37f96f9d4de2 711 {
<> 154:37f96f9d4de2 712 uint32_t mcgOutClkState = MCG_S_CLKST_VAL;
<> 154:37f96f9d4de2 713 mcg_irc_mode_t curIrcs = (mcg_irc_mode_t)MCG_S_IRCST_VAL;
<> 154:37f96f9d4de2 714 uint8_t curFcrdiv = MCG_SC_FCRDIV_VAL;
<> 154:37f96f9d4de2 715
<> 154:37f96f9d4de2 716 #if (defined(MCG_CONFIG_CHECK_PARAM) && MCG_CONFIG_CHECK_PARAM)
<> 154:37f96f9d4de2 717 /* If MCGIRCLK is used as system clock source. */
<> 154:37f96f9d4de2 718 if (kMCG_ClkOutStatInt == mcgOutClkState)
<> 154:37f96f9d4de2 719 {
<> 154:37f96f9d4de2 720 /* If need to change MCGIRCLK source or driver, return error. */
<> 154:37f96f9d4de2 721 if (((kMCG_IrcFast == curIrcs) && (fcrdiv != curFcrdiv)) || (ircs != curIrcs))
<> 154:37f96f9d4de2 722 {
<> 154:37f96f9d4de2 723 return kStatus_MCG_SourceUsed;
<> 154:37f96f9d4de2 724 }
<> 154:37f96f9d4de2 725 }
<> 154:37f96f9d4de2 726 #endif
<> 154:37f96f9d4de2 727
<> 154:37f96f9d4de2 728 /* If need to update the FCRDIV. */
<> 154:37f96f9d4de2 729 if (fcrdiv != curFcrdiv)
<> 154:37f96f9d4de2 730 {
<> 154:37f96f9d4de2 731 /* If fast IRC is in use currently, change to slow IRC. */
<> 154:37f96f9d4de2 732 if ((kMCG_IrcFast == curIrcs) && ((mcgOutClkState == kMCG_ClkOutStatInt) || (MCG->C1 & MCG_C1_IRCLKEN_MASK)))
<> 154:37f96f9d4de2 733 {
<> 154:37f96f9d4de2 734 MCG->C2 = ((MCG->C2 & ~MCG_C2_IRCS_MASK) | (MCG_C2_IRCS(kMCG_IrcSlow)));
<> 154:37f96f9d4de2 735 while (MCG_S_IRCST_VAL != kMCG_IrcSlow)
<> 154:37f96f9d4de2 736 {
<> 154:37f96f9d4de2 737 }
<> 154:37f96f9d4de2 738 }
<> 154:37f96f9d4de2 739 /* Update FCRDIV. */
<> 154:37f96f9d4de2 740 MCG->SC = (MCG->SC & ~(MCG_SC_FCRDIV_MASK | MCG_SC_ATMF_MASK | MCG_SC_LOCS0_MASK)) | MCG_SC_FCRDIV(fcrdiv);
<> 154:37f96f9d4de2 741 }
<> 154:37f96f9d4de2 742
<> 154:37f96f9d4de2 743 /* Set internal reference clock selection. */
<> 154:37f96f9d4de2 744 MCG->C2 = (MCG->C2 & ~MCG_C2_IRCS_MASK) | (MCG_C2_IRCS(ircs));
<> 154:37f96f9d4de2 745 MCG->C1 = (MCG->C1 & ~(MCG_C1_IRCLKEN_MASK | MCG_C1_IREFSTEN_MASK)) | (uint8_t)enableMode;
<> 154:37f96f9d4de2 746
<> 154:37f96f9d4de2 747 /* If MCGIRCLK is used, need to wait for MCG_S_IRCST. */
<> 154:37f96f9d4de2 748 if ((mcgOutClkState == kMCG_ClkOutStatInt) || (enableMode & kMCG_IrclkEnable))
<> 154:37f96f9d4de2 749 {
<> 154:37f96f9d4de2 750 while (MCG_S_IRCST_VAL != ircs)
<> 154:37f96f9d4de2 751 {
<> 154:37f96f9d4de2 752 }
<> 154:37f96f9d4de2 753 }
<> 154:37f96f9d4de2 754
<> 154:37f96f9d4de2 755 return kStatus_Success;
<> 154:37f96f9d4de2 756 }
<> 154:37f96f9d4de2 757
<> 154:37f96f9d4de2 758 uint32_t CLOCK_CalcPllDiv(uint32_t refFreq, uint32_t desireFreq, uint8_t *prdiv, uint8_t *vdiv)
<> 154:37f96f9d4de2 759 {
<> 154:37f96f9d4de2 760 uint8_t ret_prdiv; /* PRDIV to return. */
<> 154:37f96f9d4de2 761 uint8_t ret_vdiv; /* VDIV to return. */
<> 154:37f96f9d4de2 762 uint8_t prdiv_min; /* Min PRDIV value to make reference clock in allowed range. */
<> 154:37f96f9d4de2 763 uint8_t prdiv_max; /* Max PRDIV value to make reference clock in allowed range. */
<> 154:37f96f9d4de2 764 uint8_t prdiv_cur; /* PRDIV value for iteration. */
<> 154:37f96f9d4de2 765 uint8_t vdiv_cur; /* VDIV value for iteration. */
<> 154:37f96f9d4de2 766 uint32_t ret_freq = 0U; /* PLL output fequency to return. */
<> 154:37f96f9d4de2 767 uint32_t diff = 0xFFFFFFFFU; /* Difference between desireFreq and return frequency. */
<> 154:37f96f9d4de2 768 uint32_t ref_div; /* Reference frequency after PRDIV. */
<> 154:37f96f9d4de2 769
<> 154:37f96f9d4de2 770 /*
<> 154:37f96f9d4de2 771 Steps:
<> 154:37f96f9d4de2 772 1. Get allowed prdiv with such rules:
<> 154:37f96f9d4de2 773 1). refFreq / prdiv >= FSL_FEATURE_MCG_PLL_REF_MIN.
<> 154:37f96f9d4de2 774 2). refFreq / prdiv <= FSL_FEATURE_MCG_PLL_REF_MAX.
<> 154:37f96f9d4de2 775 2. For each allowed prdiv, there are two candidate vdiv values:
<> 154:37f96f9d4de2 776 1). (desireFreq / (refFreq / prdiv)).
<> 154:37f96f9d4de2 777 2). (desireFreq / (refFreq / prdiv)) + 1.
<> 154:37f96f9d4de2 778 If could get the precise desired frequency, return current prdiv and
<> 154:37f96f9d4de2 779 vdiv directly. Otherwise choose the one which is closer to desired
<> 154:37f96f9d4de2 780 frequency.
<> 154:37f96f9d4de2 781 */
<> 154:37f96f9d4de2 782
<> 154:37f96f9d4de2 783 /* Reference frequency is out of range. */
<> 154:37f96f9d4de2 784 if ((refFreq < FSL_FEATURE_MCG_PLL_REF_MIN) ||
<> 154:37f96f9d4de2 785 (refFreq > (FSL_FEATURE_MCG_PLL_REF_MAX * (FSL_FEATURE_MCG_PLL_PRDIV_MAX + FSL_FEATURE_MCG_PLL_PRDIV_BASE))))
<> 154:37f96f9d4de2 786 {
<> 154:37f96f9d4de2 787 return 0U;
<> 154:37f96f9d4de2 788 }
<> 154:37f96f9d4de2 789
<> 154:37f96f9d4de2 790 /* refFreq/PRDIV must in a range. First get the allowed PRDIV range. */
<> 154:37f96f9d4de2 791 prdiv_max = refFreq / FSL_FEATURE_MCG_PLL_REF_MIN;
<> 154:37f96f9d4de2 792 prdiv_min = (refFreq + FSL_FEATURE_MCG_PLL_REF_MAX - 1U) / FSL_FEATURE_MCG_PLL_REF_MAX;
<> 154:37f96f9d4de2 793
<> 154:37f96f9d4de2 794 /* PRDIV traversal. */
<> 154:37f96f9d4de2 795 for (prdiv_cur = prdiv_max; prdiv_cur >= prdiv_min; prdiv_cur--)
<> 154:37f96f9d4de2 796 {
<> 154:37f96f9d4de2 797 /* Reference frequency after PRDIV. */
<> 154:37f96f9d4de2 798 ref_div = refFreq / prdiv_cur;
<> 154:37f96f9d4de2 799
<> 154:37f96f9d4de2 800 vdiv_cur = desireFreq / ref_div;
<> 154:37f96f9d4de2 801
<> 154:37f96f9d4de2 802 if ((vdiv_cur < FSL_FEATURE_MCG_PLL_VDIV_BASE - 1U) || (vdiv_cur > FSL_FEATURE_MCG_PLL_VDIV_BASE + 31U))
<> 154:37f96f9d4de2 803 {
<> 154:37f96f9d4de2 804 /* No VDIV is available with this PRDIV. */
<> 154:37f96f9d4de2 805 continue;
<> 154:37f96f9d4de2 806 }
<> 154:37f96f9d4de2 807
<> 154:37f96f9d4de2 808 ret_freq = vdiv_cur * ref_div;
<> 154:37f96f9d4de2 809
<> 154:37f96f9d4de2 810 if (vdiv_cur >= FSL_FEATURE_MCG_PLL_VDIV_BASE)
<> 154:37f96f9d4de2 811 {
<> 154:37f96f9d4de2 812 if (ret_freq == desireFreq) /* If desire frequency is got. */
<> 154:37f96f9d4de2 813 {
<> 154:37f96f9d4de2 814 *prdiv = prdiv_cur - FSL_FEATURE_MCG_PLL_PRDIV_BASE;
<> 154:37f96f9d4de2 815 *vdiv = vdiv_cur - FSL_FEATURE_MCG_PLL_VDIV_BASE;
<> 154:37f96f9d4de2 816 return ret_freq;
<> 154:37f96f9d4de2 817 }
<> 154:37f96f9d4de2 818 /* New PRDIV/VDIV is closer. */
<> 154:37f96f9d4de2 819 if (diff > desireFreq - ret_freq)
<> 154:37f96f9d4de2 820 {
<> 154:37f96f9d4de2 821 diff = desireFreq - ret_freq;
<> 154:37f96f9d4de2 822 ret_prdiv = prdiv_cur;
<> 154:37f96f9d4de2 823 ret_vdiv = vdiv_cur;
<> 154:37f96f9d4de2 824 }
<> 154:37f96f9d4de2 825 }
<> 154:37f96f9d4de2 826 vdiv_cur++;
<> 154:37f96f9d4de2 827 if (vdiv_cur <= (FSL_FEATURE_MCG_PLL_VDIV_BASE + 31U))
<> 154:37f96f9d4de2 828 {
<> 154:37f96f9d4de2 829 ret_freq += ref_div;
<> 154:37f96f9d4de2 830 /* New PRDIV/VDIV is closer. */
<> 154:37f96f9d4de2 831 if (diff > ret_freq - desireFreq)
<> 154:37f96f9d4de2 832 {
<> 154:37f96f9d4de2 833 diff = ret_freq - desireFreq;
<> 154:37f96f9d4de2 834 ret_prdiv = prdiv_cur;
<> 154:37f96f9d4de2 835 ret_vdiv = vdiv_cur;
<> 154:37f96f9d4de2 836 }
<> 154:37f96f9d4de2 837 }
<> 154:37f96f9d4de2 838 }
<> 154:37f96f9d4de2 839
<> 154:37f96f9d4de2 840 if (0xFFFFFFFFU != diff)
<> 154:37f96f9d4de2 841 {
<> 154:37f96f9d4de2 842 /* PRDIV/VDIV found. */
<> 154:37f96f9d4de2 843 *prdiv = ret_prdiv - FSL_FEATURE_MCG_PLL_PRDIV_BASE;
<> 154:37f96f9d4de2 844 *vdiv = ret_vdiv - FSL_FEATURE_MCG_PLL_VDIV_BASE;
<> 154:37f96f9d4de2 845 ret_freq = (refFreq / ret_prdiv) * ret_vdiv;
<> 154:37f96f9d4de2 846 return ret_freq;
<> 154:37f96f9d4de2 847 }
<> 154:37f96f9d4de2 848 else
<> 154:37f96f9d4de2 849 {
<> 154:37f96f9d4de2 850 /* No proper PRDIV/VDIV found. */
<> 154:37f96f9d4de2 851 return 0U;
<> 154:37f96f9d4de2 852 }
<> 154:37f96f9d4de2 853 }
<> 154:37f96f9d4de2 854
<> 154:37f96f9d4de2 855 void CLOCK_EnablePll0(mcg_pll_config_t const *config)
<> 154:37f96f9d4de2 856 {
<> 154:37f96f9d4de2 857 assert(config);
<> 154:37f96f9d4de2 858
<> 154:37f96f9d4de2 859 uint8_t mcg_c5 = 0U;
<> 154:37f96f9d4de2 860
<> 154:37f96f9d4de2 861 mcg_c5 |= MCG_C5_PRDIV0(config->prdiv);
<> 154:37f96f9d4de2 862 MCG->C5 = mcg_c5; /* Disable the PLL first. */
<> 154:37f96f9d4de2 863
<> 154:37f96f9d4de2 864 MCG->C6 = (MCG->C6 & ~MCG_C6_VDIV0_MASK) | MCG_C6_VDIV0(config->vdiv);
<> 154:37f96f9d4de2 865
<> 154:37f96f9d4de2 866 /* Set enable mode. */
<> 154:37f96f9d4de2 867 MCG->C5 |= ((uint32_t)kMCG_PllEnableIndependent | (uint32_t)config->enableMode);
<> 154:37f96f9d4de2 868
<> 154:37f96f9d4de2 869 /* Wait for PLL lock. */
<> 154:37f96f9d4de2 870 while (!(MCG->S & MCG_S_LOCK0_MASK))
<> 154:37f96f9d4de2 871 {
<> 154:37f96f9d4de2 872 }
<> 154:37f96f9d4de2 873 }
<> 154:37f96f9d4de2 874
<> 154:37f96f9d4de2 875 void CLOCK_SetOsc0MonitorMode(mcg_monitor_mode_t mode)
<> 154:37f96f9d4de2 876 {
<> 154:37f96f9d4de2 877 /* Clear the previous flag, MCG_SC[LOCS0]. */
<> 154:37f96f9d4de2 878 MCG->SC &= ~MCG_SC_ATMF_MASK;
<> 154:37f96f9d4de2 879
<> 154:37f96f9d4de2 880 if (kMCG_MonitorNone == mode)
<> 154:37f96f9d4de2 881 {
<> 154:37f96f9d4de2 882 MCG->C6 &= ~MCG_C6_CME0_MASK;
<> 154:37f96f9d4de2 883 }
<> 154:37f96f9d4de2 884 else
<> 154:37f96f9d4de2 885 {
<> 154:37f96f9d4de2 886 if (kMCG_MonitorInt == mode)
<> 154:37f96f9d4de2 887 {
<> 154:37f96f9d4de2 888 MCG->C2 &= ~MCG_C2_LOCRE0_MASK;
<> 154:37f96f9d4de2 889 }
<> 154:37f96f9d4de2 890 else
<> 154:37f96f9d4de2 891 {
<> 154:37f96f9d4de2 892 MCG->C2 |= MCG_C2_LOCRE0_MASK;
<> 154:37f96f9d4de2 893 }
<> 154:37f96f9d4de2 894 MCG->C6 |= MCG_C6_CME0_MASK;
<> 154:37f96f9d4de2 895 }
<> 154:37f96f9d4de2 896 }
<> 154:37f96f9d4de2 897
<> 154:37f96f9d4de2 898 void CLOCK_SetRtcOscMonitorMode(mcg_monitor_mode_t mode)
<> 154:37f96f9d4de2 899 {
<> 154:37f96f9d4de2 900 uint8_t mcg_c8 = MCG->C8;
<> 154:37f96f9d4de2 901
<> 154:37f96f9d4de2 902 mcg_c8 &= ~(MCG_C8_CME1_MASK | MCG_C8_LOCRE1_MASK);
<> 154:37f96f9d4de2 903
<> 154:37f96f9d4de2 904 if (kMCG_MonitorNone != mode)
<> 154:37f96f9d4de2 905 {
<> 154:37f96f9d4de2 906 if (kMCG_MonitorReset == mode)
<> 154:37f96f9d4de2 907 {
<> 154:37f96f9d4de2 908 mcg_c8 |= MCG_C8_LOCRE1_MASK;
<> 154:37f96f9d4de2 909 }
<> 154:37f96f9d4de2 910 mcg_c8 |= MCG_C8_CME1_MASK;
<> 154:37f96f9d4de2 911 }
<> 154:37f96f9d4de2 912 MCG->C8 = mcg_c8;
<> 154:37f96f9d4de2 913 }
<> 154:37f96f9d4de2 914
<> 154:37f96f9d4de2 915 void CLOCK_SetPll0MonitorMode(mcg_monitor_mode_t mode)
<> 154:37f96f9d4de2 916 {
<> 154:37f96f9d4de2 917 uint8_t mcg_c8;
<> 154:37f96f9d4de2 918
<> 154:37f96f9d4de2 919 /* Clear previous flag. */
<> 154:37f96f9d4de2 920 MCG->S = MCG_S_LOLS0_MASK;
<> 154:37f96f9d4de2 921
<> 154:37f96f9d4de2 922 if (kMCG_MonitorNone == mode)
<> 154:37f96f9d4de2 923 {
<> 154:37f96f9d4de2 924 MCG->C6 &= ~MCG_C6_LOLIE0_MASK;
<> 154:37f96f9d4de2 925 }
<> 154:37f96f9d4de2 926 else
<> 154:37f96f9d4de2 927 {
<> 154:37f96f9d4de2 928 mcg_c8 = MCG->C8;
<> 154:37f96f9d4de2 929
<> 154:37f96f9d4de2 930 mcg_c8 &= ~MCG_C8_LOCS1_MASK;
<> 154:37f96f9d4de2 931
<> 154:37f96f9d4de2 932 if (kMCG_MonitorInt == mode)
<> 154:37f96f9d4de2 933 {
<> 154:37f96f9d4de2 934 mcg_c8 &= ~MCG_C8_LOLRE_MASK;
<> 154:37f96f9d4de2 935 }
<> 154:37f96f9d4de2 936 else
<> 154:37f96f9d4de2 937 {
<> 154:37f96f9d4de2 938 mcg_c8 |= MCG_C8_LOLRE_MASK;
<> 154:37f96f9d4de2 939 }
<> 154:37f96f9d4de2 940 MCG->C8 = mcg_c8;
<> 154:37f96f9d4de2 941 MCG->C6 |= MCG_C6_LOLIE0_MASK;
<> 154:37f96f9d4de2 942 }
<> 154:37f96f9d4de2 943 }
<> 154:37f96f9d4de2 944
<> 154:37f96f9d4de2 945 uint32_t CLOCK_GetStatusFlags(void)
<> 154:37f96f9d4de2 946 {
<> 154:37f96f9d4de2 947 uint32_t ret = 0U;
<> 154:37f96f9d4de2 948 uint8_t mcg_s = MCG->S;
<> 154:37f96f9d4de2 949
<> 154:37f96f9d4de2 950 if (MCG->SC & MCG_SC_LOCS0_MASK)
<> 154:37f96f9d4de2 951 {
<> 154:37f96f9d4de2 952 ret |= kMCG_Osc0LostFlag;
<> 154:37f96f9d4de2 953 }
<> 154:37f96f9d4de2 954 if (mcg_s & MCG_S_OSCINIT0_MASK)
<> 154:37f96f9d4de2 955 {
<> 154:37f96f9d4de2 956 ret |= kMCG_Osc0InitFlag;
<> 154:37f96f9d4de2 957 }
<> 154:37f96f9d4de2 958 if (MCG->C8 & MCG_C8_LOCS1_MASK)
<> 154:37f96f9d4de2 959 {
<> 154:37f96f9d4de2 960 ret |= kMCG_RtcOscLostFlag;
<> 154:37f96f9d4de2 961 }
<> 154:37f96f9d4de2 962 if (mcg_s & MCG_S_LOLS0_MASK)
<> 154:37f96f9d4de2 963 {
<> 154:37f96f9d4de2 964 ret |= kMCG_Pll0LostFlag;
<> 154:37f96f9d4de2 965 }
<> 154:37f96f9d4de2 966 if (mcg_s & MCG_S_LOCK0_MASK)
<> 154:37f96f9d4de2 967 {
<> 154:37f96f9d4de2 968 ret |= kMCG_Pll0LockFlag;
<> 154:37f96f9d4de2 969 }
<> 154:37f96f9d4de2 970 return ret;
<> 154:37f96f9d4de2 971 }
<> 154:37f96f9d4de2 972
<> 154:37f96f9d4de2 973 void CLOCK_ClearStatusFlags(uint32_t mask)
<> 154:37f96f9d4de2 974 {
<> 154:37f96f9d4de2 975 uint8_t reg;
<> 154:37f96f9d4de2 976
<> 154:37f96f9d4de2 977 if (mask & kMCG_Osc0LostFlag)
<> 154:37f96f9d4de2 978 {
<> 154:37f96f9d4de2 979 MCG->SC &= ~MCG_SC_ATMF_MASK;
<> 154:37f96f9d4de2 980 }
<> 154:37f96f9d4de2 981 if (mask & kMCG_RtcOscLostFlag)
<> 154:37f96f9d4de2 982 {
<> 154:37f96f9d4de2 983 reg = MCG->C8;
<> 154:37f96f9d4de2 984 MCG->C8 = reg;
<> 154:37f96f9d4de2 985 }
<> 154:37f96f9d4de2 986 if (mask & kMCG_Pll0LostFlag)
<> 154:37f96f9d4de2 987 {
<> 154:37f96f9d4de2 988 MCG->S = MCG_S_LOLS0_MASK;
<> 154:37f96f9d4de2 989 }
<> 154:37f96f9d4de2 990 }
<> 154:37f96f9d4de2 991
<> 154:37f96f9d4de2 992 void CLOCK_InitOsc0(osc_config_t const *config)
<> 154:37f96f9d4de2 993 {
<> 154:37f96f9d4de2 994 uint8_t range = CLOCK_GetOscRangeFromFreq(config->freq);
<> 154:37f96f9d4de2 995
<> 154:37f96f9d4de2 996 OSC_SetCapLoad(OSC0, config->capLoad);
<> 154:37f96f9d4de2 997 OSC_SetExtRefClkConfig(OSC0, &config->oscerConfig);
<> 154:37f96f9d4de2 998
<> 154:37f96f9d4de2 999 MCG->C2 = ((MCG->C2 & ~OSC_MODE_MASK) | MCG_C2_RANGE(range) | (uint8_t)config->workMode);
<> 154:37f96f9d4de2 1000
<> 154:37f96f9d4de2 1001 if ((kOSC_ModeExt != config->workMode) && (OSC0->CR & OSC_CR_ERCLKEN_MASK))
<> 154:37f96f9d4de2 1002 {
<> 154:37f96f9d4de2 1003 /* Wait for stable. */
<> 154:37f96f9d4de2 1004 while (!(MCG->S & MCG_S_OSCINIT0_MASK))
<> 154:37f96f9d4de2 1005 {
<> 154:37f96f9d4de2 1006 }
<> 154:37f96f9d4de2 1007 }
<> 154:37f96f9d4de2 1008 }
<> 154:37f96f9d4de2 1009
<> 154:37f96f9d4de2 1010 void CLOCK_DeinitOsc0(void)
<> 154:37f96f9d4de2 1011 {
<> 154:37f96f9d4de2 1012 OSC0->CR = 0U;
<> 154:37f96f9d4de2 1013 MCG->C2 &= ~OSC_MODE_MASK;
<> 154:37f96f9d4de2 1014 }
<> 154:37f96f9d4de2 1015
<> 154:37f96f9d4de2 1016 status_t CLOCK_TrimInternalRefClk(uint32_t extFreq, uint32_t desireFreq, uint32_t *actualFreq, mcg_atm_select_t atms)
<> 154:37f96f9d4de2 1017 {
<> 154:37f96f9d4de2 1018 uint32_t multi; /* extFreq / desireFreq */
<> 154:37f96f9d4de2 1019 uint32_t actv; /* Auto trim value. */
<> 154:37f96f9d4de2 1020 uint8_t mcg_sc;
<> 154:37f96f9d4de2 1021
<> 154:37f96f9d4de2 1022 static const uint32_t trimRange[2][2] = {
<> 154:37f96f9d4de2 1023 /* Min Max */
<> 154:37f96f9d4de2 1024 {TRIM_SIRC_MIN, TRIM_SIRC_MAX}, /* Slow IRC. */
<> 154:37f96f9d4de2 1025 {TRIM_FIRC_MIN, TRIM_FIRC_MAX} /* Fast IRC. */
<> 154:37f96f9d4de2 1026 };
<> 154:37f96f9d4de2 1027
<> 154:37f96f9d4de2 1028 if ((extFreq > TRIM_REF_CLK_MAX) || (extFreq < TRIM_REF_CLK_MIN))
<> 154:37f96f9d4de2 1029 {
<> 154:37f96f9d4de2 1030 return kStatus_MCG_AtmBusClockInvalid;
<> 154:37f96f9d4de2 1031 }
<> 154:37f96f9d4de2 1032
<> 154:37f96f9d4de2 1033 /* Check desired frequency range. */
<> 154:37f96f9d4de2 1034 if ((desireFreq < trimRange[atms][0]) || (desireFreq > trimRange[atms][1]))
<> 154:37f96f9d4de2 1035 {
<> 154:37f96f9d4de2 1036 return kStatus_MCG_AtmDesiredFreqInvalid;
<> 154:37f96f9d4de2 1037 }
<> 154:37f96f9d4de2 1038
<> 154:37f96f9d4de2 1039 /*
<> 154:37f96f9d4de2 1040 Make sure internal reference clock is not used to generate bus clock.
<> 154:37f96f9d4de2 1041 Here only need to check (MCG_S_IREFST == 1).
<> 154:37f96f9d4de2 1042 */
<> 154:37f96f9d4de2 1043 if (MCG_S_IREFST(kMCG_FllSrcInternal) == (MCG->S & MCG_S_IREFST_MASK))
<> 154:37f96f9d4de2 1044 {
<> 154:37f96f9d4de2 1045 return kStatus_MCG_AtmIrcUsed;
<> 154:37f96f9d4de2 1046 }
<> 154:37f96f9d4de2 1047
<> 154:37f96f9d4de2 1048 multi = extFreq / desireFreq;
<> 154:37f96f9d4de2 1049 actv = multi * 21U;
<> 154:37f96f9d4de2 1050
<> 154:37f96f9d4de2 1051 if (kMCG_AtmSel4m == atms)
<> 154:37f96f9d4de2 1052 {
<> 154:37f96f9d4de2 1053 actv *= 128U;
<> 154:37f96f9d4de2 1054 }
<> 154:37f96f9d4de2 1055
<> 154:37f96f9d4de2 1056 /* Now begin to start trim. */
<> 154:37f96f9d4de2 1057 MCG->ATCVL = (uint8_t)actv;
<> 154:37f96f9d4de2 1058 MCG->ATCVH = (uint8_t)(actv >> 8U);
<> 154:37f96f9d4de2 1059
<> 154:37f96f9d4de2 1060 mcg_sc = MCG->SC;
<> 154:37f96f9d4de2 1061 mcg_sc &= ~(MCG_SC_ATMS_MASK | MCG_SC_LOCS0_MASK);
<> 154:37f96f9d4de2 1062 mcg_sc |= (MCG_SC_ATMF_MASK | MCG_SC_ATMS(atms));
<> 154:37f96f9d4de2 1063 MCG->SC = (mcg_sc | MCG_SC_ATME_MASK);
<> 154:37f96f9d4de2 1064
<> 154:37f96f9d4de2 1065 /* Wait for finished. */
<> 154:37f96f9d4de2 1066 while (MCG->SC & MCG_SC_ATME_MASK)
<> 154:37f96f9d4de2 1067 {
<> 154:37f96f9d4de2 1068 }
<> 154:37f96f9d4de2 1069
<> 154:37f96f9d4de2 1070 /* Error occurs? */
<> 154:37f96f9d4de2 1071 if (MCG->SC & MCG_SC_ATMF_MASK)
<> 154:37f96f9d4de2 1072 {
<> 154:37f96f9d4de2 1073 /* Clear the failed flag. */
<> 154:37f96f9d4de2 1074 MCG->SC = mcg_sc;
<> 154:37f96f9d4de2 1075 return kStatus_MCG_AtmHardwareFail;
<> 154:37f96f9d4de2 1076 }
<> 154:37f96f9d4de2 1077
<> 154:37f96f9d4de2 1078 *actualFreq = extFreq / multi;
<> 154:37f96f9d4de2 1079
<> 154:37f96f9d4de2 1080 if (kMCG_AtmSel4m == atms)
<> 154:37f96f9d4de2 1081 {
<> 154:37f96f9d4de2 1082 s_fastIrcFreq = *actualFreq;
<> 154:37f96f9d4de2 1083 }
<> 154:37f96f9d4de2 1084 else
<> 154:37f96f9d4de2 1085 {
<> 154:37f96f9d4de2 1086 s_slowIrcFreq = *actualFreq;
<> 154:37f96f9d4de2 1087 }
<> 154:37f96f9d4de2 1088
<> 154:37f96f9d4de2 1089 return kStatus_Success;
<> 154:37f96f9d4de2 1090 }
<> 154:37f96f9d4de2 1091
<> 154:37f96f9d4de2 1092 mcg_mode_t CLOCK_GetMode(void)
<> 154:37f96f9d4de2 1093 {
<> 154:37f96f9d4de2 1094 mcg_mode_t mode = kMCG_ModeError;
<> 154:37f96f9d4de2 1095 uint32_t clkst = MCG_S_CLKST_VAL;
<> 154:37f96f9d4de2 1096 uint32_t irefst = MCG_S_IREFST_VAL;
<> 154:37f96f9d4de2 1097 uint32_t lp = MCG_C2_LP_VAL;
<> 154:37f96f9d4de2 1098 uint32_t pllst = MCG_S_PLLST_VAL;
<> 154:37f96f9d4de2 1099
<> 154:37f96f9d4de2 1100 /*------------------------------------------------------------------
<> 154:37f96f9d4de2 1101 Mode and Registers
<> 154:37f96f9d4de2 1102 ____________________________________________________________________
<> 154:37f96f9d4de2 1103
<> 154:37f96f9d4de2 1104 Mode | CLKST | IREFST | PLLST | LP
<> 154:37f96f9d4de2 1105 ____________________________________________________________________
<> 154:37f96f9d4de2 1106
<> 154:37f96f9d4de2 1107 FEI | 00(FLL) | 1(INT) | 0(FLL) | X
<> 154:37f96f9d4de2 1108 ____________________________________________________________________
<> 154:37f96f9d4de2 1109
<> 154:37f96f9d4de2 1110 FEE | 00(FLL) | 0(EXT) | 0(FLL) | X
<> 154:37f96f9d4de2 1111 ____________________________________________________________________
<> 154:37f96f9d4de2 1112
<> 154:37f96f9d4de2 1113 FBE | 10(EXT) | 0(EXT) | 0(FLL) | 0(NORMAL)
<> 154:37f96f9d4de2 1114 ____________________________________________________________________
<> 154:37f96f9d4de2 1115
<> 154:37f96f9d4de2 1116 FBI | 01(INT) | 1(INT) | 0(FLL) | 0(NORMAL)
<> 154:37f96f9d4de2 1117 ____________________________________________________________________
<> 154:37f96f9d4de2 1118
<> 154:37f96f9d4de2 1119 BLPI | 01(INT) | 1(INT) | 0(FLL) | 1(LOW POWER)
<> 154:37f96f9d4de2 1120 ____________________________________________________________________
<> 154:37f96f9d4de2 1121
<> 154:37f96f9d4de2 1122 BLPE | 10(EXT) | 0(EXT) | X | 1(LOW POWER)
<> 154:37f96f9d4de2 1123 ____________________________________________________________________
<> 154:37f96f9d4de2 1124
<> 154:37f96f9d4de2 1125 PEE | 11(PLL) | 0(EXT) | 1(PLL) | X
<> 154:37f96f9d4de2 1126 ____________________________________________________________________
<> 154:37f96f9d4de2 1127
<> 154:37f96f9d4de2 1128 PBE | 10(EXT) | 0(EXT) | 1(PLL) | O(NORMAL)
<> 154:37f96f9d4de2 1129 ____________________________________________________________________
<> 154:37f96f9d4de2 1130
<> 154:37f96f9d4de2 1131 PBI | 01(INT) | 1(INT) | 1(PLL) | 0(NORMAL)
<> 154:37f96f9d4de2 1132 ____________________________________________________________________
<> 154:37f96f9d4de2 1133
<> 154:37f96f9d4de2 1134 PEI | 11(PLL) | 1(INT) | 1(PLL) | X
<> 154:37f96f9d4de2 1135 ____________________________________________________________________
<> 154:37f96f9d4de2 1136
<> 154:37f96f9d4de2 1137 ----------------------------------------------------------------------*/
<> 154:37f96f9d4de2 1138
<> 154:37f96f9d4de2 1139 switch (clkst)
<> 154:37f96f9d4de2 1140 {
<> 154:37f96f9d4de2 1141 case kMCG_ClkOutStatFll:
<> 154:37f96f9d4de2 1142 if (kMCG_FllSrcExternal == irefst)
<> 154:37f96f9d4de2 1143 {
<> 154:37f96f9d4de2 1144 mode = kMCG_ModeFEE;
<> 154:37f96f9d4de2 1145 }
<> 154:37f96f9d4de2 1146 else
<> 154:37f96f9d4de2 1147 {
<> 154:37f96f9d4de2 1148 mode = kMCG_ModeFEI;
<> 154:37f96f9d4de2 1149 }
<> 154:37f96f9d4de2 1150 break;
<> 154:37f96f9d4de2 1151 case kMCG_ClkOutStatInt:
<> 154:37f96f9d4de2 1152 if (lp)
<> 154:37f96f9d4de2 1153 {
<> 154:37f96f9d4de2 1154 mode = kMCG_ModeBLPI;
<> 154:37f96f9d4de2 1155 }
<> 154:37f96f9d4de2 1156 else
<> 154:37f96f9d4de2 1157 {
<> 154:37f96f9d4de2 1158 {
<> 154:37f96f9d4de2 1159 mode = kMCG_ModeFBI;
<> 154:37f96f9d4de2 1160 }
<> 154:37f96f9d4de2 1161 }
<> 154:37f96f9d4de2 1162 break;
<> 154:37f96f9d4de2 1163 case kMCG_ClkOutStatExt:
<> 154:37f96f9d4de2 1164 if (lp)
<> 154:37f96f9d4de2 1165 {
<> 154:37f96f9d4de2 1166 mode = kMCG_ModeBLPE;
<> 154:37f96f9d4de2 1167 }
<> 154:37f96f9d4de2 1168 else
<> 154:37f96f9d4de2 1169 {
<> 154:37f96f9d4de2 1170 if (kMCG_PllstPll == pllst)
<> 154:37f96f9d4de2 1171 {
<> 154:37f96f9d4de2 1172 mode = kMCG_ModePBE;
<> 154:37f96f9d4de2 1173 }
<> 154:37f96f9d4de2 1174 else
<> 154:37f96f9d4de2 1175 {
<> 154:37f96f9d4de2 1176 mode = kMCG_ModeFBE;
<> 154:37f96f9d4de2 1177 }
<> 154:37f96f9d4de2 1178 }
<> 154:37f96f9d4de2 1179 break;
<> 154:37f96f9d4de2 1180 case kMCG_ClkOutStatPll:
<> 154:37f96f9d4de2 1181 {
<> 154:37f96f9d4de2 1182 mode = kMCG_ModePEE;
<> 154:37f96f9d4de2 1183 }
<> 154:37f96f9d4de2 1184 break;
<> 154:37f96f9d4de2 1185 default:
<> 154:37f96f9d4de2 1186 break;
<> 154:37f96f9d4de2 1187 }
<> 154:37f96f9d4de2 1188
<> 154:37f96f9d4de2 1189 return mode;
<> 154:37f96f9d4de2 1190 }
<> 154:37f96f9d4de2 1191
<> 154:37f96f9d4de2 1192 status_t CLOCK_SetFeiMode(mcg_drs_t drs, void (*fllStableDelay)(void))
<> 154:37f96f9d4de2 1193 {
<> 154:37f96f9d4de2 1194 uint8_t mcg_c4;
<> 154:37f96f9d4de2 1195 bool change_drs = false;
<> 154:37f96f9d4de2 1196
<> 154:37f96f9d4de2 1197 #if (defined(MCG_CONFIG_CHECK_PARAM) && MCG_CONFIG_CHECK_PARAM)
<> 154:37f96f9d4de2 1198 mcg_mode_t mode = CLOCK_GetMode();
<> 154:37f96f9d4de2 1199 if (!((kMCG_ModeFEI == mode) || (kMCG_ModeFBI == mode) || (kMCG_ModeFBE == mode) || (kMCG_ModeFEE == mode)))
<> 154:37f96f9d4de2 1200 {
<> 154:37f96f9d4de2 1201 return kStatus_MCG_ModeUnreachable;
<> 154:37f96f9d4de2 1202 }
<> 154:37f96f9d4de2 1203 #endif
<> 154:37f96f9d4de2 1204 mcg_c4 = MCG->C4;
<> 154:37f96f9d4de2 1205
<> 154:37f96f9d4de2 1206 /*
<> 154:37f96f9d4de2 1207 Errata: ERR007993
<> 154:37f96f9d4de2 1208 Workaround: Invert MCG_C4[DMX32] or change MCG_C4[DRST_DRS] before
<> 154:37f96f9d4de2 1209 reference clock source changes, then reset to previous value after
<> 154:37f96f9d4de2 1210 reference clock changes.
<> 154:37f96f9d4de2 1211 */
<> 154:37f96f9d4de2 1212 if (kMCG_FllSrcExternal == MCG_S_IREFST_VAL)
<> 154:37f96f9d4de2 1213 {
<> 154:37f96f9d4de2 1214 change_drs = true;
<> 154:37f96f9d4de2 1215 /* Change the LSB of DRST_DRS. */
<> 154:37f96f9d4de2 1216 MCG->C4 ^= (1U << MCG_C4_DRST_DRS_SHIFT);
<> 154:37f96f9d4de2 1217 }
<> 154:37f96f9d4de2 1218
<> 154:37f96f9d4de2 1219 /* Set CLKS and IREFS. */
<> 154:37f96f9d4de2 1220 MCG->C1 =
<> 154:37f96f9d4de2 1221 ((MCG->C1 & ~(MCG_C1_CLKS_MASK | MCG_C1_IREFS_MASK))) | (MCG_C1_CLKS(kMCG_ClkOutSrcOut) /* CLKS = 0 */
<> 154:37f96f9d4de2 1222 | MCG_C1_IREFS(kMCG_FllSrcInternal)); /* IREFS = 1 */
<> 154:37f96f9d4de2 1223
<> 154:37f96f9d4de2 1224 /* Wait and check status. */
<> 154:37f96f9d4de2 1225 while (kMCG_FllSrcInternal != MCG_S_IREFST_VAL)
<> 154:37f96f9d4de2 1226 {
<> 154:37f96f9d4de2 1227 }
<> 154:37f96f9d4de2 1228
<> 154:37f96f9d4de2 1229 /* Errata: ERR007993 */
<> 154:37f96f9d4de2 1230 if (change_drs)
<> 154:37f96f9d4de2 1231 {
<> 154:37f96f9d4de2 1232 MCG->C4 = mcg_c4;
<> 154:37f96f9d4de2 1233 }
<> 154:37f96f9d4de2 1234
<> 154:37f96f9d4de2 1235 /* In FEI mode, the MCG_C4[DMX32] is set to 0U. */
<> 154:37f96f9d4de2 1236 MCG->C4 = (mcg_c4 & ~(MCG_C4_DMX32_MASK | MCG_C4_DRST_DRS_MASK)) | (MCG_C4_DRST_DRS(drs));
<> 154:37f96f9d4de2 1237
<> 154:37f96f9d4de2 1238 /* Check MCG_S[CLKST] */
<> 154:37f96f9d4de2 1239 while (kMCG_ClkOutStatFll != MCG_S_CLKST_VAL)
<> 154:37f96f9d4de2 1240 {
<> 154:37f96f9d4de2 1241 }
<> 154:37f96f9d4de2 1242
<> 154:37f96f9d4de2 1243 /* Wait for FLL stable time. */
<> 154:37f96f9d4de2 1244 if (fllStableDelay)
<> 154:37f96f9d4de2 1245 {
<> 154:37f96f9d4de2 1246 fllStableDelay();
<> 154:37f96f9d4de2 1247 }
<> 154:37f96f9d4de2 1248
<> 154:37f96f9d4de2 1249 return kStatus_Success;
<> 154:37f96f9d4de2 1250 }
<> 154:37f96f9d4de2 1251
<> 154:37f96f9d4de2 1252 status_t CLOCK_SetFeeMode(uint8_t frdiv, mcg_dmx32_t dmx32, mcg_drs_t drs, void (*fllStableDelay)(void))
<> 154:37f96f9d4de2 1253 {
<> 154:37f96f9d4de2 1254 uint8_t mcg_c4;
<> 154:37f96f9d4de2 1255 bool change_drs = false;
<> 154:37f96f9d4de2 1256
<> 154:37f96f9d4de2 1257 #if (defined(MCG_CONFIG_CHECK_PARAM) && MCG_CONFIG_CHECK_PARAM)
<> 154:37f96f9d4de2 1258 mcg_mode_t mode = CLOCK_GetMode();
<> 154:37f96f9d4de2 1259 if (!((kMCG_ModeFEE == mode) || (kMCG_ModeFBI == mode) || (kMCG_ModeFBE == mode) || (kMCG_ModeFEI == mode)))
<> 154:37f96f9d4de2 1260 {
<> 154:37f96f9d4de2 1261 return kStatus_MCG_ModeUnreachable;
<> 154:37f96f9d4de2 1262 }
<> 154:37f96f9d4de2 1263 #endif
<> 154:37f96f9d4de2 1264 mcg_c4 = MCG->C4;
<> 154:37f96f9d4de2 1265
<> 154:37f96f9d4de2 1266 /*
<> 154:37f96f9d4de2 1267 Errata: ERR007993
<> 154:37f96f9d4de2 1268 Workaround: Invert MCG_C4[DMX32] or change MCG_C4[DRST_DRS] before
<> 154:37f96f9d4de2 1269 reference clock source changes, then reset to previous value after
<> 154:37f96f9d4de2 1270 reference clock changes.
<> 154:37f96f9d4de2 1271 */
<> 154:37f96f9d4de2 1272 if (kMCG_FllSrcInternal == MCG_S_IREFST_VAL)
<> 154:37f96f9d4de2 1273 {
<> 154:37f96f9d4de2 1274 change_drs = true;
<> 154:37f96f9d4de2 1275 /* Change the LSB of DRST_DRS. */
<> 154:37f96f9d4de2 1276 MCG->C4 ^= (1U << MCG_C4_DRST_DRS_SHIFT);
<> 154:37f96f9d4de2 1277 }
<> 154:37f96f9d4de2 1278
<> 154:37f96f9d4de2 1279 /* Set CLKS and IREFS. */
<> 154:37f96f9d4de2 1280 MCG->C1 = ((MCG->C1 & ~(MCG_C1_CLKS_MASK | MCG_C1_FRDIV_MASK | MCG_C1_IREFS_MASK)) |
<> 154:37f96f9d4de2 1281 (MCG_C1_CLKS(kMCG_ClkOutSrcOut) /* CLKS = 0 */
<> 154:37f96f9d4de2 1282 | MCG_C1_FRDIV(frdiv) /* FRDIV */
<> 154:37f96f9d4de2 1283 | MCG_C1_IREFS(kMCG_FllSrcExternal))); /* IREFS = 0 */
<> 154:37f96f9d4de2 1284
<> 154:37f96f9d4de2 1285 /* Wait and check status. */
<> 154:37f96f9d4de2 1286 while (kMCG_FllSrcExternal != MCG_S_IREFST_VAL)
<> 154:37f96f9d4de2 1287 {
<> 154:37f96f9d4de2 1288 }
<> 154:37f96f9d4de2 1289
<> 154:37f96f9d4de2 1290 /* Errata: ERR007993 */
<> 154:37f96f9d4de2 1291 if (change_drs)
<> 154:37f96f9d4de2 1292 {
<> 154:37f96f9d4de2 1293 MCG->C4 = mcg_c4;
<> 154:37f96f9d4de2 1294 }
<> 154:37f96f9d4de2 1295
<> 154:37f96f9d4de2 1296 /* Set DRS and DMX32. */
<> 154:37f96f9d4de2 1297 mcg_c4 = ((mcg_c4 & ~(MCG_C4_DMX32_MASK | MCG_C4_DRST_DRS_MASK)) | (MCG_C4_DMX32(dmx32) | MCG_C4_DRST_DRS(drs)));
<> 154:37f96f9d4de2 1298 MCG->C4 = mcg_c4;
<> 154:37f96f9d4de2 1299
<> 154:37f96f9d4de2 1300 /* Wait for DRST_DRS update. */
<> 154:37f96f9d4de2 1301 while (MCG->C4 != mcg_c4)
<> 154:37f96f9d4de2 1302 {
<> 154:37f96f9d4de2 1303 }
<> 154:37f96f9d4de2 1304
<> 154:37f96f9d4de2 1305 /* Check MCG_S[CLKST] */
<> 154:37f96f9d4de2 1306 while (kMCG_ClkOutStatFll != MCG_S_CLKST_VAL)
<> 154:37f96f9d4de2 1307 {
<> 154:37f96f9d4de2 1308 }
<> 154:37f96f9d4de2 1309
<> 154:37f96f9d4de2 1310 /* Wait for FLL stable time. */
<> 154:37f96f9d4de2 1311 if (fllStableDelay)
<> 154:37f96f9d4de2 1312 {
<> 154:37f96f9d4de2 1313 fllStableDelay();
<> 154:37f96f9d4de2 1314 }
<> 154:37f96f9d4de2 1315
<> 154:37f96f9d4de2 1316 return kStatus_Success;
<> 154:37f96f9d4de2 1317 }
<> 154:37f96f9d4de2 1318
<> 154:37f96f9d4de2 1319 status_t CLOCK_SetFbiMode(mcg_drs_t drs, void (*fllStableDelay)(void))
<> 154:37f96f9d4de2 1320 {
<> 154:37f96f9d4de2 1321 uint8_t mcg_c4;
<> 154:37f96f9d4de2 1322 bool change_drs = false;
<> 154:37f96f9d4de2 1323
<> 154:37f96f9d4de2 1324 #if (defined(MCG_CONFIG_CHECK_PARAM) && MCG_CONFIG_CHECK_PARAM)
<> 154:37f96f9d4de2 1325 mcg_mode_t mode = CLOCK_GetMode();
<> 154:37f96f9d4de2 1326
<> 154:37f96f9d4de2 1327 if (!((kMCG_ModeFEE == mode) || (kMCG_ModeFBI == mode) || (kMCG_ModeFBE == mode) || (kMCG_ModeFEI == mode) ||
<> 154:37f96f9d4de2 1328 (kMCG_ModeBLPI == mode)))
<> 154:37f96f9d4de2 1329
<> 154:37f96f9d4de2 1330 {
<> 154:37f96f9d4de2 1331 return kStatus_MCG_ModeUnreachable;
<> 154:37f96f9d4de2 1332 }
<> 154:37f96f9d4de2 1333 #endif
<> 154:37f96f9d4de2 1334
<> 154:37f96f9d4de2 1335 mcg_c4 = MCG->C4;
<> 154:37f96f9d4de2 1336
<> 154:37f96f9d4de2 1337 MCG->C2 &= ~MCG_C2_LP_MASK; /* Disable lowpower. */
<> 154:37f96f9d4de2 1338
<> 154:37f96f9d4de2 1339 /*
<> 154:37f96f9d4de2 1340 Errata: ERR007993
<> 154:37f96f9d4de2 1341 Workaround: Invert MCG_C4[DMX32] or change MCG_C4[DRST_DRS] before
<> 154:37f96f9d4de2 1342 reference clock source changes, then reset to previous value after
<> 154:37f96f9d4de2 1343 reference clock changes.
<> 154:37f96f9d4de2 1344 */
<> 154:37f96f9d4de2 1345 if (kMCG_FllSrcExternal == MCG_S_IREFST_VAL)
<> 154:37f96f9d4de2 1346 {
<> 154:37f96f9d4de2 1347 change_drs = true;
<> 154:37f96f9d4de2 1348 /* Change the LSB of DRST_DRS. */
<> 154:37f96f9d4de2 1349 MCG->C4 ^= (1U << MCG_C4_DRST_DRS_SHIFT);
<> 154:37f96f9d4de2 1350 }
<> 154:37f96f9d4de2 1351
<> 154:37f96f9d4de2 1352 /* Set CLKS and IREFS. */
<> 154:37f96f9d4de2 1353 MCG->C1 =
<> 154:37f96f9d4de2 1354 ((MCG->C1 & ~(MCG_C1_CLKS_MASK | MCG_C1_IREFS_MASK)) | (MCG_C1_CLKS(kMCG_ClkOutSrcInternal) /* CLKS = 1 */
<> 154:37f96f9d4de2 1355 | MCG_C1_IREFS(kMCG_FllSrcInternal))); /* IREFS = 1 */
<> 154:37f96f9d4de2 1356
<> 154:37f96f9d4de2 1357 /* Wait and check status. */
<> 154:37f96f9d4de2 1358 while (kMCG_FllSrcInternal != MCG_S_IREFST_VAL)
<> 154:37f96f9d4de2 1359 {
<> 154:37f96f9d4de2 1360 }
<> 154:37f96f9d4de2 1361
<> 154:37f96f9d4de2 1362 /* Errata: ERR007993 */
<> 154:37f96f9d4de2 1363 if (change_drs)
<> 154:37f96f9d4de2 1364 {
<> 154:37f96f9d4de2 1365 MCG->C4 = mcg_c4;
<> 154:37f96f9d4de2 1366 }
<> 154:37f96f9d4de2 1367
<> 154:37f96f9d4de2 1368 while (kMCG_ClkOutStatInt != MCG_S_CLKST_VAL)
<> 154:37f96f9d4de2 1369 {
<> 154:37f96f9d4de2 1370 }
<> 154:37f96f9d4de2 1371
<> 154:37f96f9d4de2 1372 MCG->C4 = (mcg_c4 & ~(MCG_C4_DMX32_MASK | MCG_C4_DRST_DRS_MASK)) | (MCG_C4_DRST_DRS(drs));
<> 154:37f96f9d4de2 1373
<> 154:37f96f9d4de2 1374 /* Wait for FLL stable time. */
<> 154:37f96f9d4de2 1375 if (fllStableDelay)
<> 154:37f96f9d4de2 1376 {
<> 154:37f96f9d4de2 1377 fllStableDelay();
<> 154:37f96f9d4de2 1378 }
<> 154:37f96f9d4de2 1379
<> 154:37f96f9d4de2 1380 return kStatus_Success;
<> 154:37f96f9d4de2 1381 }
<> 154:37f96f9d4de2 1382
<> 154:37f96f9d4de2 1383 status_t CLOCK_SetFbeMode(uint8_t frdiv, mcg_dmx32_t dmx32, mcg_drs_t drs, void (*fllStableDelay)(void))
<> 154:37f96f9d4de2 1384 {
<> 154:37f96f9d4de2 1385 uint8_t mcg_c4;
<> 154:37f96f9d4de2 1386 bool change_drs = false;
<> 154:37f96f9d4de2 1387
<> 154:37f96f9d4de2 1388 #if (defined(MCG_CONFIG_CHECK_PARAM) && MCG_CONFIG_CHECK_PARAM)
<> 154:37f96f9d4de2 1389 mcg_mode_t mode = CLOCK_GetMode();
<> 154:37f96f9d4de2 1390 if (!((kMCG_ModeFEE == mode) || (kMCG_ModeFBI == mode) || (kMCG_ModeFBE == mode) || (kMCG_ModeFEI == mode) ||
<> 154:37f96f9d4de2 1391 (kMCG_ModePBE == mode) || (kMCG_ModeBLPE == mode)))
<> 154:37f96f9d4de2 1392 {
<> 154:37f96f9d4de2 1393 return kStatus_MCG_ModeUnreachable;
<> 154:37f96f9d4de2 1394 }
<> 154:37f96f9d4de2 1395 #endif
<> 154:37f96f9d4de2 1396
<> 154:37f96f9d4de2 1397 /* Change to FLL mode. */
<> 154:37f96f9d4de2 1398 MCG->C6 &= ~MCG_C6_PLLS_MASK;
<> 154:37f96f9d4de2 1399 while (MCG->S & MCG_S_PLLST_MASK)
<> 154:37f96f9d4de2 1400 {
<> 154:37f96f9d4de2 1401 }
<> 154:37f96f9d4de2 1402
<> 154:37f96f9d4de2 1403 /* Set LP bit to enable the FLL */
<> 154:37f96f9d4de2 1404 MCG->C2 &= ~MCG_C2_LP_MASK;
<> 154:37f96f9d4de2 1405
<> 154:37f96f9d4de2 1406 mcg_c4 = MCG->C4;
<> 154:37f96f9d4de2 1407
<> 154:37f96f9d4de2 1408 /*
<> 154:37f96f9d4de2 1409 Errata: ERR007993
<> 154:37f96f9d4de2 1410 Workaround: Invert MCG_C4[DMX32] or change MCG_C4[DRST_DRS] before
<> 154:37f96f9d4de2 1411 reference clock source changes, then reset to previous value after
<> 154:37f96f9d4de2 1412 reference clock changes.
<> 154:37f96f9d4de2 1413 */
<> 154:37f96f9d4de2 1414 if (kMCG_FllSrcInternal == MCG_S_IREFST_VAL)
<> 154:37f96f9d4de2 1415 {
<> 154:37f96f9d4de2 1416 change_drs = true;
<> 154:37f96f9d4de2 1417 /* Change the LSB of DRST_DRS. */
<> 154:37f96f9d4de2 1418 MCG->C4 ^= (1U << MCG_C4_DRST_DRS_SHIFT);
<> 154:37f96f9d4de2 1419 }
<> 154:37f96f9d4de2 1420
<> 154:37f96f9d4de2 1421 /* Set CLKS and IREFS. */
<> 154:37f96f9d4de2 1422 MCG->C1 = ((MCG->C1 & ~(MCG_C1_CLKS_MASK | MCG_C1_FRDIV_MASK | MCG_C1_IREFS_MASK)) |
<> 154:37f96f9d4de2 1423 (MCG_C1_CLKS(kMCG_ClkOutSrcExternal) /* CLKS = 2 */
<> 154:37f96f9d4de2 1424 | MCG_C1_FRDIV(frdiv) /* FRDIV = frdiv */
<> 154:37f96f9d4de2 1425 | MCG_C1_IREFS(kMCG_FllSrcExternal))); /* IREFS = 0 */
<> 154:37f96f9d4de2 1426
<> 154:37f96f9d4de2 1427 /* Wait for Reference clock Status bit to clear */
<> 154:37f96f9d4de2 1428 while (kMCG_FllSrcExternal != MCG_S_IREFST_VAL)
<> 154:37f96f9d4de2 1429 {
<> 154:37f96f9d4de2 1430 }
<> 154:37f96f9d4de2 1431
<> 154:37f96f9d4de2 1432 /* Errata: ERR007993 */
<> 154:37f96f9d4de2 1433 if (change_drs)
<> 154:37f96f9d4de2 1434 {
<> 154:37f96f9d4de2 1435 MCG->C4 = mcg_c4;
<> 154:37f96f9d4de2 1436 }
<> 154:37f96f9d4de2 1437
<> 154:37f96f9d4de2 1438 /* Set DRST_DRS and DMX32. */
<> 154:37f96f9d4de2 1439 mcg_c4 = ((mcg_c4 & ~(MCG_C4_DMX32_MASK | MCG_C4_DRST_DRS_MASK)) | (MCG_C4_DMX32(dmx32) | MCG_C4_DRST_DRS(drs)));
<> 154:37f96f9d4de2 1440
<> 154:37f96f9d4de2 1441 /* Wait for clock status bits to show clock source is ext ref clk */
<> 154:37f96f9d4de2 1442 while (kMCG_ClkOutStatExt != MCG_S_CLKST_VAL)
<> 154:37f96f9d4de2 1443 {
<> 154:37f96f9d4de2 1444 }
<> 154:37f96f9d4de2 1445
<> 154:37f96f9d4de2 1446 /* Wait for fll stable time. */
<> 154:37f96f9d4de2 1447 if (fllStableDelay)
<> 154:37f96f9d4de2 1448 {
<> 154:37f96f9d4de2 1449 fllStableDelay();
<> 154:37f96f9d4de2 1450 }
<> 154:37f96f9d4de2 1451
<> 154:37f96f9d4de2 1452 return kStatus_Success;
<> 154:37f96f9d4de2 1453 }
<> 154:37f96f9d4de2 1454
<> 154:37f96f9d4de2 1455 status_t CLOCK_SetBlpiMode(void)
<> 154:37f96f9d4de2 1456 {
<> 154:37f96f9d4de2 1457 #if (defined(MCG_CONFIG_CHECK_PARAM) && MCG_CONFIG_CHECK_PARAM)
<> 154:37f96f9d4de2 1458 if (MCG_S_CLKST_VAL != kMCG_ClkOutStatInt)
<> 154:37f96f9d4de2 1459 {
<> 154:37f96f9d4de2 1460 return kStatus_MCG_ModeUnreachable;
<> 154:37f96f9d4de2 1461 }
<> 154:37f96f9d4de2 1462 #endif /* MCG_CONFIG_CHECK_PARAM */
<> 154:37f96f9d4de2 1463
<> 154:37f96f9d4de2 1464 /* Set LP. */
<> 154:37f96f9d4de2 1465 MCG->C2 |= MCG_C2_LP_MASK;
<> 154:37f96f9d4de2 1466
<> 154:37f96f9d4de2 1467 return kStatus_Success;
<> 154:37f96f9d4de2 1468 }
<> 154:37f96f9d4de2 1469
<> 154:37f96f9d4de2 1470 status_t CLOCK_SetBlpeMode(void)
<> 154:37f96f9d4de2 1471 {
<> 154:37f96f9d4de2 1472 #if (defined(MCG_CONFIG_CHECK_PARAM) && MCG_CONFIG_CHECK_PARAM)
<> 154:37f96f9d4de2 1473 if (MCG_S_CLKST_VAL != kMCG_ClkOutStatExt)
<> 154:37f96f9d4de2 1474 {
<> 154:37f96f9d4de2 1475 return kStatus_MCG_ModeUnreachable;
<> 154:37f96f9d4de2 1476 }
<> 154:37f96f9d4de2 1477 #endif
<> 154:37f96f9d4de2 1478
<> 154:37f96f9d4de2 1479 /* Set LP bit to enter BLPE mode. */
<> 154:37f96f9d4de2 1480 MCG->C2 |= MCG_C2_LP_MASK;
<> 154:37f96f9d4de2 1481
<> 154:37f96f9d4de2 1482 return kStatus_Success;
<> 154:37f96f9d4de2 1483 }
<> 154:37f96f9d4de2 1484
<> 154:37f96f9d4de2 1485 status_t CLOCK_SetPbeMode(mcg_pll_clk_select_t pllcs, mcg_pll_config_t const *config)
<> 154:37f96f9d4de2 1486 {
<> 154:37f96f9d4de2 1487 /*
<> 154:37f96f9d4de2 1488 This function is designed to change MCG to PBE mode from PEE/BLPE/FBE,
<> 154:37f96f9d4de2 1489 but with this workflow, the source mode could be all modes except PEI/PBI.
<> 154:37f96f9d4de2 1490 */
<> 154:37f96f9d4de2 1491 MCG->C2 &= ~MCG_C2_LP_MASK; /* Disable lowpower. */
<> 154:37f96f9d4de2 1492
<> 154:37f96f9d4de2 1493 /* Change to use external clock first. */
<> 154:37f96f9d4de2 1494 MCG->C1 = ((MCG->C1 & ~(MCG_C1_CLKS_MASK | MCG_C1_IREFS_MASK)) | MCG_C1_CLKS(kMCG_ClkOutSrcExternal));
<> 154:37f96f9d4de2 1495
<> 154:37f96f9d4de2 1496 /* Wait for CLKST clock status bits to show clock source is ext ref clk */
<> 154:37f96f9d4de2 1497 while ((MCG->S & (MCG_S_IREFST_MASK | MCG_S_CLKST_MASK)) !=
<> 154:37f96f9d4de2 1498 (MCG_S_IREFST(kMCG_FllSrcExternal) | MCG_S_CLKST(kMCG_ClkOutStatExt)))
<> 154:37f96f9d4de2 1499 {
<> 154:37f96f9d4de2 1500 }
<> 154:37f96f9d4de2 1501
<> 154:37f96f9d4de2 1502 /* Disable PLL first, then configure PLL. */
<> 154:37f96f9d4de2 1503 MCG->C6 &= ~MCG_C6_PLLS_MASK;
<> 154:37f96f9d4de2 1504 while (MCG->S & MCG_S_PLLST_MASK)
<> 154:37f96f9d4de2 1505 {
<> 154:37f96f9d4de2 1506 }
<> 154:37f96f9d4de2 1507
<> 154:37f96f9d4de2 1508 /* Configure the PLL. */
<> 154:37f96f9d4de2 1509 {
<> 154:37f96f9d4de2 1510 CLOCK_EnablePll0(config);
<> 154:37f96f9d4de2 1511 }
<> 154:37f96f9d4de2 1512
<> 154:37f96f9d4de2 1513 /* Change to PLL mode. */
<> 154:37f96f9d4de2 1514 MCG->C6 |= MCG_C6_PLLS_MASK;
<> 154:37f96f9d4de2 1515 while (!(MCG->S & MCG_S_PLLST_MASK))
<> 154:37f96f9d4de2 1516 {
<> 154:37f96f9d4de2 1517 }
<> 154:37f96f9d4de2 1518
<> 154:37f96f9d4de2 1519 return kStatus_Success;
<> 154:37f96f9d4de2 1520 }
<> 154:37f96f9d4de2 1521
<> 154:37f96f9d4de2 1522 status_t CLOCK_SetPeeMode(void)
<> 154:37f96f9d4de2 1523 {
<> 154:37f96f9d4de2 1524 #if (defined(MCG_CONFIG_CHECK_PARAM) && MCG_CONFIG_CHECK_PARAM)
<> 154:37f96f9d4de2 1525 mcg_mode_t mode = CLOCK_GetMode();
<> 154:37f96f9d4de2 1526 if (kMCG_ModePBE != mode)
<> 154:37f96f9d4de2 1527 {
<> 154:37f96f9d4de2 1528 return kStatus_MCG_ModeUnreachable;
<> 154:37f96f9d4de2 1529 }
<> 154:37f96f9d4de2 1530 #endif
<> 154:37f96f9d4de2 1531
<> 154:37f96f9d4de2 1532 /* Change to use PLL/FLL output clock first. */
<> 154:37f96f9d4de2 1533 MCG->C1 = (MCG->C1 & ~MCG_C1_CLKS_MASK) | MCG_C1_CLKS(kMCG_ClkOutSrcOut);
<> 154:37f96f9d4de2 1534
<> 154:37f96f9d4de2 1535 /* Wait for clock status bits to update */
<> 154:37f96f9d4de2 1536 while (MCG_S_CLKST_VAL != kMCG_ClkOutStatPll)
<> 154:37f96f9d4de2 1537 {
<> 154:37f96f9d4de2 1538 }
<> 154:37f96f9d4de2 1539
<> 154:37f96f9d4de2 1540 return kStatus_Success;
<> 154:37f96f9d4de2 1541 }
<> 154:37f96f9d4de2 1542
<> 154:37f96f9d4de2 1543 status_t CLOCK_ExternalModeToFbeModeQuick(void)
<> 154:37f96f9d4de2 1544 {
<> 154:37f96f9d4de2 1545 #if (defined(MCG_CONFIG_CHECK_PARAM) && MCG_CONFIG_CHECK_PARAM)
<> 154:37f96f9d4de2 1546 if (MCG->S & MCG_S_IREFST_MASK)
<> 154:37f96f9d4de2 1547 {
<> 154:37f96f9d4de2 1548 return kStatus_MCG_ModeInvalid;
<> 154:37f96f9d4de2 1549 }
<> 154:37f96f9d4de2 1550 #endif /* MCG_CONFIG_CHECK_PARAM */
<> 154:37f96f9d4de2 1551
<> 154:37f96f9d4de2 1552 /* Disable low power */
<> 154:37f96f9d4de2 1553 MCG->C2 &= ~MCG_C2_LP_MASK;
<> 154:37f96f9d4de2 1554
<> 154:37f96f9d4de2 1555 MCG->C1 = ((MCG->C1 & ~MCG_C1_CLKS_MASK) | MCG_C1_CLKS(kMCG_ClkOutSrcExternal));
<> 154:37f96f9d4de2 1556 while (MCG_S_CLKST_VAL != kMCG_ClkOutStatExt)
<> 154:37f96f9d4de2 1557 {
<> 154:37f96f9d4de2 1558 }
<> 154:37f96f9d4de2 1559
<> 154:37f96f9d4de2 1560 /* Disable PLL. */
<> 154:37f96f9d4de2 1561 MCG->C6 &= ~MCG_C6_PLLS_MASK;
<> 154:37f96f9d4de2 1562 while (MCG->S & MCG_S_PLLST_MASK)
<> 154:37f96f9d4de2 1563 {
<> 154:37f96f9d4de2 1564 }
<> 154:37f96f9d4de2 1565
<> 154:37f96f9d4de2 1566 return kStatus_Success;
<> 154:37f96f9d4de2 1567 }
<> 154:37f96f9d4de2 1568
<> 154:37f96f9d4de2 1569 status_t CLOCK_InternalModeToFbiModeQuick(void)
<> 154:37f96f9d4de2 1570 {
<> 154:37f96f9d4de2 1571 #if (defined(MCG_CONFIG_CHECK_PARAM) && MCG_CONFIG_CHECK_PARAM)
<> 154:37f96f9d4de2 1572 if (!(MCG->S & MCG_S_IREFST_MASK))
<> 154:37f96f9d4de2 1573 {
<> 154:37f96f9d4de2 1574 return kStatus_MCG_ModeInvalid;
<> 154:37f96f9d4de2 1575 }
<> 154:37f96f9d4de2 1576 #endif
<> 154:37f96f9d4de2 1577
<> 154:37f96f9d4de2 1578 /* Disable low power */
<> 154:37f96f9d4de2 1579 MCG->C2 &= ~MCG_C2_LP_MASK;
<> 154:37f96f9d4de2 1580
<> 154:37f96f9d4de2 1581 MCG->C1 = ((MCG->C1 & ~MCG_C1_CLKS_MASK) | MCG_C1_CLKS(kMCG_ClkOutSrcInternal));
<> 154:37f96f9d4de2 1582 while (MCG_S_CLKST_VAL != kMCG_ClkOutStatInt)
<> 154:37f96f9d4de2 1583 {
<> 154:37f96f9d4de2 1584 }
<> 154:37f96f9d4de2 1585
<> 154:37f96f9d4de2 1586 return kStatus_Success;
<> 154:37f96f9d4de2 1587 }
<> 154:37f96f9d4de2 1588
<> 154:37f96f9d4de2 1589 status_t CLOCK_BootToFeiMode(mcg_drs_t drs, void (*fllStableDelay)(void))
<> 154:37f96f9d4de2 1590 {
<> 154:37f96f9d4de2 1591 return CLOCK_SetFeiMode(drs, fllStableDelay);
<> 154:37f96f9d4de2 1592 }
<> 154:37f96f9d4de2 1593
<> 154:37f96f9d4de2 1594 status_t CLOCK_BootToFeeMode(
<> 154:37f96f9d4de2 1595 mcg_oscsel_t oscsel, uint8_t frdiv, mcg_dmx32_t dmx32, mcg_drs_t drs, void (*fllStableDelay)(void))
<> 154:37f96f9d4de2 1596 {
<> 154:37f96f9d4de2 1597 CLOCK_SetExternalRefClkConfig(oscsel);
<> 154:37f96f9d4de2 1598
<> 154:37f96f9d4de2 1599 return CLOCK_SetFeeMode(frdiv, dmx32, drs, fllStableDelay);
<> 154:37f96f9d4de2 1600 }
<> 154:37f96f9d4de2 1601
<> 154:37f96f9d4de2 1602 status_t CLOCK_BootToBlpiMode(uint8_t fcrdiv, mcg_irc_mode_t ircs, uint8_t ircEnableMode)
<> 154:37f96f9d4de2 1603 {
<> 154:37f96f9d4de2 1604 /* If reset mode is FEI mode, set MCGIRCLK and always success. */
<> 154:37f96f9d4de2 1605 CLOCK_SetInternalRefClkConfig(ircEnableMode, ircs, fcrdiv);
<> 154:37f96f9d4de2 1606
<> 154:37f96f9d4de2 1607 /* If reset mode is not BLPI, first enter FBI mode. */
<> 154:37f96f9d4de2 1608 MCG->C1 = (MCG->C1 & ~MCG_C1_CLKS_MASK) | MCG_C1_CLKS(kMCG_ClkOutSrcInternal);
<> 154:37f96f9d4de2 1609 while (MCG_S_CLKST_VAL != kMCG_ClkOutStatInt)
<> 154:37f96f9d4de2 1610 {
<> 154:37f96f9d4de2 1611 }
<> 154:37f96f9d4de2 1612
<> 154:37f96f9d4de2 1613 /* Enter BLPI mode. */
<> 154:37f96f9d4de2 1614 MCG->C2 |= MCG_C2_LP_MASK;
<> 154:37f96f9d4de2 1615
<> 154:37f96f9d4de2 1616 return kStatus_Success;
<> 154:37f96f9d4de2 1617 }
<> 154:37f96f9d4de2 1618
<> 154:37f96f9d4de2 1619 status_t CLOCK_BootToBlpeMode(mcg_oscsel_t oscsel)
<> 154:37f96f9d4de2 1620 {
<> 154:37f96f9d4de2 1621 CLOCK_SetExternalRefClkConfig(oscsel);
<> 154:37f96f9d4de2 1622
<> 154:37f96f9d4de2 1623 /* Set to FBE mode. */
<> 154:37f96f9d4de2 1624 MCG->C1 =
<> 154:37f96f9d4de2 1625 ((MCG->C1 & ~(MCG_C1_CLKS_MASK | MCG_C1_IREFS_MASK)) | (MCG_C1_CLKS(kMCG_ClkOutSrcExternal) /* CLKS = 2 */
<> 154:37f96f9d4de2 1626 | MCG_C1_IREFS(kMCG_FllSrcExternal))); /* IREFS = 0 */
<> 154:37f96f9d4de2 1627
<> 154:37f96f9d4de2 1628 /* Wait for MCG_S[CLKST] and MCG_S[IREFST]. */
<> 154:37f96f9d4de2 1629 while ((MCG->S & (MCG_S_IREFST_MASK | MCG_S_CLKST_MASK)) !=
<> 154:37f96f9d4de2 1630 (MCG_S_IREFST(kMCG_FllSrcExternal) | MCG_S_CLKST(kMCG_ClkOutStatExt)))
<> 154:37f96f9d4de2 1631 {
<> 154:37f96f9d4de2 1632 }
<> 154:37f96f9d4de2 1633
<> 154:37f96f9d4de2 1634 /* In FBE now, start to enter BLPE. */
<> 154:37f96f9d4de2 1635 MCG->C2 |= MCG_C2_LP_MASK;
<> 154:37f96f9d4de2 1636
<> 154:37f96f9d4de2 1637 return kStatus_Success;
<> 154:37f96f9d4de2 1638 }
<> 154:37f96f9d4de2 1639
<> 154:37f96f9d4de2 1640 status_t CLOCK_BootToPeeMode(mcg_oscsel_t oscsel, mcg_pll_clk_select_t pllcs, mcg_pll_config_t const *config)
<> 154:37f96f9d4de2 1641 {
<> 154:37f96f9d4de2 1642 assert(config);
<> 154:37f96f9d4de2 1643
<> 154:37f96f9d4de2 1644 CLOCK_SetExternalRefClkConfig(oscsel);
<> 154:37f96f9d4de2 1645
<> 154:37f96f9d4de2 1646 CLOCK_SetPbeMode(pllcs, config);
<> 154:37f96f9d4de2 1647
<> 154:37f96f9d4de2 1648 /* Change to use PLL output clock. */
<> 154:37f96f9d4de2 1649 MCG->C1 = (MCG->C1 & ~MCG_C1_CLKS_MASK) | MCG_C1_CLKS(kMCG_ClkOutSrcOut);
<> 154:37f96f9d4de2 1650 while (MCG_S_CLKST_VAL != kMCG_ClkOutStatPll)
<> 154:37f96f9d4de2 1651 {
<> 154:37f96f9d4de2 1652 }
<> 154:37f96f9d4de2 1653
<> 154:37f96f9d4de2 1654 return kStatus_Success;
<> 154:37f96f9d4de2 1655 }
<> 154:37f96f9d4de2 1656
<> 154:37f96f9d4de2 1657 /*
<> 154:37f96f9d4de2 1658 The transaction matrix. It defines the path for mode switch, the row is for
<> 154:37f96f9d4de2 1659 current mode and the column is target mode.
<> 154:37f96f9d4de2 1660 For example, switch from FEI to PEE:
<> 154:37f96f9d4de2 1661 1. Current mode FEI, next mode is mcgModeMatrix[FEI][PEE] = FBE, so swith to FBE.
<> 154:37f96f9d4de2 1662 2. Current mode FBE, next mode is mcgModeMatrix[FBE][PEE] = PBE, so swith to PBE.
<> 154:37f96f9d4de2 1663 3. Current mode PBE, next mode is mcgModeMatrix[PBE][PEE] = PEE, so swith to PEE.
<> 154:37f96f9d4de2 1664 Thus the MCG mode has changed from FEI to PEE.
<> 154:37f96f9d4de2 1665 */
<> 154:37f96f9d4de2 1666 static const mcg_mode_t mcgModeMatrix[8][8] = {
<> 154:37f96f9d4de2 1667 {kMCG_ModeFEI, kMCG_ModeFBI, kMCG_ModeFBI, kMCG_ModeFEE, kMCG_ModeFBE, kMCG_ModeFBE, kMCG_ModeFBE,
<> 154:37f96f9d4de2 1668 kMCG_ModeFBE}, /* FEI */
<> 154:37f96f9d4de2 1669 {kMCG_ModeFEI, kMCG_ModeFBI, kMCG_ModeBLPI, kMCG_ModeFEE, kMCG_ModeFBE, kMCG_ModeFBE, kMCG_ModeFBE,
<> 154:37f96f9d4de2 1670 kMCG_ModeFBE}, /* FBI */
<> 154:37f96f9d4de2 1671 {kMCG_ModeFBI, kMCG_ModeFBI, kMCG_ModeBLPI, kMCG_ModeFBI, kMCG_ModeFBI, kMCG_ModeFBI, kMCG_ModeFBI,
<> 154:37f96f9d4de2 1672 kMCG_ModeFBI}, /* BLPI */
<> 154:37f96f9d4de2 1673 {kMCG_ModeFEI, kMCG_ModeFBI, kMCG_ModeFBI, kMCG_ModeFEE, kMCG_ModeFBE, kMCG_ModeFBE, kMCG_ModeFBE,
<> 154:37f96f9d4de2 1674 kMCG_ModeFBE}, /* FEE */
<> 154:37f96f9d4de2 1675 {kMCG_ModeFEI, kMCG_ModeFBI, kMCG_ModeFBI, kMCG_ModeFEE, kMCG_ModeFBE, kMCG_ModeBLPE, kMCG_ModePBE,
<> 154:37f96f9d4de2 1676 kMCG_ModePBE}, /* FBE */
<> 154:37f96f9d4de2 1677 {kMCG_ModeFBE, kMCG_ModeFBE, kMCG_ModeFBE, kMCG_ModeFBE, kMCG_ModeFBE, kMCG_ModeBLPE, kMCG_ModePBE,
<> 154:37f96f9d4de2 1678 kMCG_ModePBE}, /* BLPE */
<> 154:37f96f9d4de2 1679 {kMCG_ModeFBE, kMCG_ModeFBE, kMCG_ModeFBE, kMCG_ModeFBE, kMCG_ModeFBE, kMCG_ModeBLPE, kMCG_ModePBE,
<> 154:37f96f9d4de2 1680 kMCG_ModePEE}, /* PBE */
<> 154:37f96f9d4de2 1681 {kMCG_ModePBE, kMCG_ModePBE, kMCG_ModePBE, kMCG_ModePBE, kMCG_ModePBE, kMCG_ModePBE, kMCG_ModePBE,
<> 154:37f96f9d4de2 1682 kMCG_ModePBE} /* PEE */
<> 154:37f96f9d4de2 1683 /* FEI FBI BLPI FEE FBE BLPE PBE PEE */
<> 154:37f96f9d4de2 1684 };
<> 154:37f96f9d4de2 1685
<> 154:37f96f9d4de2 1686 status_t CLOCK_SetMcgConfig(const mcg_config_t *config)
<> 154:37f96f9d4de2 1687 {
<> 154:37f96f9d4de2 1688 mcg_mode_t next_mode;
<> 154:37f96f9d4de2 1689 status_t status = kStatus_Success;
<> 154:37f96f9d4de2 1690
<> 154:37f96f9d4de2 1691 mcg_pll_clk_select_t pllcs = kMCG_PllClkSelPll0;
<> 154:37f96f9d4de2 1692
<> 154:37f96f9d4de2 1693 /* If need to change external clock, MCG_C7[OSCSEL]. */
<> 154:37f96f9d4de2 1694 if (MCG_C7_OSCSEL_VAL != config->oscsel)
<> 154:37f96f9d4de2 1695 {
<> 154:37f96f9d4de2 1696 /* If external clock is in use, change to FEI first. */
<> 154:37f96f9d4de2 1697 if (!(MCG->S & MCG_S_IRCST_MASK))
<> 154:37f96f9d4de2 1698 {
<> 154:37f96f9d4de2 1699 CLOCK_ExternalModeToFbeModeQuick();
<> 154:37f96f9d4de2 1700 CLOCK_SetFeiMode(config->drs, (void (*)(void))0);
<> 154:37f96f9d4de2 1701 }
<> 154:37f96f9d4de2 1702
<> 154:37f96f9d4de2 1703 CLOCK_SetExternalRefClkConfig(config->oscsel);
<> 154:37f96f9d4de2 1704 }
<> 154:37f96f9d4de2 1705
<> 154:37f96f9d4de2 1706 /* Re-configure MCGIRCLK, if MCGIRCLK is used as system clock source, then change to FEI/PEI first. */
<> 154:37f96f9d4de2 1707 if (MCG_S_CLKST_VAL == kMCG_ClkOutStatInt)
<> 154:37f96f9d4de2 1708 {
<> 154:37f96f9d4de2 1709 MCG->C2 &= ~MCG_C2_LP_MASK; /* Disable lowpower. */
<> 154:37f96f9d4de2 1710
<> 154:37f96f9d4de2 1711 {
<> 154:37f96f9d4de2 1712 CLOCK_SetFeiMode(config->drs, CLOCK_FllStableDelay);
<> 154:37f96f9d4de2 1713 }
<> 154:37f96f9d4de2 1714 }
<> 154:37f96f9d4de2 1715
<> 154:37f96f9d4de2 1716 /* Configure MCGIRCLK. */
<> 154:37f96f9d4de2 1717 CLOCK_SetInternalRefClkConfig(config->irclkEnableMode, config->ircs, config->fcrdiv);
<> 154:37f96f9d4de2 1718
<> 154:37f96f9d4de2 1719 next_mode = CLOCK_GetMode();
<> 154:37f96f9d4de2 1720
<> 154:37f96f9d4de2 1721 do
<> 154:37f96f9d4de2 1722 {
<> 154:37f96f9d4de2 1723 next_mode = mcgModeMatrix[next_mode][config->mcgMode];
<> 154:37f96f9d4de2 1724
<> 154:37f96f9d4de2 1725 switch (next_mode)
<> 154:37f96f9d4de2 1726 {
<> 154:37f96f9d4de2 1727 case kMCG_ModeFEI:
<> 154:37f96f9d4de2 1728 status = CLOCK_SetFeiMode(config->drs, CLOCK_FllStableDelay);
<> 154:37f96f9d4de2 1729 break;
<> 154:37f96f9d4de2 1730 case kMCG_ModeFEE:
<> 154:37f96f9d4de2 1731 status = CLOCK_SetFeeMode(config->frdiv, config->dmx32, config->drs, CLOCK_FllStableDelay);
<> 154:37f96f9d4de2 1732 break;
<> 154:37f96f9d4de2 1733 case kMCG_ModeFBI:
<> 154:37f96f9d4de2 1734 status = CLOCK_SetFbiMode(config->drs, (void (*)(void))0);
<> 154:37f96f9d4de2 1735 break;
<> 154:37f96f9d4de2 1736 case kMCG_ModeFBE:
<> 154:37f96f9d4de2 1737 status = CLOCK_SetFbeMode(config->frdiv, config->dmx32, config->drs, (void (*)(void))0);
<> 154:37f96f9d4de2 1738 break;
<> 154:37f96f9d4de2 1739 case kMCG_ModeBLPI:
<> 154:37f96f9d4de2 1740 status = CLOCK_SetBlpiMode();
<> 154:37f96f9d4de2 1741 break;
<> 154:37f96f9d4de2 1742 case kMCG_ModeBLPE:
<> 154:37f96f9d4de2 1743 status = CLOCK_SetBlpeMode();
<> 154:37f96f9d4de2 1744 break;
<> 154:37f96f9d4de2 1745 case kMCG_ModePBE:
<> 154:37f96f9d4de2 1746 /* If target mode is not PBE or PEE, then only need to set CLKS = EXT here. */
<> 154:37f96f9d4de2 1747 if ((kMCG_ModePEE == config->mcgMode) || (kMCG_ModePBE == config->mcgMode))
<> 154:37f96f9d4de2 1748 {
<> 154:37f96f9d4de2 1749 {
<> 154:37f96f9d4de2 1750 status = CLOCK_SetPbeMode(pllcs, &config->pll0Config);
<> 154:37f96f9d4de2 1751 }
<> 154:37f96f9d4de2 1752 }
<> 154:37f96f9d4de2 1753 else
<> 154:37f96f9d4de2 1754 {
<> 154:37f96f9d4de2 1755 MCG->C1 = ((MCG->C1 & ~MCG_C1_CLKS_MASK) | MCG_C1_CLKS(kMCG_ClkOutSrcExternal));
<> 154:37f96f9d4de2 1756 while (MCG_S_CLKST_VAL != kMCG_ClkOutStatExt)
<> 154:37f96f9d4de2 1757 {
<> 154:37f96f9d4de2 1758 }
<> 154:37f96f9d4de2 1759 }
<> 154:37f96f9d4de2 1760 break;
<> 154:37f96f9d4de2 1761 case kMCG_ModePEE:
<> 154:37f96f9d4de2 1762 status = CLOCK_SetPeeMode();
<> 154:37f96f9d4de2 1763 break;
<> 154:37f96f9d4de2 1764 default:
<> 154:37f96f9d4de2 1765 break;
<> 154:37f96f9d4de2 1766 }
<> 154:37f96f9d4de2 1767 if (kStatus_Success != status)
<> 154:37f96f9d4de2 1768 {
<> 154:37f96f9d4de2 1769 return status;
<> 154:37f96f9d4de2 1770 }
<> 154:37f96f9d4de2 1771 } while (next_mode != config->mcgMode);
<> 154:37f96f9d4de2 1772
<> 154:37f96f9d4de2 1773 if (config->pll0Config.enableMode & kMCG_PllEnableIndependent)
<> 154:37f96f9d4de2 1774 {
<> 154:37f96f9d4de2 1775 CLOCK_EnablePll0(&config->pll0Config);
<> 154:37f96f9d4de2 1776 }
<> 154:37f96f9d4de2 1777 else
<> 154:37f96f9d4de2 1778 {
<> 154:37f96f9d4de2 1779 MCG->C5 &= ~(uint32_t)kMCG_PllEnableIndependent;
<> 154:37f96f9d4de2 1780 }
<> 154:37f96f9d4de2 1781 return kStatus_Success;
<> 154:37f96f9d4de2 1782 }