linux/drivers/clk/sunxi-ng/ccu-sun5i.c
<<
>>
Prefs
   1/*
   2 * Copyright (c) 2016 Maxime Ripard. All rights reserved.
   3 *
   4 * This software is licensed under the terms of the GNU General Public
   5 * License version 2, as published by the Free Software Foundation, and
   6 * may be copied, distributed, and modified under those terms.
   7 *
   8 * This program is distributed in the hope that it will be useful,
   9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
  10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  11 * GNU General Public License for more details.
  12 */
  13
  14#include <linux/clk-provider.h>
  15#include <linux/of_address.h>
  16
  17#include "ccu_common.h"
  18#include "ccu_reset.h"
  19
  20#include "ccu_div.h"
  21#include "ccu_gate.h"
  22#include "ccu_mp.h"
  23#include "ccu_mult.h"
  24#include "ccu_nk.h"
  25#include "ccu_nkm.h"
  26#include "ccu_nkmp.h"
  27#include "ccu_nm.h"
  28#include "ccu_phase.h"
  29#include "ccu_sdm.h"
  30
  31#include "ccu-sun5i.h"
  32
  33static struct ccu_nkmp pll_core_clk = {
  34        .enable         = BIT(31),
  35        .n              = _SUNXI_CCU_MULT_OFFSET(8, 5, 0),
  36        .k              = _SUNXI_CCU_MULT(4, 2),
  37        .m              = _SUNXI_CCU_DIV(0, 2),
  38        .p              = _SUNXI_CCU_DIV(16, 2),
  39        .common         = {
  40                .reg            = 0x000,
  41                .hw.init        = CLK_HW_INIT("pll-core",
  42                                              "hosc",
  43                                              &ccu_nkmp_ops,
  44                                              0),
  45        },
  46};
  47
  48/*
  49 * The Audio PLL is supposed to have 4 outputs: 3 fixed factors from
  50 * the base (2x, 4x and 8x), and one variable divider (the one true
  51 * pll audio).
  52 *
  53 * With sigma-delta modulation for fractional-N on the audio PLL,
  54 * we have to use specific dividers. This means the variable divider
  55 * can no longer be used, as the audio codec requests the exact clock
  56 * rates we support through this mechanism. So we now hard code the
  57 * variable divider to 1. This means the clock rates will no longer
  58 * match the clock names.
  59 */
  60#define SUN5I_PLL_AUDIO_REG     0x008
  61
  62static struct ccu_sdm_setting pll_audio_sdm_table[] = {
  63        { .rate = 22579200, .pattern = 0xc0010d84, .m = 8, .n = 7 },
  64        { .rate = 24576000, .pattern = 0xc000ac02, .m = 14, .n = 14 },
  65};
  66
  67static struct ccu_nm pll_audio_base_clk = {
  68        .enable         = BIT(31),
  69        .n              = _SUNXI_CCU_MULT_OFFSET(8, 7, 0),
  70
  71        /*
  72         * The datasheet is wrong here, this doesn't have any
  73         * offset
  74         */
  75        .m              = _SUNXI_CCU_DIV_OFFSET(0, 5, 0),
  76        .sdm            = _SUNXI_CCU_SDM(pll_audio_sdm_table, 0,
  77                                         0x00c, BIT(31)),
  78        .common         = {
  79                .reg            = 0x008,
  80                .features       = CCU_FEATURE_SIGMA_DELTA_MOD,
  81                .hw.init        = CLK_HW_INIT("pll-audio-base",
  82                                              "hosc",
  83                                              &ccu_nm_ops,
  84                                              0),
  85        },
  86};
  87
  88static struct ccu_mult pll_video0_clk = {
  89        .enable         = BIT(31),
  90        .mult           = _SUNXI_CCU_MULT_OFFSET_MIN_MAX(0, 7, 0, 9, 127),
  91        .frac           = _SUNXI_CCU_FRAC(BIT(15), BIT(14),
  92                                          270000000, 297000000),
  93        .common         = {
  94                .reg            = 0x010,
  95                .features       = (CCU_FEATURE_FRACTIONAL |
  96                                   CCU_FEATURE_ALL_PREDIV),
  97                .prediv         = 8,
  98                .hw.init        = CLK_HW_INIT("pll-video0",
  99                                              "hosc",
 100                                              &ccu_mult_ops,
 101                                              0),
 102        },
 103};
 104
 105static struct ccu_nkmp pll_ve_clk = {
 106        .enable         = BIT(31),
 107        .n              = _SUNXI_CCU_MULT_OFFSET(8, 5, 0),
 108        .k              = _SUNXI_CCU_MULT(4, 2),
 109        .m              = _SUNXI_CCU_DIV(0, 2),
 110        .p              = _SUNXI_CCU_DIV(16, 2),
 111        .common         = {
 112                .reg            = 0x018,
 113                .hw.init        = CLK_HW_INIT("pll-ve",
 114                                              "hosc",
 115                                              &ccu_nkmp_ops,
 116                                              0),
 117        },
 118};
 119
 120static struct ccu_nk pll_ddr_base_clk = {
 121        .enable         = BIT(31),
 122        .n              = _SUNXI_CCU_MULT_OFFSET(8, 5, 0),
 123        .k              = _SUNXI_CCU_MULT(4, 2),
 124        .common         = {
 125                .reg            = 0x020,
 126                .hw.init        = CLK_HW_INIT("pll-ddr-base",
 127                                              "hosc",
 128                                              &ccu_nk_ops,
 129                                              0),
 130        },
 131};
 132
 133static SUNXI_CCU_M(pll_ddr_clk, "pll-ddr", "pll-ddr-base", 0x020, 0, 2,
 134                   CLK_IS_CRITICAL);
 135
 136static struct ccu_div pll_ddr_other_clk = {
 137        .div            = _SUNXI_CCU_DIV_FLAGS(16, 2, CLK_DIVIDER_POWER_OF_TWO),
 138
 139        .common         = {
 140                .reg            = 0x020,
 141                .hw.init        = CLK_HW_INIT("pll-ddr-other", "pll-ddr-base",
 142                                              &ccu_div_ops,
 143                                              0),
 144        },
 145};
 146
 147static struct ccu_nk pll_periph_clk = {
 148        .enable         = BIT(31),
 149        .n              = _SUNXI_CCU_MULT_OFFSET(8, 5, 0),
 150        .k              = _SUNXI_CCU_MULT(4, 2),
 151        .fixed_post_div = 2,
 152        .common         = {
 153                .reg            = 0x028,
 154                .features       = CCU_FEATURE_FIXED_POSTDIV,
 155                .hw.init        = CLK_HW_INIT("pll-periph",
 156                                              "hosc",
 157                                              &ccu_nk_ops,
 158                                              0),
 159        },
 160};
 161
 162static struct ccu_mult pll_video1_clk = {
 163        .enable         = BIT(31),
 164        .mult           = _SUNXI_CCU_MULT_OFFSET_MIN_MAX(0, 7, 0, 9, 127),
 165        .frac           = _SUNXI_CCU_FRAC(BIT(15), BIT(14),
 166                                  270000000, 297000000),
 167        .common         = {
 168                .reg            = 0x030,
 169                .features       = (CCU_FEATURE_FRACTIONAL |
 170                                   CCU_FEATURE_ALL_PREDIV),
 171                .prediv         = 8,
 172                .hw.init        = CLK_HW_INIT("pll-video1",
 173                                              "hosc",
 174                                              &ccu_mult_ops,
 175                                              0),
 176        },
 177};
 178
 179static SUNXI_CCU_GATE(hosc_clk, "hosc", "osc24M", 0x050, BIT(0), 0);
 180
 181#define SUN5I_AHB_REG   0x054
 182static const char * const cpu_parents[] = { "osc32k", "hosc",
 183                                            "pll-core" , "pll-periph" };
 184static const struct ccu_mux_fixed_prediv cpu_predivs[] = {
 185        { .index = 3, .div = 3, },
 186};
 187static struct ccu_mux cpu_clk = {
 188        .mux            = {
 189                .shift          = 16,
 190                .width          = 2,
 191                .fixed_predivs  = cpu_predivs,
 192                .n_predivs      = ARRAY_SIZE(cpu_predivs),
 193        },
 194        .common         = {
 195                .reg            = 0x054,
 196                .features       = CCU_FEATURE_FIXED_PREDIV,
 197                .hw.init        = CLK_HW_INIT_PARENTS("cpu",
 198                                                      cpu_parents,
 199                                                      &ccu_mux_ops,
 200                                                      CLK_SET_RATE_PARENT | CLK_IS_CRITICAL),
 201        }
 202};
 203
 204static SUNXI_CCU_M(axi_clk, "axi", "cpu", 0x054, 0, 2, 0);
 205
 206static const char * const ahb_parents[] = { "axi" , "cpu", "pll-periph" };
 207static const struct ccu_mux_fixed_prediv ahb_predivs[] = {
 208        { .index = 2, .div = 2, },
 209};
 210static struct ccu_div ahb_clk = {
 211        .div            = _SUNXI_CCU_DIV_FLAGS(4, 2, CLK_DIVIDER_POWER_OF_TWO),
 212        .mux            = {
 213                .shift          = 6,
 214                .width          = 2,
 215                .fixed_predivs  = ahb_predivs,
 216                .n_predivs      = ARRAY_SIZE(ahb_predivs),
 217        },
 218
 219        .common         = {
 220                .reg            = 0x054,
 221                .hw.init        = CLK_HW_INIT_PARENTS("ahb",
 222                                                      ahb_parents,
 223                                                      &ccu_div_ops,
 224                                                      0),
 225        },
 226};
 227
 228static struct clk_div_table apb0_div_table[] = {
 229        { .val = 0, .div = 2 },
 230        { .val = 1, .div = 2 },
 231        { .val = 2, .div = 4 },
 232        { .val = 3, .div = 8 },
 233        { /* Sentinel */ },
 234};
 235static SUNXI_CCU_DIV_TABLE(apb0_clk, "apb0", "ahb",
 236                           0x054, 8, 2, apb0_div_table, 0);
 237
 238static const char * const apb1_parents[] = { "hosc", "pll-periph", "osc32k" };
 239static SUNXI_CCU_MP_WITH_MUX(apb1_clk, "apb1", apb1_parents, 0x058,
 240                             0, 5,      /* M */
 241                             16, 2,     /* P */
 242                             24, 2,     /* mux */
 243                             0);
 244
 245static SUNXI_CCU_GATE(axi_dram_clk,     "axi-dram",     "axi",
 246                      0x05c, BIT(0), 0);
 247
 248static SUNXI_CCU_GATE(ahb_otg_clk,      "ahb-otg",      "ahb",
 249                      0x060, BIT(0), 0);
 250static SUNXI_CCU_GATE(ahb_ehci_clk,     "ahb-ehci",     "ahb",
 251                      0x060, BIT(1), 0);
 252static SUNXI_CCU_GATE(ahb_ohci_clk,     "ahb-ohci",     "ahb",
 253                      0x060, BIT(2), 0);
 254static SUNXI_CCU_GATE(ahb_ss_clk,       "ahb-ss",       "ahb",
 255                      0x060, BIT(5), 0);
 256static SUNXI_CCU_GATE(ahb_dma_clk,      "ahb-dma",      "ahb",
 257                      0x060, BIT(6), 0);
 258static SUNXI_CCU_GATE(ahb_bist_clk,     "ahb-bist",     "ahb",
 259                      0x060, BIT(7), 0);
 260static SUNXI_CCU_GATE(ahb_mmc0_clk,     "ahb-mmc0",     "ahb",
 261                      0x060, BIT(8), 0);
 262static SUNXI_CCU_GATE(ahb_mmc1_clk,     "ahb-mmc1",     "ahb",
 263                      0x060, BIT(9), 0);
 264static SUNXI_CCU_GATE(ahb_mmc2_clk,     "ahb-mmc2",     "ahb",
 265                      0x060, BIT(10), 0);
 266static SUNXI_CCU_GATE(ahb_nand_clk,     "ahb-nand",     "ahb",
 267                      0x060, BIT(13), 0);
 268static SUNXI_CCU_GATE(ahb_sdram_clk,    "ahb-sdram",    "ahb",
 269                      0x060, BIT(14), CLK_IS_CRITICAL);
 270static SUNXI_CCU_GATE(ahb_emac_clk,     "ahb-emac",     "ahb",
 271                      0x060, BIT(17), 0);
 272static SUNXI_CCU_GATE(ahb_ts_clk,       "ahb-ts",       "ahb",
 273                      0x060, BIT(18), 0);
 274static SUNXI_CCU_GATE(ahb_spi0_clk,     "ahb-spi0",     "ahb",
 275                      0x060, BIT(20), 0);
 276static SUNXI_CCU_GATE(ahb_spi1_clk,     "ahb-spi1",     "ahb",
 277                      0x060, BIT(21), 0);
 278static SUNXI_CCU_GATE(ahb_spi2_clk,     "ahb-spi2",     "ahb",
 279                      0x060, BIT(22), 0);
 280static SUNXI_CCU_GATE(ahb_gps_clk,      "ahb-gps",      "ahb",
 281                      0x060, BIT(26), 0);
 282static SUNXI_CCU_GATE(ahb_hstimer_clk,  "ahb-hstimer",  "ahb",
 283                      0x060, BIT(28), 0);
 284
 285static SUNXI_CCU_GATE(ahb_ve_clk,       "ahb-ve",       "ahb",
 286                      0x064, BIT(0), 0);
 287static SUNXI_CCU_GATE(ahb_tve_clk,      "ahb-tve",      "ahb",
 288                      0x064, BIT(2), 0);
 289static SUNXI_CCU_GATE(ahb_lcd_clk,      "ahb-lcd",      "ahb",
 290                      0x064, BIT(4), 0);
 291static SUNXI_CCU_GATE(ahb_csi_clk,      "ahb-csi",      "ahb",
 292                      0x064, BIT(8), 0);
 293static SUNXI_CCU_GATE(ahb_hdmi_clk,     "ahb-hdmi",     "ahb",
 294                      0x064, BIT(11), 0);
 295static SUNXI_CCU_GATE(ahb_de_be_clk,    "ahb-de-be",    "ahb",
 296                      0x064, BIT(12), 0);
 297static SUNXI_CCU_GATE(ahb_de_fe_clk,    "ahb-de-fe",    "ahb",
 298                      0x064, BIT(14), 0);
 299static SUNXI_CCU_GATE(ahb_iep_clk,      "ahb-iep",      "ahb",
 300                      0x064, BIT(19), 0);
 301static SUNXI_CCU_GATE(ahb_gpu_clk,      "ahb-gpu",      "ahb",
 302                      0x064, BIT(20), 0);
 303
 304static SUNXI_CCU_GATE(apb0_codec_clk,   "apb0-codec",   "apb0",
 305                      0x068, BIT(0), 0);
 306static SUNXI_CCU_GATE(apb0_spdif_clk,   "apb0-spdif",   "apb0",
 307                      0x068, BIT(1), 0);
 308static SUNXI_CCU_GATE(apb0_i2s_clk,     "apb0-i2s",     "apb0",
 309                      0x068, BIT(3), 0);
 310static SUNXI_CCU_GATE(apb0_pio_clk,     "apb0-pio",     "apb0",
 311                      0x068, BIT(5), 0);
 312static SUNXI_CCU_GATE(apb0_ir_clk,      "apb0-ir",      "apb0",
 313                      0x068, BIT(6), 0);
 314static SUNXI_CCU_GATE(apb0_keypad_clk,  "apb0-keypad",  "apb0",
 315                      0x068, BIT(10), 0);
 316
 317static SUNXI_CCU_GATE(apb1_i2c0_clk,    "apb1-i2c0",    "apb1",
 318                      0x06c, BIT(0), 0);
 319static SUNXI_CCU_GATE(apb1_i2c1_clk,    "apb1-i2c1",    "apb1",
 320                      0x06c, BIT(1), 0);
 321static SUNXI_CCU_GATE(apb1_i2c2_clk,    "apb1-i2c2",    "apb1",
 322                      0x06c, BIT(2), 0);
 323static SUNXI_CCU_GATE(apb1_uart0_clk,   "apb1-uart0",   "apb1",
 324                      0x06c, BIT(16), 0);
 325static SUNXI_CCU_GATE(apb1_uart1_clk,   "apb1-uart1",   "apb1",
 326                      0x06c, BIT(17), 0);
 327static SUNXI_CCU_GATE(apb1_uart2_clk,   "apb1-uart2",   "apb1",
 328                      0x06c, BIT(18), 0);
 329static SUNXI_CCU_GATE(apb1_uart3_clk,   "apb1-uart3",   "apb1",
 330                      0x06c, BIT(19), 0);
 331
 332static const char * const mod0_default_parents[] = { "hosc", "pll-periph",
 333                                                     "pll-ddr-other" };
 334static SUNXI_CCU_MP_WITH_MUX_GATE(nand_clk, "nand", mod0_default_parents, 0x080,
 335                                  0, 4,         /* M */
 336                                  16, 2,        /* P */
 337                                  24, 2,        /* mux */
 338                                  BIT(31),      /* gate */
 339                                  0);
 340
 341static SUNXI_CCU_MP_WITH_MUX_GATE(mmc0_clk, "mmc0", mod0_default_parents, 0x088,
 342                                  0, 4,         /* M */
 343                                  16, 2,        /* P */
 344                                  24, 2,        /* mux */
 345                                  BIT(31),      /* gate */
 346                                  0);
 347
 348static SUNXI_CCU_MP_WITH_MUX_GATE(mmc1_clk, "mmc1", mod0_default_parents, 0x08c,
 349                                  0, 4,         /* M */
 350                                  16, 2,        /* P */
 351                                  24, 2,        /* mux */
 352                                  BIT(31),      /* gate */
 353                                  0);
 354
 355static SUNXI_CCU_MP_WITH_MUX_GATE(mmc2_clk, "mmc2", mod0_default_parents, 0x090,
 356                                  0, 4,         /* M */
 357                                  16, 2,        /* P */
 358                                  24, 2,        /* mux */
 359                                  BIT(31),      /* gate */
 360                                  0);
 361
 362static SUNXI_CCU_MP_WITH_MUX_GATE(ts_clk, "ts", mod0_default_parents, 0x098,
 363                                  0, 4,         /* M */
 364                                  16, 2,        /* P */
 365                                  24, 2,        /* mux */
 366                                  BIT(31),      /* gate */
 367                                  0);
 368
 369static SUNXI_CCU_MP_WITH_MUX_GATE(ss_clk, "ss", mod0_default_parents, 0x09c,
 370                                  0, 4,         /* M */
 371                                  16, 2,        /* P */
 372                                  24, 2,        /* mux */
 373                                  BIT(31),      /* gate */
 374                                  0);
 375
 376static SUNXI_CCU_MP_WITH_MUX_GATE(spi0_clk, "spi0", mod0_default_parents, 0x0a0,
 377                                  0, 4,         /* M */
 378                                  16, 2,        /* P */
 379                                  24, 2,        /* mux */
 380                                  BIT(31),      /* gate */
 381                                  0);
 382
 383static SUNXI_CCU_MP_WITH_MUX_GATE(spi1_clk, "spi1", mod0_default_parents, 0x0a4,
 384                                  0, 4,         /* M */
 385                                  16, 2,        /* P */
 386                                  24, 2,        /* mux */
 387                                  BIT(31),      /* gate */
 388                                  0);
 389
 390static SUNXI_CCU_MP_WITH_MUX_GATE(spi2_clk, "spi2", mod0_default_parents, 0x0a8,
 391                                  0, 4,         /* M */
 392                                  16, 2,        /* P */
 393                                  24, 2,        /* mux */
 394                                  BIT(31),      /* gate */
 395                                  0);
 396
 397static SUNXI_CCU_MP_WITH_MUX_GATE(ir_clk, "ir", mod0_default_parents, 0x0b0,
 398                                  0, 4,         /* M */
 399                                  16, 2,        /* P */
 400                                  24, 2,        /* mux */
 401                                  BIT(31),      /* gate */
 402                                  0);
 403
 404static const char * const i2s_parents[] = { "pll-audio-8x", "pll-audio-4x",
 405                                            "pll-audio-2x", "pll-audio" };
 406static SUNXI_CCU_MUX_WITH_GATE(i2s_clk, "i2s", i2s_parents,
 407                               0x0b8, 16, 2, BIT(31), CLK_SET_RATE_PARENT);
 408
 409static const char * const spdif_parents[] = { "pll-audio-8x", "pll-audio-4x",
 410                                            "pll-audio-2x", "pll-audio" };
 411static SUNXI_CCU_MUX_WITH_GATE(spdif_clk, "spdif", spdif_parents,
 412                               0x0c0, 16, 2, BIT(31), CLK_SET_RATE_PARENT);
 413
 414static const char * const keypad_parents[] = { "hosc", "losc"};
 415static const u8 keypad_table[] = { 0, 2 };
 416static struct ccu_mp keypad_clk = {
 417        .enable         = BIT(31),
 418        .m              = _SUNXI_CCU_DIV(8, 5),
 419        .p              = _SUNXI_CCU_DIV(20, 2),
 420        .mux            = _SUNXI_CCU_MUX_TABLE(24, 2, keypad_table),
 421
 422        .common         = {
 423                .reg            = 0x0c4,
 424                .hw.init        = CLK_HW_INIT_PARENTS("keypad",
 425                                                      keypad_parents,
 426                                                      &ccu_mp_ops,
 427                                                      0),
 428        },
 429};
 430
 431static SUNXI_CCU_GATE(usb_ohci_clk,     "usb-ohci",     "pll-periph",
 432                      0x0cc, BIT(6), 0);
 433static SUNXI_CCU_GATE(usb_phy0_clk,     "usb-phy0",     "pll-periph",
 434                      0x0cc, BIT(8), 0);
 435static SUNXI_CCU_GATE(usb_phy1_clk,     "usb-phy1",     "pll-periph",
 436                      0x0cc, BIT(9), 0);
 437
 438static const char * const gps_parents[] = { "hosc", "pll-periph",
 439                                            "pll-video1", "pll-ve" };
 440static SUNXI_CCU_M_WITH_MUX_GATE(gps_clk, "gps", gps_parents,
 441                                 0x0d0, 0, 3, 24, 2, BIT(31), 0);
 442
 443static SUNXI_CCU_GATE(dram_ve_clk,      "dram-ve",      "pll-ddr",
 444                      0x100, BIT(0), 0);
 445static SUNXI_CCU_GATE(dram_csi_clk,     "dram-csi",     "pll-ddr",
 446                      0x100, BIT(1), 0);
 447static SUNXI_CCU_GATE(dram_ts_clk,      "dram-ts",      "pll-ddr",
 448                      0x100, BIT(3), 0);
 449static SUNXI_CCU_GATE(dram_tve_clk,     "dram-tve",     "pll-ddr",
 450                      0x100, BIT(5), 0);
 451static SUNXI_CCU_GATE(dram_de_fe_clk,   "dram-de-fe",   "pll-ddr",
 452                      0x100, BIT(25), 0);
 453static SUNXI_CCU_GATE(dram_de_be_clk,   "dram-de-be",   "pll-ddr",
 454                      0x100, BIT(26), 0);
 455static SUNXI_CCU_GATE(dram_ace_clk,     "dram-ace",     "pll-ddr",
 456                      0x100, BIT(29), 0);
 457static SUNXI_CCU_GATE(dram_iep_clk,     "dram-iep",     "pll-ddr",
 458                      0x100, BIT(31), 0);
 459
 460static const char * const de_parents[] = { "pll-video0", "pll-video1",
 461                                           "pll-ddr-other" };
 462static SUNXI_CCU_M_WITH_MUX_GATE(de_be_clk, "de-be", de_parents,
 463                                 0x104, 0, 4, 24, 2, BIT(31), 0);
 464
 465static SUNXI_CCU_M_WITH_MUX_GATE(de_fe_clk, "de-fe", de_parents,
 466                                 0x10c, 0, 4, 24, 2, BIT(31), 0);
 467
 468static const char * const tcon_parents[] = { "pll-video0", "pll-video1",
 469                                             "pll-video0-2x", "pll-video1-2x" };
 470static SUNXI_CCU_MUX_WITH_GATE(tcon_ch0_clk, "tcon-ch0-sclk", tcon_parents,
 471                               0x118, 24, 2, BIT(31), CLK_SET_RATE_PARENT);
 472
 473static SUNXI_CCU_M_WITH_MUX_GATE(tcon_ch1_sclk2_clk, "tcon-ch1-sclk2",
 474                                 tcon_parents,
 475                                 0x12c, 0, 4, 24, 2, BIT(31), CLK_SET_RATE_PARENT);
 476
 477static SUNXI_CCU_M_WITH_GATE(tcon_ch1_sclk1_clk, "tcon-ch1-sclk1", "tcon-ch1-sclk2",
 478                             0x12c, 11, 1, BIT(15), CLK_SET_RATE_PARENT);
 479
 480static const char * const csi_parents[] = { "hosc", "pll-video0", "pll-video1",
 481                                            "pll-video0-2x", "pll-video1-2x" };
 482static const u8 csi_table[] = { 0, 1, 2, 5, 6 };
 483static SUNXI_CCU_M_WITH_MUX_TABLE_GATE(csi_clk, "csi",
 484                                       csi_parents, csi_table,
 485                                       0x134, 0, 5, 24, 3, BIT(31), 0);
 486
 487static SUNXI_CCU_GATE(ve_clk,           "ve",           "pll-ve",
 488                      0x13c, BIT(31), CLK_SET_RATE_PARENT);
 489
 490static SUNXI_CCU_GATE(codec_clk,        "codec",        "pll-audio",
 491                      0x140, BIT(31), CLK_SET_RATE_PARENT);
 492
 493static SUNXI_CCU_GATE(avs_clk,          "avs",          "hosc",
 494                      0x144, BIT(31), 0);
 495
 496static const char * const hdmi_parents[] = { "pll-video0", "pll-video0-2x" };
 497static const u8 hdmi_table[] = { 0, 2 };
 498static SUNXI_CCU_M_WITH_MUX_TABLE_GATE(hdmi_clk, "hdmi",
 499                                       hdmi_parents, hdmi_table,
 500                                       0x150, 0, 4, 24, 2, BIT(31),
 501                                       CLK_SET_RATE_PARENT);
 502
 503static const char * const gpu_parents[] = { "pll-video0", "pll-ve",
 504                                            "pll-ddr-other", "pll-video1",
 505                                            "pll-video1-2x" };
 506static SUNXI_CCU_M_WITH_MUX_GATE(gpu_clk, "gpu", gpu_parents,
 507                                 0x154, 0, 4, 24, 3, BIT(31), 0);
 508
 509static const char * const mbus_parents[] = { "hosc", "pll-periph", "pll-ddr" };
 510static SUNXI_CCU_MP_WITH_MUX_GATE(mbus_clk, "mbus", mbus_parents,
 511                                  0x15c, 0, 4, 16, 2, 24, 2, BIT(31), CLK_IS_CRITICAL);
 512
 513static SUNXI_CCU_GATE(iep_clk,          "iep",          "de-be",
 514                      0x160, BIT(31), 0);
 515
 516static struct ccu_common *sun5i_a10s_ccu_clks[] = {
 517        &hosc_clk.common,
 518        &pll_core_clk.common,
 519        &pll_audio_base_clk.common,
 520        &pll_video0_clk.common,
 521        &pll_ve_clk.common,
 522        &pll_ddr_base_clk.common,
 523        &pll_ddr_clk.common,
 524        &pll_ddr_other_clk.common,
 525        &pll_periph_clk.common,
 526        &pll_video1_clk.common,
 527        &cpu_clk.common,
 528        &axi_clk.common,
 529        &ahb_clk.common,
 530        &apb0_clk.common,
 531        &apb1_clk.common,
 532        &axi_dram_clk.common,
 533        &ahb_otg_clk.common,
 534        &ahb_ehci_clk.common,
 535        &ahb_ohci_clk.common,
 536        &ahb_ss_clk.common,
 537        &ahb_dma_clk.common,
 538        &ahb_bist_clk.common,
 539        &ahb_mmc0_clk.common,
 540        &ahb_mmc1_clk.common,
 541        &ahb_mmc2_clk.common,
 542        &ahb_nand_clk.common,
 543        &ahb_sdram_clk.common,
 544        &ahb_emac_clk.common,
 545        &ahb_ts_clk.common,
 546        &ahb_spi0_clk.common,
 547        &ahb_spi1_clk.common,
 548        &ahb_spi2_clk.common,
 549        &ahb_gps_clk.common,
 550        &ahb_hstimer_clk.common,
 551        &ahb_ve_clk.common,
 552        &ahb_tve_clk.common,
 553        &ahb_lcd_clk.common,
 554        &ahb_csi_clk.common,
 555        &ahb_hdmi_clk.common,
 556        &ahb_de_be_clk.common,
 557        &ahb_de_fe_clk.common,
 558        &ahb_iep_clk.common,
 559        &ahb_gpu_clk.common,
 560        &apb0_codec_clk.common,
 561        &apb0_spdif_clk.common,
 562        &apb0_i2s_clk.common,
 563        &apb0_pio_clk.common,
 564        &apb0_ir_clk.common,
 565        &apb0_keypad_clk.common,
 566        &apb1_i2c0_clk.common,
 567        &apb1_i2c1_clk.common,
 568        &apb1_i2c2_clk.common,
 569        &apb1_uart0_clk.common,
 570        &apb1_uart1_clk.common,
 571        &apb1_uart2_clk.common,
 572        &apb1_uart3_clk.common,
 573        &nand_clk.common,
 574        &mmc0_clk.common,
 575        &mmc1_clk.common,
 576        &mmc2_clk.common,
 577        &ts_clk.common,
 578        &ss_clk.common,
 579        &spi0_clk.common,
 580        &spi1_clk.common,
 581        &spi2_clk.common,
 582        &ir_clk.common,
 583        &i2s_clk.common,
 584        &spdif_clk.common,
 585        &keypad_clk.common,
 586        &usb_ohci_clk.common,
 587        &usb_phy0_clk.common,
 588        &usb_phy1_clk.common,
 589        &gps_clk.common,
 590        &dram_ve_clk.common,
 591        &dram_csi_clk.common,
 592        &dram_ts_clk.common,
 593        &dram_tve_clk.common,
 594        &dram_de_fe_clk.common,
 595        &dram_de_be_clk.common,
 596        &dram_ace_clk.common,
 597        &dram_iep_clk.common,
 598        &de_be_clk.common,
 599        &de_fe_clk.common,
 600        &tcon_ch0_clk.common,
 601        &tcon_ch1_sclk2_clk.common,
 602        &tcon_ch1_sclk1_clk.common,
 603        &csi_clk.common,
 604        &ve_clk.common,
 605        &codec_clk.common,
 606        &avs_clk.common,
 607        &hdmi_clk.common,
 608        &gpu_clk.common,
 609        &mbus_clk.common,
 610        &iep_clk.common,
 611};
 612
 613/* We hardcode the divider to 1 for now */
 614static CLK_FIXED_FACTOR(pll_audio_clk, "pll-audio",
 615                        "pll-audio-base", 1, 1, CLK_SET_RATE_PARENT);
 616static CLK_FIXED_FACTOR(pll_audio_2x_clk, "pll-audio-2x",
 617                        "pll-audio-base", 2, 1, CLK_SET_RATE_PARENT);
 618static CLK_FIXED_FACTOR(pll_audio_4x_clk, "pll-audio-4x",
 619                        "pll-audio-base", 1, 1, CLK_SET_RATE_PARENT);
 620static CLK_FIXED_FACTOR(pll_audio_8x_clk, "pll-audio-8x",
 621                        "pll-audio-base", 1, 2, CLK_SET_RATE_PARENT);
 622static CLK_FIXED_FACTOR(pll_video0_2x_clk, "pll-video0-2x",
 623                        "pll-video0", 1, 2, CLK_SET_RATE_PARENT);
 624static CLK_FIXED_FACTOR(pll_video1_2x_clk, "pll-video1-2x",
 625                        "pll-video1", 1, 2, CLK_SET_RATE_PARENT);
 626
 627static struct clk_hw_onecell_data sun5i_a10s_hw_clks = {
 628        .hws    = {
 629                [CLK_HOSC]              = &hosc_clk.common.hw,
 630                [CLK_PLL_CORE]          = &pll_core_clk.common.hw,
 631                [CLK_PLL_AUDIO_BASE]    = &pll_audio_base_clk.common.hw,
 632                [CLK_PLL_AUDIO]         = &pll_audio_clk.hw,
 633                [CLK_PLL_AUDIO_2X]      = &pll_audio_2x_clk.hw,
 634                [CLK_PLL_AUDIO_4X]      = &pll_audio_4x_clk.hw,
 635                [CLK_PLL_AUDIO_8X]      = &pll_audio_8x_clk.hw,
 636                [CLK_PLL_VIDEO0]        = &pll_video0_clk.common.hw,
 637                [CLK_PLL_VIDEO0_2X]     = &pll_video0_2x_clk.hw,
 638                [CLK_PLL_VE]            = &pll_ve_clk.common.hw,
 639                [CLK_PLL_DDR_BASE]      = &pll_ddr_base_clk.common.hw,
 640                [CLK_PLL_DDR]           = &pll_ddr_clk.common.hw,
 641                [CLK_PLL_DDR_OTHER]     = &pll_ddr_other_clk.common.hw,
 642                [CLK_PLL_PERIPH]        = &pll_periph_clk.common.hw,
 643                [CLK_PLL_VIDEO1]        = &pll_video1_clk.common.hw,
 644                [CLK_PLL_VIDEO1_2X]     = &pll_video1_2x_clk.hw,
 645                [CLK_CPU]               = &cpu_clk.common.hw,
 646                [CLK_AXI]               = &axi_clk.common.hw,
 647                [CLK_AHB]               = &ahb_clk.common.hw,
 648                [CLK_APB0]              = &apb0_clk.common.hw,
 649                [CLK_APB1]              = &apb1_clk.common.hw,
 650                [CLK_DRAM_AXI]          = &axi_dram_clk.common.hw,
 651                [CLK_AHB_OTG]           = &ahb_otg_clk.common.hw,
 652                [CLK_AHB_EHCI]          = &ahb_ehci_clk.common.hw,
 653                [CLK_AHB_OHCI]          = &ahb_ohci_clk.common.hw,
 654                [CLK_AHB_SS]            = &ahb_ss_clk.common.hw,
 655                [CLK_AHB_DMA]           = &ahb_dma_clk.common.hw,
 656                [CLK_AHB_BIST]          = &ahb_bist_clk.common.hw,
 657                [CLK_AHB_MMC0]          = &ahb_mmc0_clk.common.hw,
 658                [CLK_AHB_MMC1]          = &ahb_mmc1_clk.common.hw,
 659                [CLK_AHB_MMC2]          = &ahb_mmc2_clk.common.hw,
 660                [CLK_AHB_NAND]          = &ahb_nand_clk.common.hw,
 661                [CLK_AHB_SDRAM]         = &ahb_sdram_clk.common.hw,
 662                [CLK_AHB_EMAC]          = &ahb_emac_clk.common.hw,
 663                [CLK_AHB_TS]            = &ahb_ts_clk.common.hw,
 664                [CLK_AHB_SPI0]          = &ahb_spi0_clk.common.hw,
 665                [CLK_AHB_SPI1]          = &ahb_spi1_clk.common.hw,
 666                [CLK_AHB_SPI2]          = &ahb_spi2_clk.common.hw,
 667                [CLK_AHB_GPS]           = &ahb_gps_clk.common.hw,
 668                [CLK_AHB_HSTIMER]       = &ahb_hstimer_clk.common.hw,
 669                [CLK_AHB_VE]            = &ahb_ve_clk.common.hw,
 670                [CLK_AHB_TVE]           = &ahb_tve_clk.common.hw,
 671                [CLK_AHB_LCD]           = &ahb_lcd_clk.common.hw,
 672                [CLK_AHB_CSI]           = &ahb_csi_clk.common.hw,
 673                [CLK_AHB_HDMI]          = &ahb_hdmi_clk.common.hw,
 674                [CLK_AHB_DE_BE]         = &ahb_de_be_clk.common.hw,
 675                [CLK_AHB_DE_FE]         = &ahb_de_fe_clk.common.hw,
 676                [CLK_AHB_IEP]           = &ahb_iep_clk.common.hw,
 677                [CLK_AHB_GPU]           = &ahb_gpu_clk.common.hw,
 678                [CLK_APB0_CODEC]        = &apb0_codec_clk.common.hw,
 679                [CLK_APB0_I2S]          = &apb0_i2s_clk.common.hw,
 680                [CLK_APB0_PIO]          = &apb0_pio_clk.common.hw,
 681                [CLK_APB0_IR]           = &apb0_ir_clk.common.hw,
 682                [CLK_APB0_KEYPAD]       = &apb0_keypad_clk.common.hw,
 683                [CLK_APB1_I2C0]         = &apb1_i2c0_clk.common.hw,
 684                [CLK_APB1_I2C1]         = &apb1_i2c1_clk.common.hw,
 685                [CLK_APB1_I2C2]         = &apb1_i2c2_clk.common.hw,
 686                [CLK_APB1_UART0]        = &apb1_uart0_clk.common.hw,
 687                [CLK_APB1_UART1]        = &apb1_uart1_clk.common.hw,
 688                [CLK_APB1_UART2]        = &apb1_uart2_clk.common.hw,
 689                [CLK_APB1_UART3]        = &apb1_uart3_clk.common.hw,
 690                [CLK_NAND]              = &nand_clk.common.hw,
 691                [CLK_MMC0]              = &mmc0_clk.common.hw,
 692                [CLK_MMC1]              = &mmc1_clk.common.hw,
 693                [CLK_MMC2]              = &mmc2_clk.common.hw,
 694                [CLK_TS]                = &ts_clk.common.hw,
 695                [CLK_SS]                = &ss_clk.common.hw,
 696                [CLK_SPI0]              = &spi0_clk.common.hw,
 697                [CLK_SPI1]              = &spi1_clk.common.hw,
 698                [CLK_SPI2]              = &spi2_clk.common.hw,
 699                [CLK_IR]                = &ir_clk.common.hw,
 700                [CLK_I2S]               = &i2s_clk.common.hw,
 701                [CLK_KEYPAD]            = &keypad_clk.common.hw,
 702                [CLK_USB_OHCI]          = &usb_ohci_clk.common.hw,
 703                [CLK_USB_PHY0]          = &usb_phy0_clk.common.hw,
 704                [CLK_USB_PHY1]          = &usb_phy1_clk.common.hw,
 705                [CLK_GPS]               = &gps_clk.common.hw,
 706                [CLK_DRAM_VE]           = &dram_ve_clk.common.hw,
 707                [CLK_DRAM_CSI]          = &dram_csi_clk.common.hw,
 708                [CLK_DRAM_TS]           = &dram_ts_clk.common.hw,
 709                [CLK_DRAM_TVE]          = &dram_tve_clk.common.hw,
 710                [CLK_DRAM_DE_FE]        = &dram_de_fe_clk.common.hw,
 711                [CLK_DRAM_DE_BE]        = &dram_de_be_clk.common.hw,
 712                [CLK_DRAM_ACE]          = &dram_ace_clk.common.hw,
 713                [CLK_DRAM_IEP]          = &dram_iep_clk.common.hw,
 714                [CLK_DE_BE]             = &de_be_clk.common.hw,
 715                [CLK_DE_FE]             = &de_fe_clk.common.hw,
 716                [CLK_TCON_CH0]          = &tcon_ch0_clk.common.hw,
 717                [CLK_TCON_CH1_SCLK]     = &tcon_ch1_sclk2_clk.common.hw,
 718                [CLK_TCON_CH1]          = &tcon_ch1_sclk1_clk.common.hw,
 719                [CLK_CSI]               = &csi_clk.common.hw,
 720                [CLK_VE]                = &ve_clk.common.hw,
 721                [CLK_CODEC]             = &codec_clk.common.hw,
 722                [CLK_AVS]               = &avs_clk.common.hw,
 723                [CLK_HDMI]              = &hdmi_clk.common.hw,
 724                [CLK_GPU]               = &gpu_clk.common.hw,
 725                [CLK_MBUS]              = &mbus_clk.common.hw,
 726                [CLK_IEP]               = &iep_clk.common.hw,
 727        },
 728        .num    = CLK_NUMBER,
 729};
 730
 731static struct ccu_reset_map sun5i_a10s_ccu_resets[] = {
 732        [RST_USB_PHY0]          =  { 0x0cc, BIT(0) },
 733        [RST_USB_PHY1]          =  { 0x0cc, BIT(1) },
 734
 735        [RST_GPS]               =  { 0x0d0, BIT(30) },
 736
 737        [RST_DE_BE]             =  { 0x104, BIT(30) },
 738
 739        [RST_DE_FE]             =  { 0x10c, BIT(30) },
 740
 741        [RST_TVE]               =  { 0x118, BIT(29) },
 742        [RST_LCD]               =  { 0x118, BIT(30) },
 743
 744        [RST_CSI]               =  { 0x134, BIT(30) },
 745
 746        [RST_VE]                =  { 0x13c, BIT(0) },
 747
 748        [RST_GPU]               =  { 0x154, BIT(30) },
 749
 750        [RST_IEP]               =  { 0x160, BIT(30) },
 751};
 752
 753static const struct sunxi_ccu_desc sun5i_a10s_ccu_desc = {
 754        .ccu_clks       = sun5i_a10s_ccu_clks,
 755        .num_ccu_clks   = ARRAY_SIZE(sun5i_a10s_ccu_clks),
 756
 757        .hw_clks        = &sun5i_a10s_hw_clks,
 758
 759        .resets         = sun5i_a10s_ccu_resets,
 760        .num_resets     = ARRAY_SIZE(sun5i_a10s_ccu_resets),
 761};
 762
 763/*
 764 * The A13 is the A10s minus the TS, GPS, HDMI, I2S and the keypad
 765 */
 766static struct clk_hw_onecell_data sun5i_a13_hw_clks = {
 767        .hws    = {
 768                [CLK_HOSC]              = &hosc_clk.common.hw,
 769                [CLK_PLL_CORE]          = &pll_core_clk.common.hw,
 770                [CLK_PLL_AUDIO_BASE]    = &pll_audio_base_clk.common.hw,
 771                [CLK_PLL_AUDIO]         = &pll_audio_clk.hw,
 772                [CLK_PLL_AUDIO_2X]      = &pll_audio_2x_clk.hw,
 773                [CLK_PLL_AUDIO_4X]      = &pll_audio_4x_clk.hw,
 774                [CLK_PLL_AUDIO_8X]      = &pll_audio_8x_clk.hw,
 775                [CLK_PLL_VIDEO0]        = &pll_video0_clk.common.hw,
 776                [CLK_PLL_VIDEO0_2X]     = &pll_video0_2x_clk.hw,
 777                [CLK_PLL_VE]            = &pll_ve_clk.common.hw,
 778                [CLK_PLL_DDR_BASE]      = &pll_ddr_base_clk.common.hw,
 779                [CLK_PLL_DDR]           = &pll_ddr_clk.common.hw,
 780                [CLK_PLL_DDR_OTHER]     = &pll_ddr_other_clk.common.hw,
 781                [CLK_PLL_PERIPH]        = &pll_periph_clk.common.hw,
 782                [CLK_PLL_VIDEO1]        = &pll_video1_clk.common.hw,
 783                [CLK_PLL_VIDEO1_2X]     = &pll_video1_2x_clk.hw,
 784                [CLK_CPU]               = &cpu_clk.common.hw,
 785                [CLK_AXI]               = &axi_clk.common.hw,
 786                [CLK_AHB]               = &ahb_clk.common.hw,
 787                [CLK_APB0]              = &apb0_clk.common.hw,
 788                [CLK_APB1]              = &apb1_clk.common.hw,
 789                [CLK_DRAM_AXI]          = &axi_dram_clk.common.hw,
 790                [CLK_AHB_OTG]           = &ahb_otg_clk.common.hw,
 791                [CLK_AHB_EHCI]          = &ahb_ehci_clk.common.hw,
 792                [CLK_AHB_OHCI]          = &ahb_ohci_clk.common.hw,
 793                [CLK_AHB_SS]            = &ahb_ss_clk.common.hw,
 794                [CLK_AHB_DMA]           = &ahb_dma_clk.common.hw,
 795                [CLK_AHB_BIST]          = &ahb_bist_clk.common.hw,
 796                [CLK_AHB_MMC0]          = &ahb_mmc0_clk.common.hw,
 797                [CLK_AHB_MMC1]          = &ahb_mmc1_clk.common.hw,
 798                [CLK_AHB_MMC2]          = &ahb_mmc2_clk.common.hw,
 799                [CLK_AHB_NAND]          = &ahb_nand_clk.common.hw,
 800                [CLK_AHB_SDRAM]         = &ahb_sdram_clk.common.hw,
 801                [CLK_AHB_EMAC]          = &ahb_emac_clk.common.hw,
 802                [CLK_AHB_SPI0]          = &ahb_spi0_clk.common.hw,
 803                [CLK_AHB_SPI1]          = &ahb_spi1_clk.common.hw,
 804                [CLK_AHB_SPI2]          = &ahb_spi2_clk.common.hw,
 805                [CLK_AHB_HSTIMER]       = &ahb_hstimer_clk.common.hw,
 806                [CLK_AHB_VE]            = &ahb_ve_clk.common.hw,
 807                [CLK_AHB_TVE]           = &ahb_tve_clk.common.hw,
 808                [CLK_AHB_LCD]           = &ahb_lcd_clk.common.hw,
 809                [CLK_AHB_CSI]           = &ahb_csi_clk.common.hw,
 810                [CLK_AHB_DE_BE]         = &ahb_de_be_clk.common.hw,
 811                [CLK_AHB_DE_FE]         = &ahb_de_fe_clk.common.hw,
 812                [CLK_AHB_IEP]           = &ahb_iep_clk.common.hw,
 813                [CLK_AHB_GPU]           = &ahb_gpu_clk.common.hw,
 814                [CLK_APB0_CODEC]        = &apb0_codec_clk.common.hw,
 815                [CLK_APB0_PIO]          = &apb0_pio_clk.common.hw,
 816                [CLK_APB0_IR]           = &apb0_ir_clk.common.hw,
 817                [CLK_APB1_I2C0]         = &apb1_i2c0_clk.common.hw,
 818                [CLK_APB1_I2C1]         = &apb1_i2c1_clk.common.hw,
 819                [CLK_APB1_I2C2]         = &apb1_i2c2_clk.common.hw,
 820                [CLK_APB1_UART0]        = &apb1_uart0_clk.common.hw,
 821                [CLK_APB1_UART1]        = &apb1_uart1_clk.common.hw,
 822                [CLK_APB1_UART2]        = &apb1_uart2_clk.common.hw,
 823                [CLK_APB1_UART3]        = &apb1_uart3_clk.common.hw,
 824                [CLK_NAND]              = &nand_clk.common.hw,
 825                [CLK_MMC0]              = &mmc0_clk.common.hw,
 826                [CLK_MMC1]              = &mmc1_clk.common.hw,
 827                [CLK_MMC2]              = &mmc2_clk.common.hw,
 828                [CLK_SS]                = &ss_clk.common.hw,
 829                [CLK_SPI0]              = &spi0_clk.common.hw,
 830                [CLK_SPI1]              = &spi1_clk.common.hw,
 831                [CLK_SPI2]              = &spi2_clk.common.hw,
 832                [CLK_IR]                = &ir_clk.common.hw,
 833                [CLK_USB_OHCI]          = &usb_ohci_clk.common.hw,
 834                [CLK_USB_PHY0]          = &usb_phy0_clk.common.hw,
 835                [CLK_USB_PHY1]          = &usb_phy1_clk.common.hw,
 836                [CLK_DRAM_VE]           = &dram_ve_clk.common.hw,
 837                [CLK_DRAM_CSI]          = &dram_csi_clk.common.hw,
 838                [CLK_DRAM_TVE]          = &dram_tve_clk.common.hw,
 839                [CLK_DRAM_DE_FE]        = &dram_de_fe_clk.common.hw,
 840                [CLK_DRAM_DE_BE]        = &dram_de_be_clk.common.hw,
 841                [CLK_DRAM_ACE]          = &dram_ace_clk.common.hw,
 842                [CLK_DRAM_IEP]          = &dram_iep_clk.common.hw,
 843                [CLK_DE_BE]             = &de_be_clk.common.hw,
 844                [CLK_DE_FE]             = &de_fe_clk.common.hw,
 845                [CLK_TCON_CH0]          = &tcon_ch0_clk.common.hw,
 846                [CLK_TCON_CH1_SCLK]     = &tcon_ch1_sclk2_clk.common.hw,
 847                [CLK_TCON_CH1]          = &tcon_ch1_sclk1_clk.common.hw,
 848                [CLK_CSI]               = &csi_clk.common.hw,
 849                [CLK_VE]                = &ve_clk.common.hw,
 850                [CLK_CODEC]             = &codec_clk.common.hw,
 851                [CLK_AVS]               = &avs_clk.common.hw,
 852                [CLK_GPU]               = &gpu_clk.common.hw,
 853                [CLK_MBUS]              = &mbus_clk.common.hw,
 854                [CLK_IEP]               = &iep_clk.common.hw,
 855        },
 856        .num    = CLK_NUMBER,
 857};
 858
 859static const struct sunxi_ccu_desc sun5i_a13_ccu_desc = {
 860        .ccu_clks       = sun5i_a10s_ccu_clks,
 861        .num_ccu_clks   = ARRAY_SIZE(sun5i_a10s_ccu_clks),
 862
 863        .hw_clks        = &sun5i_a13_hw_clks,
 864
 865        .resets         = sun5i_a10s_ccu_resets,
 866        .num_resets     = ARRAY_SIZE(sun5i_a10s_ccu_resets),
 867};
 868
 869/*
 870 * The GR8 is the A10s CCU minus the HDMI and keypad, plus SPDIF
 871 */
 872static struct clk_hw_onecell_data sun5i_gr8_hw_clks = {
 873        .hws    = {
 874                [CLK_HOSC]              = &hosc_clk.common.hw,
 875                [CLK_PLL_CORE]          = &pll_core_clk.common.hw,
 876                [CLK_PLL_AUDIO_BASE]    = &pll_audio_base_clk.common.hw,
 877                [CLK_PLL_AUDIO]         = &pll_audio_clk.hw,
 878                [CLK_PLL_AUDIO_2X]      = &pll_audio_2x_clk.hw,
 879                [CLK_PLL_AUDIO_4X]      = &pll_audio_4x_clk.hw,
 880                [CLK_PLL_AUDIO_8X]      = &pll_audio_8x_clk.hw,
 881                [CLK_PLL_VIDEO0]        = &pll_video0_clk.common.hw,
 882                [CLK_PLL_VIDEO0_2X]     = &pll_video0_2x_clk.hw,
 883                [CLK_PLL_VE]            = &pll_ve_clk.common.hw,
 884                [CLK_PLL_DDR_BASE]      = &pll_ddr_base_clk.common.hw,
 885                [CLK_PLL_DDR]           = &pll_ddr_clk.common.hw,
 886                [CLK_PLL_DDR_OTHER]     = &pll_ddr_other_clk.common.hw,
 887                [CLK_PLL_PERIPH]        = &pll_periph_clk.common.hw,
 888                [CLK_PLL_VIDEO1]        = &pll_video1_clk.common.hw,
 889                [CLK_PLL_VIDEO1_2X]     = &pll_video1_2x_clk.hw,
 890                [CLK_CPU]               = &cpu_clk.common.hw,
 891                [CLK_AXI]               = &axi_clk.common.hw,
 892                [CLK_AHB]               = &ahb_clk.common.hw,
 893                [CLK_APB0]              = &apb0_clk.common.hw,
 894                [CLK_APB1]              = &apb1_clk.common.hw,
 895                [CLK_DRAM_AXI]          = &axi_dram_clk.common.hw,
 896                [CLK_AHB_OTG]           = &ahb_otg_clk.common.hw,
 897                [CLK_AHB_EHCI]          = &ahb_ehci_clk.common.hw,
 898                [CLK_AHB_OHCI]          = &ahb_ohci_clk.common.hw,
 899                [CLK_AHB_SS]            = &ahb_ss_clk.common.hw,
 900                [CLK_AHB_DMA]           = &ahb_dma_clk.common.hw,
 901                [CLK_AHB_BIST]          = &ahb_bist_clk.common.hw,
 902                [CLK_AHB_MMC0]          = &ahb_mmc0_clk.common.hw,
 903                [CLK_AHB_MMC1]          = &ahb_mmc1_clk.common.hw,
 904                [CLK_AHB_MMC2]          = &ahb_mmc2_clk.common.hw,
 905                [CLK_AHB_NAND]          = &ahb_nand_clk.common.hw,
 906                [CLK_AHB_SDRAM]         = &ahb_sdram_clk.common.hw,
 907                [CLK_AHB_EMAC]          = &ahb_emac_clk.common.hw,
 908                [CLK_AHB_TS]            = &ahb_ts_clk.common.hw,
 909                [CLK_AHB_SPI0]          = &ahb_spi0_clk.common.hw,
 910                [CLK_AHB_SPI1]          = &ahb_spi1_clk.common.hw,
 911                [CLK_AHB_SPI2]          = &ahb_spi2_clk.common.hw,
 912                [CLK_AHB_GPS]           = &ahb_gps_clk.common.hw,
 913                [CLK_AHB_HSTIMER]       = &ahb_hstimer_clk.common.hw,
 914                [CLK_AHB_VE]            = &ahb_ve_clk.common.hw,
 915                [CLK_AHB_TVE]           = &ahb_tve_clk.common.hw,
 916                [CLK_AHB_LCD]           = &ahb_lcd_clk.common.hw,
 917                [CLK_AHB_CSI]           = &ahb_csi_clk.common.hw,
 918                [CLK_AHB_DE_BE]         = &ahb_de_be_clk.common.hw,
 919                [CLK_AHB_DE_FE]         = &ahb_de_fe_clk.common.hw,
 920                [CLK_AHB_IEP]           = &ahb_iep_clk.common.hw,
 921                [CLK_AHB_GPU]           = &ahb_gpu_clk.common.hw,
 922                [CLK_APB0_CODEC]        = &apb0_codec_clk.common.hw,
 923                [CLK_APB0_SPDIF]        = &apb0_spdif_clk.common.hw,
 924                [CLK_APB0_I2S]          = &apb0_i2s_clk.common.hw,
 925                [CLK_APB0_PIO]          = &apb0_pio_clk.common.hw,
 926                [CLK_APB0_IR]           = &apb0_ir_clk.common.hw,
 927                [CLK_APB1_I2C0]         = &apb1_i2c0_clk.common.hw,
 928                [CLK_APB1_I2C1]         = &apb1_i2c1_clk.common.hw,
 929                [CLK_APB1_I2C2]         = &apb1_i2c2_clk.common.hw,
 930                [CLK_APB1_UART0]        = &apb1_uart0_clk.common.hw,
 931                [CLK_APB1_UART1]        = &apb1_uart1_clk.common.hw,
 932                [CLK_APB1_UART2]        = &apb1_uart2_clk.common.hw,
 933                [CLK_APB1_UART3]        = &apb1_uart3_clk.common.hw,
 934                [CLK_NAND]              = &nand_clk.common.hw,
 935                [CLK_MMC0]              = &mmc0_clk.common.hw,
 936                [CLK_MMC1]              = &mmc1_clk.common.hw,
 937                [CLK_MMC2]              = &mmc2_clk.common.hw,
 938                [CLK_TS]                = &ts_clk.common.hw,
 939                [CLK_SS]                = &ss_clk.common.hw,
 940                [CLK_SPI0]              = &spi0_clk.common.hw,
 941                [CLK_SPI1]              = &spi1_clk.common.hw,
 942                [CLK_SPI2]              = &spi2_clk.common.hw,
 943                [CLK_IR]                = &ir_clk.common.hw,
 944                [CLK_I2S]               = &i2s_clk.common.hw,
 945                [CLK_SPDIF]             = &spdif_clk.common.hw,
 946                [CLK_USB_OHCI]          = &usb_ohci_clk.common.hw,
 947                [CLK_USB_PHY0]          = &usb_phy0_clk.common.hw,
 948                [CLK_USB_PHY1]          = &usb_phy1_clk.common.hw,
 949                [CLK_GPS]               = &gps_clk.common.hw,
 950                [CLK_DRAM_VE]           = &dram_ve_clk.common.hw,
 951                [CLK_DRAM_CSI]          = &dram_csi_clk.common.hw,
 952                [CLK_DRAM_TS]           = &dram_ts_clk.common.hw,
 953                [CLK_DRAM_TVE]          = &dram_tve_clk.common.hw,
 954                [CLK_DRAM_DE_FE]        = &dram_de_fe_clk.common.hw,
 955                [CLK_DRAM_DE_BE]        = &dram_de_be_clk.common.hw,
 956                [CLK_DRAM_ACE]          = &dram_ace_clk.common.hw,
 957                [CLK_DRAM_IEP]          = &dram_iep_clk.common.hw,
 958                [CLK_DE_BE]             = &de_be_clk.common.hw,
 959                [CLK_DE_FE]             = &de_fe_clk.common.hw,
 960                [CLK_TCON_CH0]          = &tcon_ch0_clk.common.hw,
 961                [CLK_TCON_CH1_SCLK]     = &tcon_ch1_sclk2_clk.common.hw,
 962                [CLK_TCON_CH1]          = &tcon_ch1_sclk1_clk.common.hw,
 963                [CLK_CSI]               = &csi_clk.common.hw,
 964                [CLK_VE]                = &ve_clk.common.hw,
 965                [CLK_CODEC]             = &codec_clk.common.hw,
 966                [CLK_AVS]               = &avs_clk.common.hw,
 967                [CLK_GPU]               = &gpu_clk.common.hw,
 968                [CLK_MBUS]              = &mbus_clk.common.hw,
 969                [CLK_IEP]               = &iep_clk.common.hw,
 970        },
 971        .num    = CLK_NUMBER,
 972};
 973
 974static const struct sunxi_ccu_desc sun5i_gr8_ccu_desc = {
 975        .ccu_clks       = sun5i_a10s_ccu_clks,
 976        .num_ccu_clks   = ARRAY_SIZE(sun5i_a10s_ccu_clks),
 977
 978        .hw_clks        = &sun5i_gr8_hw_clks,
 979
 980        .resets         = sun5i_a10s_ccu_resets,
 981        .num_resets     = ARRAY_SIZE(sun5i_a10s_ccu_resets),
 982};
 983
 984static void __init sun5i_ccu_init(struct device_node *node,
 985                                  const struct sunxi_ccu_desc *desc)
 986{
 987        void __iomem *reg;
 988        u32 val;
 989
 990        reg = of_io_request_and_map(node, 0, of_node_full_name(node));
 991        if (IS_ERR(reg)) {
 992                pr_err("%pOF: Could not map the clock registers\n", node);
 993                return;
 994        }
 995
 996        /* Force the PLL-Audio-1x divider to 1 */
 997        val = readl(reg + SUN5I_PLL_AUDIO_REG);
 998        val &= ~GENMASK(29, 26);
 999        writel(val | (0 << 26), reg + SUN5I_PLL_AUDIO_REG);
1000
1001        /*
1002         * Use the peripheral PLL as the AHB parent, instead of CPU /
1003         * AXI which have rate changes due to cpufreq.
1004         *
1005         * This is especially a big deal for the HS timer whose parent
1006         * clock is AHB.
1007         */
1008        val = readl(reg + SUN5I_AHB_REG);
1009        val &= ~GENMASK(7, 6);
1010        writel(val | (2 << 6), reg + SUN5I_AHB_REG);
1011
1012        sunxi_ccu_probe(node, reg, desc);
1013}
1014
1015static void __init sun5i_a10s_ccu_setup(struct device_node *node)
1016{
1017        sun5i_ccu_init(node, &sun5i_a10s_ccu_desc);
1018}
1019CLK_OF_DECLARE(sun5i_a10s_ccu, "allwinner,sun5i-a10s-ccu",
1020               sun5i_a10s_ccu_setup);
1021
1022static void __init sun5i_a13_ccu_setup(struct device_node *node)
1023{
1024        sun5i_ccu_init(node, &sun5i_a13_ccu_desc);
1025}
1026CLK_OF_DECLARE(sun5i_a13_ccu, "allwinner,sun5i-a13-ccu",
1027               sun5i_a13_ccu_setup);
1028
1029static void __init sun5i_gr8_ccu_setup(struct device_node *node)
1030{
1031        sun5i_ccu_init(node, &sun5i_gr8_ccu_desc);
1032}
1033CLK_OF_DECLARE(sun5i_gr8_ccu, "nextthing,gr8-ccu",
1034               sun5i_gr8_ccu_setup);
1035