From c4c0d058915a370de4fbb29a6afc4b43b46f1e5a Mon Sep 17 00:00:00 2001 From: Nicholas C Date: Mon, 10 Feb 2020 20:36:22 -0600 Subject: [PATCH] arch/arm/src/imxrt; Adds clock config logic and Kconfig menus for FLEXIO on IMXRT --- arch/arm/src/imxrt/Kconfig | 134 +++++++++++++++++- .../src/imxrt/hardware/rt102x/imxrt102x_ccm.h | 32 +++-- .../src/imxrt/hardware/rt105x/imxrt105x_ccm.h | 3 +- .../src/imxrt/hardware/rt106x/imxrt106x_ccm.h | 3 +- arch/arm/src/imxrt/imxrt_clockconfig.c | 58 +++++++- 5 files changed, 209 insertions(+), 21 deletions(-) diff --git a/arch/arm/src/imxrt/Kconfig b/arch/arm/src/imxrt/Kconfig index 0e1518ff945..ca4e61d3eef 100644 --- a/arch/arm/src/imxrt/Kconfig +++ b/arch/arm/src/imxrt/Kconfig @@ -145,6 +145,10 @@ config IMXRT_USDHC bool default n +config IMXRT_FLEXIO + bool + default n + config IMXRT_HAVE_LPUART bool default n @@ -200,6 +204,128 @@ config IMXRT_LCD menu "FlexIO Peripherals" +config IMXRT_FLEXIO1 + bool "FLEXIO1" + default n + select IMXRT_FLEXIO + +if IMXRT_FLEXIO1 + +choice + prompt "FLEXIO1 Clock Source" + default FLEXIO1_CLK_PLL3_SW + ---help--- + The clock source that drives the FLEXIO. + Used to set FLEXIO1_CLK_SEL. + +config FLEXIO1_CLK_PLL4 + bool "PLL4" + +config FLEXIO1_CLK_PLL3_PFD2 + bool "PLL3_PFD2" + +if ARCH_FAMILY_IMXRT105x || ARCH_FAMILY_IMXRT106x + +config FLEXIO1_CLK_PLL5 + bool "PLL5" + +endif # ARCH_FAMILY_IMXRT105x || ARCH_FAMILY_IMXRT106x + +config FLEXIO1_CLK_PLL3_SW + bool "PLL3_SW_CLK" + +endchoice # FLEXIO1 Clock Source + +config FLEXIO1_CLK + int + default 0 if FLEXIO1_CLK_PLL4 + default 1 if FLEXIO1_CLK_PLL3_PFD2 + default 2 if FLEXIO1_CLK_PLL5 + default 3 if FLEXIO1_CLK_PLL3_SW + +config FLEXIO1_PRED_DIVIDER + int "FLEXIO1 Predivider" + range 1 8 + default 2 + ---help--- + The clock source predivider value (FLEXIO1_PRED). [1-8] + +config FLEXIO1_PODF_DIVIDER + int "FLEXIO1 Divider" + range 1 8 + default 8 + ---help--- + The clock source divider value (FLEXIO1_PODF). [1-8] + +endif # IMXRT_FLEXIO1 + +if ARCH_FAMILY_IMXRT105x || ARCH_FAMILY_IMXRT106x + +config IMXRT_FLEXIO2 + bool "FLEXIO2" + default n + select IMXRT_FLEXIO + +if IMXRT_FLEXIO2 || IMXRT_FLEXIO3 + +choice + prompt "FLEXIO2 Clock Source" + default FLEXIO2_CLK_PLL3_SW + ---help--- + The clock source that drives the FLEXIO. + Used to set FLEXIO2_CLK_SEL. + +config FLEXIO2_CLK_PLL4 + bool "PLL4" + +config FLEXIO2_CLK_PLL3_PFD2 + bool "PLL3_PFD2" + +config FLEXIO2_CLK_PLL5 + bool "PLL5" + +config FLEXIO2_CLK_PLL3_SW + bool "PLL3_SW_CLK" + +endchoice # FLEXIO2 Clock Source + +config FLEXIO2_CLK + int + default 0 if FLEXIO2_CLK_PLL4 + default 1 if FLEXIO2_CLK_PLL3_PFD2 + default 2 if FLEXIO2_CLK_PLL5 + default 3 if FLEXIO2_CLK_PLL3_SW + +config FLEXIO2_PRED_DIVIDER + int + prompt "FLEXIO2 Predivider" + range 1 8 + default 2 + ---help--- + The clock source predivider value (FLEXIO2_PRED). [1-8] + +config FLEXIO2_PODF_DIVIDER + int + prompt "FLEXIO2 Divider" + range 1 8 + default 8 + ---help--- + The clock source divider value (FLEXIO2_PODF). [1-8] + +endif # IMXRT_FLEXIO2 || IMXRT_FLEXIO3 + +if ARCH_FAMILY_IMXRT106x + +config IMXRT_FLEXIO3 + bool "FLEXIO3" + default n + select IMXRT_FLEXIO + ---help--- + FLEXIO3 uses the FLEXIO2 clock settings. + +endif # ARCH_FAMILY_IMXRT106x +endif # ARCH_FAMILY_IMXRT105x || ARCH_FAMILY_IMXRT106x + endmenu # FlexIO Peripherals menu "LPUART Peripherals" @@ -369,17 +495,17 @@ menuconfig IMXRT_LPSPI1 default n select IMXRT_LPSPI -config IMXRT_LPSPI2 +menuconfig IMXRT_LPSPI2 bool "LPSPI2" default n select IMXRT_LPSPI -config IMXRT_LPSPI3 +menuconfig IMXRT_LPSPI3 bool "LPSPI3" default n select IMXRT_LPSPI -config IMXRT_LPSPI4 +menuconfig IMXRT_LPSPI4 bool "LPSPI4" default n select IMXRT_LPSPI @@ -719,7 +845,7 @@ endif # DEBUG_SENSORS endif # IMXRT_ENC4 -endif # ARCH_FAMILY_IMXRT105x | ARCH_FAMILY_IMXRT106x +endif # ARCH_FAMILY_IMXRT105x || ARCH_FAMILY_IMXRT106x endmenu # ENC Peripherals diff --git a/arch/arm/src/imxrt/hardware/rt102x/imxrt102x_ccm.h b/arch/arm/src/imxrt/hardware/rt102x/imxrt102x_ccm.h index fb0310ce552..73e20e86af7 100644 --- a/arch/arm/src/imxrt/hardware/rt102x/imxrt102x_ccm.h +++ b/arch/arm/src/imxrt/hardware/rt102x/imxrt102x_ccm.h @@ -155,6 +155,7 @@ /* Helper Macros *************************************************************/ #define CCM_PODF_FROM_DIVISOR(n) ((n)-1) /* PODF Values are divisor-1 */ +#define CCM_PRED_FROM_DIVISOR(n) ((n)-1) /* PRED Values are divisor-1 */ /* Register bit definitions **************************************************/ @@ -313,12 +314,13 @@ # define CCM_CSCMR2_CAN_CLK_SEL_OSC_CLK ((uint32_t)(1) << CCM_CSCMR2_CAN_CLK_SEL_SHIFT) # define CCM_CSCMR2_CAN_CLK_SEL_PLL3_SW_80 ((uint32_t)(2) << CCM_CSCMR2_CAN_CLK_SEL_SHIFT) /* Bits 10-18: Reserved */ -#define CCM_CSCMR2_FLEXIO2_CLK_SEL_SHIFT (19) /* Bits 19-20: Selector for flexio2 clock multiplexer */ -#define CCM_CSCMR2_FLEXIO2_CLK_SEL_MASK (0x3 << CCM_CSCMR2_FLEXIO2_CLK_SEL_SHIFT) -# define CCM_CSCMR2_FLEXIO2_CLK_SEL(n) ((uint32_t)(n) << CCM_CSCMR2_FLEXIO2_CLK_SEL_SHIFT) -# define CCM_CSCMR2_FLEXIO2_CLK_SEL_PLL4 ((uint32_t)(0) << CCM_CSCMR2_FLEXIO2_CLK_SEL_SHIFT) -# define CCM_CSCMR2_FLEXIO2_CLK_SEL_PLL3_PFD2 ((uint32_t)(1) << CCM_CSCMR2_FLEXIO2_CLK_SEL_SHIFT) -# define CCM_CSCMR2_FLEXIO2_CLK_SEL_PLL3_SW ((uint32_t)(3) << CCM_CSCMR2_FLEXIO2_CLK_SEL_SHIFT) + +#define CCM_CSCMR2_FLEXIO1_CLK_SEL_SHIFT (19) /* Bits 19-20: Selector for flexio2 clock multiplexer */ +#define CCM_CSCMR2_FLEXIO1_CLK_SEL_MASK (0x3 << CCM_CSCMR2_FLEXIO1_CLK_SEL_SHIFT) +# define CCM_CSCMR2_FLEXIO1_CLK_SEL(n) ((uint32_t)(n) << CCM_CSCMR2_FLEXIO1_CLK_SEL_SHIFT) +# define CCM_CSCMR2_FLEXIO1_CLK_SEL_PLL4 ((uint32_t)(0) << CCM_CSCMR2_FLEXIO1_CLK_SEL_SHIFT) +# define CCM_CSCMR2_FLEXIO1_CLK_SEL_PLL3_PFD2 ((uint32_t)(1) << CCM_CSCMR2_FLEXIO1_CLK_SEL_SHIFT) +# define CCM_CSCMR2_FLEXIO1_CLK_SEL_PLL3_SW ((uint32_t)(3) << CCM_CSCMR2_FLEXIO1_CLK_SEL_SHIFT) /* Bits 21-31: Reserved */ /* Serial Clock Divider Register 1 */ @@ -351,20 +353,22 @@ #define CCM_CS1CDR_SAI1_CLK_PRED_SHIFT (6) /* Bits 6-8: Divider for sai1 clock pred */ #define CCM_CS1CDR_SAI1_CLK_PRED_MASK (0x7 << CCM_CS1CDR_SAI1_CLK_PRED_SHIFT) # define CCM_CS1CDR_SAI1_CLK_PRED(n) ((uint32_t)(n) << CCM_CS1CDR_SAI1_CLK_PRED_SHIFT) -#define CCM_CS1CDR_FLEXIO2_CLK_PRED_SHIFT (9) /* Bits 9-11: Divider for flexio2 clock */ -#define CCM_CS1CDR_FLEXIO2_CLK_PRED_MASK (0x7 << CCM_CS1CDR_FLEXIO2_CLK_PRED_SHIFT) -# define CCM_CS1CDR_FLEXIO2_CLK_PRED(n) ((uint32_t)(n) << CCM_CS1CDR_FLEXIO2_CLK_PRED_SHIFT) +#define CCM_CS1CDR_FLEXIO1_CLK_PRED_SHIFT (9) /* Bits 9-11: Divider for flexio2 clock */ +#define CCM_CS1CDR_FLEXIO1_CLK_PRED_MASK (0x7 << CCM_CS1CDR_FLEXIO1_CLK_PRED_SHIFT) +# define CCM_CS1CDR_FLEXIO1_CLK_PRED(n) ((uint32_t)(n) << CCM_CS1CDR_FLEXIO1_CLK_PRED_SHIFT) /* Bits 12-15: Reserved */ + #define CCM_CS1CDR_SAI3_CLK_PODF_SHIFT (16) /* Bits 16-21: Divider for sai3 clock podf */ #define CCM_CS1CDR_SAI3_CLK_PODF_MASK (0x3f << CCM_CS1CDR_SAI3_CLK_PODF_SHIFT) # define CCM_CS1CDR_SAI3_CLK_PODF(n) ((uint32_t)(n) << CCM_CS1CDR_SAI3_CLK_PODF_SHIFT) #define CCM_CS1CDR_SAI3_CLK_PRED_SHIFT (22) /* Bits 22-24: Divider for sai3 clock pred */ #define CCM_CS1CDR_SAI3_CLK_PRED_MASK (0x7 << CCM_CS1CDR_SAI3_CLK_PRED_SHIFT) # define CCM_CS1CDR_SAI3_CLK_PRED(n) ((uint32_t)(n) << CCM_CS1CDR_SAI3_CLK_PRED_SHIFT) -#define CCM_CS1CDR_FLEXIO2_CLK_PODF_SHIFT (25) /* Bits 25-27: Divider for flexio2 clock */ -#define CCM_CS1CDR_FLEXIO2_CLK_PODF_MASK (0x7 << CCM_CS1CDR_FLEXIO2_CLK_PODF_SHIFT) -# define CCM_CS1CDR_FLEXIO2_CLK_PODF(n) ((uint32_t)(n) << CCM_CS1CDR_FLEXIO2_CLK_PODF_SHIFT) +#define CCM_CS1CDR_FLEXIO1_CLK_PODF_SHIFT (25) /* Bits 25-27: Divider for flexio2 clock */ +#define CCM_CS1CDR_FLEXIO1_CLK_PODF_MASK (0x7 << CCM_CS1CDR_FLEXIO1_CLK_PODF_SHIFT) +# define CCM_CS1CDR_FLEXIO1_CLK_PODF(n) ((uint32_t)(n) << CCM_CS1CDR_FLEXIO1_CLK_PODF_SHIFT) /* Bits 28-31: Reserved */ + /* Clock Divider Register 2 */ #define CCM_CS2CDR_SAI2_CLK_PODF_SHIFT (0) /* Bits 0-5: Divider for sai2 clock podf */ @@ -717,7 +721,7 @@ #define CCM_CMEOR_MOD_EN_OV_CAN1_CPI (1 << 30) /* Bit 30: Overide clock enable signal from CAN1 */ /* Bit 31: Reserved */ -/* Analog System PLL (2) Control Register **********************************/ +/* Analog System PLL (2) Control Register ***********************************/ #define CCM_ANALOG_PLL_SYS_DIV_SELECT_SHIFT (0) /* Bits 0: This field controls the PLL loop divider 20 or 22 */ #define CCM_ANALOG_PLL_SYS_DIV_SELECT_MASK (0x3 << CCM_ANALOG_PLL_SYS_DIV_SELECT_SHIFT) @@ -735,7 +739,7 @@ /* Bits 17-30 Reserved */ #define CCM_ANALOG_PLL_SYS_LOCK (1 << 31) /* Bit 31: PLL is currently locked */ -/* Analog USB1 480MHz PLL (3) Control Register **********************************/ +/* Analog USB1 480MHz PLL (3) Control Register *******************************/ /* Bit 0: Reserved */ #define CCM_ANALOG_PLL_USB1_DIV_SELECT_SHIFT (1) /* Bit 1: This field controls the PLL loop divider 20 or 22 */ #define CCM_ANALOG_PLL_USB1_DIV_SELECT(n) ((uint32_t)(n) << CCM_ANALOG_PLL_USB1_DIV_SELECT_SHIFT) diff --git a/arch/arm/src/imxrt/hardware/rt105x/imxrt105x_ccm.h b/arch/arm/src/imxrt/hardware/rt105x/imxrt105x_ccm.h index c154ea067cc..bc0c8fc1a57 100644 --- a/arch/arm/src/imxrt/hardware/rt105x/imxrt105x_ccm.h +++ b/arch/arm/src/imxrt/hardware/rt105x/imxrt105x_ccm.h @@ -160,9 +160,10 @@ #define IMXRT_CCM_ANALOG_MISC1 (IMXRT_ANATOP_BASE + IMXRT_CCM_ANALOG_MISC1_OFFSET) #define IMXRT_CCM_ANALOG_MISC2 (IMXRT_ANATOP_BASE + IMXRT_CCM_ANALOG_MISC2_OFFSET) -/* Helper Macros *********************************************************************************/ +/* Helper Macros ********************************************************************************************/ #define CCM_PODF_FROM_DIVISOR(n) ((n)-1) /* PODF Values are divisor-1 */ +#define CCM_PRED_FROM_DIVISOR(n) ((n)-1) /* PRED Values are divisor-1 */ /* Register bit definitions *********************************************************************************/ diff --git a/arch/arm/src/imxrt/hardware/rt106x/imxrt106x_ccm.h b/arch/arm/src/imxrt/hardware/rt106x/imxrt106x_ccm.h index 39b4fb20d4e..f15e660b878 100644 --- a/arch/arm/src/imxrt/hardware/rt106x/imxrt106x_ccm.h +++ b/arch/arm/src/imxrt/hardware/rt106x/imxrt106x_ccm.h @@ -160,9 +160,10 @@ #define IMXRT_CCM_ANALOG_MISC1 (IMXRT_ANATOP_BASE + IMXRT_CCM_ANALOG_MISC1_OFFSET) #define IMXRT_CCM_ANALOG_MISC2 (IMXRT_ANATOP_BASE + IMXRT_CCM_ANALOG_MISC2_OFFSET) -/* Helper Macros *********************************************************************************/ +/* Helper Macros ********************************************************************************************/ #define CCM_PODF_FROM_DIVISOR(n) ((n)-1) /* PODF Values are divisor-1 */ +#define CCM_PRED_FROM_DIVISOR(n) ((n)-1) /* PRED Values are divisor-1 */ /* Register bit definitions *********************************************************************************/ diff --git a/arch/arm/src/imxrt/imxrt_clockconfig.c b/arch/arm/src/imxrt/imxrt_clockconfig.c index ec29f107254..e883f984479 100644 --- a/arch/arm/src/imxrt/imxrt_clockconfig.c +++ b/arch/arm/src/imxrt/imxrt_clockconfig.c @@ -228,7 +228,6 @@ static void imxrt_lcd_clockconfig(void) ****************************************************************************/ static void imxrt_pllsetup(void) - { #ifdef CONFIG_ARCH_FAMILY_IMXRT102x uint32_t pll2reg; @@ -541,6 +540,63 @@ void imxrt_clockconfig(void) reg |= CCM_CSCDR1_UART_CLK_PODF(CCM_PODF_FROM_DIVISOR(1)); putreg32(reg, IMXRT_CCM_CSCDR1); +#ifdef CONFIG_IMXRT_FLEXIO1 +#ifdef CONFIG_ARCH_FAMILY_IMXRT102x + /* Set FlEXIO1 source */ + + reg = getreg32(IMXRT_CCM_CSCMR2); + reg &= ~CCM_CSCMR2_FLEXIO1_CLK_SEL_MASK; + reg |= CCM_CSCMR2_FLEXIO1_CLK_SEL(CONFIG_FLEXIO1_CLK); + putreg32(reg, IMXRT_CCM_CSCMR2); + + /* Set FlEXIO1 divider */ + + reg = getreg32(IMXRT_CCM_CS1CDR); + reg &= ~(CCM_CS1CDR_FLEXIO1_CLK_PODF_MASK | \ + CCM_CS1CDR_FLEXIO1_CLK_PRED_MASK); + reg |= CCM_CS1CDR_FLEXIO1_CLK_PODF + (CCM_PODF_FROM_DIVISOR(CONFIG_FLEXIO1_PODF_DIVIDER)); + reg |= CCM_CS1CDR_FLEXIO1_CLK_PRED + (CCM_PRED_FROM_DIVISOR(CONFIG_FLEXIO1_PRED_DIVIDER)); + putreg32(reg, IMXRT_CCM_CS1CDR); + +#elif (defined(CONFIG_ARCH_FAMILY_IMXRT105x) || defined(CONFIG_ARCH_FAMILY_IMXRT106x)) + /* Set FlEXIO1 source & divider */ + + reg = getreg32(IMXRT_CCM_CDCDR); + reg &= ~(CCM_CDCDR_FLEXIO1_CLK_SEL_MASK | CCM_CDCDR_FLEXIO1_CLK_PODF_MASK | \ + CCM_CDCDR_FLEXIO1_CLK_PRED_MASK); + reg |= CCM_CDCDR_FLEXIO1_CLK_SEL(CONFIG_FLEXIO1_CLK); + reg |= CCM_CDCDR_FLEXIO1_CLK_PODF + (CCM_PODF_FROM_DIVISOR(CONFIG_FLEXIO1_PODF_DIVIDER)); + reg |= CCM_CDCDR_FLEXIO1_CLK_PRED + (CCM_PRED_FROM_DIVISOR(CONFIG_FLEXIO1_PRED_DIVIDER)); + putreg32(reg, IMXRT_CCM_CDCDR); + +#endif /* CONFIG_ARCH_FAMILY_IMXRT102x */ +#endif /* CONFIG_IMXRT_FLEXIO1 */ + +#if (defined(CONFIG_IMXRT_FLEXIO2) || defined(CONFIG_IMXRT_FLEXIO3)) + /* Set FlEXIO2 source */ + + reg = getreg32(IMXRT_CCM_CSCMR2); + reg &= ~CCM_CSCMR2_FLEXIO2_CLK_SEL_MASK; + reg |= CCM_CSCMR2_FLEXIO2_CLK_SEL(CONFIG_FLEXIO2_CLK); + putreg32(reg, IMXRT_CCM_CSCMR2); + + /* Set FlEXIO2 divider */ + + reg = getreg32(IMXRT_CCM_CS1CDR); + reg &= ~(CCM_CS1CDR_FLEXIO2_CLK_PODF_MASK | \ + CCM_CS1CDR_FLEXIO2_CLK_PRED_MASK); + reg |= CCM_CS1CDR_FLEXIO2_CLK_PODF + (CCM_PODF_FROM_DIVISOR(CONFIG_FLEXIO2_PODF_DIVIDER)); + reg |= CCM_CS1CDR_FLEXIO2_CLK_PRED + (CCM_PRED_FROM_DIVISOR(CONFIG_FLEXIO2_PRED_DIVIDER)); + putreg32(reg, IMXRT_CCM_CS1CDR); + +#endif /* CONFIG_IMXRT_FLEXIO2 */ + #ifdef CONFIG_IMXRT_LPI2C /* Set LPI2C source to PLL3 60M */