1 // SPDX-License-Identifier: GPL-2.0+ 2 /* 3 * Copyright (C) 2017, STMicroelectronics - All Rights Reserved 4 * Author(s): Vikas Manocha, <vikas.manocha@st.com> for STMicroelectronics. 5 */ 6 7 #include <common.h> 8 #include <clk-uclass.h> 9 #include <dm.h> 10 #include <stm32_rcc.h> 11 12 #include <asm/io.h> 13 #include <asm/arch/stm32.h> 14 #include <asm/arch/stm32_pwr.h> 15 16 #include <dt-bindings/mfd/stm32f7-rcc.h> 17 18 #define RCC_CR_HSION BIT(0) 19 #define RCC_CR_HSEON BIT(16) 20 #define RCC_CR_HSERDY BIT(17) 21 #define RCC_CR_HSEBYP BIT(18) 22 #define RCC_CR_CSSON BIT(19) 23 #define RCC_CR_PLLON BIT(24) 24 #define RCC_CR_PLLRDY BIT(25) 25 #define RCC_CR_PLLSAION BIT(28) 26 #define RCC_CR_PLLSAIRDY BIT(29) 27 28 #define RCC_PLLCFGR_PLLM_MASK GENMASK(5, 0) 29 #define RCC_PLLCFGR_PLLN_MASK GENMASK(14, 6) 30 #define RCC_PLLCFGR_PLLP_MASK GENMASK(17, 16) 31 #define RCC_PLLCFGR_PLLQ_MASK GENMASK(27, 24) 32 #define RCC_PLLCFGR_PLLSRC BIT(22) 33 #define RCC_PLLCFGR_PLLM_SHIFT 0 34 #define RCC_PLLCFGR_PLLN_SHIFT 6 35 #define RCC_PLLCFGR_PLLP_SHIFT 16 36 #define RCC_PLLCFGR_PLLQ_SHIFT 24 37 38 #define RCC_CFGR_AHB_PSC_MASK GENMASK(7, 4) 39 #define RCC_CFGR_APB1_PSC_MASK GENMASK(12, 10) 40 #define RCC_CFGR_APB2_PSC_MASK GENMASK(15, 13) 41 #define RCC_CFGR_SW0 BIT(0) 42 #define RCC_CFGR_SW1 BIT(1) 43 #define RCC_CFGR_SW_MASK GENMASK(1, 0) 44 #define RCC_CFGR_SW_HSI 0 45 #define RCC_CFGR_SW_HSE RCC_CFGR_SW0 46 #define RCC_CFGR_SW_PLL RCC_CFGR_SW1 47 #define RCC_CFGR_SWS0 BIT(2) 48 #define RCC_CFGR_SWS1 BIT(3) 49 #define RCC_CFGR_SWS_MASK GENMASK(3, 2) 50 #define RCC_CFGR_SWS_HSI 0 51 #define RCC_CFGR_SWS_HSE RCC_CFGR_SWS0 52 #define RCC_CFGR_SWS_PLL RCC_CFGR_SWS1 53 #define RCC_CFGR_HPRE_SHIFT 4 54 #define RCC_CFGR_PPRE1_SHIFT 10 55 #define RCC_CFGR_PPRE2_SHIFT 13 56 57 #define RCC_PLLSAICFGR_PLLSAIN_MASK GENMASK(14, 6) 58 #define RCC_PLLSAICFGR_PLLSAIP_MASK GENMASK(17, 16) 59 #define RCC_PLLSAICFGR_PLLSAIQ_MASK GENMASK(27, 24) 60 #define RCC_PLLSAICFGR_PLLSAIR_MASK GENMASK(30, 28) 61 #define RCC_PLLSAICFGR_PLLSAIN_SHIFT 6 62 #define RCC_PLLSAICFGR_PLLSAIP_SHIFT 16 63 #define RCC_PLLSAICFGR_PLLSAIQ_SHIFT 24 64 #define RCC_PLLSAICFGR_PLLSAIR_SHIFT 28 65 #define RCC_PLLSAICFGR_PLLSAIP_4 BIT(16) 66 #define RCC_PLLSAICFGR_PLLSAIQ_4 BIT(26) 67 #define RCC_PLLSAICFGR_PLLSAIR_3 BIT(29) | BIT(28) 68 69 #define RCC_DCKCFGRX_TIMPRE BIT(24) 70 #define RCC_DCKCFGRX_CK48MSEL BIT(27) 71 #define RCC_DCKCFGRX_SDMMC1SEL BIT(28) 72 #define RCC_DCKCFGR2_SDMMC2SEL BIT(29) 73 74 #define RCC_DCKCFGR_PLLSAIDIVR_SHIFT 16 75 #define RCC_DCKCFGR_PLLSAIDIVR_MASK GENMASK(17, 16) 76 #define RCC_DCKCFGR_PLLSAIDIVR_2 0 77 78 /* 79 * RCC AHB1ENR specific definitions 80 */ 81 #define RCC_AHB1ENR_ETHMAC_EN BIT(25) 82 #define RCC_AHB1ENR_ETHMAC_TX_EN BIT(26) 83 #define RCC_AHB1ENR_ETHMAC_RX_EN BIT(27) 84 85 /* 86 * RCC APB1ENR specific definitions 87 */ 88 #define RCC_APB1ENR_TIM2EN BIT(0) 89 #define RCC_APB1ENR_PWREN BIT(28) 90 91 /* 92 * RCC APB2ENR specific definitions 93 */ 94 #define RCC_APB2ENR_SYSCFGEN BIT(14) 95 #define RCC_APB2ENR_SAI1EN BIT(22) 96 97 enum pllsai_div { 98 PLLSAIP, 99 PLLSAIQ, 100 PLLSAIR, 101 }; 102 103 static const struct stm32_clk_info stm32f4_clk_info = { 104 /* 180 MHz */ 105 .sys_pll_psc = { 106 .pll_n = 360, 107 .pll_p = 2, 108 .pll_q = 8, 109 .ahb_psc = AHB_PSC_1, 110 .apb1_psc = APB_PSC_4, 111 .apb2_psc = APB_PSC_2, 112 }, 113 .has_overdrive = false, 114 .v2 = false, 115 }; 116 117 static const struct stm32_clk_info stm32f7_clk_info = { 118 /* 200 MHz */ 119 .sys_pll_psc = { 120 .pll_n = 400, 121 .pll_p = 2, 122 .pll_q = 8, 123 .ahb_psc = AHB_PSC_1, 124 .apb1_psc = APB_PSC_4, 125 .apb2_psc = APB_PSC_2, 126 }, 127 .has_overdrive = true, 128 .v2 = true, 129 }; 130 131 struct stm32_clk { 132 struct stm32_rcc_regs *base; 133 struct stm32_pwr_regs *pwr_regs; 134 struct stm32_clk_info info; 135 unsigned long hse_rate; 136 }; 137 138 #ifdef CONFIG_VIDEO_STM32 139 static const u8 plldivr_table[] = { 0, 0, 2, 3, 4, 5, 6, 7 }; 140 #endif 141 static const u8 pllsaidivr_table[] = { 2, 4, 8, 16 }; 142 143 static int configure_clocks(struct udevice *dev) 144 { 145 struct stm32_clk *priv = dev_get_priv(dev); 146 struct stm32_rcc_regs *regs = priv->base; 147 struct stm32_pwr_regs *pwr = priv->pwr_regs; 148 struct pll_psc *sys_pll_psc = &priv->info.sys_pll_psc; 149 150 /* Reset RCC configuration */ 151 setbits_le32(®s->cr, RCC_CR_HSION); 152 writel(0, ®s->cfgr); /* Reset CFGR */ 153 clrbits_le32(®s->cr, (RCC_CR_HSEON | RCC_CR_CSSON 154 | RCC_CR_PLLON | RCC_CR_PLLSAION)); 155 writel(0x24003010, ®s->pllcfgr); /* Reset value from RM */ 156 clrbits_le32(®s->cr, RCC_CR_HSEBYP); 157 writel(0, ®s->cir); /* Disable all interrupts */ 158 159 /* Configure for HSE+PLL operation */ 160 setbits_le32(®s->cr, RCC_CR_HSEON); 161 while (!(readl(®s->cr) & RCC_CR_HSERDY)) 162 ; 163 164 setbits_le32(®s->cfgr, (( 165 sys_pll_psc->ahb_psc << RCC_CFGR_HPRE_SHIFT) 166 | (sys_pll_psc->apb1_psc << RCC_CFGR_PPRE1_SHIFT) 167 | (sys_pll_psc->apb2_psc << RCC_CFGR_PPRE2_SHIFT))); 168 169 /* Configure the main PLL */ 170 setbits_le32(®s->pllcfgr, RCC_PLLCFGR_PLLSRC); /* pll source HSE */ 171 clrsetbits_le32(®s->pllcfgr, RCC_PLLCFGR_PLLM_MASK, 172 sys_pll_psc->pll_m << RCC_PLLCFGR_PLLM_SHIFT); 173 clrsetbits_le32(®s->pllcfgr, RCC_PLLCFGR_PLLN_MASK, 174 sys_pll_psc->pll_n << RCC_PLLCFGR_PLLN_SHIFT); 175 clrsetbits_le32(®s->pllcfgr, RCC_PLLCFGR_PLLP_MASK, 176 ((sys_pll_psc->pll_p >> 1) - 1) << RCC_PLLCFGR_PLLP_SHIFT); 177 clrsetbits_le32(®s->pllcfgr, RCC_PLLCFGR_PLLQ_MASK, 178 sys_pll_psc->pll_q << RCC_PLLCFGR_PLLQ_SHIFT); 179 180 /* configure SDMMC clock */ 181 if (priv->info.v2) { /*stm32f7 case */ 182 /* select PLLQ as 48MHz clock source */ 183 clrbits_le32(®s->dckcfgr2, RCC_DCKCFGRX_CK48MSEL); 184 185 /* select 48MHz as SDMMC1 clock source */ 186 clrbits_le32(®s->dckcfgr2, RCC_DCKCFGRX_SDMMC1SEL); 187 188 /* select 48MHz as SDMMC2 clock source */ 189 clrbits_le32(®s->dckcfgr2, RCC_DCKCFGR2_SDMMC2SEL); 190 } else { /* stm32f4 case */ 191 /* select PLLQ as 48MHz clock source */ 192 clrbits_le32(®s->dckcfgr, RCC_DCKCFGRX_CK48MSEL); 193 194 /* select 48MHz as SDMMC1 clock source */ 195 clrbits_le32(®s->dckcfgr, RCC_DCKCFGRX_SDMMC1SEL); 196 } 197 198 #ifdef CONFIG_VIDEO_STM32 199 /* 200 * Configure the SAI PLL to generate LTDC pixel clock 201 */ 202 clrsetbits_le32(®s->pllsaicfgr, RCC_PLLSAICFGR_PLLSAIR_MASK, 203 RCC_PLLSAICFGR_PLLSAIR_3); 204 clrsetbits_le32(®s->pllsaicfgr, RCC_PLLSAICFGR_PLLSAIN_MASK, 205 195 << RCC_PLLSAICFGR_PLLSAIN_SHIFT); 206 207 clrsetbits_le32(®s->dckcfgr, RCC_DCKCFGR_PLLSAIDIVR_MASK, 208 RCC_DCKCFGR_PLLSAIDIVR_2 << RCC_DCKCFGR_PLLSAIDIVR_SHIFT); 209 #endif 210 /* Enable the main PLL */ 211 setbits_le32(®s->cr, RCC_CR_PLLON); 212 while (!(readl(®s->cr) & RCC_CR_PLLRDY)) 213 ; 214 215 #ifdef CONFIG_VIDEO_STM32 216 /* Enable the SAI PLL */ 217 setbits_le32(®s->cr, RCC_CR_PLLSAION); 218 while (!(readl(®s->cr) & RCC_CR_PLLSAIRDY)) 219 ; 220 #endif 221 setbits_le32(®s->apb1enr, RCC_APB1ENR_PWREN); 222 223 if (priv->info.has_overdrive) { 224 /* 225 * Enable high performance mode 226 * System frequency up to 200 MHz 227 */ 228 setbits_le32(&pwr->cr1, PWR_CR1_ODEN); 229 /* Infinite wait! */ 230 while (!(readl(&pwr->csr1) & PWR_CSR1_ODRDY)) 231 ; 232 /* Enable the Over-drive switch */ 233 setbits_le32(&pwr->cr1, PWR_CR1_ODSWEN); 234 /* Infinite wait! */ 235 while (!(readl(&pwr->csr1) & PWR_CSR1_ODSWRDY)) 236 ; 237 } 238 239 stm32_flash_latency_cfg(5); 240 clrbits_le32(®s->cfgr, (RCC_CFGR_SW0 | RCC_CFGR_SW1)); 241 setbits_le32(®s->cfgr, RCC_CFGR_SW_PLL); 242 243 while ((readl(®s->cfgr) & RCC_CFGR_SWS_MASK) != 244 RCC_CFGR_SWS_PLL) 245 ; 246 247 #ifdef CONFIG_ETH_DESIGNWARE 248 /* gate the SYSCFG clock, needed to set RMII ethernet interface */ 249 setbits_le32(®s->apb2enr, RCC_APB2ENR_SYSCFGEN); 250 #endif 251 252 return 0; 253 } 254 255 static bool stm32_clk_get_ck48msel(struct stm32_clk *priv) 256 { 257 struct stm32_rcc_regs *regs = priv->base; 258 259 if (priv->info.v2) /*stm32f7 case */ 260 return readl(®s->dckcfgr2) & RCC_DCKCFGRX_CK48MSEL; 261 else 262 263 return readl(®s->dckcfgr) & RCC_DCKCFGRX_CK48MSEL; 264 } 265 266 static unsigned long stm32_clk_get_pllsai_vco_rate(struct stm32_clk *priv) 267 { 268 struct stm32_rcc_regs *regs = priv->base; 269 u16 pllm, pllsain; 270 271 pllm = (readl(®s->pllcfgr) & RCC_PLLCFGR_PLLM_MASK); 272 pllsain = ((readl(®s->pllsaicfgr) & RCC_PLLSAICFGR_PLLSAIN_MASK) 273 >> RCC_PLLSAICFGR_PLLSAIN_SHIFT); 274 275 return ((priv->hse_rate / pllm) * pllsain); 276 } 277 278 static unsigned long stm32_clk_get_pllsai_rate(struct stm32_clk *priv, 279 enum pllsai_div output) 280 { 281 struct stm32_rcc_regs *regs = priv->base; 282 u16 pll_div_output; 283 284 switch (output) { 285 case PLLSAIP: 286 pll_div_output = ((((readl(®s->pllsaicfgr) 287 & RCC_PLLSAICFGR_PLLSAIP_MASK) 288 >> RCC_PLLSAICFGR_PLLSAIP_SHIFT) + 1) << 1); 289 break; 290 case PLLSAIQ: 291 pll_div_output = (readl(®s->pllsaicfgr) 292 & RCC_PLLSAICFGR_PLLSAIQ_MASK) 293 >> RCC_PLLSAICFGR_PLLSAIQ_SHIFT; 294 break; 295 case PLLSAIR: 296 pll_div_output = (readl(®s->pllsaicfgr) 297 & RCC_PLLSAICFGR_PLLSAIR_MASK) 298 >> RCC_PLLSAICFGR_PLLSAIR_SHIFT; 299 break; 300 default: 301 pr_err("incorrect PLLSAI output %d\n", output); 302 return -EINVAL; 303 } 304 305 return (stm32_clk_get_pllsai_vco_rate(priv) / pll_div_output); 306 } 307 308 static bool stm32_get_timpre(struct stm32_clk *priv) 309 { 310 struct stm32_rcc_regs *regs = priv->base; 311 u32 val; 312 313 if (priv->info.v2) /*stm32f7 case */ 314 val = readl(®s->dckcfgr2); 315 else 316 val = readl(®s->dckcfgr); 317 /* get timer prescaler */ 318 return !!(val & RCC_DCKCFGRX_TIMPRE); 319 } 320 321 static u32 stm32_get_hclk_rate(struct stm32_rcc_regs *regs, u32 sysclk) 322 { 323 u8 shift; 324 /* Prescaler table lookups for clock computation */ 325 u8 ahb_psc_table[16] = { 326 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 3, 4, 6, 7, 8, 9 327 }; 328 329 shift = ahb_psc_table[( 330 (readl(®s->cfgr) & RCC_CFGR_AHB_PSC_MASK) 331 >> RCC_CFGR_HPRE_SHIFT)]; 332 333 return sysclk >> shift; 334 }; 335 336 static u8 stm32_get_apb_shift(struct stm32_rcc_regs *regs, enum apb apb) 337 { 338 /* Prescaler table lookups for clock computation */ 339 u8 apb_psc_table[8] = { 340 0, 0, 0, 0, 1, 2, 3, 4 341 }; 342 343 if (apb == APB1) 344 return apb_psc_table[( 345 (readl(®s->cfgr) & RCC_CFGR_APB1_PSC_MASK) 346 >> RCC_CFGR_PPRE1_SHIFT)]; 347 else /* APB2 */ 348 return apb_psc_table[( 349 (readl(®s->cfgr) & RCC_CFGR_APB2_PSC_MASK) 350 >> RCC_CFGR_PPRE2_SHIFT)]; 351 }; 352 353 static u32 stm32_get_timer_rate(struct stm32_clk *priv, u32 sysclk, 354 enum apb apb) 355 { 356 struct stm32_rcc_regs *regs = priv->base; 357 u8 shift = stm32_get_apb_shift(regs, apb); 358 359 if (stm32_get_timpre(priv)) 360 /* 361 * if APB prescaler is configured to a 362 * division factor of 1, 2 or 4 363 */ 364 switch (shift) { 365 case 0: 366 case 1: 367 case 2: 368 return stm32_get_hclk_rate(regs, sysclk); 369 default: 370 return (sysclk >> shift) * 4; 371 } 372 else 373 /* 374 * if APB prescaler is configured to a 375 * division factor of 1 376 */ 377 if (shift == 0) 378 return sysclk; 379 else 380 return (sysclk >> shift) * 2; 381 }; 382 383 static ulong stm32_clk_get_rate(struct clk *clk) 384 { 385 struct stm32_clk *priv = dev_get_priv(clk->dev); 386 struct stm32_rcc_regs *regs = priv->base; 387 u32 sysclk = 0; 388 u32 vco; 389 u32 sdmmcxsel_bit; 390 u32 saidivr; 391 u32 pllsai_rate; 392 u16 pllm, plln, pllp, pllq; 393 394 if ((readl(®s->cfgr) & RCC_CFGR_SWS_MASK) == 395 RCC_CFGR_SWS_PLL) { 396 pllm = (readl(®s->pllcfgr) & RCC_PLLCFGR_PLLM_MASK); 397 plln = ((readl(®s->pllcfgr) & RCC_PLLCFGR_PLLN_MASK) 398 >> RCC_PLLCFGR_PLLN_SHIFT); 399 pllp = ((((readl(®s->pllcfgr) & RCC_PLLCFGR_PLLP_MASK) 400 >> RCC_PLLCFGR_PLLP_SHIFT) + 1) << 1); 401 pllq = ((readl(®s->pllcfgr) & RCC_PLLCFGR_PLLQ_MASK) 402 >> RCC_PLLCFGR_PLLQ_SHIFT); 403 vco = (priv->hse_rate / pllm) * plln; 404 sysclk = vco / pllp; 405 } else { 406 return -EINVAL; 407 } 408 409 switch (clk->id) { 410 /* 411 * AHB CLOCK: 3 x 32 bits consecutive registers are used : 412 * AHB1, AHB2 and AHB3 413 */ 414 case STM32F7_AHB1_CLOCK(GPIOA) ... STM32F7_AHB3_CLOCK(QSPI): 415 return stm32_get_hclk_rate(regs, sysclk); 416 /* APB1 CLOCK */ 417 case STM32F7_APB1_CLOCK(TIM2) ... STM32F7_APB1_CLOCK(UART8): 418 /* For timer clock, an additionnal prescaler is used*/ 419 switch (clk->id) { 420 case STM32F7_APB1_CLOCK(TIM2): 421 case STM32F7_APB1_CLOCK(TIM3): 422 case STM32F7_APB1_CLOCK(TIM4): 423 case STM32F7_APB1_CLOCK(TIM5): 424 case STM32F7_APB1_CLOCK(TIM6): 425 case STM32F7_APB1_CLOCK(TIM7): 426 case STM32F7_APB1_CLOCK(TIM12): 427 case STM32F7_APB1_CLOCK(TIM13): 428 case STM32F7_APB1_CLOCK(TIM14): 429 return stm32_get_timer_rate(priv, sysclk, APB1); 430 } 431 return (sysclk >> stm32_get_apb_shift(regs, APB1)); 432 433 /* APB2 CLOCK */ 434 case STM32F7_APB2_CLOCK(TIM1) ... STM32F7_APB2_CLOCK(DSI): 435 switch (clk->id) { 436 /* 437 * particular case for SDMMC1 and SDMMC2 : 438 * 48Mhz source clock can be from main PLL or from 439 * PLLSAIP 440 */ 441 case STM32F7_APB2_CLOCK(SDMMC1): 442 case STM32F7_APB2_CLOCK(SDMMC2): 443 if (clk->id == STM32F7_APB2_CLOCK(SDMMC1)) 444 sdmmcxsel_bit = RCC_DCKCFGRX_SDMMC1SEL; 445 else 446 sdmmcxsel_bit = RCC_DCKCFGR2_SDMMC2SEL; 447 448 if (readl(®s->dckcfgr2) & sdmmcxsel_bit) 449 /* System clock is selected as SDMMC1 clock */ 450 return sysclk; 451 /* 452 * 48 MHz can be generated by either PLLSAIP 453 * or by PLLQ depending of CK48MSEL bit of RCC_DCKCFGR 454 */ 455 if (stm32_clk_get_ck48msel(priv)) 456 return stm32_clk_get_pllsai_rate(priv, PLLSAIP); 457 else 458 return (vco / pllq); 459 break; 460 461 /* For timer clock, an additionnal prescaler is used*/ 462 case STM32F7_APB2_CLOCK(TIM1): 463 case STM32F7_APB2_CLOCK(TIM8): 464 case STM32F7_APB2_CLOCK(TIM9): 465 case STM32F7_APB2_CLOCK(TIM10): 466 case STM32F7_APB2_CLOCK(TIM11): 467 return stm32_get_timer_rate(priv, sysclk, APB2); 468 break; 469 470 /* particular case for LTDC clock */ 471 case STM32F7_APB2_CLOCK(LTDC): 472 saidivr = readl(®s->dckcfgr); 473 saidivr = (saidivr & RCC_DCKCFGR_PLLSAIDIVR_MASK) 474 >> RCC_DCKCFGR_PLLSAIDIVR_SHIFT; 475 pllsai_rate = stm32_clk_get_pllsai_rate(priv, PLLSAIR); 476 477 return pllsai_rate / pllsaidivr_table[saidivr]; 478 } 479 return (sysclk >> stm32_get_apb_shift(regs, APB2)); 480 481 default: 482 pr_err("clock index %ld out of range\n", clk->id); 483 return -EINVAL; 484 } 485 } 486 487 static ulong stm32_set_rate(struct clk *clk, ulong rate) 488 { 489 #ifdef CONFIG_VIDEO_STM32 490 struct stm32_clk *priv = dev_get_priv(clk->dev); 491 struct stm32_rcc_regs *regs = priv->base; 492 u32 pllsair_rate, pllsai_vco_rate, current_rate; 493 u32 best_div, best_diff, diff; 494 u16 div; 495 u8 best_plldivr, best_pllsaidivr; 496 u8 i, j; 497 bool found = false; 498 499 /* Only set_rate for LTDC clock is implemented */ 500 if (clk->id != STM32F7_APB2_CLOCK(LTDC)) { 501 pr_err("set_rate not implemented for clock index %ld\n", 502 clk->id); 503 return 0; 504 } 505 506 if (rate == stm32_clk_get_rate(clk)) 507 /* already set to requested rate */ 508 return rate; 509 510 /* get the current PLLSAIR output freq */ 511 pllsair_rate = stm32_clk_get_pllsai_rate(priv, PLLSAIR); 512 best_div = pllsair_rate / rate; 513 514 /* look into pllsaidivr_table if this divider is available*/ 515 for (i = 0 ; i < sizeof(pllsaidivr_table); i++) 516 if (best_div == pllsaidivr_table[i]) { 517 /* set pll_saidivr with found value */ 518 clrsetbits_le32(®s->dckcfgr, 519 RCC_DCKCFGR_PLLSAIDIVR_MASK, 520 pllsaidivr_table[i]); 521 return rate; 522 } 523 524 /* 525 * As no pllsaidivr value is suitable to obtain requested freq, 526 * test all combination of pllsaidivr * pllsair and find the one 527 * which give freq closest to requested rate. 528 */ 529 530 pllsai_vco_rate = stm32_clk_get_pllsai_vco_rate(priv); 531 best_diff = ULONG_MAX; 532 best_pllsaidivr = 0; 533 best_plldivr = 0; 534 /* 535 * start at index 2 of plldivr_table as divider value at index 0 536 * and 1 are 0) 537 */ 538 for (i = 2; i < sizeof(plldivr_table); i++) { 539 for (j = 0; j < sizeof(pllsaidivr_table); j++) { 540 div = plldivr_table[i] * pllsaidivr_table[j]; 541 current_rate = pllsai_vco_rate / div; 542 /* perfect combination is found ? */ 543 if (current_rate == rate) { 544 best_pllsaidivr = j; 545 best_plldivr = i; 546 found = true; 547 break; 548 } 549 550 diff = (current_rate > rate) ? 551 current_rate - rate : rate - current_rate; 552 553 /* found a better combination ? */ 554 if (diff < best_diff) { 555 best_diff = diff; 556 best_pllsaidivr = j; 557 best_plldivr = i; 558 } 559 } 560 561 if (found) 562 break; 563 } 564 565 /* Disable the SAI PLL */ 566 clrbits_le32(®s->cr, RCC_CR_PLLSAION); 567 568 /* set pll_saidivr with found value */ 569 clrsetbits_le32(®s->dckcfgr, RCC_DCKCFGR_PLLSAIDIVR_MASK, 570 best_pllsaidivr << RCC_DCKCFGR_PLLSAIDIVR_SHIFT); 571 572 /* set pllsair with found value */ 573 clrsetbits_le32(®s->pllsaicfgr, RCC_PLLSAICFGR_PLLSAIR_MASK, 574 plldivr_table[best_plldivr] 575 << RCC_PLLSAICFGR_PLLSAIR_SHIFT); 576 577 /* Enable the SAI PLL */ 578 setbits_le32(®s->cr, RCC_CR_PLLSAION); 579 while (!(readl(®s->cr) & RCC_CR_PLLSAIRDY)) 580 ; 581 582 div = plldivr_table[best_plldivr] * pllsaidivr_table[best_pllsaidivr]; 583 return pllsai_vco_rate / div; 584 #else 585 return 0; 586 #endif 587 } 588 589 static int stm32_clk_enable(struct clk *clk) 590 { 591 struct stm32_clk *priv = dev_get_priv(clk->dev); 592 struct stm32_rcc_regs *regs = priv->base; 593 u32 offset = clk->id / 32; 594 u32 bit_index = clk->id % 32; 595 596 debug("%s: clkid = %ld, offset from AHB1ENR is %d, bit_index = %d\n", 597 __func__, clk->id, offset, bit_index); 598 setbits_le32(®s->ahb1enr + offset, BIT(bit_index)); 599 600 return 0; 601 } 602 603 static int stm32_clk_probe(struct udevice *dev) 604 { 605 struct ofnode_phandle_args args; 606 struct udevice *fixed_clock_dev = NULL; 607 struct clk clk; 608 int err; 609 610 debug("%s\n", __func__); 611 612 struct stm32_clk *priv = dev_get_priv(dev); 613 fdt_addr_t addr; 614 615 addr = dev_read_addr(dev); 616 if (addr == FDT_ADDR_T_NONE) 617 return -EINVAL; 618 619 priv->base = (struct stm32_rcc_regs *)addr; 620 621 switch (dev_get_driver_data(dev)) { 622 case STM32F4: 623 memcpy(&priv->info, &stm32f4_clk_info, 624 sizeof(struct stm32_clk_info)); 625 break; 626 case STM32F7: 627 memcpy(&priv->info, &stm32f7_clk_info, 628 sizeof(struct stm32_clk_info)); 629 break; 630 default: 631 return -EINVAL; 632 } 633 634 /* retrieve HSE frequency (external oscillator) */ 635 err = uclass_get_device_by_name(UCLASS_CLK, "clk-hse", 636 &fixed_clock_dev); 637 638 if (err) { 639 pr_err("Can't find fixed clock (%d)", err); 640 return err; 641 } 642 643 err = clk_request(fixed_clock_dev, &clk); 644 if (err) { 645 pr_err("Can't request %s clk (%d)", fixed_clock_dev->name, 646 err); 647 return err; 648 } 649 650 /* 651 * set pllm factor accordingly to the external oscillator 652 * frequency (HSE). For STM32F4 and STM32F7, we want VCO 653 * freq at 1MHz 654 * if input PLL frequency is 25Mhz, divide it by 25 655 */ 656 clk.id = 0; 657 priv->hse_rate = clk_get_rate(&clk); 658 659 if (priv->hse_rate < 1000000) { 660 pr_err("%s: unexpected HSE clock rate = %ld \"n", __func__, 661 priv->hse_rate); 662 return -EINVAL; 663 } 664 665 priv->info.sys_pll_psc.pll_m = priv->hse_rate / 1000000; 666 667 if (priv->info.has_overdrive) { 668 err = dev_read_phandle_with_args(dev, "st,syscfg", NULL, 0, 0, 669 &args); 670 if (err) { 671 debug("%s: can't find syscon device (%d)\n", __func__, 672 err); 673 return err; 674 } 675 676 priv->pwr_regs = (struct stm32_pwr_regs *)ofnode_get_addr(args.node); 677 } 678 679 configure_clocks(dev); 680 681 return 0; 682 } 683 684 static int stm32_clk_of_xlate(struct clk *clk, struct ofnode_phandle_args *args) 685 { 686 debug("%s(clk=%p)\n", __func__, clk); 687 688 if (args->args_count != 2) { 689 debug("Invaild args_count: %d\n", args->args_count); 690 return -EINVAL; 691 } 692 693 if (args->args_count) 694 clk->id = args->args[1]; 695 else 696 clk->id = 0; 697 698 return 0; 699 } 700 701 static struct clk_ops stm32_clk_ops = { 702 .of_xlate = stm32_clk_of_xlate, 703 .enable = stm32_clk_enable, 704 .get_rate = stm32_clk_get_rate, 705 .set_rate = stm32_set_rate, 706 }; 707 708 U_BOOT_DRIVER(stm32fx_clk) = { 709 .name = "stm32fx_rcc_clock", 710 .id = UCLASS_CLK, 711 .ops = &stm32_clk_ops, 712 .probe = stm32_clk_probe, 713 .priv_auto_alloc_size = sizeof(struct stm32_clk), 714 .flags = DM_FLAG_PRE_RELOC, 715 }; 716