1 // SPDX-License-Identifier: GPL-2.0-only
3 * Realtek RTL83XX clock driver
4 * Copyright (C) 2022 Markus Stockhausen <markus.stockhausen@gmx.de>
6 * This driver provides basic clock support for the central core clock unit (CCU) and its PLLs
7 * inside the RTL838X and RTL8389X SOC. Currently CPU, memory and LXB clock information can be
8 * accessed. To make use of the driver add the following devices and configurations at the
9 * appropriate locations to the DT.
11 * #include <dt-bindings/clock/rtl83xx-clk.h>
13 * sram0: sram@9f000000 {
14 * compatible = "mmio-sram";
15 * reg = <0x9f000000 0x18000>;
16 * #address-cells = <1>;
18 * ranges = <0 0x9f000000 0x18000>;
22 * compatible = "fixed-clock";
24 * clock-frequency = <25000000>;
27 * ccu: clock-controller {
28 * compatible = "realtek,rtl8380-clock";
31 * clock-names = "ref_clk";
35 * The SRAM part is needed to be able to set clocks. When changing clocks the code must not run
36 * from DRAM. Otherwise system might freeze. Take care to adjust CCU compatibility, SRAM address
37 * and size to the target SOC device. Afterwards one can access/identify the clocks in the other
38 * DT devices with <&ccu CLK_CPU>, <&ccu CLK_MEM> or <&ccu CLK_LXB>. Additionally the clocks can
39 * be used inside the kernel with
41 * cpu_clk = clk_get(NULL, "cpu_clk");
42 * mem_clk = clk_get(NULL, "mem_clk");
43 * lxb_clk = clk_get(NULL, "lxb_clk");
45 * This driver can be directly used by the DT based cpufreq driver (CONFIG_CPUFREQ_DT) if CPU
46 * references the right clock and sane operating points (OPP) are provided. E.g.
49 * compatible = "mips,mips4KEc";
51 * clocks = <&ccu CLK_CPU>;
52 * operating-points-v2 = <&cpu_opp_table>;
55 * cpu_opp_table: opp-table-0 {
56 * compatible = "operating-points-v2";
59 * opp-hz = /bits/ 64 <425000000>;
65 #include <asm/cacheflush.h>
66 #include <asm/mipsmtregs.h>
67 #include <dt-bindings/clock/rtl83xx-clk.h>
68 #include <linux/clk.h>
69 #include <linux/clk-provider.h>
70 #include <linux/clkdev.h>
71 #include <linux/cpu.h>
72 #include <linux/delay.h>
73 #include <linux/genalloc.h>
75 #include <linux/ioport.h>
76 #include <linux/of_address.h>
77 #include <linux/of_platform.h>
78 #include <linux/platform_device.h>
79 #include <linux/slab.h>
81 #include "clk-rtl83xx.h"
83 #define read_sw(reg) ioread32(((void *)RTL_SW_CORE_BASE) + reg)
84 #define read_soc(reg) ioread32(((void *)RTL_SOC_BASE) + reg)
86 #define write_sw(val, reg) iowrite32(val, ((void *)RTL_SW_CORE_BASE) + reg)
87 #define write_soc(val, reg) iowrite32(val, ((void *)RTL_SOC_BASE) + reg)
90 * some hardware specific definitions
105 #define OSC_RATE 25000000
107 static const int rtcl_regs
[SOC_COUNT
][REG_COUNT
][CLK_COUNT
] = {
109 { RTL838X_PLL_CPU_CTRL0
, RTL838X_PLL_MEM_CTRL0
, RTL838X_PLL_LXB_CTRL0
},
110 { RTL838X_PLL_CPU_CTRL1
, RTL838X_PLL_MEM_CTRL1
, RTL838X_PLL_LXB_CTRL1
},
112 { RTL839X_PLL_CPU_CTRL0
, RTL839X_PLL_MEM_CTRL0
, RTL839X_PLL_LXB_CTRL0
},
113 { RTL839X_PLL_CPU_CTRL1
, RTL839X_PLL_MEM_CTRL1
, RTL839X_PLL_LXB_CTRL1
},
117 #define RTCL_REG_SET(_rate, _ctrl0, _ctrl1) \
124 struct rtcl_reg_set
{
131 * The following configuration tables are valid operation points for their corresponding PLLs.
132 * The magic numbers are precalculated mulitpliers and dividers to keep the driver simple. They
133 * also provide rates outside the allowed physical specifications. E.g. DDR3 memory has a lower
134 * limit of 303 MHz or the CPU might get unstable if set to anything above its startup frequency.
135 * Additionally the Realtek SOCs tend to expect CPU speed > MEM speed > LXB speed. The caller or
136 * DT configuration must take care that only valid operating points are selected.
139 static const struct rtcl_reg_set rtcl_838x_cpu_reg_set
[] = {
140 RTCL_REG_SET(300000000, 0x045c8, 0x1414530e),
141 RTCL_REG_SET(325000000, 0x04648, 0x1414530e),
142 RTCL_REG_SET(350000000, 0x046c8, 0x1414530e),
143 RTCL_REG_SET(375000000, 0x04748, 0x1414530e),
144 RTCL_REG_SET(400000000, 0x045c8, 0x0c14530e),
145 RTCL_REG_SET(425000000, 0x04628, 0x0c14530e),
146 RTCL_REG_SET(450000000, 0x04688, 0x0c14530e),
147 RTCL_REG_SET(475000000, 0x046e8, 0x0c14530e),
148 RTCL_REG_SET(500000000, 0x04748, 0x0c14530e),
149 RTCL_REG_SET(525000000, 0x047a8, 0x0c14530e),
150 RTCL_REG_SET(550000000, 0x04808, 0x0c14530e),
151 RTCL_REG_SET(575000000, 0x04868, 0x0c14530e),
152 RTCL_REG_SET(600000000, 0x048c8, 0x0c14530e),
153 RTCL_REG_SET(625000000, 0x04928, 0x0c14530e)
156 static const struct rtcl_reg_set rtcl_838x_mem_reg_set
[] = {
157 RTCL_REG_SET(200000000, 0x041bc, 0x14018C80),
158 RTCL_REG_SET(225000000, 0x0417c, 0x0c018C80),
159 RTCL_REG_SET(250000000, 0x041ac, 0x0c018C80),
160 RTCL_REG_SET(275000000, 0x0412c, 0x04018C80),
161 RTCL_REG_SET(300000000, 0x0414c, 0x04018c80),
162 RTCL_REG_SET(325000000, 0x0416c, 0x04018c80),
163 RTCL_REG_SET(350000000, 0x0418c, 0x04018c80),
164 RTCL_REG_SET(375000000, 0x041ac, 0x04018c80)
167 static const struct rtcl_reg_set rtcl_838x_lxb_reg_set
[] = {
168 RTCL_REG_SET(100000000, 0x043c8, 0x001ad30e),
169 RTCL_REG_SET(125000000, 0x043c8, 0x001ad30e),
170 RTCL_REG_SET(150000000, 0x04508, 0x1c1ad30e),
171 RTCL_REG_SET(175000000, 0x04508, 0x1c1ad30e),
172 RTCL_REG_SET(200000000, 0x047c8, 0x001ad30e)
175 static const struct rtcl_reg_set rtcl_839x_cpu_reg_set
[] = {
176 RTCL_REG_SET(400000000, 0x0414c, 0x00000005),
177 RTCL_REG_SET(425000000, 0x041ec, 0x00000006),
178 RTCL_REG_SET(450000000, 0x0417c, 0x00000005),
179 RTCL_REG_SET(475000000, 0x0422c, 0x00000006),
180 RTCL_REG_SET(500000000, 0x041ac, 0x00000005),
181 RTCL_REG_SET(525000000, 0x0426c, 0x00000006),
182 RTCL_REG_SET(550000000, 0x0412c, 0x00000004),
183 RTCL_REG_SET(575000000, 0x042ac, 0x00000006),
184 RTCL_REG_SET(600000000, 0x0414c, 0x00000004),
185 RTCL_REG_SET(625000000, 0x042ec, 0x00000006),
186 RTCL_REG_SET(650000000, 0x0416c, 0x00000004),
187 RTCL_REG_SET(675000000, 0x04324, 0x00000006),
188 RTCL_REG_SET(700000000, 0x0418c, 0x00000004),
189 RTCL_REG_SET(725000000, 0x0436c, 0x00000006),
190 RTCL_REG_SET(750000000, 0x0438c, 0x00000006),
191 RTCL_REG_SET(775000000, 0x043ac, 0x00000006),
192 RTCL_REG_SET(800000000, 0x043cc, 0x00000006),
193 RTCL_REG_SET(825000000, 0x043ec, 0x00000006),
194 RTCL_REG_SET(850000000, 0x0440c, 0x00000006)
197 static const struct rtcl_reg_set rtcl_839x_mem_reg_set
[] = {
198 RTCL_REG_SET(100000000, 0x041cc, 0x00000000),
199 RTCL_REG_SET(125000000, 0x041ac, 0x00000007),
200 RTCL_REG_SET(150000000, 0x0414c, 0x00000006),
201 RTCL_REG_SET(175000000, 0x0418c, 0x00000006),
202 RTCL_REG_SET(200000000, 0x041cc, 0x00000006),
203 RTCL_REG_SET(225000000, 0x0417c, 0x00000005),
204 RTCL_REG_SET(250000000, 0x041ac, 0x00000005),
205 RTCL_REG_SET(275000000, 0x0412c, 0x00000004),
206 RTCL_REG_SET(300000000, 0x0414c, 0x00000004),
207 RTCL_REG_SET(325000000, 0x0416c, 0x00000004),
208 RTCL_REG_SET(350000000, 0x0418c, 0x00000004),
209 RTCL_REG_SET(375000000, 0x041ac, 0x00000004),
210 RTCL_REG_SET(400000000, 0x041cc, 0x00000004)
213 static const struct rtcl_reg_set rtcl_839x_lxb_reg_set
[] = {
214 RTCL_REG_SET(50000000, 0x1414c, 0x00000003),
215 RTCL_REG_SET(100000000, 0x0814c, 0x00000003),
216 RTCL_REG_SET(150000000, 0x0414c, 0x00000003),
217 RTCL_REG_SET(200000000, 0x0414c, 0x00000007)
220 struct rtcl_rtab_set
{
222 const struct rtcl_reg_set
*rset
;
225 #define RTCL_RTAB_SET(_rset) \
227 .count = ARRAY_SIZE(_rset), \
231 static const struct rtcl_rtab_set rtcl_rtab_set
[SOC_COUNT
][CLK_COUNT
] = {
233 RTCL_RTAB_SET(rtcl_838x_cpu_reg_set
),
234 RTCL_RTAB_SET(rtcl_838x_mem_reg_set
),
235 RTCL_RTAB_SET(rtcl_838x_lxb_reg_set
)
237 RTCL_RTAB_SET(rtcl_839x_cpu_reg_set
),
238 RTCL_RTAB_SET(rtcl_839x_mem_reg_set
),
239 RTCL_RTAB_SET(rtcl_839x_lxb_reg_set
)
243 #define RTCL_ROUND_SET(_min, _max, _step) \
250 struct rtcl_round_set
{
256 static const struct rtcl_round_set rtcl_round_set
[SOC_COUNT
][CLK_COUNT
] = {
258 RTCL_ROUND_SET(300000000, 625000000, 25000000),
259 RTCL_ROUND_SET(200000000, 375000000, 25000000),
260 RTCL_ROUND_SET(100000000, 200000000, 25000000)
262 RTCL_ROUND_SET(400000000, 850000000, 25000000),
263 RTCL_ROUND_SET(100000000, 400000000, 25000000),
264 RTCL_ROUND_SET(50000000, 200000000, 50000000)
268 static const int rtcl_divn3
[] = { 2, 3, 4, 6 };
269 static const int rtcl_xdiv
[] = { 2, 4, 2 };
272 * module data structures
275 #define RTCL_CLK_INFO(_idx, _name, _pname, _dname) \
279 .parent_name = _pname, \
280 .display_name = _dname, \
283 struct rtcl_clk_info
{
286 const char *parent_name
;
287 const char *display_name
;
296 unsigned long startup
;
299 static const struct rtcl_clk_info rtcl_clk_info
[CLK_COUNT
] = {
300 RTCL_CLK_INFO(CLK_CPU
, "cpu_clk", "ref_clk", "CPU"),
301 RTCL_CLK_INFO(CLK_MEM
, "mem_clk", "ref_clk", "MEM"),
302 RTCL_CLK_INFO(CLK_LXB
, "lxb_clk", "ref_clk", "LXB")
318 struct rtcl_sram sram
;
319 struct rtcl_dram dram
;
320 struct device_node
*np
;
321 struct platform_device
*pdev
;
322 struct rtcl_clk clks
[CLK_COUNT
];
325 struct rtcl_ccu
*rtcl_ccu
;
327 #define rtcl_hw_to_clk(_hw) container_of(_hw, struct rtcl_clk, hw)
330 * SRAM relocatable assembler functions. The dram() parts point to normal kernel memory while
331 * the sram() parts are the same functions but relocated to SRAM.
334 extern void rtcl_838x_dram_start(void);
335 extern int rtcl_838x_dram_size
;
337 extern void (*rtcl_838x_dram_set_rate
)(int clk_idx
, int ctrl0
, int ctrl1
);
338 static void (*rtcl_838x_sram_set_rate
)(int clk_idx
, int ctrl0
, int ctrl1
);
340 extern void rtcl_839x_dram_start(void);
341 extern int rtcl_839x_dram_size
;
343 extern void (*rtcl_839x_dram_set_rate
)(int clk_idx
, int ctrl0
, int ctrl1
);
344 static void (*rtcl_839x_sram_set_rate
)(int clk_idx
, int ctrl0
, int ctrl1
);
347 * clock setter/getter functions
350 static unsigned long rtcl_recalc_rate(struct clk_hw
*hw
, unsigned long parent_rate
)
352 struct rtcl_clk
*clk
= rtcl_hw_to_clk(hw
);
353 unsigned int ctrl0
, ctrl1
, div1
, div2
, cmu_ncode_in
;
354 unsigned int cmu_sel_prediv
, cmu_sel_div4
, cmu_divn2
, cmu_divn2_selb
, cmu_divn3_sel
;
356 if ((clk
->idx
>= CLK_COUNT
) || (!rtcl_ccu
) || (rtcl_ccu
->soc
>= SOC_COUNT
))
359 ctrl0
= read_sw(rtcl_regs
[rtcl_ccu
->soc
][REG_CTRL0
][clk
->idx
]);
360 ctrl1
= read_sw(rtcl_regs
[rtcl_ccu
->soc
][REG_CTRL1
][clk
->idx
]);
362 cmu_sel_prediv
= 1 << RTL_PLL_CTRL0_CMU_SEL_PREDIV(ctrl0
);
363 cmu_sel_div4
= RTL_PLL_CTRL0_CMU_SEL_DIV4(ctrl0
) ? 4 : 1;
364 cmu_ncode_in
= RTL_PLL_CTRL0_CMU_NCODE_IN(ctrl0
) + 4;
365 cmu_divn2
= RTL_PLL_CTRL0_CMU_DIVN2(ctrl0
) + 4;
367 switch (rtcl_ccu
->soc
) {
369 if ((ctrl0
== 0) && (ctrl1
== 0) && (clk
->idx
== CLK_LXB
))
372 cmu_divn2_selb
= RTL838X_PLL_CTRL1_CMU_DIVN2_SELB(ctrl1
);
373 cmu_divn3_sel
= rtcl_divn3
[RTL838X_PLL_CTRL1_CMU_DIVN3_SEL(ctrl1
)];
376 cmu_divn2_selb
= RTL839X_PLL_CTRL1_CMU_DIVN2_SELB(ctrl1
);
377 cmu_divn3_sel
= rtcl_divn3
[RTL839X_PLL_CTRL1_CMU_DIVN3_SEL(ctrl1
)];
380 div1
= cmu_divn2_selb
? cmu_divn3_sel
: cmu_divn2
;
381 div2
= rtcl_xdiv
[clk
->idx
];
383 return (((parent_rate
/ 16) * cmu_ncode_in
) / (div1
* div2
)) *
384 cmu_sel_prediv
* cmu_sel_div4
* 16;
387 static int rtcl_838x_set_rate(int clk_idx
, const struct rtcl_reg_set
*reg
)
389 unsigned long irqflags
;
391 * Runtime of this function (including locking)
392 * CPU: up to 14000 cycles / up to 56 us at 250 MHz (half default speed)
394 spin_lock_irqsave(&rtcl_ccu
->lock
, irqflags
);
395 rtcl_838x_sram_set_rate(clk_idx
, reg
->ctrl0
, reg
->ctrl1
);
396 spin_unlock_irqrestore(&rtcl_ccu
->lock
, irqflags
);
401 static int rtcl_839x_set_rate(int clk_idx
, const struct rtcl_reg_set
*reg
)
403 unsigned long vpflags
;
404 unsigned long irqflags
;
406 * Runtime of this function (including locking)
407 * CPU: up to 31000 cycles / up to 89 us at 350 MHz (half default speed)
409 spin_lock_irqsave(&rtcl_ccu
->lock
, irqflags
);
411 rtcl_839x_sram_set_rate(clk_idx
, reg
->ctrl0
, reg
->ctrl1
);
413 spin_unlock_irqrestore(&rtcl_ccu
->lock
, irqflags
);
418 static int rtcl_set_rate(struct clk_hw
*hw
, unsigned long rate
, unsigned long parent_rate
)
421 struct rtcl_clk
*clk
= rtcl_hw_to_clk(hw
);
422 const struct rtcl_rtab_set
*rtab
= &rtcl_rtab_set
[rtcl_ccu
->soc
][clk
->idx
];
423 const struct rtcl_round_set
*round
= &rtcl_round_set
[rtcl_ccu
->soc
][clk
->idx
];
425 if ((parent_rate
!= OSC_RATE
) || (!rtcl_ccu
->sram
.vbase
))
428 * Currently we do not know if SRAM is stable on these devices. Maybe someone changes memory in
429 * this region and does not care about proper allocation. So check if something might go wrong.
431 if (unlikely(*rtcl_ccu
->sram
.pmark
!= RTL_SRAM_MARKER
)) {
432 dev_err(&rtcl_ccu
->pdev
->dev
, "SRAM code lost\n");
436 tab_idx
= (rate
- round
->min
) / round
->step
;
437 if ((tab_idx
< 0) || (tab_idx
>= rtab
->count
) || (rtab
->rset
[tab_idx
].rate
!= rate
))
440 rtcl_ccu
->clks
[clk
->idx
].rate
= rate
;
442 switch (rtcl_ccu
->soc
) {
444 return rtcl_838x_set_rate(clk
->idx
, &rtab
->rset
[tab_idx
]);
446 return rtcl_839x_set_rate(clk
->idx
, &rtab
->rset
[tab_idx
]);
452 static long rtcl_round_rate(struct clk_hw
*hw
, unsigned long rate
, unsigned long *parent_rate
)
454 struct rtcl_clk
*clk
= rtcl_hw_to_clk(hw
);
455 unsigned long rrate
= max(clk
->min
, min(clk
->max
, rate
));
456 const struct rtcl_round_set
*round
= &rtcl_round_set
[rtcl_ccu
->soc
][clk
->idx
];
458 rrate
= ((rrate
+ (round
->step
>> 1)) / round
->step
) * round
->step
;
459 rrate
-= (rrate
> clk
->max
) ? round
->step
: 0;
460 rrate
+= (rrate
< clk
->min
) ? round
->step
: 0;
466 * Initialization functions to register the CCU and its clocks
469 #define RTCL_SRAM_FUNC(SOC, PBASE, FN) ({ \
470 rtcl_##SOC##_sram_##FN = ((void *)&rtcl_##SOC##_dram_##FN - \
471 (void *)&rtcl_##SOC##_dram_start) + \
474 static const struct clk_ops rtcl_clk_ops
= {
475 .set_rate
= rtcl_set_rate
,
476 .round_rate
= rtcl_round_rate
,
477 .recalc_rate
= rtcl_recalc_rate
,
480 static int rtcl_ccu_create(struct device_node
*np
)
484 if (of_device_is_compatible(np
, "realtek,rtl8380-clock"))
486 else if (of_device_is_compatible(np
, "realtek,rtl8390-clock"))
491 rtcl_ccu
= kzalloc(sizeof(*rtcl_ccu
), GFP_KERNEL
);
492 if (IS_ERR(rtcl_ccu
))
497 rtcl_ccu
->dram
.type
= RTL_MC_MCR_DRAMTYPE(read_soc(RTL_MC_MCR
));
498 rtcl_ccu
->dram
.buswidth
= RTL_MC_DCR_BUSWIDTH(read_soc(RTL_MC_DCR
));
499 spin_lock_init(&rtcl_ccu
->lock
);
504 int rtcl_register_clkhw(int clk_idx
)
508 struct clk_init_data hw_init
= { };
509 struct rtcl_clk
*rclk
= &rtcl_ccu
->clks
[clk_idx
];
510 struct clk_parent_data parent_data
= { .fw_name
= rtcl_clk_info
[clk_idx
].parent_name
};
513 rclk
->hw
.init
= &hw_init
;
515 hw_init
.num_parents
= 1;
516 hw_init
.ops
= &rtcl_clk_ops
;
517 hw_init
.parent_data
= &parent_data
;
518 hw_init
.name
= rtcl_clk_info
[clk_idx
].name
;
520 ret
= of_clk_hw_register(rtcl_ccu
->np
, &rclk
->hw
);
524 clk_hw_register_clkdev(&rclk
->hw
, rtcl_clk_info
[clk_idx
].name
, NULL
);
526 clk
= clk_get(NULL
, rtcl_clk_info
[clk_idx
].name
);
527 rclk
->startup
= clk_get_rate(clk
);
532 rclk
->min
= rtcl_round_set
[rtcl_ccu
->soc
][clk_idx
].min
;
533 rclk
->max
= rtcl_round_set
[rtcl_ccu
->soc
][clk_idx
].max
;
537 * TODO: This driver supports PLL reclocking and nothing else. Additional required steps for non
538 * CPU PLLs are missing. E.g. if we want to change memory clocks the right way we must adapt a lot
539 * of other settings like MCR and DTRx timing registers (0xb80001000, 0xb8001008, ...) and initiate
540 * a DLL reset so that hardware operates in the allowed limits. This is far too complex without
541 * official support. Avoid this for now.
543 rclk
->min
= rclk
->max
= rclk
->startup
;
550 static struct clk_hw
*rtcl_get_clkhw(struct of_phandle_args
*clkspec
, void *prv
)
552 unsigned int idx
= clkspec
->args
[0];
554 if (idx
>= CLK_COUNT
) {
555 pr_err("%s: Invalid index %u\n", __func__
, idx
);
556 return ERR_PTR(-EINVAL
);
559 return &rtcl_ccu
->clks
[idx
].hw
;
562 static int rtcl_ccu_register_clocks(void)
566 for (clk_idx
= 0; clk_idx
< CLK_COUNT
; clk_idx
++) {
567 ret
= rtcl_register_clkhw(clk_idx
);
569 pr_err("%s: Couldn't register %s clock\n",
570 __func__
, rtcl_clk_info
[clk_idx
].display_name
);
571 goto err_hw_unregister
;
575 ret
= of_clk_add_hw_provider(rtcl_ccu
->np
, rtcl_get_clkhw
, rtcl_ccu
);
577 pr_err("%s: Couldn't register clock provider of %s\n",
578 __func__
, of_node_full_name(rtcl_ccu
->np
));
579 goto err_hw_unregister
;
585 for (--clk_idx
; clk_idx
>= 0; --clk_idx
)
586 clk_hw_unregister(&rtcl_ccu
->clks
[clk_idx
].hw
);
591 int rtcl_init_sram(void)
593 struct gen_pool
*sram_pool
;
594 phys_addr_t sram_pbase
;
595 unsigned long sram_vbase
;
596 struct device_node
*node
;
597 struct platform_device
*pdev
= NULL
;
600 const char *wrn
= ", rate setting disabled.\n";
602 switch (rtcl_ccu
->soc
) {
604 dram_start
= &rtcl_838x_dram_start
;
605 dram_size
= rtcl_838x_dram_size
;
608 dram_start
= &rtcl_839x_dram_start
;
609 dram_size
= rtcl_839x_dram_size
;
615 for_each_compatible_node(node
, NULL
, "mmio-sram") {
616 pdev
= of_find_device_by_node(node
);
624 dev_warn(&rtcl_ccu
->pdev
->dev
, "no SRAM device found%s", wrn
);
628 sram_pool
= gen_pool_get(&pdev
->dev
, NULL
);
630 dev_warn(&rtcl_ccu
->pdev
->dev
, "SRAM pool unavailable%s", wrn
);
634 sram_vbase
= gen_pool_alloc(sram_pool
, dram_size
);
636 dev_warn(&rtcl_ccu
->pdev
->dev
, "can not allocate SRAM%s", wrn
);
640 sram_pbase
= gen_pool_virt_to_phys(sram_pool
, sram_vbase
);
641 memcpy((void *)sram_pbase
, dram_start
, dram_size
);
642 flush_icache_range((unsigned long)sram_pbase
, (unsigned long)(sram_pbase
+ dram_size
));
644 switch (rtcl_ccu
->soc
) {
646 RTCL_SRAM_FUNC(838x
, sram_pbase
, set_rate
);
649 RTCL_SRAM_FUNC(839x
, sram_pbase
, set_rate
);
653 rtcl_ccu
->sram
.pmark
= (int *)((void *)sram_pbase
+ (dram_size
- 4));
654 rtcl_ccu
->sram
.vbase
= sram_vbase
;
659 put_device(&pdev
->dev
);
664 void rtcl_ccu_log_early(void)
667 char meminfo
[80], clkinfo
[255], msg
[255] = "rtl83xx-clk: initialized";
669 sprintf(meminfo
, " (%d Bit DDR%d)", rtcl_ccu
->dram
.buswidth
, rtcl_ccu
->dram
.type
);
670 for (clk_idx
= 0; clk_idx
< CLK_COUNT
; clk_idx
++) {
671 sprintf(clkinfo
, ", %s %lu MHz", rtcl_clk_info
[clk_idx
].display_name
,
672 rtcl_ccu
->clks
[clk_idx
].startup
/ 1000000);
673 if (clk_idx
== CLK_MEM
)
674 strcat(clkinfo
, meminfo
);
675 strcat(msg
, clkinfo
);
677 pr_info("%s\n", msg
);
680 void rtcl_ccu_log_late(void)
683 struct rtcl_clk
*rclk
;
684 bool overclock
= false;
685 char clkinfo
[80], msg
[255] = "rate setting enabled";
687 for (clk_idx
= 0; clk_idx
< CLK_COUNT
; clk_idx
++) {
688 rclk
= &rtcl_ccu
->clks
[clk_idx
];
689 overclock
|= rclk
->max
> rclk
->startup
;
690 sprintf(clkinfo
, ", %s %lu-%lu MHz", rtcl_clk_info
[clk_idx
].display_name
,
691 rclk
->min
/ 1000000, rclk
->max
/ 1000000);
692 strcat(msg
, clkinfo
);
695 strcat(msg
, ", OVERCLOCK AT OWN RISK");
697 dev_info(&rtcl_ccu
->pdev
->dev
, "%s\n", msg
);
701 * Early registration: This module provides core startup clocks that are needed for generic SOC
702 * init and for further builtin devices (e.g. UART). Register asap via clock framework.
705 static void __init
rtcl_probe_early(struct device_node
*np
)
707 if (rtcl_ccu_create(np
))
710 if (rtcl_ccu_register_clocks())
713 rtcl_ccu_log_early();
716 CLK_OF_DECLARE_DRIVER(rtl838x_clk
, "realtek,rtl8380-clock", rtcl_probe_early
);
717 CLK_OF_DECLARE_DRIVER(rtl839x_clk
, "realtek,rtl8390-clock", rtcl_probe_early
);
720 * Late registration: Finally register as normal platform driver. At this point we can make use
721 * of other modules like SRAM.
724 static const struct of_device_id rtcl_dt_ids
[] = {
725 { .compatible
= "realtek,rtl8380-clock" },
726 { .compatible
= "realtek,rtl8390-clock" },
730 static int rtcl_probe_late(struct platform_device
*pdev
)
735 dev_err(&pdev
->dev
, "early initialization not run");
738 rtcl_ccu
->pdev
= pdev
;
739 ret
= rtcl_init_sram();
748 static struct platform_driver rtcl_platform_driver
= {
750 .name
= "rtl83xx-clk",
751 .of_match_table
= rtcl_dt_ids
,
753 .probe
= rtcl_probe_late
,
756 static int __init
rtcl_init_subsys(void)
758 return platform_driver_register(&rtcl_platform_driver
);
762 * The driver does not know when SRAM module has finally loaded. With an arch_initcall() we might
763 * overtake SRAM initialization. Be polite and give the system a little more time.
766 subsys_initcall(rtcl_init_subsys
);