From 782013d0ff2c9f076952c0e172bfcb7016699d5f Mon Sep 17 00:00:00 2001 From: Keith Packard Date: Tue, 2 Aug 2016 16:32:43 -0700 Subject: [PATCH] altos/stmf0: Hook up clock output support This was used to try and not have two xtals on telemini, but failed because the provided clock has too much noise. Signed-off-by: Keith Packard --- src/stmf0/ao_timer.c | 36 +++++++++++++++++++++++++++--------- src/stmf0/stm32f0.h | 9 +++++++++ 2 files changed, 36 insertions(+), 9 deletions(-) diff --git a/src/stmf0/ao_timer.c b/src/stmf0/ao_timer.c index 2cb994c3..5c05e4f1 100644 --- a/src/stmf0/ao_timer.c +++ b/src/stmf0/ao_timer.c @@ -176,13 +176,12 @@ ao_clock_normal_start(void) while (!(stm_rcc.cr & (1 << STM_RCC_CR_HSERDY))) asm("nop"); -#ifdef STM_PLLSRC /* Disable the PLL */ stm_rcc.cr &= ~(1 << STM_RCC_CR_PLLON); while (stm_rcc.cr & (1 << STM_RCC_CR_PLLRDY)) asm("nop"); - /* PLLVCO to 48MHz (for USB) -> PLLMUL = 3 */ + /* Set multiplier */ cfgr = stm_rcc.cfgr; cfgr &= ~(STM_RCC_CFGR_PLLMUL_MASK << STM_RCC_CFGR_PLLMUL); cfgr |= (AO_RCC_CFGR_PLLMUL << STM_RCC_CFGR_PLLMUL); @@ -192,8 +191,8 @@ ao_clock_normal_start(void) cfgr |= (STM_RCC_CFGR_PLLSRC_TARGET_CLOCK << STM_RCC_CFGR_PLLSRC); stm_rcc.cfgr = cfgr; - /* Disable pre divider */ - stm_rcc.cfgr2 = (STM_RCC_CFGR2_PREDIV_1 << STM_RCC_CFGR2_PREDIV); + /* Set pre divider */ + stm_rcc.cfgr2 = (AO_RCC_CFGR2_PLLDIV << STM_RCC_CFGR2_PREDIV); /* Enable the PLL and wait for it */ stm_rcc.cr |= (1 << STM_RCC_CR_PLLON); @@ -202,9 +201,6 @@ ao_clock_normal_start(void) #endif -#endif - - #if AO_HSI48 #define STM_RCC_CFGR_SWS_TARGET_CLOCK STM_RCC_CFGR_SWS_HSI48 #define STM_RCC_CFGR_SW_TARGET_CLOCK STM_RCC_CFGR_SW_HSI48 @@ -226,6 +222,8 @@ ao_clock_normal_start(void) #define STM_PLLSRC STM_HSI #define STM_RCC_CFGR_PLLSRC_TARGET_CLOCK 0 #endif + + } static void @@ -303,14 +301,34 @@ ao_clock_init(void) /* Clear reset flags */ stm_rcc.csr |= (1 << STM_RCC_CSR_RMVF); +#ifdef AO_MCO_PORT + cfgr = stm_rcc.cfgr; + + /* Send PLL clock to MCO */ + cfgr &= ~(STM_RCC_CFGR_MCO_MASK << STM_RCC_CFGR_MCO); + cfgr |= (STM_RCC_CFGR_MCO_PLLCLK << STM_RCC_CFGR_MCO); + + /* Divide by 1 */ + cfgr &= ~(STM_RCC_CFGR_MCOPRE_DIV_MASK << STM_RCC_CFGR_MCOPRE); + cfgr |= (STM_RCC_CFGR_MCOPRE_DIV_1 << STM_RCC_CFGR_MCOPRE); + + /* Don't divide PLL */ + cfgr |= (1 << STM_RCC_CFGR_PLL_NODIV); + + stm_rcc.cfgr = cfgr; + + ao_enable_port(AO_MCO_PORT); + stm_ospeedr_set(AO_MCO_PORT, AO_MCO_PIN, STM_OSPEEDR_HIGH); + stm_afr_set(AO_MCO_PORT, AO_MCO_PIN, AO_MCO_AF); +#endif + #if DEBUG_THE_CLOCK /* Output SYSCLK on PA8 for measurments */ stm_rcc.ahbenr |= (1 << STM_RCC_AHBENR_GPIOAEN); stm_afr_set(&stm_gpioa, 8, STM_AFR_AF0); - stm_moder_set(&stm_gpioa, 8, STM_MODER_ALTERNATE); - stm_ospeedr_set(&stm_gpioa, 8, STM_OSPEEDR_40MHz); + stm_ospeedr_set(&stm_gpioa, 8, STM_OSPEEDR_HIGH); stm_rcc.cfgr |= (STM_RCC_CFGR_MCOPRE_DIV_1 << STM_RCC_CFGR_MCOPRE); stm_rcc.cfgr |= (STM_RCC_CFGR_MCOSEL_HSE << STM_RCC_CFGR_MCOSEL); diff --git a/src/stmf0/stm32f0.h b/src/stmf0/stm32f0.h index d528e492..054200e0 100644 --- a/src/stmf0/stm32f0.h +++ b/src/stmf0/stm32f0.h @@ -313,6 +313,15 @@ extern struct stm_rcc stm_rcc; #define STM_RCC_CFGR_MCO (24) # define STM_RCC_CFGR_MCO_DISABLE 0 +# define STM_RCC_CFGR_MCO_RC 1 +# define STM_RCC_CFGR_MCO_LSI 2 +# define STM_RCC_CFGR_MCO_LSE 3 +# define STM_RCC_CFGR_MCO_SYSCLK 4 +# define STM_RCC_CFGR_MCO_HSI 5 +# define STM_RCC_CFGR_MCO_HSE 6 +# define STM_RCC_CFGR_MCO_PLLCLK 7 +# define STM_RCC_CFGR_MCO_HSI48 8 +# define STM_RCC_CFGR_MCO_MASK (0xf) #define STM_RCC_CFGR_PLLMUL (18) #define STM_RCC_CFGR_PLLMUL_2 0 -- 2.30.2