clock-k2l.c 2.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899
  1. /*
  2. * Keystone2: get clk rate for K2L
  3. *
  4. * (C) Copyright 2012-2014
  5. * Texas Instruments Incorporated, <www.ti.com>
  6. *
  7. * SPDX-License-Identifier: GPL-2.0+
  8. */
  9. #include <common.h>
  10. #include <asm/arch/clock.h>
  11. #include <asm/arch/clock_defs.h>
  12. /**
  13. * pll_freq_get - get pll frequency
  14. * Fout = Fref * NF(mult) / NR(prediv) / OD
  15. * @pll: pll identifier
  16. */
  17. static unsigned long pll_freq_get(int pll)
  18. {
  19. unsigned long mult = 1, prediv = 1, output_div = 2;
  20. unsigned long ret;
  21. u32 tmp, reg;
  22. if (pll == CORE_PLL) {
  23. ret = external_clk[sys_clk];
  24. if (pllctl_reg_read(pll, ctl) & PLLCTL_PLLEN) {
  25. /* PLL mode */
  26. tmp = __raw_readl(KS2_MAINPLLCTL0);
  27. prediv = (tmp & PLL_DIV_MASK) + 1;
  28. mult = (((tmp & PLLM_MULT_HI_SMASK) >> 6) |
  29. (pllctl_reg_read(pll, mult) &
  30. PLLM_MULT_LO_MASK)) + 1;
  31. output_div = ((pllctl_reg_read(pll, secctl) >>
  32. PLL_CLKOD_SHIFT) & PLL_CLKOD_MASK) + 1;
  33. ret = ret / prediv / output_div * mult;
  34. }
  35. } else {
  36. switch (pll) {
  37. case PASS_PLL:
  38. ret = external_clk[pa_clk];
  39. reg = KS2_PASSPLLCTL0;
  40. break;
  41. case TETRIS_PLL:
  42. ret = external_clk[tetris_clk];
  43. reg = KS2_ARMPLLCTL0;
  44. break;
  45. case DDR3_PLL:
  46. ret = external_clk[ddr3_clk];
  47. reg = KS2_DDR3APLLCTL0;
  48. break;
  49. default:
  50. return 0;
  51. }
  52. tmp = __raw_readl(reg);
  53. if (!(tmp & PLLCTL_BYPASS)) {
  54. /* Bypass disabled */
  55. prediv = (tmp & PLL_DIV_MASK) + 1;
  56. mult = ((tmp >> PLL_MULT_SHIFT) & PLL_MULT_MASK) + 1;
  57. output_div = ((tmp >> PLL_CLKOD_SHIFT) &
  58. PLL_CLKOD_MASK) + 1;
  59. ret = ((ret / prediv) * mult) / output_div;
  60. }
  61. }
  62. return ret;
  63. }
  64. unsigned long clk_get_rate(unsigned int clk)
  65. {
  66. switch (clk) {
  67. case core_pll_clk: return pll_freq_get(CORE_PLL);
  68. case pass_pll_clk: return pll_freq_get(PASS_PLL);
  69. case tetris_pll_clk: return pll_freq_get(TETRIS_PLL);
  70. case ddr3_pll_clk: return pll_freq_get(DDR3_PLL);
  71. case sys_clk0_1_clk:
  72. case sys_clk0_clk: return pll_freq_get(CORE_PLL) / pll0div_read(1);
  73. case sys_clk1_clk: return pll_freq_get(CORE_PLL) / pll0div_read(2);
  74. case sys_clk2_clk: return pll_freq_get(CORE_PLL) / pll0div_read(3);
  75. case sys_clk3_clk: return pll_freq_get(CORE_PLL) / pll0div_read(4);
  76. case sys_clk0_2_clk: return clk_get_rate(sys_clk0_clk) / 2;
  77. case sys_clk0_3_clk: return clk_get_rate(sys_clk0_clk) / 3;
  78. case sys_clk0_4_clk: return clk_get_rate(sys_clk0_clk) / 4;
  79. case sys_clk0_6_clk: return clk_get_rate(sys_clk0_clk) / 6;
  80. case sys_clk0_8_clk: return clk_get_rate(sys_clk0_clk) / 8;
  81. case sys_clk0_12_clk: return clk_get_rate(sys_clk0_clk) / 12;
  82. case sys_clk0_24_clk: return clk_get_rate(sys_clk0_clk) / 24;
  83. case sys_clk1_3_clk: return clk_get_rate(sys_clk1_clk) / 3;
  84. case sys_clk1_4_clk: return clk_get_rate(sys_clk1_clk) / 4;
  85. case sys_clk1_6_clk: return clk_get_rate(sys_clk1_clk) / 6;
  86. case sys_clk1_12_clk: return clk_get_rate(sys_clk1_clk) / 12;
  87. default:
  88. break;
  89. }
  90. return 0;
  91. }