1 // SPDX-License-Identifier: GPL-2.0
3 * Copyright (c) 2017-2020, The Linux Foundation. All rights reserved.
6 #include <linux/clk-provider.h>
7 #include <linux/module.h>
8 #include <linux/platform_device.h>
9 #include <linux/regmap.h>
11 #include <dt-bindings/clock/qcom,gpucc-sm8150.h>
14 #include "clk-alpha-pll.h"
15 #include "clk-branch.h"
18 #include "clk-regmap.h"
26 P_GPU_CC_PLL1_OUT_MAIN
,
29 static const struct pll_vco trion_vco
[] = {
30 { 249600000, 2000000000, 0 },
33 static struct alpha_pll_config gpu_cc_pll1_config
= {
36 .config_ctl_val
= 0x20485699,
37 .config_ctl_hi_val
= 0x00002267,
38 .config_ctl_hi1_val
= 0x00000024,
39 .test_ctl_val
= 0x00000000,
40 .test_ctl_hi_val
= 0x00000000,
41 .test_ctl_hi1_val
= 0x00000020,
42 .user_ctl_val
= 0x00000000,
43 .user_ctl_hi_val
= 0x00000805,
44 .user_ctl_hi1_val
= 0x000000d0,
47 static struct clk_alpha_pll gpu_cc_pll1
= {
49 .vco_table
= trion_vco
,
50 .num_vco
= ARRAY_SIZE(trion_vco
),
51 .regs
= clk_alpha_pll_regs
[CLK_ALPHA_PLL_TYPE_TRION
],
53 .hw
.init
= &(struct clk_init_data
){
54 .name
= "gpu_cc_pll1",
55 .parent_data
= &(const struct clk_parent_data
){
59 .ops
= &clk_alpha_pll_trion_ops
,
64 static const struct parent_map gpu_cc_parent_map_0
[] = {
66 { P_GPU_CC_PLL1_OUT_MAIN
, 3 },
67 { P_GPLL0_OUT_MAIN
, 5 },
68 { P_GPLL0_OUT_MAIN_DIV
, 6 },
71 static const struct clk_parent_data gpu_cc_parent_data_0
[] = {
72 { .fw_name
= "bi_tcxo" },
73 { .hw
= &gpu_cc_pll1
.clkr
.hw
},
74 { .fw_name
= "gcc_gpu_gpll0_clk_src" },
75 { .fw_name
= "gcc_gpu_gpll0_div_clk_src" },
78 static const struct freq_tbl ftbl_gpu_cc_gmu_clk_src
[] = {
79 F(19200000, P_BI_TCXO
, 1, 0, 0),
80 F(200000000, P_GPLL0_OUT_MAIN_DIV
, 1.5, 0, 0),
81 F(500000000, P_GPU_CC_PLL1_OUT_MAIN
, 1, 0, 0),
85 static const struct freq_tbl ftbl_gpu_cc_gmu_clk_src_sc8180x
[] = {
86 F(19200000, P_BI_TCXO
, 1, 0, 0),
87 F(200000000, P_GPLL0_OUT_MAIN_DIV
, 1.5, 0, 0),
88 F(400000000, P_GPLL0_OUT_MAIN
, 1.5, 0, 0),
89 F(500000000, P_GPU_CC_PLL1_OUT_MAIN
, 1, 0, 0),
93 static struct clk_rcg2 gpu_cc_gmu_clk_src
= {
97 .parent_map
= gpu_cc_parent_map_0
,
98 .freq_tbl
= ftbl_gpu_cc_gmu_clk_src
,
99 .clkr
.hw
.init
= &(struct clk_init_data
){
100 .name
= "gpu_cc_gmu_clk_src",
101 .parent_data
= gpu_cc_parent_data_0
,
102 .num_parents
= ARRAY_SIZE(gpu_cc_parent_data_0
),
103 .flags
= CLK_SET_RATE_PARENT
,
104 .ops
= &clk_rcg2_ops
,
108 static struct clk_branch gpu_cc_ahb_clk
= {
110 .halt_check
= BRANCH_HALT_DELAY
,
112 .enable_reg
= 0x1078,
113 .enable_mask
= BIT(0),
114 .hw
.init
= &(struct clk_init_data
){
115 .name
= "gpu_cc_ahb_clk",
116 .ops
= &clk_branch2_ops
,
121 static struct clk_branch gpu_cc_crc_ahb_clk
= {
123 .halt_check
= BRANCH_HALT
,
125 .enable_reg
= 0x107c,
126 .enable_mask
= BIT(0),
127 .hw
.init
= &(struct clk_init_data
){
128 .name
= "gpu_cc_crc_ahb_clk",
129 .ops
= &clk_branch2_ops
,
134 static struct clk_branch gpu_cc_cx_apb_clk
= {
136 .halt_check
= BRANCH_HALT
,
138 .enable_reg
= 0x1088,
139 .enable_mask
= BIT(0),
140 .hw
.init
= &(struct clk_init_data
){
141 .name
= "gpu_cc_cx_apb_clk",
142 .ops
= &clk_branch2_ops
,
147 static struct clk_branch gpu_cc_cx_gmu_clk
= {
149 .halt_check
= BRANCH_HALT
,
151 .enable_reg
= 0x1098,
152 .enable_mask
= BIT(0),
153 .hw
.init
= &(struct clk_init_data
){
154 .name
= "gpu_cc_cx_gmu_clk",
155 .parent_hws
= (const struct clk_hw
*[]){
156 &gpu_cc_gmu_clk_src
.clkr
.hw
,
159 .flags
= CLK_SET_RATE_PARENT
,
160 .ops
= &clk_branch2_ops
,
165 static struct clk_branch gpu_cc_cx_snoc_dvm_clk
= {
167 .halt_check
= BRANCH_HALT
,
169 .enable_reg
= 0x108c,
170 .enable_mask
= BIT(0),
171 .hw
.init
= &(struct clk_init_data
){
172 .name
= "gpu_cc_cx_snoc_dvm_clk",
173 .ops
= &clk_branch2_ops
,
178 static struct clk_branch gpu_cc_cxo_aon_clk
= {
180 .halt_check
= BRANCH_HALT
,
182 .enable_reg
= 0x1004,
183 .enable_mask
= BIT(0),
184 .hw
.init
= &(struct clk_init_data
){
185 .name
= "gpu_cc_cxo_aon_clk",
186 .ops
= &clk_branch2_ops
,
191 static struct clk_branch gpu_cc_cxo_clk
= {
193 .halt_check
= BRANCH_HALT
,
195 .enable_reg
= 0x109c,
196 .enable_mask
= BIT(0),
197 .hw
.init
= &(struct clk_init_data
){
198 .name
= "gpu_cc_cxo_clk",
199 .ops
= &clk_branch2_ops
,
204 static struct clk_branch gpu_cc_gx_gmu_clk
= {
206 .halt_check
= BRANCH_HALT
,
208 .enable_reg
= 0x1064,
209 .enable_mask
= BIT(0),
210 .hw
.init
= &(struct clk_init_data
){
211 .name
= "gpu_cc_gx_gmu_clk",
212 .parent_hws
= (const struct clk_hw
*[]){
213 &gpu_cc_gmu_clk_src
.clkr
.hw
,
216 .flags
= CLK_SET_RATE_PARENT
,
217 .ops
= &clk_branch2_ops
,
222 static struct gdsc gpu_cx_gdsc
= {
224 .gds_hw_ctrl
= 0x1540,
226 .name
= "gpu_cx_gdsc",
228 .pwrsts
= PWRSTS_OFF_ON
,
232 static struct gdsc gpu_gx_gdsc
= {
234 .clamp_io_ctrl
= 0x1508,
236 .name
= "gpu_gx_gdsc",
237 .power_on
= gdsc_gx_do_nothing_enable
,
239 .pwrsts
= PWRSTS_OFF_ON
,
240 .flags
= CLAMP_IO
| AON_RESET
| POLL_CFG_GDSCR
,
243 static struct clk_regmap
*gpu_cc_sm8150_clocks
[] = {
244 [GPU_CC_AHB_CLK
] = &gpu_cc_ahb_clk
.clkr
,
245 [GPU_CC_CRC_AHB_CLK
] = &gpu_cc_crc_ahb_clk
.clkr
,
246 [GPU_CC_CX_APB_CLK
] = &gpu_cc_cx_apb_clk
.clkr
,
247 [GPU_CC_CX_GMU_CLK
] = &gpu_cc_cx_gmu_clk
.clkr
,
248 [GPU_CC_CX_SNOC_DVM_CLK
] = &gpu_cc_cx_snoc_dvm_clk
.clkr
,
249 [GPU_CC_CXO_AON_CLK
] = &gpu_cc_cxo_aon_clk
.clkr
,
250 [GPU_CC_CXO_CLK
] = &gpu_cc_cxo_clk
.clkr
,
251 [GPU_CC_GMU_CLK_SRC
] = &gpu_cc_gmu_clk_src
.clkr
,
252 [GPU_CC_GX_GMU_CLK
] = &gpu_cc_gx_gmu_clk
.clkr
,
253 [GPU_CC_PLL1
] = &gpu_cc_pll1
.clkr
,
256 static const struct qcom_reset_map gpu_cc_sm8150_resets
[] = {
257 [GPUCC_GPU_CC_CX_BCR
] = { 0x1068 },
258 [GPUCC_GPU_CC_GMU_BCR
] = { 0x111c },
259 [GPUCC_GPU_CC_GX_BCR
] = { 0x1008 },
260 [GPUCC_GPU_CC_SPDM_BCR
] = { 0x1110 },
261 [GPUCC_GPU_CC_XO_BCR
] = { 0x1000 },
264 static struct gdsc
*gpu_cc_sm8150_gdscs
[] = {
265 [GPU_CX_GDSC
] = &gpu_cx_gdsc
,
266 [GPU_GX_GDSC
] = &gpu_gx_gdsc
,
269 static const struct regmap_config gpu_cc_sm8150_regmap_config
= {
273 .max_register
= 0x8008,
277 static const struct qcom_cc_desc gpu_cc_sm8150_desc
= {
278 .config
= &gpu_cc_sm8150_regmap_config
,
279 .clks
= gpu_cc_sm8150_clocks
,
280 .num_clks
= ARRAY_SIZE(gpu_cc_sm8150_clocks
),
281 .resets
= gpu_cc_sm8150_resets
,
282 .num_resets
= ARRAY_SIZE(gpu_cc_sm8150_resets
),
283 .gdscs
= gpu_cc_sm8150_gdscs
,
284 .num_gdscs
= ARRAY_SIZE(gpu_cc_sm8150_gdscs
),
287 static const struct of_device_id gpu_cc_sm8150_match_table
[] = {
288 { .compatible
= "qcom,sc8180x-gpucc" },
289 { .compatible
= "qcom,sm8150-gpucc" },
292 MODULE_DEVICE_TABLE(of
, gpu_cc_sm8150_match_table
);
294 static int gpu_cc_sm8150_probe(struct platform_device
*pdev
)
296 struct regmap
*regmap
;
298 regmap
= qcom_cc_map(pdev
, &gpu_cc_sm8150_desc
);
300 return PTR_ERR(regmap
);
302 if (of_device_is_compatible(pdev
->dev
.of_node
, "qcom,sc8180x-gpucc"))
303 gpu_cc_gmu_clk_src
.freq_tbl
= ftbl_gpu_cc_gmu_clk_src_sc8180x
;
305 clk_trion_pll_configure(&gpu_cc_pll1
, regmap
, &gpu_cc_pll1_config
);
307 return qcom_cc_really_probe(&pdev
->dev
, &gpu_cc_sm8150_desc
, regmap
);
310 static struct platform_driver gpu_cc_sm8150_driver
= {
311 .probe
= gpu_cc_sm8150_probe
,
313 .name
= "sm8150-gpucc",
314 .of_match_table
= gpu_cc_sm8150_match_table
,
318 module_platform_driver(gpu_cc_sm8150_driver
);
320 MODULE_DESCRIPTION("QTI GPUCC SM8150 Driver");
321 MODULE_LICENSE("GPL v2");