Orange Pi5 kernel

Deprecated Linux kernel 5.10.110 for OrangePi 5/5B/5+ boards

3 Commits   0 Branches   0 Tags
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  1) // SPDX-License-Identifier: GPL-2.0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  2) #include <linux/kernel.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  3) #include <linux/clk-provider.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  4) #include <linux/of_address.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  5) #include <linux/init.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  6) #include <linux/io.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  7) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  8) #define CLK_COUNT 4 /* cpu_clk, sys_clk, usb_clk, sdio_clk */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  9) static struct clk *clks[CLK_COUNT];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 10) static struct clk_onecell_data clk_data = { clks, CLK_COUNT };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 11) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 12) #define SYSCLK_DIV	0x20
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 13) #define CPUCLK_DIV	0x24
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 14) #define DIV_BYPASS	BIT(23)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 15) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 16) /*** CLKGEN_PLL ***/
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 17) #define extract_pll_n(val)	((val >>  0) & ((1u << 7) - 1))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 18) #define extract_pll_k(val)	((val >> 13) & ((1u << 3) - 1))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 19) #define extract_pll_m(val)	((val >> 16) & ((1u << 3) - 1))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 20) #define extract_pll_isel(val)	((val >> 24) & ((1u << 3) - 1))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 21) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 22) static void __init make_pll(int idx, const char *parent, void __iomem *base)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 23) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 24) 	char name[8];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 25) 	u32 val, mul, div;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 26) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 27) 	sprintf(name, "pll%d", idx);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 28) 	val = readl(base + idx * 8);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 29) 	mul =  extract_pll_n(val) + 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 30) 	div = (extract_pll_m(val) + 1) << extract_pll_k(val);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 31) 	clk_register_fixed_factor(NULL, name, parent, 0, mul, div);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 32) 	if (extract_pll_isel(val) != 1)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 33) 		panic("%s: input not set to XTAL_IN\n", name);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 34) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 35) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 36) static void __init make_cd(int idx, void __iomem *base)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 37) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 38) 	char name[8];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 39) 	u32 val, mul, div;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 40) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 41) 	sprintf(name, "cd%d", idx);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 42) 	val = readl(base + idx * 8);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 43) 	mul =  1 << 27;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 44) 	div = (2 << 27) + val;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 45) 	clk_register_fixed_factor(NULL, name, "pll2", 0, mul, div);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 46) 	if (val > 0xf0000000)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 47) 		panic("%s: unsupported divider %x\n", name, val);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 48) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 49) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 50) static void __init tango4_clkgen_setup(struct device_node *np)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 51) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 52) 	struct clk **pp = clk_data.clks;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 53) 	void __iomem *base = of_iomap(np, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 54) 	const char *parent = of_clk_get_parent_name(np, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 55) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 56) 	if (!base)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 57) 		panic("%pOFn: invalid address\n", np);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 58) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 59) 	if (readl(base + CPUCLK_DIV) & DIV_BYPASS)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 60) 		panic("%pOFn: unsupported cpuclk setup\n", np);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 61) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 62) 	if (readl(base + SYSCLK_DIV) & DIV_BYPASS)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 63) 		panic("%pOFn: unsupported sysclk setup\n", np);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 64) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 65) 	writel(0x100, base + CPUCLK_DIV); /* disable frequency ramping */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 66) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 67) 	make_pll(0, parent, base);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 68) 	make_pll(1, parent, base);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 69) 	make_pll(2, parent, base);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 70) 	make_cd(2, base + 0x80);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 71) 	make_cd(6, base + 0x80);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 72) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 73) 	pp[0] = clk_register_divider(NULL, "cpu_clk", "pll0", 0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 74) 			base + CPUCLK_DIV, 8, 8, CLK_DIVIDER_ONE_BASED, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 75) 	pp[1] = clk_register_fixed_factor(NULL, "sys_clk", "pll1", 0, 1, 4);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 76) 	pp[2] = clk_register_fixed_factor(NULL,  "usb_clk", "cd2", 0, 1, 2);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 77) 	pp[3] = clk_register_fixed_factor(NULL, "sdio_clk", "cd6", 0, 1, 2);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 78) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 79) 	if (IS_ERR(pp[0]) || IS_ERR(pp[1]) || IS_ERR(pp[2]) || IS_ERR(pp[3]))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 80) 		panic("%pOFn: clk registration failed\n", np);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 81) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 82) 	if (of_clk_add_provider(np, of_clk_src_onecell_get, &clk_data))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 83) 		panic("%pOFn: clk provider registration failed\n", np);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 84) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 85) CLK_OF_DECLARE(tango4_clkgen, "sigma,tango4-clkgen", tango4_clkgen_setup);