Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
hic_init.c
00001 /** 00002 * @file hic_init.c 00003 * @brief 00004 * 00005 * DAPLink Interface Firmware 00006 * Copyright (c) 2009-2016, ARM Limited, All Rights Reserved 00007 * Copyright (c) 2016-2017 NXP 00008 * SPDX-License-Identifier: Apache-2.0 00009 * 00010 * Licensed under the Apache License, Version 2.0 (the "License"); you may 00011 * not use this file except in compliance with the License. 00012 * You may obtain a copy of the License at 00013 * 00014 * http://www.apache.org/licenses/LICENSE-2.0 00015 * 00016 * Unless required by applicable law or agreed to in writing, software 00017 * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT 00018 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 00019 * See the License for the specific language governing permissions and 00020 * limitations under the License. 00021 */ 00022 00023 #include "hic_init.h" 00024 #include "gpio.h" 00025 #include "fsl_clock.h " 00026 #include "usb_phy.h" 00027 #include "util.h" 00028 00029 static void busy_wait(uint32_t cycles) 00030 { 00031 volatile uint32_t i; 00032 i = cycles; 00033 00034 while (i > 0) { 00035 i--; 00036 } 00037 } 00038 00039 static void fll_delay(void) 00040 { 00041 // ~2.5ms at 16MHz core clock 00042 busy_wait(10000); 00043 } 00044 00045 // This IRQ handler will be invoked if VDD falls below the trip point. 00046 void LVD_LVW_IRQHandler(void) 00047 { 00048 if (PMC->LVDSC1 & PMC_LVDSC1_LVDF_MASK) 00049 { 00050 util_assert(false && "low voltage detect tripped"); 00051 PMC->LVDSC1 |= PMC_LVDSC1_LVDACK_MASK; 00052 } 00053 if (PMC->LVDSC2 & PMC_LVDSC2_LVWF_MASK) 00054 { 00055 util_assert(false && "low voltage warning tripped"); 00056 PMC->LVDSC2 |= PMC_LVDSC2_LVWACK_MASK; 00057 } 00058 } 00059 00060 //! - MPU is disabled and gated. 00061 //! - 8kB cache is enabled. SRAM is not cached, so no flushing is required for normal operation. 00062 //! - Enable low voltage warning interrupt. 00063 //! - Disable USB current limiter so the voltage doesn't drop as we enable high speed clocks. 00064 void sdk_init(void) 00065 { 00066 CLOCK_SetXtal0Freq(16000000U); // 16 MHz crystal 00067 CLOCK_SetXtal32Freq(0); 00068 00069 // Disable the MPU if it's enabled. 00070 if (SIM->SCGC7 & SIM_SCGC7_MPU_MASK) 00071 { 00072 SYSMPU->CESR = 0; 00073 SIM->SCGC7 &= ~SIM_SCGC7_MPU_MASK; 00074 } 00075 00076 // Invalidate and enable code cache. 00077 LMEM->PCCCR = LMEM_PCCCR_GO_MASK | LMEM_PCCCR_INVW1_MASK | LMEM_PCCCR_INVW0_MASK | LMEM_PCCCR_ENCACHE_MASK; 00078 00079 // Enable LVD/LVW IRQ. 00080 PMC->LVDSC1 |= PMC_LVDSC1_LVDACK_MASK; 00081 PMC->LVDSC1 = PMC_LVDSC1_LVDIE_MASK | PMC_LVDSC1_LVDV(0); // low trip point 00082 PMC->LVDSC2 |= PMC_LVDSC2_LVWACK_MASK; 00083 PMC->LVDSC2 = PMC_LVDSC2_LVWIE_MASK | PMC_LVDSC2_LVWV(0); // low trip point 00084 // NVIC_EnableIRQ(LVD_LVW_IRQn); 00085 00086 // Disable USB inrush current limiter. 00087 SIM->USBPHYCTL |= SIM_USBPHYCTL_USBDISILIM_MASK; 00088 } 00089 00090 //! - Turn on 16MHz crystal oscillator. 00091 //! - Turn on 32kHz IRC. 00092 //! - Switch core clock to System PLL at 120 MHz, bus clock at 60 MHz, flash clock at 24 MHz. 00093 //! - Enable the 480MHz USB PHY PLL. 00094 //! - Ungate USBPHY and USBHS. 00095 //! - Configure the USB PHY. 00096 void hic_enable_usb_clocks(void) 00097 { 00098 // Enable external oscillator and 32kHz IRC. 00099 MCG->C1 |= MCG_C1_IRCLKEN_MASK; // Select 32k IR. 00100 // Delay at least 100µs for 32kHz IRQ to stabilize. 00101 fll_delay(); 00102 // Configure OSC for very high freq, low power mode. 00103 MCG->C2 = (MCG->C2 & ~(MCG_C2_RANGE_MASK | MCG_C2_HGO_MASK)) | MCG_C2_RANGE(2); 00104 OSC0->CR |= OSC_CR_ERCLKEN_MASK; // Enable OSC. 00105 MCG->C2 |= MCG_C2_EREFS_MASK; // Select OSC as ext ref. 00106 00107 // Wait for the oscillator to stabilize. 00108 while (!(MCG->S & MCG_S_OSCINIT0_MASK)) 00109 { 00110 } 00111 00112 // Divide 16MHz xtal by 512 = 31.25kHz 00113 CLOCK_SetFbeMode(4, kMCG_Dmx32Default , kMCG_DrsMid , fll_delay); 00114 00115 // Set dividers before switching to SYSPLL. 00116 SIM->CLKDIV1 = SIM_CLKDIV1_OUTDIV1(0) // System/core /1 = 120MHz 00117 | SIM_CLKDIV1_OUTDIV2(1) // Bus /2 = 60Mhz 00118 | SIM_CLKDIV1_OUTDIV3(4) // FlexBus /5 = 24Mhz 00119 | SIM_CLKDIV1_OUTDIV4(4); // Flash /5 = 24MHz 00120 00121 // 120MHz SYSPLL 00122 mcg_pll_config_t pllConfig; 00123 pllConfig.enableMode = 0; 00124 pllConfig.prdiv = 2 - 1; 00125 pllConfig.vdiv = 30 - 16; 00126 CLOCK_SetPbeMode(kMCG_PllClkSelPll0 , &pllConfig); 00127 CLOCK_SetPeeMode(); 00128 00129 // Enable USB clock source and init phy. This turns on the 480MHz PLL. 00130 CLOCK_EnableUsbhs0Clock(kCLOCK_UsbSrcPll0 , CLOCK_GetFreq(kCLOCK_PllFllSelClk )); 00131 USB_EhciPhyInit(0, CPU_XTAL_CLK_HZ); 00132 00133 SystemCoreClockUpdate(); 00134 } 00135 00136 void hic_power_target(void) 00137 { 00138 // Keep powered off in bootloader mode 00139 // to prevent the target from effecting the state 00140 // of the reset line / reset button 00141 if (!daplink_is_bootloader()) { 00142 // configure pin as GPIO 00143 PIN_POWER_EN_PORT->PCR[PIN_POWER_EN_BIT] = PORT_PCR_MUX(1); 00144 // force always on logic 1 00145 PIN_POWER_EN_GPIO->PSOR = 1UL << PIN_POWER_EN_BIT; 00146 PIN_POWER_EN_GPIO->PDDR |= 1UL << PIN_POWER_EN_BIT; 00147 00148 // Let the voltage rails stabilize. This is especailly important 00149 // during software resets, since the target's 3.3v rail can take 00150 // 20-50ms to drain. During this time the target could be driving 00151 // the reset pin low, causing the bootloader to think the reset 00152 // button is pressed. 00153 // Note: With optimization set to -O2 the value 5115 delays for ~1ms @ 20.9Mhz core 00154 busy_wait(5115 * 50); 00155 } 00156 }
Generated on Tue Jul 12 2022 15:37:18 by
