xref: /openbmc/linux/drivers/clk/qcom/gpucc-sm6375.c (revision c900529f3d9161bfde5cca0754f83b4d3c3e0220)
18397e242SKonrad Dybcio // SPDX-License-Identifier: GPL-2.0-only
28397e242SKonrad Dybcio /*
38397e242SKonrad Dybcio  * Copyright (c) 2021, The Linux Foundation. All rights reserved.
48397e242SKonrad Dybcio  * Copyright (c) 2023, Linaro Limited
58397e242SKonrad Dybcio  */
68397e242SKonrad Dybcio 
78397e242SKonrad Dybcio #include <linux/clk-provider.h>
8*a96cbb14SRob Herring #include <linux/mod_devicetable.h>
98397e242SKonrad Dybcio #include <linux/module.h>
10*a96cbb14SRob Herring #include <linux/platform_device.h>
11097d359cSKonrad Dybcio #include <linux/pm_runtime.h>
128397e242SKonrad Dybcio #include <linux/regmap.h>
138397e242SKonrad Dybcio 
148397e242SKonrad Dybcio #include <dt-bindings/clock/qcom,sm6375-gpucc.h>
158397e242SKonrad Dybcio 
168397e242SKonrad Dybcio #include "clk-alpha-pll.h"
178397e242SKonrad Dybcio #include "clk-branch.h"
188397e242SKonrad Dybcio #include "clk-rcg.h"
198397e242SKonrad Dybcio #include "clk-regmap.h"
208397e242SKonrad Dybcio #include "clk-regmap-divider.h"
218397e242SKonrad Dybcio #include "clk-regmap-mux.h"
228397e242SKonrad Dybcio #include "clk-regmap-phy-mux.h"
238397e242SKonrad Dybcio #include "gdsc.h"
248397e242SKonrad Dybcio #include "reset.h"
258397e242SKonrad Dybcio 
268397e242SKonrad Dybcio enum {
278397e242SKonrad Dybcio 	DT_BI_TCXO,
288397e242SKonrad Dybcio 	DT_GCC_GPU_GPLL0_CLK_SRC,
298397e242SKonrad Dybcio 	DT_GCC_GPU_GPLL0_DIV_CLK_SRC,
308397e242SKonrad Dybcio 	DT_GCC_GPU_SNOC_DVM_GFX_CLK,
318397e242SKonrad Dybcio };
328397e242SKonrad Dybcio 
338397e242SKonrad Dybcio enum {
348397e242SKonrad Dybcio 	P_BI_TCXO,
358397e242SKonrad Dybcio 	P_GCC_GPU_GPLL0_CLK_SRC,
368397e242SKonrad Dybcio 	P_GCC_GPU_GPLL0_DIV_CLK_SRC,
378397e242SKonrad Dybcio 	P_GPU_CC_PLL0_OUT_EVEN,
388397e242SKonrad Dybcio 	P_GPU_CC_PLL0_OUT_MAIN,
398397e242SKonrad Dybcio 	P_GPU_CC_PLL0_OUT_ODD,
408397e242SKonrad Dybcio 	P_GPU_CC_PLL1_OUT_EVEN,
418397e242SKonrad Dybcio 	P_GPU_CC_PLL1_OUT_MAIN,
428397e242SKonrad Dybcio 	P_GPU_CC_PLL1_OUT_ODD,
438397e242SKonrad Dybcio };
448397e242SKonrad Dybcio 
458397e242SKonrad Dybcio static struct pll_vco lucid_vco[] = {
468397e242SKonrad Dybcio 	{ 249600000, 2000000000, 0 },
478397e242SKonrad Dybcio };
488397e242SKonrad Dybcio 
498397e242SKonrad Dybcio /* 532MHz Configuration */
508397e242SKonrad Dybcio static const struct alpha_pll_config gpucc_pll0_config = {
518397e242SKonrad Dybcio 	.l = 0x1b,
528397e242SKonrad Dybcio 	.alpha = 0xb555,
538397e242SKonrad Dybcio 	.config_ctl_val = 0x20485699,
548397e242SKonrad Dybcio 	.config_ctl_hi_val = 0x00002261,
558397e242SKonrad Dybcio 	.config_ctl_hi1_val = 0x329a299c,
568397e242SKonrad Dybcio 	.user_ctl_val = 0x00000001,
578397e242SKonrad Dybcio 	.user_ctl_hi_val = 0x00000805,
588397e242SKonrad Dybcio 	.user_ctl_hi1_val = 0x00000000,
598397e242SKonrad Dybcio };
608397e242SKonrad Dybcio 
618397e242SKonrad Dybcio static struct clk_alpha_pll gpucc_pll0 = {
628397e242SKonrad Dybcio 	.offset = 0x0,
638397e242SKonrad Dybcio 	.vco_table = lucid_vco,
648397e242SKonrad Dybcio 	.num_vco = ARRAY_SIZE(lucid_vco),
658397e242SKonrad Dybcio 	.regs = clk_alpha_pll_regs[CLK_ALPHA_PLL_TYPE_LUCID],
668397e242SKonrad Dybcio 	.clkr = {
678397e242SKonrad Dybcio 		.hw.init = &(struct clk_init_data){
688397e242SKonrad Dybcio 			.name = "gpucc_pll0",
698397e242SKonrad Dybcio 			.parent_data = &(const struct clk_parent_data){
708397e242SKonrad Dybcio 				.index = P_BI_TCXO,
718397e242SKonrad Dybcio 			},
728397e242SKonrad Dybcio 			.num_parents = 1,
738397e242SKonrad Dybcio 			.ops = &clk_alpha_pll_lucid_ops,
748397e242SKonrad Dybcio 		},
758397e242SKonrad Dybcio 	},
768397e242SKonrad Dybcio };
778397e242SKonrad Dybcio 
788397e242SKonrad Dybcio /* 514MHz Configuration */
798397e242SKonrad Dybcio static const struct alpha_pll_config gpucc_pll1_config = {
808397e242SKonrad Dybcio 	.l = 0x1a,
818397e242SKonrad Dybcio 	.alpha = 0xc555,
828397e242SKonrad Dybcio 	.config_ctl_val = 0x20485699,
838397e242SKonrad Dybcio 	.config_ctl_hi_val = 0x00002261,
848397e242SKonrad Dybcio 	.config_ctl_hi1_val = 0x329a299c,
858397e242SKonrad Dybcio 	.user_ctl_val = 0x00000001,
868397e242SKonrad Dybcio 	.user_ctl_hi_val = 0x00000805,
878397e242SKonrad Dybcio 	.user_ctl_hi1_val = 0x00000000,
888397e242SKonrad Dybcio };
898397e242SKonrad Dybcio 
908397e242SKonrad Dybcio static struct clk_alpha_pll gpucc_pll1 = {
918397e242SKonrad Dybcio 	.offset = 0x100,
928397e242SKonrad Dybcio 	.vco_table = lucid_vco,
938397e242SKonrad Dybcio 	.num_vco = ARRAY_SIZE(lucid_vco),
948397e242SKonrad Dybcio 	.regs = clk_alpha_pll_regs[CLK_ALPHA_PLL_TYPE_LUCID],
958397e242SKonrad Dybcio 	.clkr = {
968397e242SKonrad Dybcio 		.hw.init = &(struct clk_init_data){
978397e242SKonrad Dybcio 			.name = "gpucc_pll1",
988397e242SKonrad Dybcio 			.parent_data = &(const struct clk_parent_data){
998397e242SKonrad Dybcio 				.index = P_BI_TCXO,
1008397e242SKonrad Dybcio 			},
1018397e242SKonrad Dybcio 			.num_parents = 1,
1028397e242SKonrad Dybcio 			.ops = &clk_alpha_pll_lucid_ops,
1038397e242SKonrad Dybcio 		},
1048397e242SKonrad Dybcio 	},
1058397e242SKonrad Dybcio };
1068397e242SKonrad Dybcio 
1078397e242SKonrad Dybcio static const struct parent_map gpucc_parent_map_0[] = {
1088397e242SKonrad Dybcio 	{ P_BI_TCXO, 0 },
1098397e242SKonrad Dybcio 	{ P_GPU_CC_PLL0_OUT_MAIN, 1 },
1108397e242SKonrad Dybcio 	{ P_GPU_CC_PLL1_OUT_MAIN, 3 },
1118397e242SKonrad Dybcio 	{ P_GCC_GPU_GPLL0_CLK_SRC, 5 },
1128397e242SKonrad Dybcio 	{ P_GCC_GPU_GPLL0_DIV_CLK_SRC, 6 },
1138397e242SKonrad Dybcio };
1148397e242SKonrad Dybcio 
1158397e242SKonrad Dybcio static const struct clk_parent_data gpucc_parent_data_0[] = {
1168397e242SKonrad Dybcio 	{ .index = P_BI_TCXO },
1178397e242SKonrad Dybcio 	{ .hw = &gpucc_pll0.clkr.hw },
1188397e242SKonrad Dybcio 	{ .hw = &gpucc_pll1.clkr.hw },
1198397e242SKonrad Dybcio 	{ .index = DT_GCC_GPU_GPLL0_CLK_SRC },
1208397e242SKonrad Dybcio 	{ .index = DT_GCC_GPU_GPLL0_DIV_CLK_SRC },
1218397e242SKonrad Dybcio };
1228397e242SKonrad Dybcio 
1238397e242SKonrad Dybcio static const struct parent_map gpucc_parent_map_1[] = {
1248397e242SKonrad Dybcio 	{ P_BI_TCXO, 0 },
1258397e242SKonrad Dybcio 	{ P_GPU_CC_PLL0_OUT_EVEN, 1 },
1268397e242SKonrad Dybcio 	{ P_GPU_CC_PLL0_OUT_ODD, 2 },
1278397e242SKonrad Dybcio 	{ P_GPU_CC_PLL1_OUT_EVEN, 3 },
1288397e242SKonrad Dybcio 	{ P_GPU_CC_PLL1_OUT_ODD, 4 },
1298397e242SKonrad Dybcio 	{ P_GCC_GPU_GPLL0_CLK_SRC, 5 },
1308397e242SKonrad Dybcio };
1318397e242SKonrad Dybcio 
1328397e242SKonrad Dybcio static const struct clk_parent_data gpucc_parent_data_1[] = {
1338397e242SKonrad Dybcio 	{ .index = P_BI_TCXO },
1348397e242SKonrad Dybcio 	{ .hw = &gpucc_pll0.clkr.hw },
1358397e242SKonrad Dybcio 	{ .hw = &gpucc_pll0.clkr.hw },
1368397e242SKonrad Dybcio 	{ .hw = &gpucc_pll1.clkr.hw },
1378397e242SKonrad Dybcio 	{ .hw = &gpucc_pll1.clkr.hw },
1388397e242SKonrad Dybcio 	{ .index = DT_GCC_GPU_GPLL0_CLK_SRC },
1398397e242SKonrad Dybcio };
1408397e242SKonrad Dybcio 
1418397e242SKonrad Dybcio static const struct freq_tbl ftbl_gpucc_gmu_clk_src[] = {
1428397e242SKonrad Dybcio 	F(200000000, P_GCC_GPU_GPLL0_DIV_CLK_SRC, 1.5, 0, 0),
1438397e242SKonrad Dybcio 	{ }
1448397e242SKonrad Dybcio };
1458397e242SKonrad Dybcio 
1468397e242SKonrad Dybcio static struct clk_rcg2 gpucc_gmu_clk_src = {
1478397e242SKonrad Dybcio 	.cmd_rcgr = 0x1120,
1488397e242SKonrad Dybcio 	.mnd_width = 0,
1498397e242SKonrad Dybcio 	.hid_width = 5,
1508397e242SKonrad Dybcio 	.parent_map = gpucc_parent_map_0,
1518397e242SKonrad Dybcio 	.freq_tbl = ftbl_gpucc_gmu_clk_src,
1528397e242SKonrad Dybcio 	.clkr.hw.init = &(struct clk_init_data){
1538397e242SKonrad Dybcio 		.name = "gpucc_gmu_clk_src",
1548397e242SKonrad Dybcio 		.parent_data = gpucc_parent_data_0,
1558397e242SKonrad Dybcio 		.num_parents = ARRAY_SIZE(gpucc_parent_data_0),
1568397e242SKonrad Dybcio 		.ops = &clk_rcg2_shared_ops,
1578397e242SKonrad Dybcio 	},
1588397e242SKonrad Dybcio };
1598397e242SKonrad Dybcio 
1608397e242SKonrad Dybcio static const struct freq_tbl ftbl_gpucc_gx_gfx3d_clk_src[] = {
1618397e242SKonrad Dybcio 	F(266000000, P_GPU_CC_PLL0_OUT_EVEN, 2, 0, 0),
1628397e242SKonrad Dybcio 	F(390000000, P_GPU_CC_PLL0_OUT_EVEN, 2, 0, 0),
1638397e242SKonrad Dybcio 	F(490000000, P_GPU_CC_PLL0_OUT_EVEN, 2, 0, 0),
1648397e242SKonrad Dybcio 	F(650000000, P_GPU_CC_PLL0_OUT_EVEN, 2, 0, 0),
1658397e242SKonrad Dybcio 	F(770000000, P_GPU_CC_PLL0_OUT_EVEN, 2, 0, 0),
1668397e242SKonrad Dybcio 	F(840000000, P_GPU_CC_PLL0_OUT_EVEN, 2, 0, 0),
1678397e242SKonrad Dybcio 	F(900000000, P_GPU_CC_PLL0_OUT_EVEN, 2, 0, 0),
1688397e242SKonrad Dybcio 	{ }
1698397e242SKonrad Dybcio };
1708397e242SKonrad Dybcio 
1718397e242SKonrad Dybcio static struct clk_rcg2 gpucc_gx_gfx3d_clk_src = {
1728397e242SKonrad Dybcio 	.cmd_rcgr = 0x101c,
1738397e242SKonrad Dybcio 	.mnd_width = 0,
1748397e242SKonrad Dybcio 	.hid_width = 5,
1758397e242SKonrad Dybcio 	.parent_map = gpucc_parent_map_1,
1768397e242SKonrad Dybcio 	.freq_tbl = ftbl_gpucc_gx_gfx3d_clk_src,
1778397e242SKonrad Dybcio 	.clkr.hw.init = &(struct clk_init_data){
1788397e242SKonrad Dybcio 		.name = "gpucc_gx_gfx3d_clk_src",
1798397e242SKonrad Dybcio 		.parent_data = gpucc_parent_data_1,
1808397e242SKonrad Dybcio 		.num_parents = ARRAY_SIZE(gpucc_parent_data_1),
1818397e242SKonrad Dybcio 		.flags = CLK_SET_RATE_PARENT | CLK_OPS_PARENT_ENABLE,
1828397e242SKonrad Dybcio 		.ops = &clk_rcg2_ops,
1838397e242SKonrad Dybcio 	},
1848397e242SKonrad Dybcio };
1858397e242SKonrad Dybcio 
1868397e242SKonrad Dybcio static struct clk_branch gpucc_ahb_clk = {
1878397e242SKonrad Dybcio 	.halt_reg = 0x1078,
1888397e242SKonrad Dybcio 	.halt_check = BRANCH_HALT_DELAY,
1898397e242SKonrad Dybcio 	.clkr = {
1908397e242SKonrad Dybcio 		.enable_reg = 0x1078,
1918397e242SKonrad Dybcio 		.enable_mask = BIT(0),
1928397e242SKonrad Dybcio 		.hw.init = &(struct clk_init_data){
1938397e242SKonrad Dybcio 			.name = "gpucc_ahb_clk",
1948397e242SKonrad Dybcio 			.flags = CLK_IS_CRITICAL,
1958397e242SKonrad Dybcio 			.ops = &clk_branch2_ops,
1968397e242SKonrad Dybcio 		},
1978397e242SKonrad Dybcio 	},
1988397e242SKonrad Dybcio };
1998397e242SKonrad Dybcio 
2008397e242SKonrad Dybcio static struct clk_branch gpucc_cx_gfx3d_clk = {
2018397e242SKonrad Dybcio 	.halt_reg = 0x10a4,
2028397e242SKonrad Dybcio 	.halt_check = BRANCH_HALT_DELAY,
2038397e242SKonrad Dybcio 	.clkr = {
2048397e242SKonrad Dybcio 		.enable_reg = 0x10a4,
2058397e242SKonrad Dybcio 		.enable_mask = BIT(0),
2068397e242SKonrad Dybcio 		.hw.init = &(struct clk_init_data){
2078397e242SKonrad Dybcio 			.name = "gpucc_cx_gfx3d_clk",
2088397e242SKonrad Dybcio 			.parent_hws = (const struct clk_hw*[]) {
2098397e242SKonrad Dybcio 				&gpucc_gx_gfx3d_clk_src.clkr.hw,
2108397e242SKonrad Dybcio 			},
2118397e242SKonrad Dybcio 			.num_parents = 1,
2128397e242SKonrad Dybcio 			.flags = CLK_SET_RATE_PARENT,
2138397e242SKonrad Dybcio 			.ops = &clk_branch2_ops,
2148397e242SKonrad Dybcio 		},
2158397e242SKonrad Dybcio 	},
2168397e242SKonrad Dybcio };
2178397e242SKonrad Dybcio 
2188397e242SKonrad Dybcio static struct clk_branch gpucc_cx_gfx3d_slv_clk = {
2198397e242SKonrad Dybcio 	.halt_reg = 0x10a8,
2208397e242SKonrad Dybcio 	.halt_check = BRANCH_HALT_DELAY,
2218397e242SKonrad Dybcio 	.clkr = {
2228397e242SKonrad Dybcio 		.enable_reg = 0x10a8,
2238397e242SKonrad Dybcio 		.enable_mask = BIT(0),
2248397e242SKonrad Dybcio 		.hw.init = &(struct clk_init_data){
2258397e242SKonrad Dybcio 			.name = "gpucc_cx_gfx3d_slv_clk",
2268397e242SKonrad Dybcio 			.parent_hws = (const struct clk_hw*[]) {
2278397e242SKonrad Dybcio 				&gpucc_gx_gfx3d_clk_src.clkr.hw,
2288397e242SKonrad Dybcio 			},
2298397e242SKonrad Dybcio 			.num_parents = 1,
2308397e242SKonrad Dybcio 			.flags = CLK_SET_RATE_PARENT,
2318397e242SKonrad Dybcio 			.ops = &clk_branch2_ops,
2328397e242SKonrad Dybcio 		},
2338397e242SKonrad Dybcio 	},
2348397e242SKonrad Dybcio };
2358397e242SKonrad Dybcio 
2368397e242SKonrad Dybcio static struct clk_branch gpucc_cx_gmu_clk = {
2378397e242SKonrad Dybcio 	.halt_reg = 0x1098,
2388397e242SKonrad Dybcio 	.halt_check = BRANCH_HALT,
2398397e242SKonrad Dybcio 	.clkr = {
2408397e242SKonrad Dybcio 		.enable_reg = 0x1098,
2418397e242SKonrad Dybcio 		.enable_mask = BIT(0),
2428397e242SKonrad Dybcio 		.hw.init = &(struct clk_init_data){
2438397e242SKonrad Dybcio 			.name = "gpucc_cx_gmu_clk",
2448397e242SKonrad Dybcio 			.parent_hws = (const struct clk_hw*[]) {
2458397e242SKonrad Dybcio 				&gpucc_gmu_clk_src.clkr.hw,
2468397e242SKonrad Dybcio 			},
2478397e242SKonrad Dybcio 			.num_parents = 1,
2488397e242SKonrad Dybcio 			.flags = CLK_SET_RATE_PARENT,
2498397e242SKonrad Dybcio 			.ops = &clk_branch2_ops,
2508397e242SKonrad Dybcio 		},
2518397e242SKonrad Dybcio 	},
2528397e242SKonrad Dybcio };
2538397e242SKonrad Dybcio 
2548397e242SKonrad Dybcio static struct clk_branch gpucc_cx_snoc_dvm_clk = {
2558397e242SKonrad Dybcio 	.halt_reg = 0x108c,
2568397e242SKonrad Dybcio 	.halt_check = BRANCH_HALT_DELAY,
2578397e242SKonrad Dybcio 	.clkr = {
2588397e242SKonrad Dybcio 		.enable_reg = 0x108c,
2598397e242SKonrad Dybcio 		.enable_mask = BIT(0),
2608397e242SKonrad Dybcio 		.hw.init = &(struct clk_init_data){
2618397e242SKonrad Dybcio 			.name = "gpucc_cx_snoc_dvm_clk",
2628397e242SKonrad Dybcio 			.parent_data = &(const struct clk_parent_data){
2638397e242SKonrad Dybcio 				.index = DT_GCC_GPU_SNOC_DVM_GFX_CLK,
2648397e242SKonrad Dybcio 			},
2658397e242SKonrad Dybcio 			.num_parents = 1,
2668397e242SKonrad Dybcio 			.ops = &clk_branch2_ops,
2678397e242SKonrad Dybcio 		},
2688397e242SKonrad Dybcio 	},
2698397e242SKonrad Dybcio };
2708397e242SKonrad Dybcio 
2718397e242SKonrad Dybcio static struct clk_branch gpucc_cxo_aon_clk = {
2728397e242SKonrad Dybcio 	.halt_reg = 0x1004,
2738397e242SKonrad Dybcio 	.halt_check = BRANCH_HALT_DELAY,
2748397e242SKonrad Dybcio 	.clkr = {
2758397e242SKonrad Dybcio 		.enable_reg = 0x1004,
2768397e242SKonrad Dybcio 		.enable_mask = BIT(0),
2778397e242SKonrad Dybcio 		.hw.init = &(struct clk_init_data){
2788397e242SKonrad Dybcio 			.name = "gpucc_cxo_aon_clk",
2798397e242SKonrad Dybcio 			.ops = &clk_branch2_ops,
2808397e242SKonrad Dybcio 		},
2818397e242SKonrad Dybcio 	},
2828397e242SKonrad Dybcio };
2838397e242SKonrad Dybcio 
2848397e242SKonrad Dybcio static struct clk_branch gpucc_cxo_clk = {
2858397e242SKonrad Dybcio 	.halt_reg = 0x109c,
2868397e242SKonrad Dybcio 	.halt_check = BRANCH_HALT,
2878397e242SKonrad Dybcio 	.clkr = {
2888397e242SKonrad Dybcio 		.enable_reg = 0x109c,
2898397e242SKonrad Dybcio 		.enable_mask = BIT(0),
2908397e242SKonrad Dybcio 		.hw.init = &(struct clk_init_data){
2918397e242SKonrad Dybcio 			.name = "gpucc_cxo_clk",
2928397e242SKonrad Dybcio 			.ops = &clk_branch2_ops,
2938397e242SKonrad Dybcio 		},
2948397e242SKonrad Dybcio 	},
2958397e242SKonrad Dybcio };
2968397e242SKonrad Dybcio 
2978397e242SKonrad Dybcio static struct clk_branch gpucc_gx_cxo_clk = {
2988397e242SKonrad Dybcio 	.halt_reg = 0x1060,
2998397e242SKonrad Dybcio 	.halt_check = BRANCH_HALT_DELAY,
3008397e242SKonrad Dybcio 	.clkr = {
3018397e242SKonrad Dybcio 		.enable_reg = 0x1060,
3028397e242SKonrad Dybcio 		.enable_mask = BIT(0),
3038397e242SKonrad Dybcio 		.hw.init = &(struct clk_init_data){
3048397e242SKonrad Dybcio 			.name = "gpucc_gx_cxo_clk",
3058397e242SKonrad Dybcio 			.flags = CLK_IS_CRITICAL,
3068397e242SKonrad Dybcio 			.ops = &clk_branch2_ops,
3078397e242SKonrad Dybcio 		},
3088397e242SKonrad Dybcio 	},
3098397e242SKonrad Dybcio };
3108397e242SKonrad Dybcio 
3118397e242SKonrad Dybcio static struct clk_branch gpucc_gx_gfx3d_clk = {
3128397e242SKonrad Dybcio 	.halt_reg = 0x1054,
3138397e242SKonrad Dybcio 	.halt_check = BRANCH_HALT_DELAY,
3148397e242SKonrad Dybcio 	.clkr = {
3158397e242SKonrad Dybcio 		.enable_reg = 0x1054,
3168397e242SKonrad Dybcio 		.enable_mask = BIT(0),
3178397e242SKonrad Dybcio 		.hw.init = &(struct clk_init_data){
3188397e242SKonrad Dybcio 			.name = "gpucc_gx_gfx3d_clk",
3198397e242SKonrad Dybcio 			.parent_hws = (const struct clk_hw*[]) {
3208397e242SKonrad Dybcio 				&gpucc_gx_gfx3d_clk_src.clkr.hw,
3218397e242SKonrad Dybcio 			},
3228397e242SKonrad Dybcio 			.num_parents = 1,
3238397e242SKonrad Dybcio 			.flags = CLK_SET_RATE_PARENT,
3248397e242SKonrad Dybcio 			.ops = &clk_branch2_ops,
3258397e242SKonrad Dybcio 		},
3268397e242SKonrad Dybcio 	},
3278397e242SKonrad Dybcio };
3288397e242SKonrad Dybcio 
3298397e242SKonrad Dybcio static struct clk_branch gpucc_gx_gmu_clk = {
3308397e242SKonrad Dybcio 	.halt_reg = 0x1064,
3318397e242SKonrad Dybcio 	.halt_check = BRANCH_HALT,
3328397e242SKonrad Dybcio 	.clkr = {
3338397e242SKonrad Dybcio 		.enable_reg = 0x1064,
3348397e242SKonrad Dybcio 		.enable_mask = BIT(0),
3358397e242SKonrad Dybcio 		.hw.init = &(struct clk_init_data){
3368397e242SKonrad Dybcio 			.name = "gpucc_gx_gmu_clk",
3378397e242SKonrad Dybcio 			.parent_hws = (const struct clk_hw*[]) {
3388397e242SKonrad Dybcio 				&gpucc_gmu_clk_src.clkr.hw,
3398397e242SKonrad Dybcio 			},
3408397e242SKonrad Dybcio 			.num_parents = 1,
3418397e242SKonrad Dybcio 			.flags = CLK_SET_RATE_PARENT,
3428397e242SKonrad Dybcio 			.ops = &clk_branch2_ops,
3438397e242SKonrad Dybcio 		},
3448397e242SKonrad Dybcio 	},
3458397e242SKonrad Dybcio };
3468397e242SKonrad Dybcio 
3478397e242SKonrad Dybcio static struct clk_branch gpucc_sleep_clk = {
3488397e242SKonrad Dybcio 	.halt_reg = 0x1090,
3498397e242SKonrad Dybcio 	.halt_check = BRANCH_HALT_VOTED,
3508397e242SKonrad Dybcio 	.clkr = {
3518397e242SKonrad Dybcio 		.enable_reg = 0x1090,
3528397e242SKonrad Dybcio 		.enable_mask = BIT(0),
3538397e242SKonrad Dybcio 		.hw.init = &(struct clk_init_data){
3548397e242SKonrad Dybcio 			.name = "gpucc_sleep_clk",
3558397e242SKonrad Dybcio 			.ops = &clk_branch2_ops,
3568397e242SKonrad Dybcio 		},
3578397e242SKonrad Dybcio 	},
3588397e242SKonrad Dybcio };
3598397e242SKonrad Dybcio 
3608397e242SKonrad Dybcio static struct gdsc gpu_cx_gdsc = {
3618397e242SKonrad Dybcio 	.gdscr = 0x106c,
3628397e242SKonrad Dybcio 	.gds_hw_ctrl = 0x1540,
36393f21d92SKonrad Dybcio 	.clk_dis_wait_val = 8,
3648397e242SKonrad Dybcio 	.pd = {
3658397e242SKonrad Dybcio 		.name = "gpu_cx_gdsc",
3668397e242SKonrad Dybcio 	},
3678397e242SKonrad Dybcio 	.pwrsts = PWRSTS_OFF_ON,
3688397e242SKonrad Dybcio 	.flags = VOTABLE,
3698397e242SKonrad Dybcio };
3708397e242SKonrad Dybcio 
3718397e242SKonrad Dybcio static struct gdsc gpu_gx_gdsc = {
3728397e242SKonrad Dybcio 	.gdscr = 0x100c,
3738397e242SKonrad Dybcio 	.clamp_io_ctrl = 0x1508,
3748397e242SKonrad Dybcio 	.resets = (unsigned int []){ GPU_GX_BCR, GPU_ACD_BCR, GPU_GX_ACD_MISC_BCR },
3758397e242SKonrad Dybcio 	.reset_count = 3,
3768397e242SKonrad Dybcio 	.pd = {
3778397e242SKonrad Dybcio 		.name = "gpu_gx_gdsc",
3788397e242SKonrad Dybcio 	},
3798397e242SKonrad Dybcio 	.pwrsts = PWRSTS_OFF_ON,
3808397e242SKonrad Dybcio 	.flags = CLAMP_IO | SW_RESET | AON_RESET,
3818397e242SKonrad Dybcio };
3828397e242SKonrad Dybcio 
3838397e242SKonrad Dybcio static struct clk_regmap *gpucc_sm6375_clocks[] = {
3848397e242SKonrad Dybcio 	[GPU_CC_AHB_CLK] = &gpucc_ahb_clk.clkr,
3858397e242SKonrad Dybcio 	[GPU_CC_CX_GFX3D_CLK] = &gpucc_cx_gfx3d_clk.clkr,
3868397e242SKonrad Dybcio 	[GPU_CC_CX_GFX3D_SLV_CLK] = &gpucc_cx_gfx3d_slv_clk.clkr,
3878397e242SKonrad Dybcio 	[GPU_CC_CX_GMU_CLK] = &gpucc_cx_gmu_clk.clkr,
3888397e242SKonrad Dybcio 	[GPU_CC_CX_SNOC_DVM_CLK] = &gpucc_cx_snoc_dvm_clk.clkr,
3898397e242SKonrad Dybcio 	[GPU_CC_CXO_AON_CLK] = &gpucc_cxo_aon_clk.clkr,
3908397e242SKonrad Dybcio 	[GPU_CC_CXO_CLK] = &gpucc_cxo_clk.clkr,
3918397e242SKonrad Dybcio 	[GPU_CC_GMU_CLK_SRC] = &gpucc_gmu_clk_src.clkr,
3928397e242SKonrad Dybcio 	[GPU_CC_GX_CXO_CLK] = &gpucc_gx_cxo_clk.clkr,
3938397e242SKonrad Dybcio 	[GPU_CC_GX_GFX3D_CLK] = &gpucc_gx_gfx3d_clk.clkr,
3948397e242SKonrad Dybcio 	[GPU_CC_GX_GFX3D_CLK_SRC] = &gpucc_gx_gfx3d_clk_src.clkr,
3958397e242SKonrad Dybcio 	[GPU_CC_GX_GMU_CLK] = &gpucc_gx_gmu_clk.clkr,
3968397e242SKonrad Dybcio 	[GPU_CC_PLL0] = &gpucc_pll0.clkr,
3978397e242SKonrad Dybcio 	[GPU_CC_PLL1] = &gpucc_pll1.clkr,
3988397e242SKonrad Dybcio 	[GPU_CC_SLEEP_CLK] = &gpucc_sleep_clk.clkr,
3998397e242SKonrad Dybcio };
4008397e242SKonrad Dybcio 
4018397e242SKonrad Dybcio static const struct qcom_reset_map gpucc_sm6375_resets[] = {
4028397e242SKonrad Dybcio 	[GPU_GX_BCR] = { 0x1008 },
4038397e242SKonrad Dybcio 	[GPU_ACD_BCR] = { 0x1160 },
4048397e242SKonrad Dybcio 	[GPU_GX_ACD_MISC_BCR] = { 0x8004 },
4058397e242SKonrad Dybcio };
4068397e242SKonrad Dybcio 
4078397e242SKonrad Dybcio static struct gdsc *gpucc_sm6375_gdscs[] = {
4088397e242SKonrad Dybcio 	[GPU_CX_GDSC] = &gpu_cx_gdsc,
4098397e242SKonrad Dybcio 	[GPU_GX_GDSC] = &gpu_gx_gdsc,
4108397e242SKonrad Dybcio };
4118397e242SKonrad Dybcio 
4128397e242SKonrad Dybcio static const struct regmap_config gpucc_sm6375_regmap_config = {
4138397e242SKonrad Dybcio 	.reg_bits = 32,
4148397e242SKonrad Dybcio 	.reg_stride = 4,
4158397e242SKonrad Dybcio 	.val_bits = 32,
4168397e242SKonrad Dybcio 	.max_register = 0x9000,
4178397e242SKonrad Dybcio 	.fast_io = true,
4188397e242SKonrad Dybcio };
4198397e242SKonrad Dybcio 
4208397e242SKonrad Dybcio static const struct qcom_cc_desc gpucc_sm6375_desc = {
4218397e242SKonrad Dybcio 	.config = &gpucc_sm6375_regmap_config,
4228397e242SKonrad Dybcio 	.clks = gpucc_sm6375_clocks,
4238397e242SKonrad Dybcio 	.num_clks = ARRAY_SIZE(gpucc_sm6375_clocks),
4248397e242SKonrad Dybcio 	.resets = gpucc_sm6375_resets,
4258397e242SKonrad Dybcio 	.num_resets = ARRAY_SIZE(gpucc_sm6375_resets),
4268397e242SKonrad Dybcio 	.gdscs = gpucc_sm6375_gdscs,
4278397e242SKonrad Dybcio 	.num_gdscs = ARRAY_SIZE(gpucc_sm6375_gdscs),
4288397e242SKonrad Dybcio };
4298397e242SKonrad Dybcio 
4308397e242SKonrad Dybcio static const struct of_device_id gpucc_sm6375_match_table[] = {
4318397e242SKonrad Dybcio 	{ .compatible = "qcom,sm6375-gpucc" },
4328397e242SKonrad Dybcio 	{ }
4338397e242SKonrad Dybcio };
4348397e242SKonrad Dybcio MODULE_DEVICE_TABLE(of, gpucc_sm6375_match_table);
4358397e242SKonrad Dybcio 
gpucc_sm6375_probe(struct platform_device * pdev)4368397e242SKonrad Dybcio static int gpucc_sm6375_probe(struct platform_device *pdev)
4378397e242SKonrad Dybcio {
4388397e242SKonrad Dybcio 	struct regmap *regmap;
439097d359cSKonrad Dybcio 	int ret;
440097d359cSKonrad Dybcio 
441097d359cSKonrad Dybcio 	ret = devm_pm_runtime_enable(&pdev->dev);
442097d359cSKonrad Dybcio 	if (ret)
443097d359cSKonrad Dybcio 		return ret;
444097d359cSKonrad Dybcio 
445097d359cSKonrad Dybcio 	ret = pm_runtime_resume_and_get(&pdev->dev);
446097d359cSKonrad Dybcio 	if (ret)
447097d359cSKonrad Dybcio 		return ret;
4488397e242SKonrad Dybcio 
4498397e242SKonrad Dybcio 	regmap = qcom_cc_map(pdev, &gpucc_sm6375_desc);
450097d359cSKonrad Dybcio 	if (IS_ERR(regmap)) {
451097d359cSKonrad Dybcio 		pm_runtime_put(&pdev->dev);
4528397e242SKonrad Dybcio 		return PTR_ERR(regmap);
453097d359cSKonrad Dybcio 	}
4548397e242SKonrad Dybcio 
4558397e242SKonrad Dybcio 	clk_lucid_pll_configure(&gpucc_pll0, regmap, &gpucc_pll0_config);
4568397e242SKonrad Dybcio 	clk_lucid_pll_configure(&gpucc_pll1, regmap, &gpucc_pll1_config);
4578397e242SKonrad Dybcio 
458097d359cSKonrad Dybcio 	ret = qcom_cc_really_probe(pdev, &gpucc_sm6375_desc, regmap);
459097d359cSKonrad Dybcio 	pm_runtime_put(&pdev->dev);
460097d359cSKonrad Dybcio 
461097d359cSKonrad Dybcio 	return ret;
4628397e242SKonrad Dybcio }
4638397e242SKonrad Dybcio 
4648397e242SKonrad Dybcio static struct platform_driver gpucc_sm6375_driver = {
4658397e242SKonrad Dybcio 	.probe = gpucc_sm6375_probe,
4668397e242SKonrad Dybcio 	.driver = {
4678397e242SKonrad Dybcio 		.name = "gpucc-sm6375",
4688397e242SKonrad Dybcio 		.of_match_table = gpucc_sm6375_match_table,
4698397e242SKonrad Dybcio 	},
4708397e242SKonrad Dybcio };
4718397e242SKonrad Dybcio module_platform_driver(gpucc_sm6375_driver);
4728397e242SKonrad Dybcio 
4738397e242SKonrad Dybcio MODULE_DESCRIPTION("QTI GPUCC SM6375 Driver");
4748397e242SKonrad Dybcio MODULE_LICENSE("GPL");
475