1*092209f1SKonrad Dybcio // SPDX-License-Identifier: GPL-2.0-only 2*092209f1SKonrad Dybcio /* 3*092209f1SKonrad Dybcio * Copyright (c) 2019-2020, The Linux Foundation. All rights reserved. 4*092209f1SKonrad Dybcio * Copyright (c) 2023, Linaro Limited 5*092209f1SKonrad Dybcio */ 6*092209f1SKonrad Dybcio 7*092209f1SKonrad Dybcio #include <linux/clk-provider.h> 8*092209f1SKonrad Dybcio #include <linux/module.h> 9*092209f1SKonrad Dybcio #include <linux/of_device.h> 10*092209f1SKonrad Dybcio #include <linux/regmap.h> 11*092209f1SKonrad Dybcio 12*092209f1SKonrad Dybcio #include <dt-bindings/clock/qcom,sm6115-gpucc.h> 13*092209f1SKonrad Dybcio 14*092209f1SKonrad Dybcio #include "clk-alpha-pll.h" 15*092209f1SKonrad Dybcio #include "clk-branch.h" 16*092209f1SKonrad Dybcio #include "clk-rcg.h" 17*092209f1SKonrad Dybcio #include "clk-regmap.h" 18*092209f1SKonrad Dybcio #include "clk-regmap-divider.h" 19*092209f1SKonrad Dybcio #include "clk-regmap-mux.h" 20*092209f1SKonrad Dybcio #include "clk-regmap-phy-mux.h" 21*092209f1SKonrad Dybcio #include "gdsc.h" 22*092209f1SKonrad Dybcio #include "reset.h" 23*092209f1SKonrad Dybcio 24*092209f1SKonrad Dybcio enum { 25*092209f1SKonrad Dybcio DT_BI_TCXO, 26*092209f1SKonrad Dybcio DT_GCC_GPU_GPLL0_CLK_SRC, 27*092209f1SKonrad Dybcio DT_GCC_GPU_GPLL0_DIV_CLK_SRC, 28*092209f1SKonrad Dybcio }; 29*092209f1SKonrad Dybcio 30*092209f1SKonrad Dybcio enum { 31*092209f1SKonrad Dybcio P_BI_TCXO, 32*092209f1SKonrad Dybcio P_GPLL0_OUT_MAIN, 33*092209f1SKonrad Dybcio P_GPLL0_OUT_MAIN_DIV, 34*092209f1SKonrad Dybcio P_GPU_CC_PLL0_OUT_AUX2, 35*092209f1SKonrad Dybcio P_GPU_CC_PLL0_OUT_MAIN, 36*092209f1SKonrad Dybcio P_GPU_CC_PLL1_OUT_AUX, 37*092209f1SKonrad Dybcio P_GPU_CC_PLL1_OUT_MAIN, 38*092209f1SKonrad Dybcio }; 39*092209f1SKonrad Dybcio 40*092209f1SKonrad Dybcio static struct pll_vco default_vco[] = { 41*092209f1SKonrad Dybcio { 1000000000, 2000000000, 0 }, 42*092209f1SKonrad Dybcio }; 43*092209f1SKonrad Dybcio 44*092209f1SKonrad Dybcio static struct pll_vco pll1_vco[] = { 45*092209f1SKonrad Dybcio { 500000000, 1000000000, 2 }, 46*092209f1SKonrad Dybcio }; 47*092209f1SKonrad Dybcio 48*092209f1SKonrad Dybcio static const struct alpha_pll_config gpu_cc_pll0_config = { 49*092209f1SKonrad Dybcio .l = 0x3e, 50*092209f1SKonrad Dybcio .alpha = 0, 51*092209f1SKonrad Dybcio .alpha_hi = 0x80, 52*092209f1SKonrad Dybcio .vco_val = 0x0 << 20, 53*092209f1SKonrad Dybcio .vco_mask = GENMASK(21, 20), 54*092209f1SKonrad Dybcio .alpha_en_mask = BIT(24), 55*092209f1SKonrad Dybcio .main_output_mask = BIT(0), 56*092209f1SKonrad Dybcio .aux_output_mask = BIT(1), 57*092209f1SKonrad Dybcio .aux2_output_mask = BIT(2), 58*092209f1SKonrad Dybcio .config_ctl_val = 0x4001055b, 59*092209f1SKonrad Dybcio .test_ctl_hi1_val = 0x1, 60*092209f1SKonrad Dybcio }; 61*092209f1SKonrad Dybcio 62*092209f1SKonrad Dybcio /* 1200MHz configuration */ 63*092209f1SKonrad Dybcio static struct clk_alpha_pll gpu_cc_pll0 = { 64*092209f1SKonrad Dybcio .offset = 0x0, 65*092209f1SKonrad Dybcio .vco_table = default_vco, 66*092209f1SKonrad Dybcio .num_vco = ARRAY_SIZE(default_vco), 67*092209f1SKonrad Dybcio .flags = SUPPORTS_DYNAMIC_UPDATE, 68*092209f1SKonrad Dybcio .regs = clk_alpha_pll_regs[CLK_ALPHA_PLL_TYPE_DEFAULT], 69*092209f1SKonrad Dybcio .clkr = { 70*092209f1SKonrad Dybcio .hw.init = &(struct clk_init_data){ 71*092209f1SKonrad Dybcio .name = "gpu_cc_pll0", 72*092209f1SKonrad Dybcio .parent_data = &(const struct clk_parent_data){ 73*092209f1SKonrad Dybcio .index = DT_BI_TCXO, 74*092209f1SKonrad Dybcio }, 75*092209f1SKonrad Dybcio .num_parents = 1, 76*092209f1SKonrad Dybcio .ops = &clk_alpha_pll_ops, 77*092209f1SKonrad Dybcio }, 78*092209f1SKonrad Dybcio }, 79*092209f1SKonrad Dybcio }; 80*092209f1SKonrad Dybcio 81*092209f1SKonrad Dybcio static const struct clk_div_table post_div_table_gpu_cc_pll0_out_aux2[] = { 82*092209f1SKonrad Dybcio { 0x0, 1 }, 83*092209f1SKonrad Dybcio { } 84*092209f1SKonrad Dybcio }; 85*092209f1SKonrad Dybcio 86*092209f1SKonrad Dybcio static struct clk_alpha_pll_postdiv gpu_cc_pll0_out_aux2 = { 87*092209f1SKonrad Dybcio .offset = 0x0, 88*092209f1SKonrad Dybcio .post_div_shift = 8, 89*092209f1SKonrad Dybcio .post_div_table = post_div_table_gpu_cc_pll0_out_aux2, 90*092209f1SKonrad Dybcio .num_post_div = ARRAY_SIZE(post_div_table_gpu_cc_pll0_out_aux2), 91*092209f1SKonrad Dybcio .width = 4, 92*092209f1SKonrad Dybcio .regs = clk_alpha_pll_regs[CLK_ALPHA_PLL_TYPE_DEFAULT], 93*092209f1SKonrad Dybcio .clkr.hw.init = &(struct clk_init_data){ 94*092209f1SKonrad Dybcio .name = "gpu_cc_pll0_out_aux2", 95*092209f1SKonrad Dybcio .parent_hws = (const struct clk_hw*[]) { 96*092209f1SKonrad Dybcio &gpu_cc_pll0.clkr.hw, 97*092209f1SKonrad Dybcio }, 98*092209f1SKonrad Dybcio .num_parents = 1, 99*092209f1SKonrad Dybcio .flags = CLK_SET_RATE_PARENT, 100*092209f1SKonrad Dybcio .ops = &clk_alpha_pll_postdiv_ops, 101*092209f1SKonrad Dybcio }, 102*092209f1SKonrad Dybcio }; 103*092209f1SKonrad Dybcio 104*092209f1SKonrad Dybcio /* 640MHz configuration */ 105*092209f1SKonrad Dybcio static const struct alpha_pll_config gpu_cc_pll1_config = { 106*092209f1SKonrad Dybcio .l = 0x21, 107*092209f1SKonrad Dybcio .alpha = 0x55555555, 108*092209f1SKonrad Dybcio .alpha_hi = 0x55, 109*092209f1SKonrad Dybcio .alpha_en_mask = BIT(24), 110*092209f1SKonrad Dybcio .vco_val = 0x2 << 20, 111*092209f1SKonrad Dybcio .vco_mask = GENMASK(21, 20), 112*092209f1SKonrad Dybcio .main_output_mask = BIT(0), 113*092209f1SKonrad Dybcio .aux_output_mask = BIT(1), 114*092209f1SKonrad Dybcio .config_ctl_val = 0x4001055b, 115*092209f1SKonrad Dybcio .test_ctl_hi1_val = 0x1, 116*092209f1SKonrad Dybcio }; 117*092209f1SKonrad Dybcio 118*092209f1SKonrad Dybcio static struct clk_alpha_pll gpu_cc_pll1 = { 119*092209f1SKonrad Dybcio .offset = 0x100, 120*092209f1SKonrad Dybcio .vco_table = pll1_vco, 121*092209f1SKonrad Dybcio .num_vco = ARRAY_SIZE(pll1_vco), 122*092209f1SKonrad Dybcio .flags = SUPPORTS_DYNAMIC_UPDATE, 123*092209f1SKonrad Dybcio .regs = clk_alpha_pll_regs[CLK_ALPHA_PLL_TYPE_DEFAULT], 124*092209f1SKonrad Dybcio .clkr = { 125*092209f1SKonrad Dybcio .hw.init = &(struct clk_init_data){ 126*092209f1SKonrad Dybcio .name = "gpu_cc_pll1", 127*092209f1SKonrad Dybcio .parent_data = &(const struct clk_parent_data){ 128*092209f1SKonrad Dybcio .index = DT_BI_TCXO, 129*092209f1SKonrad Dybcio }, 130*092209f1SKonrad Dybcio .num_parents = 1, 131*092209f1SKonrad Dybcio .ops = &clk_alpha_pll_ops, 132*092209f1SKonrad Dybcio }, 133*092209f1SKonrad Dybcio }, 134*092209f1SKonrad Dybcio }; 135*092209f1SKonrad Dybcio 136*092209f1SKonrad Dybcio static const struct clk_div_table post_div_table_gpu_cc_pll1_out_aux[] = { 137*092209f1SKonrad Dybcio { 0x0, 1 }, 138*092209f1SKonrad Dybcio { } 139*092209f1SKonrad Dybcio }; 140*092209f1SKonrad Dybcio 141*092209f1SKonrad Dybcio static struct clk_alpha_pll_postdiv gpu_cc_pll1_out_aux = { 142*092209f1SKonrad Dybcio .offset = 0x100, 143*092209f1SKonrad Dybcio .post_div_shift = 15, 144*092209f1SKonrad Dybcio .post_div_table = post_div_table_gpu_cc_pll1_out_aux, 145*092209f1SKonrad Dybcio .num_post_div = ARRAY_SIZE(post_div_table_gpu_cc_pll1_out_aux), 146*092209f1SKonrad Dybcio .width = 3, 147*092209f1SKonrad Dybcio .regs = clk_alpha_pll_regs[CLK_ALPHA_PLL_TYPE_DEFAULT], 148*092209f1SKonrad Dybcio .clkr.hw.init = &(struct clk_init_data){ 149*092209f1SKonrad Dybcio .name = "gpu_cc_pll1_out_aux", 150*092209f1SKonrad Dybcio .parent_hws = (const struct clk_hw*[]) { 151*092209f1SKonrad Dybcio &gpu_cc_pll1.clkr.hw, 152*092209f1SKonrad Dybcio }, 153*092209f1SKonrad Dybcio .num_parents = 1, 154*092209f1SKonrad Dybcio .flags = CLK_SET_RATE_PARENT, 155*092209f1SKonrad Dybcio .ops = &clk_alpha_pll_postdiv_ops, 156*092209f1SKonrad Dybcio }, 157*092209f1SKonrad Dybcio }; 158*092209f1SKonrad Dybcio 159*092209f1SKonrad Dybcio static const struct parent_map gpu_cc_parent_map_0[] = { 160*092209f1SKonrad Dybcio { P_BI_TCXO, 0 }, 161*092209f1SKonrad Dybcio { P_GPU_CC_PLL0_OUT_MAIN, 1 }, 162*092209f1SKonrad Dybcio { P_GPU_CC_PLL1_OUT_MAIN, 3 }, 163*092209f1SKonrad Dybcio { P_GPLL0_OUT_MAIN, 5 }, 164*092209f1SKonrad Dybcio { P_GPLL0_OUT_MAIN_DIV, 6 }, 165*092209f1SKonrad Dybcio }; 166*092209f1SKonrad Dybcio 167*092209f1SKonrad Dybcio static const struct clk_parent_data gpu_cc_parent_data_0[] = { 168*092209f1SKonrad Dybcio { .index = P_BI_TCXO }, 169*092209f1SKonrad Dybcio { .hw = &gpu_cc_pll0.clkr.hw }, 170*092209f1SKonrad Dybcio { .hw = &gpu_cc_pll1.clkr.hw }, 171*092209f1SKonrad Dybcio { .index = DT_GCC_GPU_GPLL0_CLK_SRC }, 172*092209f1SKonrad Dybcio { .index = DT_GCC_GPU_GPLL0_DIV_CLK_SRC }, 173*092209f1SKonrad Dybcio }; 174*092209f1SKonrad Dybcio 175*092209f1SKonrad Dybcio static const struct parent_map gpu_cc_parent_map_1[] = { 176*092209f1SKonrad Dybcio { P_BI_TCXO, 0 }, 177*092209f1SKonrad Dybcio { P_GPU_CC_PLL0_OUT_AUX2, 2 }, 178*092209f1SKonrad Dybcio { P_GPU_CC_PLL1_OUT_AUX, 3 }, 179*092209f1SKonrad Dybcio { P_GPLL0_OUT_MAIN, 5 }, 180*092209f1SKonrad Dybcio }; 181*092209f1SKonrad Dybcio 182*092209f1SKonrad Dybcio static const struct clk_parent_data gpu_cc_parent_data_1[] = { 183*092209f1SKonrad Dybcio { .index = P_BI_TCXO }, 184*092209f1SKonrad Dybcio { .hw = &gpu_cc_pll0_out_aux2.clkr.hw }, 185*092209f1SKonrad Dybcio { .hw = &gpu_cc_pll1_out_aux.clkr.hw }, 186*092209f1SKonrad Dybcio { .index = DT_GCC_GPU_GPLL0_CLK_SRC }, 187*092209f1SKonrad Dybcio }; 188*092209f1SKonrad Dybcio 189*092209f1SKonrad Dybcio static const struct freq_tbl ftbl_gpu_cc_gmu_clk_src[] = { 190*092209f1SKonrad Dybcio F(200000000, P_GPLL0_OUT_MAIN, 3, 0, 0), 191*092209f1SKonrad Dybcio { } 192*092209f1SKonrad Dybcio }; 193*092209f1SKonrad Dybcio 194*092209f1SKonrad Dybcio static struct clk_rcg2 gpu_cc_gmu_clk_src = { 195*092209f1SKonrad Dybcio .cmd_rcgr = 0x1120, 196*092209f1SKonrad Dybcio .mnd_width = 0, 197*092209f1SKonrad Dybcio .hid_width = 5, 198*092209f1SKonrad Dybcio .parent_map = gpu_cc_parent_map_0, 199*092209f1SKonrad Dybcio .freq_tbl = ftbl_gpu_cc_gmu_clk_src, 200*092209f1SKonrad Dybcio .clkr.hw.init = &(struct clk_init_data){ 201*092209f1SKonrad Dybcio .name = "gpu_cc_gmu_clk_src", 202*092209f1SKonrad Dybcio .parent_data = gpu_cc_parent_data_0, 203*092209f1SKonrad Dybcio .num_parents = ARRAY_SIZE(gpu_cc_parent_data_0), 204*092209f1SKonrad Dybcio .flags = CLK_SET_RATE_PARENT, 205*092209f1SKonrad Dybcio .ops = &clk_rcg2_shared_ops, 206*092209f1SKonrad Dybcio }, 207*092209f1SKonrad Dybcio }; 208*092209f1SKonrad Dybcio 209*092209f1SKonrad Dybcio static const struct freq_tbl ftbl_gpu_cc_gx_gfx3d_clk_src[] = { 210*092209f1SKonrad Dybcio F(320000000, P_GPU_CC_PLL1_OUT_AUX, 2, 0, 0), 211*092209f1SKonrad Dybcio F(465000000, P_GPU_CC_PLL1_OUT_AUX, 2, 0, 0), 212*092209f1SKonrad Dybcio F(600000000, P_GPU_CC_PLL0_OUT_AUX2, 2, 0, 0), 213*092209f1SKonrad Dybcio F(745000000, P_GPU_CC_PLL0_OUT_AUX2, 2, 0, 0), 214*092209f1SKonrad Dybcio F(820000000, P_GPU_CC_PLL0_OUT_AUX2, 2, 0, 0), 215*092209f1SKonrad Dybcio F(900000000, P_GPU_CC_PLL0_OUT_AUX2, 2, 0, 0), 216*092209f1SKonrad Dybcio F(950000000, P_GPU_CC_PLL0_OUT_AUX2, 2, 0, 0), 217*092209f1SKonrad Dybcio F(980000000, P_GPU_CC_PLL0_OUT_AUX2, 2, 0, 0), 218*092209f1SKonrad Dybcio { } 219*092209f1SKonrad Dybcio }; 220*092209f1SKonrad Dybcio 221*092209f1SKonrad Dybcio static struct clk_rcg2 gpu_cc_gx_gfx3d_clk_src = { 222*092209f1SKonrad Dybcio .cmd_rcgr = 0x101c, 223*092209f1SKonrad Dybcio .mnd_width = 0, 224*092209f1SKonrad Dybcio .hid_width = 5, 225*092209f1SKonrad Dybcio .parent_map = gpu_cc_parent_map_1, 226*092209f1SKonrad Dybcio .freq_tbl = ftbl_gpu_cc_gx_gfx3d_clk_src, 227*092209f1SKonrad Dybcio .clkr.hw.init = &(struct clk_init_data){ 228*092209f1SKonrad Dybcio .name = "gpu_cc_gx_gfx3d_clk_src", 229*092209f1SKonrad Dybcio .parent_data = gpu_cc_parent_data_1, 230*092209f1SKonrad Dybcio .num_parents = ARRAY_SIZE(gpu_cc_parent_data_1), 231*092209f1SKonrad Dybcio .flags = CLK_SET_RATE_PARENT | CLK_OPS_PARENT_ENABLE, 232*092209f1SKonrad Dybcio .ops = &clk_rcg2_ops, 233*092209f1SKonrad Dybcio }, 234*092209f1SKonrad Dybcio }; 235*092209f1SKonrad Dybcio 236*092209f1SKonrad Dybcio static struct clk_branch gpu_cc_ahb_clk = { 237*092209f1SKonrad Dybcio .halt_reg = 0x1078, 238*092209f1SKonrad Dybcio .halt_check = BRANCH_HALT_DELAY, 239*092209f1SKonrad Dybcio .clkr = { 240*092209f1SKonrad Dybcio .enable_reg = 0x1078, 241*092209f1SKonrad Dybcio .enable_mask = BIT(0), 242*092209f1SKonrad Dybcio .hw.init = &(struct clk_init_data){ 243*092209f1SKonrad Dybcio .name = "gpu_cc_ahb_clk", 244*092209f1SKonrad Dybcio .flags = CLK_IS_CRITICAL, 245*092209f1SKonrad Dybcio .ops = &clk_branch2_ops, 246*092209f1SKonrad Dybcio }, 247*092209f1SKonrad Dybcio }, 248*092209f1SKonrad Dybcio }; 249*092209f1SKonrad Dybcio 250*092209f1SKonrad Dybcio static struct clk_branch gpu_cc_crc_ahb_clk = { 251*092209f1SKonrad Dybcio .halt_reg = 0x107c, 252*092209f1SKonrad Dybcio .halt_check = BRANCH_HALT_DELAY, 253*092209f1SKonrad Dybcio .clkr = { 254*092209f1SKonrad Dybcio .enable_reg = 0x107c, 255*092209f1SKonrad Dybcio .enable_mask = BIT(0), 256*092209f1SKonrad Dybcio .hw.init = &(struct clk_init_data){ 257*092209f1SKonrad Dybcio .name = "gpu_cc_crc_ahb_clk", 258*092209f1SKonrad Dybcio .ops = &clk_branch2_ops, 259*092209f1SKonrad Dybcio }, 260*092209f1SKonrad Dybcio }, 261*092209f1SKonrad Dybcio }; 262*092209f1SKonrad Dybcio 263*092209f1SKonrad Dybcio static struct clk_branch gpu_cc_cx_gfx3d_clk = { 264*092209f1SKonrad Dybcio .halt_reg = 0x10a4, 265*092209f1SKonrad Dybcio .halt_check = BRANCH_HALT_DELAY, 266*092209f1SKonrad Dybcio .clkr = { 267*092209f1SKonrad Dybcio .enable_reg = 0x10a4, 268*092209f1SKonrad Dybcio .enable_mask = BIT(0), 269*092209f1SKonrad Dybcio .hw.init = &(struct clk_init_data){ 270*092209f1SKonrad Dybcio .name = "gpu_cc_cx_gfx3d_clk", 271*092209f1SKonrad Dybcio .parent_data = &(const struct clk_parent_data){ 272*092209f1SKonrad Dybcio .hw = &gpu_cc_gx_gfx3d_clk_src.clkr.hw, 273*092209f1SKonrad Dybcio }, 274*092209f1SKonrad Dybcio .num_parents = 1, 275*092209f1SKonrad Dybcio .flags = CLK_SET_RATE_PARENT, 276*092209f1SKonrad Dybcio .ops = &clk_branch2_ops, 277*092209f1SKonrad Dybcio }, 278*092209f1SKonrad Dybcio }, 279*092209f1SKonrad Dybcio }; 280*092209f1SKonrad Dybcio 281*092209f1SKonrad Dybcio static struct clk_branch gpu_cc_cx_gmu_clk = { 282*092209f1SKonrad Dybcio .halt_reg = 0x1098, 283*092209f1SKonrad Dybcio .halt_check = BRANCH_HALT, 284*092209f1SKonrad Dybcio .clkr = { 285*092209f1SKonrad Dybcio .enable_reg = 0x1098, 286*092209f1SKonrad Dybcio .enable_mask = BIT(0), 287*092209f1SKonrad Dybcio .hw.init = &(struct clk_init_data){ 288*092209f1SKonrad Dybcio .name = "gpu_cc_cx_gmu_clk", 289*092209f1SKonrad Dybcio .parent_data = &(const struct clk_parent_data){ 290*092209f1SKonrad Dybcio .hw = &gpu_cc_gmu_clk_src.clkr.hw, 291*092209f1SKonrad Dybcio }, 292*092209f1SKonrad Dybcio .num_parents = 1, 293*092209f1SKonrad Dybcio .flags = CLK_SET_RATE_PARENT, 294*092209f1SKonrad Dybcio .ops = &clk_branch2_ops, 295*092209f1SKonrad Dybcio }, 296*092209f1SKonrad Dybcio }, 297*092209f1SKonrad Dybcio }; 298*092209f1SKonrad Dybcio 299*092209f1SKonrad Dybcio static struct clk_branch gpu_cc_cx_snoc_dvm_clk = { 300*092209f1SKonrad Dybcio .halt_reg = 0x108c, 301*092209f1SKonrad Dybcio .halt_check = BRANCH_HALT_DELAY, 302*092209f1SKonrad Dybcio .clkr = { 303*092209f1SKonrad Dybcio .enable_reg = 0x108c, 304*092209f1SKonrad Dybcio .enable_mask = BIT(0), 305*092209f1SKonrad Dybcio .hw.init = &(struct clk_init_data){ 306*092209f1SKonrad Dybcio .name = "gpu_cc_cx_snoc_dvm_clk", 307*092209f1SKonrad Dybcio .ops = &clk_branch2_ops, 308*092209f1SKonrad Dybcio }, 309*092209f1SKonrad Dybcio }, 310*092209f1SKonrad Dybcio }; 311*092209f1SKonrad Dybcio 312*092209f1SKonrad Dybcio static struct clk_branch gpu_cc_cxo_aon_clk = { 313*092209f1SKonrad Dybcio .halt_reg = 0x1004, 314*092209f1SKonrad Dybcio .halt_check = BRANCH_HALT_DELAY, 315*092209f1SKonrad Dybcio .clkr = { 316*092209f1SKonrad Dybcio .enable_reg = 0x1004, 317*092209f1SKonrad Dybcio .enable_mask = BIT(0), 318*092209f1SKonrad Dybcio .hw.init = &(struct clk_init_data){ 319*092209f1SKonrad Dybcio .name = "gpu_cc_cxo_aon_clk", 320*092209f1SKonrad Dybcio .ops = &clk_branch2_ops, 321*092209f1SKonrad Dybcio }, 322*092209f1SKonrad Dybcio }, 323*092209f1SKonrad Dybcio }; 324*092209f1SKonrad Dybcio 325*092209f1SKonrad Dybcio static struct clk_branch gpu_cc_cxo_clk = { 326*092209f1SKonrad Dybcio .halt_reg = 0x109c, 327*092209f1SKonrad Dybcio .halt_check = BRANCH_HALT, 328*092209f1SKonrad Dybcio .clkr = { 329*092209f1SKonrad Dybcio .enable_reg = 0x109c, 330*092209f1SKonrad Dybcio .enable_mask = BIT(0), 331*092209f1SKonrad Dybcio .hw.init = &(struct clk_init_data){ 332*092209f1SKonrad Dybcio .name = "gpu_cc_cxo_clk", 333*092209f1SKonrad Dybcio .ops = &clk_branch2_ops, 334*092209f1SKonrad Dybcio }, 335*092209f1SKonrad Dybcio }, 336*092209f1SKonrad Dybcio }; 337*092209f1SKonrad Dybcio 338*092209f1SKonrad Dybcio static struct clk_branch gpu_cc_gx_cxo_clk = { 339*092209f1SKonrad Dybcio .halt_reg = 0x1060, 340*092209f1SKonrad Dybcio .halt_check = BRANCH_HALT_DELAY, 341*092209f1SKonrad Dybcio .clkr = { 342*092209f1SKonrad Dybcio .enable_reg = 0x1060, 343*092209f1SKonrad Dybcio .enable_mask = BIT(0), 344*092209f1SKonrad Dybcio .hw.init = &(struct clk_init_data){ 345*092209f1SKonrad Dybcio .name = "gpu_cc_gx_cxo_clk", 346*092209f1SKonrad Dybcio .flags = CLK_IS_CRITICAL, 347*092209f1SKonrad Dybcio .ops = &clk_branch2_ops, 348*092209f1SKonrad Dybcio }, 349*092209f1SKonrad Dybcio }, 350*092209f1SKonrad Dybcio }; 351*092209f1SKonrad Dybcio 352*092209f1SKonrad Dybcio static struct clk_branch gpu_cc_gx_gfx3d_clk = { 353*092209f1SKonrad Dybcio .halt_reg = 0x1054, 354*092209f1SKonrad Dybcio .halt_check = BRANCH_HALT_SKIP, 355*092209f1SKonrad Dybcio .clkr = { 356*092209f1SKonrad Dybcio .enable_reg = 0x1054, 357*092209f1SKonrad Dybcio .enable_mask = BIT(0), 358*092209f1SKonrad Dybcio .hw.init = &(struct clk_init_data){ 359*092209f1SKonrad Dybcio .name = "gpu_cc_gx_gfx3d_clk", 360*092209f1SKonrad Dybcio .parent_data = &(const struct clk_parent_data){ 361*092209f1SKonrad Dybcio .hw = &gpu_cc_gx_gfx3d_clk_src.clkr.hw, 362*092209f1SKonrad Dybcio }, 363*092209f1SKonrad Dybcio .num_parents = 1, 364*092209f1SKonrad Dybcio .flags = CLK_SET_RATE_PARENT, 365*092209f1SKonrad Dybcio .ops = &clk_branch2_ops, 366*092209f1SKonrad Dybcio }, 367*092209f1SKonrad Dybcio }, 368*092209f1SKonrad Dybcio }; 369*092209f1SKonrad Dybcio 370*092209f1SKonrad Dybcio static struct clk_branch gpu_cc_sleep_clk = { 371*092209f1SKonrad Dybcio .halt_reg = 0x1090, 372*092209f1SKonrad Dybcio .halt_check = BRANCH_HALT_DELAY, 373*092209f1SKonrad Dybcio .clkr = { 374*092209f1SKonrad Dybcio .enable_reg = 0x1090, 375*092209f1SKonrad Dybcio .enable_mask = BIT(0), 376*092209f1SKonrad Dybcio .hw.init = &(struct clk_init_data){ 377*092209f1SKonrad Dybcio .name = "gpu_cc_sleep_clk", 378*092209f1SKonrad Dybcio .ops = &clk_branch2_ops, 379*092209f1SKonrad Dybcio }, 380*092209f1SKonrad Dybcio }, 381*092209f1SKonrad Dybcio }; 382*092209f1SKonrad Dybcio 383*092209f1SKonrad Dybcio static struct clk_branch gpu_cc_hlos1_vote_gpu_smmu_clk = { 384*092209f1SKonrad Dybcio .halt_reg = 0x5000, 385*092209f1SKonrad Dybcio .halt_check = BRANCH_VOTED, 386*092209f1SKonrad Dybcio .clkr = { 387*092209f1SKonrad Dybcio .enable_reg = 0x5000, 388*092209f1SKonrad Dybcio .enable_mask = BIT(0), 389*092209f1SKonrad Dybcio .hw.init = &(struct clk_init_data){ 390*092209f1SKonrad Dybcio .name = "gpu_cc_hlos1_vote_gpu_smmu_clk", 391*092209f1SKonrad Dybcio .ops = &clk_branch2_ops, 392*092209f1SKonrad Dybcio }, 393*092209f1SKonrad Dybcio }, 394*092209f1SKonrad Dybcio }; 395*092209f1SKonrad Dybcio 396*092209f1SKonrad Dybcio static struct gdsc gpu_cx_gdsc = { 397*092209f1SKonrad Dybcio .gdscr = 0x106c, 398*092209f1SKonrad Dybcio .gds_hw_ctrl = 0x1540, 399*092209f1SKonrad Dybcio .pd = { 400*092209f1SKonrad Dybcio .name = "gpu_cx_gdsc", 401*092209f1SKonrad Dybcio }, 402*092209f1SKonrad Dybcio .pwrsts = PWRSTS_OFF_ON, 403*092209f1SKonrad Dybcio .flags = VOTABLE, 404*092209f1SKonrad Dybcio }; 405*092209f1SKonrad Dybcio 406*092209f1SKonrad Dybcio static struct gdsc gpu_gx_gdsc = { 407*092209f1SKonrad Dybcio .gdscr = 0x100c, 408*092209f1SKonrad Dybcio .clamp_io_ctrl = 0x1508, 409*092209f1SKonrad Dybcio .resets = (unsigned int []){ GPU_GX_BCR }, 410*092209f1SKonrad Dybcio .reset_count = 1, 411*092209f1SKonrad Dybcio .pd = { 412*092209f1SKonrad Dybcio .name = "gpu_gx_gdsc", 413*092209f1SKonrad Dybcio }, 414*092209f1SKonrad Dybcio .parent = &gpu_cx_gdsc.pd, 415*092209f1SKonrad Dybcio .pwrsts = PWRSTS_OFF_ON, 416*092209f1SKonrad Dybcio .flags = CLAMP_IO | SW_RESET | VOTABLE, 417*092209f1SKonrad Dybcio }; 418*092209f1SKonrad Dybcio 419*092209f1SKonrad Dybcio static struct clk_regmap *gpu_cc_sm6115_clocks[] = { 420*092209f1SKonrad Dybcio [GPU_CC_AHB_CLK] = &gpu_cc_ahb_clk.clkr, 421*092209f1SKonrad Dybcio [GPU_CC_CRC_AHB_CLK] = &gpu_cc_crc_ahb_clk.clkr, 422*092209f1SKonrad Dybcio [GPU_CC_CX_GFX3D_CLK] = &gpu_cc_cx_gfx3d_clk.clkr, 423*092209f1SKonrad Dybcio [GPU_CC_CX_GMU_CLK] = &gpu_cc_cx_gmu_clk.clkr, 424*092209f1SKonrad Dybcio [GPU_CC_CX_SNOC_DVM_CLK] = &gpu_cc_cx_snoc_dvm_clk.clkr, 425*092209f1SKonrad Dybcio [GPU_CC_CXO_AON_CLK] = &gpu_cc_cxo_aon_clk.clkr, 426*092209f1SKonrad Dybcio [GPU_CC_CXO_CLK] = &gpu_cc_cxo_clk.clkr, 427*092209f1SKonrad Dybcio [GPU_CC_GMU_CLK_SRC] = &gpu_cc_gmu_clk_src.clkr, 428*092209f1SKonrad Dybcio [GPU_CC_GX_CXO_CLK] = &gpu_cc_gx_cxo_clk.clkr, 429*092209f1SKonrad Dybcio [GPU_CC_GX_GFX3D_CLK] = &gpu_cc_gx_gfx3d_clk.clkr, 430*092209f1SKonrad Dybcio [GPU_CC_GX_GFX3D_CLK_SRC] = &gpu_cc_gx_gfx3d_clk_src.clkr, 431*092209f1SKonrad Dybcio [GPU_CC_PLL0] = &gpu_cc_pll0.clkr, 432*092209f1SKonrad Dybcio [GPU_CC_PLL0_OUT_AUX2] = &gpu_cc_pll0_out_aux2.clkr, 433*092209f1SKonrad Dybcio [GPU_CC_PLL1] = &gpu_cc_pll1.clkr, 434*092209f1SKonrad Dybcio [GPU_CC_PLL1_OUT_AUX] = &gpu_cc_pll1_out_aux.clkr, 435*092209f1SKonrad Dybcio [GPU_CC_SLEEP_CLK] = &gpu_cc_sleep_clk.clkr, 436*092209f1SKonrad Dybcio [GPU_CC_HLOS1_VOTE_GPU_SMMU_CLK] = &gpu_cc_hlos1_vote_gpu_smmu_clk.clkr, 437*092209f1SKonrad Dybcio }; 438*092209f1SKonrad Dybcio 439*092209f1SKonrad Dybcio static const struct qcom_reset_map gpu_cc_sm6115_resets[] = { 440*092209f1SKonrad Dybcio [GPU_GX_BCR] = { 0x1008 }, 441*092209f1SKonrad Dybcio }; 442*092209f1SKonrad Dybcio 443*092209f1SKonrad Dybcio static struct gdsc *gpu_cc_sm6115_gdscs[] = { 444*092209f1SKonrad Dybcio [GPU_CX_GDSC] = &gpu_cx_gdsc, 445*092209f1SKonrad Dybcio [GPU_GX_GDSC] = &gpu_gx_gdsc, 446*092209f1SKonrad Dybcio }; 447*092209f1SKonrad Dybcio 448*092209f1SKonrad Dybcio static const struct regmap_config gpu_cc_sm6115_regmap_config = { 449*092209f1SKonrad Dybcio .reg_bits = 32, 450*092209f1SKonrad Dybcio .reg_stride = 4, 451*092209f1SKonrad Dybcio .val_bits = 32, 452*092209f1SKonrad Dybcio .max_register = 0x9000, 453*092209f1SKonrad Dybcio .fast_io = true, 454*092209f1SKonrad Dybcio }; 455*092209f1SKonrad Dybcio 456*092209f1SKonrad Dybcio static const struct qcom_cc_desc gpu_cc_sm6115_desc = { 457*092209f1SKonrad Dybcio .config = &gpu_cc_sm6115_regmap_config, 458*092209f1SKonrad Dybcio .clks = gpu_cc_sm6115_clocks, 459*092209f1SKonrad Dybcio .num_clks = ARRAY_SIZE(gpu_cc_sm6115_clocks), 460*092209f1SKonrad Dybcio .resets = gpu_cc_sm6115_resets, 461*092209f1SKonrad Dybcio .num_resets = ARRAY_SIZE(gpu_cc_sm6115_resets), 462*092209f1SKonrad Dybcio .gdscs = gpu_cc_sm6115_gdscs, 463*092209f1SKonrad Dybcio .num_gdscs = ARRAY_SIZE(gpu_cc_sm6115_gdscs), 464*092209f1SKonrad Dybcio }; 465*092209f1SKonrad Dybcio 466*092209f1SKonrad Dybcio static const struct of_device_id gpu_cc_sm6115_match_table[] = { 467*092209f1SKonrad Dybcio { .compatible = "qcom,sm6115-gpucc" }, 468*092209f1SKonrad Dybcio { } 469*092209f1SKonrad Dybcio }; 470*092209f1SKonrad Dybcio MODULE_DEVICE_TABLE(of, gpu_cc_sm6115_match_table); 471*092209f1SKonrad Dybcio 472*092209f1SKonrad Dybcio static int gpu_cc_sm6115_probe(struct platform_device *pdev) 473*092209f1SKonrad Dybcio { 474*092209f1SKonrad Dybcio struct regmap *regmap; 475*092209f1SKonrad Dybcio 476*092209f1SKonrad Dybcio regmap = qcom_cc_map(pdev, &gpu_cc_sm6115_desc); 477*092209f1SKonrad Dybcio if (IS_ERR(regmap)) 478*092209f1SKonrad Dybcio return PTR_ERR(regmap); 479*092209f1SKonrad Dybcio 480*092209f1SKonrad Dybcio clk_alpha_pll_configure(&gpu_cc_pll0, regmap, &gpu_cc_pll0_config); 481*092209f1SKonrad Dybcio clk_alpha_pll_configure(&gpu_cc_pll1, regmap, &gpu_cc_pll1_config); 482*092209f1SKonrad Dybcio 483*092209f1SKonrad Dybcio /* Set recommended WAKEUP/SLEEP settings for the gpu_cc_cx_gmu_clk */ 484*092209f1SKonrad Dybcio qcom_branch_set_wakeup(regmap, gpu_cc_cx_gmu_clk, 0xf); 485*092209f1SKonrad Dybcio qcom_branch_set_sleep(regmap, gpu_cc_cx_gmu_clk, 0xf); 486*092209f1SKonrad Dybcio 487*092209f1SKonrad Dybcio qcom_branch_set_force_mem_core(regmap, gpu_cc_gx_gfx3d_clk, true); 488*092209f1SKonrad Dybcio qcom_branch_set_force_periph_on(regmap, gpu_cc_gx_gfx3d_clk, true); 489*092209f1SKonrad Dybcio 490*092209f1SKonrad Dybcio return qcom_cc_really_probe(pdev, &gpu_cc_sm6115_desc, regmap); 491*092209f1SKonrad Dybcio } 492*092209f1SKonrad Dybcio 493*092209f1SKonrad Dybcio static struct platform_driver gpu_cc_sm6115_driver = { 494*092209f1SKonrad Dybcio .probe = gpu_cc_sm6115_probe, 495*092209f1SKonrad Dybcio .driver = { 496*092209f1SKonrad Dybcio .name = "sm6115-gpucc", 497*092209f1SKonrad Dybcio .of_match_table = gpu_cc_sm6115_match_table, 498*092209f1SKonrad Dybcio }, 499*092209f1SKonrad Dybcio }; 500*092209f1SKonrad Dybcio module_platform_driver(gpu_cc_sm6115_driver); 501*092209f1SKonrad Dybcio 502*092209f1SKonrad Dybcio MODULE_DESCRIPTION("QTI GPU_CC SM6115 Driver"); 503*092209f1SKonrad Dybcio MODULE_LICENSE("GPL"); 504