]> git.kernelconcepts.de Git - karo-tx-uboot.git/blob - arch/arm/cpu/armv7/ls102xa/clock.c
Merge branch 'karo-tx-uboot' into kc-merge
[karo-tx-uboot.git] / arch / arm / cpu / armv7 / ls102xa / clock.c
1 /*
2  * Copyright 2014 Freescale Semiconductor, Inc.
3  *
4  * SPDX-License-Identifier:     GPL-2.0+
5  */
6
7 #include <common.h>
8 #include <asm/io.h>
9 #include <asm/arch/immap_ls102xa.h>
10 #include <asm/arch/clock.h>
11 #include <fsl_ifc.h>
12
13 DECLARE_GLOBAL_DATA_PTR;
14
15 #ifndef CONFIG_SYS_FSL_NUM_CC_PLLS
16 #define CONFIG_SYS_FSL_NUM_CC_PLLS      2
17 #endif
18
19 void get_sys_info(struct sys_info *sys_info)
20 {
21         struct ccsr_gur __iomem *gur = (void *)(CONFIG_SYS_FSL_GUTS_ADDR);
22 #ifdef CONFIG_FSL_IFC
23         struct fsl_ifc *ifc_regs = (void *)CONFIG_SYS_IFC_ADDR;
24         u32 ccr;
25 #endif
26         struct ccsr_clk *clk = (void *)(CONFIG_SYS_FSL_LS1_CLK_ADDR);
27         unsigned int cpu;
28         const u8 core_cplx_pll[6] = {
29                 [0] = 0,        /* CC1 PPL / 1 */
30                 [1] = 0,        /* CC1 PPL / 2 */
31                 [4] = 1,        /* CC2 PPL / 1 */
32                 [5] = 1,        /* CC2 PPL / 2 */
33         };
34
35         const u8 core_cplx_pll_div[6] = {
36                 [0] = 1,        /* CC1 PPL / 1 */
37                 [1] = 2,        /* CC1 PPL / 2 */
38                 [4] = 1,        /* CC2 PPL / 1 */
39                 [5] = 2,        /* CC2 PPL / 2 */
40         };
41
42         uint i;
43         uint freq_c_pll[CONFIG_SYS_FSL_NUM_CC_PLLS];
44         uint ratio[CONFIG_SYS_FSL_NUM_CC_PLLS];
45         unsigned long sysclk = CONFIG_SYS_CLK_FREQ;
46
47         sys_info->freq_systembus = sysclk;
48 #ifdef CONFIG_DDR_CLK_FREQ
49         sys_info->freq_ddrbus = CONFIG_DDR_CLK_FREQ;
50 #else
51         sys_info->freq_ddrbus = sysclk;
52 #endif
53
54         sys_info->freq_systembus *= (in_be32(&gur->rcwsr[0]) >>
55                 RCWSR0_SYS_PLL_RAT_SHIFT) & RCWSR0_SYS_PLL_RAT_MASK;
56         sys_info->freq_ddrbus *= (in_be32(&gur->rcwsr[0]) >>
57                 RCWSR0_MEM_PLL_RAT_SHIFT) & RCWSR0_MEM_PLL_RAT_MASK;
58
59         for (i = 0; i < CONFIG_SYS_FSL_NUM_CC_PLLS; i++) {
60                 ratio[i] = (in_be32(&clk->pllcgsr[i].pllcngsr) >> 1) & 0x3f;
61                 if (ratio[i] > 4)
62                         freq_c_pll[i] = sysclk * ratio[i];
63                 else
64                         freq_c_pll[i] = sys_info->freq_systembus * ratio[i];
65         }
66
67         for (cpu = 0; cpu < CONFIG_MAX_CPUS; cpu++) {
68                 u32 c_pll_sel = (in_be32(&clk->clkcsr[cpu].clkcncsr) >> 27)
69                                 & 0xf;
70                 u32 cplx_pll = core_cplx_pll[c_pll_sel];
71
72                 sys_info->freq_processor[cpu] =
73                         freq_c_pll[cplx_pll] / core_cplx_pll_div[c_pll_sel];
74         }
75
76 #if defined(CONFIG_FSL_IFC)
77         ccr = in_be32(&ifc_regs->ifc_ccr);
78         ccr = ((ccr & IFC_CCR_CLK_DIV_MASK) >> IFC_CCR_CLK_DIV_SHIFT) + 1;
79
80         sys_info->freq_localbus = sys_info->freq_systembus / ccr;
81 #endif
82 }
83
84 int get_clocks(void)
85 {
86         struct sys_info sys_info;
87
88         get_sys_info(&sys_info);
89         gd->cpu_clk = sys_info.freq_processor[0];
90         gd->bus_clk = sys_info.freq_systembus;
91         gd->mem_clk = sys_info.freq_ddrbus * 2;
92
93 #if defined(CONFIG_FSL_ESDHC)
94         gd->arch.sdhc_clk = gd->bus_clk;
95 #endif
96
97         return 0;
98 }
99
100 ulong get_bus_freq(ulong dummy)
101 {
102         return gd->bus_clk;
103 }
104
105 ulong get_ddr_freq(ulong dummy)
106 {
107         return gd->mem_clk;
108 }
109
110 int get_serial_clock(void)
111 {
112         return gd->bus_clk / 2;
113 }
114
115 unsigned int mxc_get_clock(enum mxc_clock clk)
116 {
117         switch (clk) {
118         case MXC_I2C_CLK:
119                 return get_bus_freq(0) / 2;
120         case MXC_ESDHC_CLK:
121                 return get_bus_freq(0);
122         case MXC_DSPI_CLK:
123                 return get_bus_freq(0) / 2;
124         case MXC_UART_CLK:
125                 return get_bus_freq(0) / 2;
126         default:
127                 printf("Unsupported clock\n");
128         }
129         return 0;
130 }