linux/drivers/clk/mediatek/clk-mt8173.c
<<
>>
Prefs
   1/*
   2 * Copyright (c) 2014 MediaTek Inc.
   3 * Author: James Liao <jamesjj.liao@mediatek.com>
   4 *
   5 * This program is free software; you can redistribute it and/or modify
   6 * it under the terms of the GNU General Public License version 2 as
   7 * published by the Free Software Foundation.
   8 *
   9 * This program is distributed in the hope that it will be useful,
  10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
  11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  12 * GNU General Public License for more details.
  13 */
  14
  15#include <linux/clk.h>
  16#include <linux/of.h>
  17#include <linux/of_address.h>
  18
  19#include "clk-mtk.h"
  20#include "clk-gate.h"
  21#include "clk-cpumux.h"
  22
  23#include <dt-bindings/clock/mt8173-clk.h>
  24
  25/*
  26 * For some clocks, we don't care what their actual rates are. And these
  27 * clocks may change their rate on different products or different scenarios.
  28 * So we model these clocks' rate as 0, to denote it's not an actual rate.
  29 */
  30#define DUMMY_RATE              0
  31
  32static DEFINE_SPINLOCK(mt8173_clk_lock);
  33
  34static const struct mtk_fixed_clk fixed_clks[] __initconst = {
  35        FIXED_CLK(CLK_TOP_CLKPH_MCK_O, "clkph_mck_o", "clk26m", DUMMY_RATE),
  36        FIXED_CLK(CLK_TOP_USB_SYSPLL_125M, "usb_syspll_125m", "clk26m", 125 * MHZ),
  37        FIXED_CLK(CLK_TOP_DSI0_DIG, "dsi0_dig", "clk26m", DUMMY_RATE),
  38        FIXED_CLK(CLK_TOP_DSI1_DIG, "dsi1_dig", "clk26m", DUMMY_RATE),
  39        FIXED_CLK(CLK_TOP_LVDS_PXL, "lvds_pxl", "lvdspll", DUMMY_RATE),
  40        FIXED_CLK(CLK_TOP_LVDS_CTS, "lvds_cts", "lvdspll", DUMMY_RATE),
  41};
  42
  43static const struct mtk_fixed_factor top_divs[] __initconst = {
  44        FACTOR(CLK_TOP_ARMCA7PLL_754M, "armca7pll_754m", "armca7pll", 1, 2),
  45        FACTOR(CLK_TOP_ARMCA7PLL_502M, "armca7pll_502m", "armca7pll", 1, 3),
  46
  47        FACTOR(CLK_TOP_MAIN_H546M, "main_h546m", "mainpll", 1, 2),
  48        FACTOR(CLK_TOP_MAIN_H364M, "main_h364m", "mainpll", 1, 3),
  49        FACTOR(CLK_TOP_MAIN_H218P4M, "main_h218p4m", "mainpll", 1, 5),
  50        FACTOR(CLK_TOP_MAIN_H156M, "main_h156m", "mainpll", 1, 7),
  51
  52        FACTOR(CLK_TOP_TVDPLL_445P5M, "tvdpll_445p5m", "tvdpll", 1, 4),
  53        FACTOR(CLK_TOP_TVDPLL_594M, "tvdpll_594m", "tvdpll", 1, 3),
  54
  55        FACTOR(CLK_TOP_UNIV_624M, "univ_624m", "univpll", 1, 2),
  56        FACTOR(CLK_TOP_UNIV_416M, "univ_416m", "univpll", 1, 3),
  57        FACTOR(CLK_TOP_UNIV_249P6M, "univ_249p6m", "univpll", 1, 5),
  58        FACTOR(CLK_TOP_UNIV_178P3M, "univ_178p3m", "univpll", 1, 7),
  59        FACTOR(CLK_TOP_UNIV_48M, "univ_48m", "univpll", 1, 26),
  60
  61        FACTOR(CLK_TOP_CLKRTC_EXT, "clkrtc_ext", "clk32k", 1, 1),
  62        FACTOR(CLK_TOP_CLKRTC_INT, "clkrtc_int", "clk26m", 1, 793),
  63        FACTOR(CLK_TOP_FPC, "fpc_ck", "clk26m", 1, 1),
  64
  65        FACTOR(CLK_TOP_HDMITXPLL_D2, "hdmitxpll_d2", "hdmitx_dig_cts", 1, 2),
  66        FACTOR(CLK_TOP_HDMITXPLL_D3, "hdmitxpll_d3", "hdmitx_dig_cts", 1, 3),
  67
  68        FACTOR(CLK_TOP_ARMCA7PLL_D2, "armca7pll_d2", "armca7pll_754m", 1, 1),
  69        FACTOR(CLK_TOP_ARMCA7PLL_D3, "armca7pll_d3", "armca7pll_502m", 1, 1),
  70
  71        FACTOR(CLK_TOP_APLL1, "apll1_ck", "apll1", 1, 1),
  72        FACTOR(CLK_TOP_APLL2, "apll2_ck", "apll2", 1, 1),
  73
  74        FACTOR(CLK_TOP_DMPLL, "dmpll_ck", "clkph_mck_o", 1, 1),
  75        FACTOR(CLK_TOP_DMPLL_D2, "dmpll_d2", "clkph_mck_o", 1, 2),
  76        FACTOR(CLK_TOP_DMPLL_D4, "dmpll_d4", "clkph_mck_o", 1, 4),
  77        FACTOR(CLK_TOP_DMPLL_D8, "dmpll_d8", "clkph_mck_o", 1, 8),
  78        FACTOR(CLK_TOP_DMPLL_D16, "dmpll_d16", "clkph_mck_o", 1, 16),
  79
  80        FACTOR(CLK_TOP_LVDSPLL_D2, "lvdspll_d2", "lvdspll", 1, 2),
  81        FACTOR(CLK_TOP_LVDSPLL_D4, "lvdspll_d4", "lvdspll", 1, 4),
  82        FACTOR(CLK_TOP_LVDSPLL_D8, "lvdspll_d8", "lvdspll", 1, 8),
  83
  84        FACTOR(CLK_TOP_MMPLL, "mmpll_ck", "mmpll", 1, 1),
  85        FACTOR(CLK_TOP_MMPLL_D2, "mmpll_d2", "mmpll", 1, 2),
  86
  87        FACTOR(CLK_TOP_MSDCPLL, "msdcpll_ck", "msdcpll", 1, 1),
  88        FACTOR(CLK_TOP_MSDCPLL_D2, "msdcpll_d2", "msdcpll", 1, 2),
  89        FACTOR(CLK_TOP_MSDCPLL_D4, "msdcpll_d4", "msdcpll", 1, 4),
  90        FACTOR(CLK_TOP_MSDCPLL2, "msdcpll2_ck", "msdcpll2", 1, 1),
  91        FACTOR(CLK_TOP_MSDCPLL2_D2, "msdcpll2_d2", "msdcpll2", 1, 2),
  92        FACTOR(CLK_TOP_MSDCPLL2_D4, "msdcpll2_d4", "msdcpll2", 1, 4),
  93
  94        FACTOR(CLK_TOP_SYSPLL_D2, "syspll_d2", "main_h546m", 1, 1),
  95        FACTOR(CLK_TOP_SYSPLL1_D2, "syspll1_d2", "main_h546m", 1, 2),
  96        FACTOR(CLK_TOP_SYSPLL1_D4, "syspll1_d4", "main_h546m", 1, 4),
  97        FACTOR(CLK_TOP_SYSPLL1_D8, "syspll1_d8", "main_h546m", 1, 8),
  98        FACTOR(CLK_TOP_SYSPLL1_D16, "syspll1_d16", "main_h546m", 1, 16),
  99        FACTOR(CLK_TOP_SYSPLL_D3, "syspll_d3", "main_h364m", 1, 1),
 100        FACTOR(CLK_TOP_SYSPLL2_D2, "syspll2_d2", "main_h364m", 1, 2),
 101        FACTOR(CLK_TOP_SYSPLL2_D4, "syspll2_d4", "main_h364m", 1, 4),
 102        FACTOR(CLK_TOP_SYSPLL_D5, "syspll_d5", "main_h218p4m", 1, 1),
 103        FACTOR(CLK_TOP_SYSPLL3_D2, "syspll3_d2", "main_h218p4m", 1, 2),
 104        FACTOR(CLK_TOP_SYSPLL3_D4, "syspll3_d4", "main_h218p4m", 1, 4),
 105        FACTOR(CLK_TOP_SYSPLL_D7, "syspll_d7", "main_h156m", 1, 1),
 106        FACTOR(CLK_TOP_SYSPLL4_D2, "syspll4_d2", "main_h156m", 1, 2),
 107        FACTOR(CLK_TOP_SYSPLL4_D4, "syspll4_d4", "main_h156m", 1, 4),
 108
 109        FACTOR(CLK_TOP_TVDPLL, "tvdpll_ck", "tvdpll_594m", 1, 1),
 110        FACTOR(CLK_TOP_TVDPLL_D2, "tvdpll_d2", "tvdpll_594m", 1, 2),
 111        FACTOR(CLK_TOP_TVDPLL_D4, "tvdpll_d4", "tvdpll_594m", 1, 4),
 112        FACTOR(CLK_TOP_TVDPLL_D8, "tvdpll_d8", "tvdpll_594m", 1, 8),
 113        FACTOR(CLK_TOP_TVDPLL_D16, "tvdpll_d16", "tvdpll_594m", 1, 16),
 114
 115        FACTOR(CLK_TOP_UNIVPLL_D2, "univpll_d2", "univ_624m", 1, 1),
 116        FACTOR(CLK_TOP_UNIVPLL1_D2, "univpll1_d2", "univ_624m", 1, 2),
 117        FACTOR(CLK_TOP_UNIVPLL1_D4, "univpll1_d4", "univ_624m", 1, 4),
 118        FACTOR(CLK_TOP_UNIVPLL1_D8, "univpll1_d8", "univ_624m", 1, 8),
 119        FACTOR(CLK_TOP_UNIVPLL_D3, "univpll_d3", "univ_416m", 1, 1),
 120        FACTOR(CLK_TOP_UNIVPLL2_D2, "univpll2_d2", "univ_416m", 1, 2),
 121        FACTOR(CLK_TOP_UNIVPLL2_D4, "univpll2_d4", "univ_416m", 1, 4),
 122        FACTOR(CLK_TOP_UNIVPLL2_D8, "univpll2_d8", "univ_416m", 1, 8),
 123        FACTOR(CLK_TOP_UNIVPLL_D5, "univpll_d5", "univ_249p6m", 1, 1),
 124        FACTOR(CLK_TOP_UNIVPLL3_D2, "univpll3_d2", "univ_249p6m", 1, 2),
 125        FACTOR(CLK_TOP_UNIVPLL3_D4, "univpll3_d4", "univ_249p6m", 1, 4),
 126        FACTOR(CLK_TOP_UNIVPLL3_D8, "univpll3_d8", "univ_249p6m", 1, 8),
 127        FACTOR(CLK_TOP_UNIVPLL_D7, "univpll_d7", "univ_178p3m", 1, 1),
 128        FACTOR(CLK_TOP_UNIVPLL_D26, "univpll_d26", "univ_48m", 1, 1),
 129        FACTOR(CLK_TOP_UNIVPLL_D52, "univpll_d52", "univ_48m", 1, 2),
 130
 131        FACTOR(CLK_TOP_VCODECPLL, "vcodecpll_ck", "vcodecpll", 1, 3),
 132        FACTOR(CLK_TOP_VCODECPLL_370P5, "vcodecpll_370p5", "vcodecpll", 1, 4),
 133
 134        FACTOR(CLK_TOP_VENCPLL, "vencpll_ck", "vencpll", 1, 1),
 135        FACTOR(CLK_TOP_VENCPLL_D2, "vencpll_d2", "vencpll", 1, 2),
 136        FACTOR(CLK_TOP_VENCPLL_D4, "vencpll_d4", "vencpll", 1, 4),
 137};
 138
 139static const char * const axi_parents[] __initconst = {
 140        "clk26m",
 141        "syspll1_d2",
 142        "syspll_d5",
 143        "syspll1_d4",
 144        "univpll_d5",
 145        "univpll2_d2",
 146        "dmpll_d2",
 147        "dmpll_d4"
 148};
 149
 150static const char * const mem_parents[] __initconst = {
 151        "clk26m",
 152        "dmpll_ck"
 153};
 154
 155static const char * const ddrphycfg_parents[] __initconst = {
 156        "clk26m",
 157        "syspll1_d8"
 158};
 159
 160static const char * const mm_parents[] __initconst = {
 161        "clk26m",
 162        "vencpll_d2",
 163        "main_h364m",
 164        "syspll1_d2",
 165        "syspll_d5",
 166        "syspll1_d4",
 167        "univpll1_d2",
 168        "univpll2_d2",
 169        "dmpll_d2"
 170};
 171
 172static const char * const pwm_parents[] __initconst = {
 173        "clk26m",
 174        "univpll2_d4",
 175        "univpll3_d2",
 176        "univpll1_d4"
 177};
 178
 179static const char * const vdec_parents[] __initconst = {
 180        "clk26m",
 181        "vcodecpll_ck",
 182        "tvdpll_445p5m",
 183        "univpll_d3",
 184        "vencpll_d2",
 185        "syspll_d3",
 186        "univpll1_d2",
 187        "mmpll_d2",
 188        "dmpll_d2",
 189        "dmpll_d4"
 190};
 191
 192static const char * const venc_parents[] __initconst = {
 193        "clk26m",
 194        "vcodecpll_ck",
 195        "tvdpll_445p5m",
 196        "univpll_d3",
 197        "vencpll_d2",
 198        "syspll_d3",
 199        "univpll1_d2",
 200        "univpll2_d2",
 201        "dmpll_d2",
 202        "dmpll_d4"
 203};
 204
 205static const char * const mfg_parents[] __initconst = {
 206        "clk26m",
 207        "mmpll_ck",
 208        "dmpll_ck",
 209        "clk26m",
 210        "clk26m",
 211        "clk26m",
 212        "clk26m",
 213        "clk26m",
 214        "clk26m",
 215        "syspll_d3",
 216        "syspll1_d2",
 217        "syspll_d5",
 218        "univpll_d3",
 219        "univpll1_d2",
 220        "univpll_d5",
 221        "univpll2_d2"
 222};
 223
 224static const char * const camtg_parents[] __initconst = {
 225        "clk26m",
 226        "univpll_d26",
 227        "univpll2_d2",
 228        "syspll3_d2",
 229        "syspll3_d4",
 230        "univpll1_d4"
 231};
 232
 233static const char * const uart_parents[] __initconst = {
 234        "clk26m",
 235        "univpll2_d8"
 236};
 237
 238static const char * const spi_parents[] __initconst = {
 239        "clk26m",
 240        "syspll3_d2",
 241        "syspll1_d4",
 242        "syspll4_d2",
 243        "univpll3_d2",
 244        "univpll2_d4",
 245        "univpll1_d8"
 246};
 247
 248static const char * const usb20_parents[] __initconst = {
 249        "clk26m",
 250        "univpll1_d8",
 251        "univpll3_d4"
 252};
 253
 254static const char * const usb30_parents[] __initconst = {
 255        "clk26m",
 256        "univpll3_d2",
 257        "usb_syspll_125m",
 258        "univpll2_d4"
 259};
 260
 261static const char * const msdc50_0_h_parents[] __initconst = {
 262        "clk26m",
 263        "syspll1_d2",
 264        "syspll2_d2",
 265        "syspll4_d2",
 266        "univpll_d5",
 267        "univpll1_d4"
 268};
 269
 270static const char * const msdc50_0_parents[] __initconst = {
 271        "clk26m",
 272        "msdcpll_ck",
 273        "msdcpll_d2",
 274        "univpll1_d4",
 275        "syspll2_d2",
 276        "syspll_d7",
 277        "msdcpll_d4",
 278        "vencpll_d4",
 279        "tvdpll_ck",
 280        "univpll_d2",
 281        "univpll1_d2",
 282        "mmpll_ck",
 283        "msdcpll2_ck",
 284        "msdcpll2_d2",
 285        "msdcpll2_d4"
 286};
 287
 288static const char * const msdc30_1_parents[] __initconst = {
 289        "clk26m",
 290        "univpll2_d2",
 291        "msdcpll_d4",
 292        "univpll1_d4",
 293        "syspll2_d2",
 294        "syspll_d7",
 295        "univpll_d7",
 296        "vencpll_d4"
 297};
 298
 299static const char * const msdc30_2_parents[] __initconst = {
 300        "clk26m",
 301        "univpll2_d2",
 302        "msdcpll_d4",
 303        "univpll1_d4",
 304        "syspll2_d2",
 305        "syspll_d7",
 306        "univpll_d7",
 307        "vencpll_d2"
 308};
 309
 310static const char * const msdc30_3_parents[] __initconst = {
 311        "clk26m",
 312        "msdcpll2_ck",
 313        "msdcpll2_d2",
 314        "univpll2_d2",
 315        "msdcpll2_d4",
 316        "msdcpll_d4",
 317        "univpll1_d4",
 318        "syspll2_d2",
 319        "syspll_d7",
 320        "univpll_d7",
 321        "vencpll_d4",
 322        "msdcpll_ck",
 323        "msdcpll_d2",
 324        "msdcpll_d4"
 325};
 326
 327static const char * const audio_parents[] __initconst = {
 328        "clk26m",
 329        "syspll3_d4",
 330        "syspll4_d4",
 331        "syspll1_d16"
 332};
 333
 334static const char * const aud_intbus_parents[] __initconst = {
 335        "clk26m",
 336        "syspll1_d4",
 337        "syspll4_d2",
 338        "univpll3_d2",
 339        "univpll2_d8",
 340        "dmpll_d4",
 341        "dmpll_d8"
 342};
 343
 344static const char * const pmicspi_parents[] __initconst = {
 345        "clk26m",
 346        "syspll1_d8",
 347        "syspll3_d4",
 348        "syspll1_d16",
 349        "univpll3_d4",
 350        "univpll_d26",
 351        "dmpll_d8",
 352        "dmpll_d16"
 353};
 354
 355static const char * const scp_parents[] __initconst = {
 356        "clk26m",
 357        "syspll1_d2",
 358        "univpll_d5",
 359        "syspll_d5",
 360        "dmpll_d2",
 361        "dmpll_d4"
 362};
 363
 364static const char * const atb_parents[] __initconst = {
 365        "clk26m",
 366        "syspll1_d2",
 367        "univpll_d5",
 368        "dmpll_d2"
 369};
 370
 371static const char * const venc_lt_parents[] __initconst = {
 372        "clk26m",
 373        "univpll_d3",
 374        "vcodecpll_ck",
 375        "tvdpll_445p5m",
 376        "vencpll_d2",
 377        "syspll_d3",
 378        "univpll1_d2",
 379        "univpll2_d2",
 380        "syspll1_d2",
 381        "univpll_d5",
 382        "vcodecpll_370p5",
 383        "dmpll_ck"
 384};
 385
 386static const char * const dpi0_parents[] __initconst = {
 387        "clk26m",
 388        "tvdpll_d2",
 389        "tvdpll_d4",
 390        "clk26m",
 391        "clk26m",
 392        "tvdpll_d8",
 393        "tvdpll_d16"
 394};
 395
 396static const char * const irda_parents[] __initconst = {
 397        "clk26m",
 398        "univpll2_d4",
 399        "syspll2_d4"
 400};
 401
 402static const char * const cci400_parents[] __initconst = {
 403        "clk26m",
 404        "vencpll_ck",
 405        "armca7pll_754m",
 406        "armca7pll_502m",
 407        "univpll_d2",
 408        "syspll_d2",
 409        "msdcpll_ck",
 410        "dmpll_ck"
 411};
 412
 413static const char * const aud_1_parents[] __initconst = {
 414        "clk26m",
 415        "apll1_ck",
 416        "univpll2_d4",
 417        "univpll2_d8"
 418};
 419
 420static const char * const aud_2_parents[] __initconst = {
 421        "clk26m",
 422        "apll2_ck",
 423        "univpll2_d4",
 424        "univpll2_d8"
 425};
 426
 427static const char * const mem_mfg_in_parents[] __initconst = {
 428        "clk26m",
 429        "mmpll_ck",
 430        "dmpll_ck",
 431        "clk26m"
 432};
 433
 434static const char * const axi_mfg_in_parents[] __initconst = {
 435        "clk26m",
 436        "axi_sel",
 437        "dmpll_d2"
 438};
 439
 440static const char * const scam_parents[] __initconst = {
 441        "clk26m",
 442        "syspll3_d2",
 443        "univpll2_d4",
 444        "dmpll_d4"
 445};
 446
 447static const char * const spinfi_ifr_parents[] __initconst = {
 448        "clk26m",
 449        "univpll2_d8",
 450        "univpll3_d4",
 451        "syspll4_d2",
 452        "univpll2_d4",
 453        "univpll3_d2",
 454        "syspll1_d4",
 455        "univpll1_d4"
 456};
 457
 458static const char * const hdmi_parents[] __initconst = {
 459        "clk26m",
 460        "hdmitx_dig_cts",
 461        "hdmitxpll_d2",
 462        "hdmitxpll_d3"
 463};
 464
 465static const char * const dpilvds_parents[] __initconst = {
 466        "clk26m",
 467        "lvdspll",
 468        "lvdspll_d2",
 469        "lvdspll_d4",
 470        "lvdspll_d8",
 471        "fpc_ck"
 472};
 473
 474static const char * const msdc50_2_h_parents[] __initconst = {
 475        "clk26m",
 476        "syspll1_d2",
 477        "syspll2_d2",
 478        "syspll4_d2",
 479        "univpll_d5",
 480        "univpll1_d4"
 481};
 482
 483static const char * const hdcp_parents[] __initconst = {
 484        "clk26m",
 485        "syspll4_d2",
 486        "syspll3_d4",
 487        "univpll2_d4"
 488};
 489
 490static const char * const hdcp_24m_parents[] __initconst = {
 491        "clk26m",
 492        "univpll_d26",
 493        "univpll_d52",
 494        "univpll2_d8"
 495};
 496
 497static const char * const rtc_parents[] __initconst = {
 498        "clkrtc_int",
 499        "clkrtc_ext",
 500        "clk26m",
 501        "univpll3_d8"
 502};
 503
 504static const char * const i2s0_m_ck_parents[] __initconst = {
 505        "apll1_div1",
 506        "apll2_div1"
 507};
 508
 509static const char * const i2s1_m_ck_parents[] __initconst = {
 510        "apll1_div2",
 511        "apll2_div2"
 512};
 513
 514static const char * const i2s2_m_ck_parents[] __initconst = {
 515        "apll1_div3",
 516        "apll2_div3"
 517};
 518
 519static const char * const i2s3_m_ck_parents[] __initconst = {
 520        "apll1_div4",
 521        "apll2_div4"
 522};
 523
 524static const char * const i2s3_b_ck_parents[] __initconst = {
 525        "apll1_div5",
 526        "apll2_div5"
 527};
 528
 529static const char * const ca53_parents[] __initconst = {
 530        "clk26m",
 531        "armca7pll",
 532        "mainpll",
 533        "univpll"
 534};
 535
 536static const char * const ca57_parents[] __initconst = {
 537        "clk26m",
 538        "armca15pll",
 539        "mainpll",
 540        "univpll"
 541};
 542
 543static const struct mtk_composite cpu_muxes[] __initconst = {
 544        MUX(CLK_INFRA_CA53SEL, "infra_ca53_sel", ca53_parents, 0x0000, 0, 2),
 545        MUX(CLK_INFRA_CA57SEL, "infra_ca57_sel", ca57_parents, 0x0000, 2, 2),
 546};
 547
 548static const struct mtk_composite top_muxes[] __initconst = {
 549        /* CLK_CFG_0 */
 550        MUX(CLK_TOP_AXI_SEL, "axi_sel", axi_parents, 0x0040, 0, 3),
 551        MUX(CLK_TOP_MEM_SEL, "mem_sel", mem_parents, 0x0040, 8, 1),
 552        MUX_GATE(CLK_TOP_DDRPHYCFG_SEL, "ddrphycfg_sel", ddrphycfg_parents, 0x0040, 16, 1, 23),
 553        MUX_GATE(CLK_TOP_MM_SEL, "mm_sel", mm_parents, 0x0040, 24, 4, 31),
 554        /* CLK_CFG_1 */
 555        MUX_GATE(CLK_TOP_PWM_SEL, "pwm_sel", pwm_parents, 0x0050, 0, 2, 7),
 556        MUX_GATE(CLK_TOP_VDEC_SEL, "vdec_sel", vdec_parents, 0x0050, 8, 4, 15),
 557        MUX_GATE(CLK_TOP_VENC_SEL, "venc_sel", venc_parents, 0x0050, 16, 4, 23),
 558        MUX_GATE(CLK_TOP_MFG_SEL, "mfg_sel", mfg_parents, 0x0050, 24, 4, 31),
 559        /* CLK_CFG_2 */
 560        MUX_GATE(CLK_TOP_CAMTG_SEL, "camtg_sel", camtg_parents, 0x0060, 0, 3, 7),
 561        MUX_GATE(CLK_TOP_UART_SEL, "uart_sel", uart_parents, 0x0060, 8, 1, 15),
 562        MUX_GATE(CLK_TOP_SPI_SEL, "spi_sel", spi_parents, 0x0060, 16, 3, 23),
 563        MUX_GATE(CLK_TOP_USB20_SEL, "usb20_sel", usb20_parents, 0x0060, 24, 2, 31),
 564        /* CLK_CFG_3 */
 565        MUX_GATE(CLK_TOP_USB30_SEL, "usb30_sel", usb30_parents, 0x0070, 0, 2, 7),
 566        MUX_GATE(CLK_TOP_MSDC50_0_H_SEL, "msdc50_0_h_sel", msdc50_0_h_parents, 0x0070, 8, 3, 15),
 567        MUX_GATE(CLK_TOP_MSDC50_0_SEL, "msdc50_0_sel", msdc50_0_parents, 0x0070, 16, 4, 23),
 568        MUX_GATE(CLK_TOP_MSDC30_1_SEL, "msdc30_1_sel", msdc30_1_parents, 0x0070, 24, 3, 31),
 569        /* CLK_CFG_4 */
 570        MUX_GATE(CLK_TOP_MSDC30_2_SEL, "msdc30_2_sel", msdc30_2_parents, 0x0080, 0, 3, 7),
 571        MUX_GATE(CLK_TOP_MSDC30_3_SEL, "msdc30_3_sel", msdc30_3_parents, 0x0080, 8, 4, 15),
 572        MUX_GATE(CLK_TOP_AUDIO_SEL, "audio_sel", audio_parents, 0x0080, 16, 2, 23),
 573        MUX_GATE(CLK_TOP_AUD_INTBUS_SEL, "aud_intbus_sel", aud_intbus_parents, 0x0080, 24, 3, 31),
 574        /* CLK_CFG_5 */
 575        MUX_GATE(CLK_TOP_PMICSPI_SEL, "pmicspi_sel", pmicspi_parents, 0x0090, 0, 3, 7 /* 7:5 */),
 576        MUX_GATE(CLK_TOP_SCP_SEL, "scp_sel", scp_parents, 0x0090, 8, 3, 15),
 577        MUX_GATE(CLK_TOP_ATB_SEL, "atb_sel", atb_parents, 0x0090, 16, 2, 23),
 578        MUX_GATE(CLK_TOP_VENC_LT_SEL, "venclt_sel", venc_lt_parents, 0x0090, 24, 4, 31),
 579        /* CLK_CFG_6 */
 580        /*
 581         * The dpi0_sel clock should not propagate rate changes to its parent
 582         * clock so the dpi driver can have full control over PLL and divider.
 583         */
 584        MUX_GATE_FLAGS(CLK_TOP_DPI0_SEL, "dpi0_sel", dpi0_parents, 0x00a0, 0, 3, 7, 0),
 585        MUX_GATE(CLK_TOP_IRDA_SEL, "irda_sel", irda_parents, 0x00a0, 8, 2, 15),
 586        MUX_GATE(CLK_TOP_CCI400_SEL, "cci400_sel", cci400_parents, 0x00a0, 16, 3, 23),
 587        MUX_GATE(CLK_TOP_AUD_1_SEL, "aud_1_sel", aud_1_parents, 0x00a0, 24, 2, 31),
 588        /* CLK_CFG_7 */
 589        MUX_GATE(CLK_TOP_AUD_2_SEL, "aud_2_sel", aud_2_parents, 0x00b0, 0, 2, 7),
 590        MUX_GATE(CLK_TOP_MEM_MFG_IN_SEL, "mem_mfg_in_sel", mem_mfg_in_parents, 0x00b0, 8, 2, 15),
 591        MUX_GATE(CLK_TOP_AXI_MFG_IN_SEL, "axi_mfg_in_sel", axi_mfg_in_parents, 0x00b0, 16, 2, 23),
 592        MUX_GATE(CLK_TOP_SCAM_SEL, "scam_sel", scam_parents, 0x00b0, 24, 2, 31),
 593        /* CLK_CFG_12 */
 594        MUX_GATE(CLK_TOP_SPINFI_IFR_SEL, "spinfi_ifr_sel", spinfi_ifr_parents, 0x00c0, 0, 3, 7),
 595        MUX_GATE(CLK_TOP_HDMI_SEL, "hdmi_sel", hdmi_parents, 0x00c0, 8, 2, 15),
 596        MUX_GATE(CLK_TOP_DPILVDS_SEL, "dpilvds_sel", dpilvds_parents, 0x00c0, 24, 3, 31),
 597        /* CLK_CFG_13 */
 598        MUX_GATE(CLK_TOP_MSDC50_2_H_SEL, "msdc50_2_h_sel", msdc50_2_h_parents, 0x00d0, 0, 3, 7),
 599        MUX_GATE(CLK_TOP_HDCP_SEL, "hdcp_sel", hdcp_parents, 0x00d0, 8, 2, 15),
 600        MUX_GATE(CLK_TOP_HDCP_24M_SEL, "hdcp_24m_sel", hdcp_24m_parents, 0x00d0, 16, 2, 23),
 601        MUX(CLK_TOP_RTC_SEL, "rtc_sel", rtc_parents, 0x00d0, 24, 2),
 602
 603        DIV_GATE(CLK_TOP_APLL1_DIV0, "apll1_div0", "aud_1_sel", 0x12c, 8, 0x120, 4, 24),
 604        DIV_GATE(CLK_TOP_APLL1_DIV1, "apll1_div1", "aud_1_sel", 0x12c, 9, 0x124, 8, 0),
 605        DIV_GATE(CLK_TOP_APLL1_DIV2, "apll1_div2", "aud_1_sel", 0x12c, 10, 0x124, 8, 8),
 606        DIV_GATE(CLK_TOP_APLL1_DIV3, "apll1_div3", "aud_1_sel", 0x12c, 11, 0x124, 8, 16),
 607        DIV_GATE(CLK_TOP_APLL1_DIV4, "apll1_div4", "aud_1_sel", 0x12c, 12, 0x124, 8, 24),
 608        DIV_GATE(CLK_TOP_APLL1_DIV5, "apll1_div5", "apll1_div4", 0x12c, 13, 0x12c, 4, 0),
 609
 610        DIV_GATE(CLK_TOP_APLL2_DIV0, "apll2_div0", "aud_2_sel", 0x12c, 16, 0x120, 4, 28),
 611        DIV_GATE(CLK_TOP_APLL2_DIV1, "apll2_div1", "aud_2_sel", 0x12c, 17, 0x128, 8, 0),
 612        DIV_GATE(CLK_TOP_APLL2_DIV2, "apll2_div2", "aud_2_sel", 0x12c, 18, 0x128, 8, 8),
 613        DIV_GATE(CLK_TOP_APLL2_DIV3, "apll2_div3", "aud_2_sel", 0x12c, 19, 0x128, 8, 16),
 614        DIV_GATE(CLK_TOP_APLL2_DIV4, "apll2_div4", "aud_2_sel", 0x12c, 20, 0x128, 8, 24),
 615        DIV_GATE(CLK_TOP_APLL2_DIV5, "apll2_div5", "apll2_div4", 0x12c, 21, 0x12c, 4, 4),
 616
 617        MUX(CLK_TOP_I2S0_M_SEL, "i2s0_m_ck_sel", i2s0_m_ck_parents, 0x120, 4, 1),
 618        MUX(CLK_TOP_I2S1_M_SEL, "i2s1_m_ck_sel", i2s1_m_ck_parents, 0x120, 5, 1),
 619        MUX(CLK_TOP_I2S2_M_SEL, "i2s2_m_ck_sel", i2s2_m_ck_parents, 0x120, 6, 1),
 620        MUX(CLK_TOP_I2S3_M_SEL, "i2s3_m_ck_sel", i2s3_m_ck_parents, 0x120, 7, 1),
 621        MUX(CLK_TOP_I2S3_B_SEL, "i2s3_b_ck_sel", i2s3_b_ck_parents, 0x120, 8, 1),
 622};
 623
 624static const struct mtk_gate_regs infra_cg_regs __initconst = {
 625        .set_ofs = 0x0040,
 626        .clr_ofs = 0x0044,
 627        .sta_ofs = 0x0048,
 628};
 629
 630#define GATE_ICG(_id, _name, _parent, _shift) { \
 631                .id = _id,                                      \
 632                .name = _name,                                  \
 633                .parent_name = _parent,                         \
 634                .regs = &infra_cg_regs,                         \
 635                .shift = _shift,                                \
 636                .ops = &mtk_clk_gate_ops_setclr,                \
 637        }
 638
 639static const struct mtk_gate infra_clks[] __initconst = {
 640        GATE_ICG(CLK_INFRA_DBGCLK, "infra_dbgclk", "axi_sel", 0),
 641        GATE_ICG(CLK_INFRA_SMI, "infra_smi", "mm_sel", 1),
 642        GATE_ICG(CLK_INFRA_AUDIO, "infra_audio", "aud_intbus_sel", 5),
 643        GATE_ICG(CLK_INFRA_GCE, "infra_gce", "axi_sel", 6),
 644        GATE_ICG(CLK_INFRA_L2C_SRAM, "infra_l2c_sram", "axi_sel", 7),
 645        GATE_ICG(CLK_INFRA_M4U, "infra_m4u", "mem_sel", 8),
 646        GATE_ICG(CLK_INFRA_CPUM, "infra_cpum", "cpum_ck", 15),
 647        GATE_ICG(CLK_INFRA_KP, "infra_kp", "axi_sel", 16),
 648        GATE_ICG(CLK_INFRA_CEC, "infra_cec", "clk26m", 18),
 649        GATE_ICG(CLK_INFRA_PMICSPI, "infra_pmicspi", "pmicspi_sel", 22),
 650        GATE_ICG(CLK_INFRA_PMICWRAP, "infra_pmicwrap", "axi_sel", 23),
 651};
 652
 653static const struct mtk_fixed_factor infra_divs[] __initconst = {
 654        FACTOR(CLK_INFRA_CLK_13M, "clk13m", "clk26m", 1, 2),
 655};
 656
 657static const struct mtk_gate_regs peri0_cg_regs __initconst = {
 658        .set_ofs = 0x0008,
 659        .clr_ofs = 0x0010,
 660        .sta_ofs = 0x0018,
 661};
 662
 663static const struct mtk_gate_regs peri1_cg_regs __initconst = {
 664        .set_ofs = 0x000c,
 665        .clr_ofs = 0x0014,
 666        .sta_ofs = 0x001c,
 667};
 668
 669#define GATE_PERI0(_id, _name, _parent, _shift) {       \
 670                .id = _id,                                      \
 671                .name = _name,                                  \
 672                .parent_name = _parent,                         \
 673                .regs = &peri0_cg_regs,                         \
 674                .shift = _shift,                                \
 675                .ops = &mtk_clk_gate_ops_setclr,                \
 676        }
 677
 678#define GATE_PERI1(_id, _name, _parent, _shift) {       \
 679                .id = _id,                                      \
 680                .name = _name,                                  \
 681                .parent_name = _parent,                         \
 682                .regs = &peri1_cg_regs,                         \
 683                .shift = _shift,                                \
 684                .ops = &mtk_clk_gate_ops_setclr,                \
 685        }
 686
 687static const struct mtk_gate peri_gates[] __initconst = {
 688        /* PERI0 */
 689        GATE_PERI0(CLK_PERI_NFI, "peri_nfi", "axi_sel", 0),
 690        GATE_PERI0(CLK_PERI_THERM, "peri_therm", "axi_sel", 1),
 691        GATE_PERI0(CLK_PERI_PWM1, "peri_pwm1", "axi_sel", 2),
 692        GATE_PERI0(CLK_PERI_PWM2, "peri_pwm2", "axi_sel", 3),
 693        GATE_PERI0(CLK_PERI_PWM3, "peri_pwm3", "axi_sel", 4),
 694        GATE_PERI0(CLK_PERI_PWM4, "peri_pwm4", "axi_sel", 5),
 695        GATE_PERI0(CLK_PERI_PWM5, "peri_pwm5", "axi_sel", 6),
 696        GATE_PERI0(CLK_PERI_PWM6, "peri_pwm6", "axi_sel", 7),
 697        GATE_PERI0(CLK_PERI_PWM7, "peri_pwm7", "axi_sel", 8),
 698        GATE_PERI0(CLK_PERI_PWM, "peri_pwm", "axi_sel", 9),
 699        GATE_PERI0(CLK_PERI_USB0, "peri_usb0", "usb20_sel", 10),
 700        GATE_PERI0(CLK_PERI_USB1, "peri_usb1", "usb20_sel", 11),
 701        GATE_PERI0(CLK_PERI_AP_DMA, "peri_ap_dma", "axi_sel", 12),
 702        GATE_PERI0(CLK_PERI_MSDC30_0, "peri_msdc30_0", "msdc50_0_sel", 13),
 703        GATE_PERI0(CLK_PERI_MSDC30_1, "peri_msdc30_1", "msdc30_1_sel", 14),
 704        GATE_PERI0(CLK_PERI_MSDC30_2, "peri_msdc30_2", "msdc30_2_sel", 15),
 705        GATE_PERI0(CLK_PERI_MSDC30_3, "peri_msdc30_3", "msdc30_3_sel", 16),
 706        GATE_PERI0(CLK_PERI_NLI_ARB, "peri_nli_arb", "axi_sel", 17),
 707        GATE_PERI0(CLK_PERI_IRDA, "peri_irda", "irda_sel", 18),
 708        GATE_PERI0(CLK_PERI_UART0, "peri_uart0", "axi_sel", 19),
 709        GATE_PERI0(CLK_PERI_UART1, "peri_uart1", "axi_sel", 20),
 710        GATE_PERI0(CLK_PERI_UART2, "peri_uart2", "axi_sel", 21),
 711        GATE_PERI0(CLK_PERI_UART3, "peri_uart3", "axi_sel", 22),
 712        GATE_PERI0(CLK_PERI_I2C0, "peri_i2c0", "axi_sel", 23),
 713        GATE_PERI0(CLK_PERI_I2C1, "peri_i2c1", "axi_sel", 24),
 714        GATE_PERI0(CLK_PERI_I2C2, "peri_i2c2", "axi_sel", 25),
 715        GATE_PERI0(CLK_PERI_I2C3, "peri_i2c3", "axi_sel", 26),
 716        GATE_PERI0(CLK_PERI_I2C4, "peri_i2c4", "axi_sel", 27),
 717        GATE_PERI0(CLK_PERI_AUXADC, "peri_auxadc", "clk26m", 28),
 718        GATE_PERI0(CLK_PERI_SPI0, "peri_spi0", "spi_sel", 29),
 719        GATE_PERI0(CLK_PERI_I2C5, "peri_i2c5", "axi_sel", 30),
 720        GATE_PERI0(CLK_PERI_NFIECC, "peri_nfiecc", "axi_sel", 31),
 721        /* PERI1 */
 722        GATE_PERI1(CLK_PERI_SPI, "peri_spi", "spi_sel", 0),
 723        GATE_PERI1(CLK_PERI_IRRX, "peri_irrx", "spi_sel", 1),
 724        GATE_PERI1(CLK_PERI_I2C6, "peri_i2c6", "axi_sel", 2),
 725};
 726
 727static const char * const uart_ck_sel_parents[] __initconst = {
 728        "clk26m",
 729        "uart_sel",
 730};
 731
 732static const struct mtk_composite peri_clks[] __initconst = {
 733        MUX(CLK_PERI_UART0_SEL, "uart0_ck_sel", uart_ck_sel_parents, 0x40c, 0, 1),
 734        MUX(CLK_PERI_UART1_SEL, "uart1_ck_sel", uart_ck_sel_parents, 0x40c, 1, 1),
 735        MUX(CLK_PERI_UART2_SEL, "uart2_ck_sel", uart_ck_sel_parents, 0x40c, 2, 1),
 736        MUX(CLK_PERI_UART3_SEL, "uart3_ck_sel", uart_ck_sel_parents, 0x40c, 3, 1),
 737};
 738
 739static const struct mtk_gate_regs cg_regs_4_8_0 __initconst = {
 740        .set_ofs = 0x0004,
 741        .clr_ofs = 0x0008,
 742        .sta_ofs = 0x0000,
 743};
 744
 745#define GATE_IMG(_id, _name, _parent, _shift) {                 \
 746                .id = _id,                                      \
 747                .name = _name,                                  \
 748                .parent_name = _parent,                         \
 749                .regs = &cg_regs_4_8_0,                         \
 750                .shift = _shift,                                \
 751                .ops = &mtk_clk_gate_ops_setclr,                \
 752        }
 753
 754static const struct mtk_gate img_clks[] __initconst = {
 755        GATE_IMG(CLK_IMG_LARB2_SMI, "img_larb2_smi", "mm_sel", 0),
 756        GATE_IMG(CLK_IMG_CAM_SMI, "img_cam_smi", "mm_sel", 5),
 757        GATE_IMG(CLK_IMG_CAM_CAM, "img_cam_cam", "mm_sel", 6),
 758        GATE_IMG(CLK_IMG_SEN_TG, "img_sen_tg", "camtg_sel", 7),
 759        GATE_IMG(CLK_IMG_SEN_CAM, "img_sen_cam", "mm_sel", 8),
 760        GATE_IMG(CLK_IMG_CAM_SV, "img_cam_sv", "mm_sel", 9),
 761        GATE_IMG(CLK_IMG_FD, "img_fd", "mm_sel", 11),
 762};
 763
 764static const struct mtk_gate_regs mm0_cg_regs __initconst = {
 765        .set_ofs = 0x0104,
 766        .clr_ofs = 0x0108,
 767        .sta_ofs = 0x0100,
 768};
 769
 770static const struct mtk_gate_regs mm1_cg_regs __initconst = {
 771        .set_ofs = 0x0114,
 772        .clr_ofs = 0x0118,
 773        .sta_ofs = 0x0110,
 774};
 775
 776#define GATE_MM0(_id, _name, _parent, _shift) {                 \
 777                .id = _id,                                      \
 778                .name = _name,                                  \
 779                .parent_name = _parent,                         \
 780                .regs = &mm0_cg_regs,                           \
 781                .shift = _shift,                                \
 782                .ops = &mtk_clk_gate_ops_setclr,                \
 783        }
 784
 785#define GATE_MM1(_id, _name, _parent, _shift) {                 \
 786                .id = _id,                                      \
 787                .name = _name,                                  \
 788                .parent_name = _parent,                         \
 789                .regs = &mm1_cg_regs,                           \
 790                .shift = _shift,                                \
 791                .ops = &mtk_clk_gate_ops_setclr,                \
 792        }
 793
 794static const struct mtk_gate mm_clks[] __initconst = {
 795        /* MM0 */
 796        GATE_MM0(CLK_MM_SMI_COMMON, "mm_smi_common", "mm_sel", 0),
 797        GATE_MM0(CLK_MM_SMI_LARB0, "mm_smi_larb0", "mm_sel", 1),
 798        GATE_MM0(CLK_MM_CAM_MDP, "mm_cam_mdp", "mm_sel", 2),
 799        GATE_MM0(CLK_MM_MDP_RDMA0, "mm_mdp_rdma0", "mm_sel", 3),
 800        GATE_MM0(CLK_MM_MDP_RDMA1, "mm_mdp_rdma1", "mm_sel", 4),
 801        GATE_MM0(CLK_MM_MDP_RSZ0, "mm_mdp_rsz0", "mm_sel", 5),
 802        GATE_MM0(CLK_MM_MDP_RSZ1, "mm_mdp_rsz1", "mm_sel", 6),
 803        GATE_MM0(CLK_MM_MDP_RSZ2, "mm_mdp_rsz2", "mm_sel", 7),
 804        GATE_MM0(CLK_MM_MDP_TDSHP0, "mm_mdp_tdshp0", "mm_sel", 8),
 805        GATE_MM0(CLK_MM_MDP_TDSHP1, "mm_mdp_tdshp1", "mm_sel", 9),
 806        GATE_MM0(CLK_MM_MDP_WDMA, "mm_mdp_wdma", "mm_sel", 11),
 807        GATE_MM0(CLK_MM_MDP_WROT0, "mm_mdp_wrot0", "mm_sel", 12),
 808        GATE_MM0(CLK_MM_MDP_WROT1, "mm_mdp_wrot1", "mm_sel", 13),
 809        GATE_MM0(CLK_MM_FAKE_ENG, "mm_fake_eng", "mm_sel", 14),
 810        GATE_MM0(CLK_MM_MUTEX_32K, "mm_mutex_32k", "rtc_sel", 15),
 811        GATE_MM0(CLK_MM_DISP_OVL0, "mm_disp_ovl0", "mm_sel", 16),
 812        GATE_MM0(CLK_MM_DISP_OVL1, "mm_disp_ovl1", "mm_sel", 17),
 813        GATE_MM0(CLK_MM_DISP_RDMA0, "mm_disp_rdma0", "mm_sel", 18),
 814        GATE_MM0(CLK_MM_DISP_RDMA1, "mm_disp_rdma1", "mm_sel", 19),
 815        GATE_MM0(CLK_MM_DISP_RDMA2, "mm_disp_rdma2", "mm_sel", 20),
 816        GATE_MM0(CLK_MM_DISP_WDMA0, "mm_disp_wdma0", "mm_sel", 21),
 817        GATE_MM0(CLK_MM_DISP_WDMA1, "mm_disp_wdma1", "mm_sel", 22),
 818        GATE_MM0(CLK_MM_DISP_COLOR0, "mm_disp_color0", "mm_sel", 23),
 819        GATE_MM0(CLK_MM_DISP_COLOR1, "mm_disp_color1", "mm_sel", 24),
 820        GATE_MM0(CLK_MM_DISP_AAL, "mm_disp_aal", "mm_sel", 25),
 821        GATE_MM0(CLK_MM_DISP_GAMMA, "mm_disp_gamma", "mm_sel", 26),
 822        GATE_MM0(CLK_MM_DISP_UFOE, "mm_disp_ufoe", "mm_sel", 27),
 823        GATE_MM0(CLK_MM_DISP_SPLIT0, "mm_disp_split0", "mm_sel", 28),
 824        GATE_MM0(CLK_MM_DISP_SPLIT1, "mm_disp_split1", "mm_sel", 29),
 825        GATE_MM0(CLK_MM_DISP_MERGE, "mm_disp_merge", "mm_sel", 30),
 826        GATE_MM0(CLK_MM_DISP_OD, "mm_disp_od", "mm_sel", 31),
 827        /* MM1 */
 828        GATE_MM1(CLK_MM_DISP_PWM0MM, "mm_disp_pwm0mm", "mm_sel", 0),
 829        GATE_MM1(CLK_MM_DISP_PWM026M, "mm_disp_pwm026m", "pwm_sel", 1),
 830        GATE_MM1(CLK_MM_DISP_PWM1MM, "mm_disp_pwm1mm", "mm_sel", 2),
 831        GATE_MM1(CLK_MM_DISP_PWM126M, "mm_disp_pwm126m", "pwm_sel", 3),
 832        GATE_MM1(CLK_MM_DSI0_ENGINE, "mm_dsi0_engine", "mm_sel", 4),
 833        GATE_MM1(CLK_MM_DSI0_DIGITAL, "mm_dsi0_digital", "dsi0_dig", 5),
 834        GATE_MM1(CLK_MM_DSI1_ENGINE, "mm_dsi1_engine", "mm_sel", 6),
 835        GATE_MM1(CLK_MM_DSI1_DIGITAL, "mm_dsi1_digital", "dsi1_dig", 7),
 836        GATE_MM1(CLK_MM_DPI_PIXEL, "mm_dpi_pixel", "dpi0_sel", 8),
 837        GATE_MM1(CLK_MM_DPI_ENGINE, "mm_dpi_engine", "mm_sel", 9),
 838        GATE_MM1(CLK_MM_DPI1_PIXEL, "mm_dpi1_pixel", "lvds_pxl", 10),
 839        GATE_MM1(CLK_MM_DPI1_ENGINE, "mm_dpi1_engine", "mm_sel", 11),
 840        GATE_MM1(CLK_MM_HDMI_PIXEL, "mm_hdmi_pixel", "dpi0_sel", 12),
 841        GATE_MM1(CLK_MM_HDMI_PLLCK, "mm_hdmi_pllck", "hdmi_sel", 13),
 842        GATE_MM1(CLK_MM_HDMI_AUDIO, "mm_hdmi_audio", "apll1", 14),
 843        GATE_MM1(CLK_MM_HDMI_SPDIF, "mm_hdmi_spdif", "apll2", 15),
 844        GATE_MM1(CLK_MM_LVDS_PIXEL, "mm_lvds_pixel", "lvds_pxl", 16),
 845        GATE_MM1(CLK_MM_LVDS_CTS, "mm_lvds_cts", "lvds_cts", 17),
 846        GATE_MM1(CLK_MM_SMI_LARB4, "mm_smi_larb4", "mm_sel", 18),
 847        GATE_MM1(CLK_MM_HDMI_HDCP, "mm_hdmi_hdcp", "hdcp_sel", 19),
 848        GATE_MM1(CLK_MM_HDMI_HDCP24M, "mm_hdmi_hdcp24m", "hdcp_24m_sel", 20),
 849};
 850
 851static const struct mtk_gate_regs vdec0_cg_regs __initconst = {
 852        .set_ofs = 0x0000,
 853        .clr_ofs = 0x0004,
 854        .sta_ofs = 0x0000,
 855};
 856
 857static const struct mtk_gate_regs vdec1_cg_regs __initconst = {
 858        .set_ofs = 0x0008,
 859        .clr_ofs = 0x000c,
 860        .sta_ofs = 0x0008,
 861};
 862
 863#define GATE_VDEC0(_id, _name, _parent, _shift) {               \
 864                .id = _id,                                      \
 865                .name = _name,                                  \
 866                .parent_name = _parent,                         \
 867                .regs = &vdec0_cg_regs,                         \
 868                .shift = _shift,                                \
 869                .ops = &mtk_clk_gate_ops_setclr_inv,            \
 870        }
 871
 872#define GATE_VDEC1(_id, _name, _parent, _shift) {               \
 873                .id = _id,                                      \
 874                .name = _name,                                  \
 875                .parent_name = _parent,                         \
 876                .regs = &vdec1_cg_regs,                         \
 877                .shift = _shift,                                \
 878                .ops = &mtk_clk_gate_ops_setclr_inv,            \
 879        }
 880
 881static const struct mtk_gate vdec_clks[] __initconst = {
 882        GATE_VDEC0(CLK_VDEC_CKEN, "vdec_cken", "vdec_sel", 0),
 883        GATE_VDEC1(CLK_VDEC_LARB_CKEN, "vdec_larb_cken", "mm_sel", 0),
 884};
 885
 886#define GATE_VENC(_id, _name, _parent, _shift) {                \
 887                .id = _id,                                      \
 888                .name = _name,                                  \
 889                .parent_name = _parent,                         \
 890                .regs = &cg_regs_4_8_0,                         \
 891                .shift = _shift,                                \
 892                .ops = &mtk_clk_gate_ops_setclr_inv,            \
 893        }
 894
 895static const struct mtk_gate venc_clks[] __initconst = {
 896        GATE_VENC(CLK_VENC_CKE0, "venc_cke0", "mm_sel", 0),
 897        GATE_VENC(CLK_VENC_CKE1, "venc_cke1", "venc_sel", 4),
 898        GATE_VENC(CLK_VENC_CKE2, "venc_cke2", "venc_sel", 8),
 899        GATE_VENC(CLK_VENC_CKE3, "venc_cke3", "venc_sel", 12),
 900};
 901
 902#define GATE_VENCLT(_id, _name, _parent, _shift) {              \
 903                .id = _id,                                      \
 904                .name = _name,                                  \
 905                .parent_name = _parent,                         \
 906                .regs = &cg_regs_4_8_0,                         \
 907                .shift = _shift,                                \
 908                .ops = &mtk_clk_gate_ops_setclr_inv,            \
 909        }
 910
 911static const struct mtk_gate venclt_clks[] __initconst = {
 912        GATE_VENCLT(CLK_VENCLT_CKE0, "venclt_cke0", "mm_sel", 0),
 913        GATE_VENCLT(CLK_VENCLT_CKE1, "venclt_cke1", "venclt_sel", 4),
 914};
 915
 916static struct clk_onecell_data *mt8173_top_clk_data __initdata;
 917static struct clk_onecell_data *mt8173_pll_clk_data __initdata;
 918
 919static void __init mtk_clk_enable_critical(void)
 920{
 921        if (!mt8173_top_clk_data || !mt8173_pll_clk_data)
 922                return;
 923
 924        clk_prepare_enable(mt8173_pll_clk_data->clks[CLK_APMIXED_ARMCA15PLL]);
 925        clk_prepare_enable(mt8173_pll_clk_data->clks[CLK_APMIXED_ARMCA7PLL]);
 926        clk_prepare_enable(mt8173_top_clk_data->clks[CLK_TOP_MEM_SEL]);
 927        clk_prepare_enable(mt8173_top_clk_data->clks[CLK_TOP_DDRPHYCFG_SEL]);
 928        clk_prepare_enable(mt8173_top_clk_data->clks[CLK_TOP_CCI400_SEL]);
 929        clk_prepare_enable(mt8173_top_clk_data->clks[CLK_TOP_RTC_SEL]);
 930}
 931
 932static void __init mtk_topckgen_init(struct device_node *node)
 933{
 934        struct clk_onecell_data *clk_data;
 935        void __iomem *base;
 936        int r;
 937
 938        base = of_iomap(node, 0);
 939        if (!base) {
 940                pr_err("%s(): ioremap failed\n", __func__);
 941                return;
 942        }
 943
 944        mt8173_top_clk_data = clk_data = mtk_alloc_clk_data(CLK_TOP_NR_CLK);
 945
 946        mtk_clk_register_fixed_clks(fixed_clks, ARRAY_SIZE(fixed_clks), clk_data);
 947        mtk_clk_register_factors(top_divs, ARRAY_SIZE(top_divs), clk_data);
 948        mtk_clk_register_composites(top_muxes, ARRAY_SIZE(top_muxes), base,
 949                        &mt8173_clk_lock, clk_data);
 950
 951        r = of_clk_add_provider(node, of_clk_src_onecell_get, clk_data);
 952        if (r)
 953                pr_err("%s(): could not register clock provider: %d\n",
 954                        __func__, r);
 955
 956        mtk_clk_enable_critical();
 957}
 958CLK_OF_DECLARE(mtk_topckgen, "mediatek,mt8173-topckgen", mtk_topckgen_init);
 959
 960static void __init mtk_infrasys_init(struct device_node *node)
 961{
 962        struct clk_onecell_data *clk_data;
 963        int r;
 964
 965        clk_data = mtk_alloc_clk_data(CLK_INFRA_NR_CLK);
 966
 967        mtk_clk_register_gates(node, infra_clks, ARRAY_SIZE(infra_clks),
 968                                                clk_data);
 969        mtk_clk_register_factors(infra_divs, ARRAY_SIZE(infra_divs), clk_data);
 970
 971        mtk_clk_register_cpumuxes(node, cpu_muxes, ARRAY_SIZE(cpu_muxes),
 972                                  clk_data);
 973
 974        r = of_clk_add_provider(node, of_clk_src_onecell_get, clk_data);
 975        if (r)
 976                pr_err("%s(): could not register clock provider: %d\n",
 977                        __func__, r);
 978
 979        mtk_register_reset_controller(node, 2, 0x30);
 980}
 981CLK_OF_DECLARE(mtk_infrasys, "mediatek,mt8173-infracfg", mtk_infrasys_init);
 982
 983static void __init mtk_pericfg_init(struct device_node *node)
 984{
 985        struct clk_onecell_data *clk_data;
 986        int r;
 987        void __iomem *base;
 988
 989        base = of_iomap(node, 0);
 990        if (!base) {
 991                pr_err("%s(): ioremap failed\n", __func__);
 992                return;
 993        }
 994
 995        clk_data = mtk_alloc_clk_data(CLK_PERI_NR_CLK);
 996
 997        mtk_clk_register_gates(node, peri_gates, ARRAY_SIZE(peri_gates),
 998                                                clk_data);
 999        mtk_clk_register_composites(peri_clks, ARRAY_SIZE(peri_clks), base,
1000                        &mt8173_clk_lock, clk_data);
1001
1002        r = of_clk_add_provider(node, of_clk_src_onecell_get, clk_data);
1003        if (r)
1004                pr_err("%s(): could not register clock provider: %d\n",
1005                        __func__, r);
1006
1007        mtk_register_reset_controller(node, 2, 0);
1008}
1009CLK_OF_DECLARE(mtk_pericfg, "mediatek,mt8173-pericfg", mtk_pericfg_init);
1010
1011struct mtk_clk_usb {
1012        int id;
1013        const char *name;
1014        const char *parent;
1015        u32 reg_ofs;
1016};
1017
1018#define APMIXED_USB(_id, _name, _parent, _reg_ofs) {                    \
1019                .id = _id,                                              \
1020                .name = _name,                                          \
1021                .parent = _parent,                                      \
1022                .reg_ofs = _reg_ofs,                                    \
1023        }
1024
1025static const struct mtk_clk_usb apmixed_usb[] __initconst = {
1026        APMIXED_USB(CLK_APMIXED_REF2USB_TX, "ref2usb_tx", "clk26m", 0x8),
1027};
1028
1029#define MT8173_PLL_FMAX         (3000UL * MHZ)
1030
1031#define CON0_MT8173_RST_BAR     BIT(24)
1032
1033#define PLL_B(_id, _name, _reg, _pwr_reg, _en_mask, _flags, _pcwbits,   \
1034                        _pd_reg, _pd_shift, _tuner_reg, _pcw_reg,       \
1035                        _pcw_shift, _div_table) {                       \
1036                .id = _id,                                              \
1037                .name = _name,                                          \
1038                .reg = _reg,                                            \
1039                .pwr_reg = _pwr_reg,                                    \
1040                .en_mask = _en_mask,                                    \
1041                .flags = _flags,                                        \
1042                .rst_bar_mask = CON0_MT8173_RST_BAR,                    \
1043                .fmax = MT8173_PLL_FMAX,                                \
1044                .pcwbits = _pcwbits,                                    \
1045                .pd_reg = _pd_reg,                                      \
1046                .pd_shift = _pd_shift,                                  \
1047                .tuner_reg = _tuner_reg,                                \
1048                .pcw_reg = _pcw_reg,                                    \
1049                .pcw_shift = _pcw_shift,                                \
1050                .div_table = _div_table,                                \
1051        }
1052
1053#define PLL(_id, _name, _reg, _pwr_reg, _en_mask, _flags, _pcwbits,     \
1054                        _pd_reg, _pd_shift, _tuner_reg, _pcw_reg,       \
1055                        _pcw_shift)                                     \
1056                PLL_B(_id, _name, _reg, _pwr_reg, _en_mask, _flags, _pcwbits, \
1057                        _pd_reg, _pd_shift, _tuner_reg, _pcw_reg, _pcw_shift, \
1058                        NULL)
1059
1060static const struct mtk_pll_div_table mmpll_div_table[] = {
1061        { .div = 0, .freq = MT8173_PLL_FMAX },
1062        { .div = 1, .freq = 1000000000 },
1063        { .div = 2, .freq = 702000000 },
1064        { .div = 3, .freq = 253500000 },
1065        { .div = 4, .freq = 126750000 },
1066        { } /* sentinel */
1067};
1068
1069static const struct mtk_pll_data plls[] = {
1070        PLL(CLK_APMIXED_ARMCA15PLL, "armca15pll", 0x200, 0x20c, 0x00000001, 0, 21, 0x204, 24, 0x0, 0x204, 0),
1071        PLL(CLK_APMIXED_ARMCA7PLL, "armca7pll", 0x210, 0x21c, 0x00000001, 0, 21, 0x214, 24, 0x0, 0x214, 0),
1072        PLL(CLK_APMIXED_MAINPLL, "mainpll", 0x220, 0x22c, 0xf0000101, HAVE_RST_BAR, 21, 0x220, 4, 0x0, 0x224, 0),
1073        PLL(CLK_APMIXED_UNIVPLL, "univpll", 0x230, 0x23c, 0xfe000001, HAVE_RST_BAR, 7, 0x230, 4, 0x0, 0x234, 14),
1074        PLL_B(CLK_APMIXED_MMPLL, "mmpll", 0x240, 0x24c, 0x00000001, 0, 21, 0x244, 24, 0x0, 0x244, 0, mmpll_div_table),
1075        PLL(CLK_APMIXED_MSDCPLL, "msdcpll", 0x250, 0x25c, 0x00000001, 0, 21, 0x250, 4, 0x0, 0x254, 0),
1076        PLL(CLK_APMIXED_VENCPLL, "vencpll", 0x260, 0x26c, 0x00000001, 0, 21, 0x260, 4, 0x0, 0x264, 0),
1077        PLL(CLK_APMIXED_TVDPLL, "tvdpll", 0x270, 0x27c, 0x00000001, 0, 21, 0x270, 4, 0x0, 0x274, 0),
1078        PLL(CLK_APMIXED_MPLL, "mpll", 0x280, 0x28c, 0x00000001, 0, 21, 0x280, 4, 0x0, 0x284, 0),
1079        PLL(CLK_APMIXED_VCODECPLL, "vcodecpll", 0x290, 0x29c, 0x00000001, 0, 21, 0x290, 4, 0x0, 0x294, 0),
1080        PLL(CLK_APMIXED_APLL1, "apll1", 0x2a0, 0x2b0, 0x00000001, 0, 31, 0x2a0, 4, 0x2a4, 0x2a4, 0),
1081        PLL(CLK_APMIXED_APLL2, "apll2", 0x2b4, 0x2c4, 0x00000001, 0, 31, 0x2b4, 4, 0x2b8, 0x2b8, 0),
1082        PLL(CLK_APMIXED_LVDSPLL, "lvdspll", 0x2d0, 0x2dc, 0x00000001, 0, 21, 0x2d0, 4, 0x0, 0x2d4, 0),
1083        PLL(CLK_APMIXED_MSDCPLL2, "msdcpll2", 0x2f0, 0x2fc, 0x00000001, 0, 21, 0x2f0, 4, 0x0, 0x2f4, 0),
1084};
1085
1086static void __init mtk_apmixedsys_init(struct device_node *node)
1087{
1088        struct clk_onecell_data *clk_data;
1089        void __iomem *base;
1090        struct clk *clk;
1091        int r, i;
1092
1093        base = of_iomap(node, 0);
1094        if (!base) {
1095                pr_err("%s(): ioremap failed\n", __func__);
1096                return;
1097        }
1098
1099        mt8173_pll_clk_data = clk_data = mtk_alloc_clk_data(CLK_APMIXED_NR_CLK);
1100        if (!clk_data) {
1101                iounmap(base);
1102                return;
1103        }
1104
1105        mtk_clk_register_plls(node, plls, ARRAY_SIZE(plls), clk_data);
1106
1107        for (i = 0; i < ARRAY_SIZE(apmixed_usb); i++) {
1108                const struct mtk_clk_usb *cku = &apmixed_usb[i];
1109
1110                clk = mtk_clk_register_ref2usb_tx(cku->name, cku->parent,
1111                                        base + cku->reg_ofs);
1112
1113                if (IS_ERR(clk)) {
1114                        pr_err("Failed to register clk %s: %ld\n", cku->name,
1115                                        PTR_ERR(clk));
1116                        continue;
1117                }
1118
1119                clk_data->clks[cku->id] = clk;
1120        }
1121
1122        clk = clk_register_divider(NULL, "hdmi_ref", "tvdpll_594m", 0,
1123                                   base + 0x40, 16, 3, CLK_DIVIDER_POWER_OF_TWO,
1124                                   NULL);
1125        clk_data->clks[CLK_APMIXED_HDMI_REF] = clk;
1126
1127        r = of_clk_add_provider(node, of_clk_src_onecell_get, clk_data);
1128        if (r)
1129                pr_err("%s(): could not register clock provider: %d\n",
1130                        __func__, r);
1131
1132        mtk_clk_enable_critical();
1133}
1134CLK_OF_DECLARE(mtk_apmixedsys, "mediatek,mt8173-apmixedsys",
1135                mtk_apmixedsys_init);
1136
1137static void __init mtk_imgsys_init(struct device_node *node)
1138{
1139        struct clk_onecell_data *clk_data;
1140        int r;
1141
1142        clk_data = mtk_alloc_clk_data(CLK_IMG_NR_CLK);
1143
1144        mtk_clk_register_gates(node, img_clks, ARRAY_SIZE(img_clks),
1145                                                clk_data);
1146
1147        r = of_clk_add_provider(node, of_clk_src_onecell_get, clk_data);
1148
1149        if (r)
1150                pr_err("%s(): could not register clock provider: %d\n",
1151                        __func__, r);
1152}
1153CLK_OF_DECLARE(mtk_imgsys, "mediatek,mt8173-imgsys", mtk_imgsys_init);
1154
1155static void __init mtk_mmsys_init(struct device_node *node)
1156{
1157        struct clk_onecell_data *clk_data;
1158        int r;
1159
1160        clk_data = mtk_alloc_clk_data(CLK_MM_NR_CLK);
1161
1162        mtk_clk_register_gates(node, mm_clks, ARRAY_SIZE(mm_clks),
1163                                                clk_data);
1164
1165        r = of_clk_add_provider(node, of_clk_src_onecell_get, clk_data);
1166        if (r)
1167                pr_err("%s(): could not register clock provider: %d\n",
1168                        __func__, r);
1169}
1170CLK_OF_DECLARE(mtk_mmsys, "mediatek,mt8173-mmsys", mtk_mmsys_init);
1171
1172static void __init mtk_vdecsys_init(struct device_node *node)
1173{
1174        struct clk_onecell_data *clk_data;
1175        int r;
1176
1177        clk_data = mtk_alloc_clk_data(CLK_VDEC_NR_CLK);
1178
1179        mtk_clk_register_gates(node, vdec_clks, ARRAY_SIZE(vdec_clks),
1180                                                clk_data);
1181
1182        r = of_clk_add_provider(node, of_clk_src_onecell_get, clk_data);
1183        if (r)
1184                pr_err("%s(): could not register clock provider: %d\n",
1185                        __func__, r);
1186}
1187CLK_OF_DECLARE(mtk_vdecsys, "mediatek,mt8173-vdecsys", mtk_vdecsys_init);
1188
1189static void __init mtk_vencsys_init(struct device_node *node)
1190{
1191        struct clk_onecell_data *clk_data;
1192        int r;
1193
1194        clk_data = mtk_alloc_clk_data(CLK_VENC_NR_CLK);
1195
1196        mtk_clk_register_gates(node, venc_clks, ARRAY_SIZE(venc_clks),
1197                                                clk_data);
1198
1199        r = of_clk_add_provider(node, of_clk_src_onecell_get, clk_data);
1200        if (r)
1201                pr_err("%s(): could not register clock provider: %d\n",
1202                        __func__, r);
1203}
1204CLK_OF_DECLARE(mtk_vencsys, "mediatek,mt8173-vencsys", mtk_vencsys_init);
1205
1206static void __init mtk_vencltsys_init(struct device_node *node)
1207{
1208        struct clk_onecell_data *clk_data;
1209        int r;
1210
1211        clk_data = mtk_alloc_clk_data(CLK_VENCLT_NR_CLK);
1212
1213        mtk_clk_register_gates(node, venclt_clks, ARRAY_SIZE(venclt_clks),
1214                                                clk_data);
1215
1216        r = of_clk_add_provider(node, of_clk_src_onecell_get, clk_data);
1217        if (r)
1218                pr_err("%s(): could not register clock provider: %d\n",
1219                        __func__, r);
1220}
1221CLK_OF_DECLARE(mtk_vencltsys, "mediatek,mt8173-vencltsys", mtk_vencltsys_init);
1222