linux/drivers/clk/rockchip/clk-pll.c
<<
>>
Prefs
   1/*
   2 * Copyright (c) 2014 MundoReader S.L.
   3 * Author: Heiko Stuebner <heiko@sntech.de>
   4 *
   5 * Copyright (c) 2015 Rockchip Electronics Co. Ltd.
   6 * Author: Xing Zheng <zhengxing@rock-chips.com>
   7 *
   8 * This program is free software; you can redistribute it and/or modify
   9 * it under the terms of the GNU General Public License as published by
  10 * the Free Software Foundation; either version 2 of the License, or
  11 * (at your option) any later version.
  12 *
  13 * This program is distributed in the hope that it will be useful,
  14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
  15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  16 * GNU General Public License for more details.
  17 */
  18
  19#include <asm/div64.h>
  20#include <linux/slab.h>
  21#include <linux/io.h>
  22#include <linux/delay.h>
  23#include <linux/clk-provider.h>
  24#include <linux/regmap.h>
  25#include <linux/clk.h>
  26#include "clk.h"
  27
  28#define PLL_MODE_MASK           0x3
  29#define PLL_MODE_SLOW           0x0
  30#define PLL_MODE_NORM           0x1
  31#define PLL_MODE_DEEP           0x2
  32#define PLL_RK3328_MODE_MASK    0x1
  33
  34struct rockchip_clk_pll {
  35        struct clk_hw           hw;
  36
  37        struct clk_mux          pll_mux;
  38        const struct clk_ops    *pll_mux_ops;
  39
  40        struct notifier_block   clk_nb;
  41
  42        void __iomem            *reg_base;
  43        int                     lock_offset;
  44        unsigned int            lock_shift;
  45        enum rockchip_pll_type  type;
  46        u8                      flags;
  47        const struct rockchip_pll_rate_table *rate_table;
  48        unsigned int            rate_count;
  49        spinlock_t              *lock;
  50
  51        struct rockchip_clk_provider *ctx;
  52};
  53
  54#define to_rockchip_clk_pll(_hw) container_of(_hw, struct rockchip_clk_pll, hw)
  55#define to_rockchip_clk_pll_nb(nb) \
  56                        container_of(nb, struct rockchip_clk_pll, clk_nb)
  57
  58static const struct rockchip_pll_rate_table *rockchip_get_pll_settings(
  59                            struct rockchip_clk_pll *pll, unsigned long rate)
  60{
  61        const struct rockchip_pll_rate_table  *rate_table = pll->rate_table;
  62        int i;
  63
  64        for (i = 0; i < pll->rate_count; i++) {
  65                if (rate == rate_table[i].rate)
  66                        return &rate_table[i];
  67        }
  68
  69        return NULL;
  70}
  71
  72static long rockchip_pll_round_rate(struct clk_hw *hw,
  73                            unsigned long drate, unsigned long *prate)
  74{
  75        struct rockchip_clk_pll *pll = to_rockchip_clk_pll(hw);
  76        const struct rockchip_pll_rate_table *rate_table = pll->rate_table;
  77        int i;
  78
  79        /* Assumming rate_table is in descending order */
  80        for (i = 0; i < pll->rate_count; i++) {
  81                if (drate >= rate_table[i].rate)
  82                        return rate_table[i].rate;
  83        }
  84
  85        /* return minimum supported value */
  86        return rate_table[i - 1].rate;
  87}
  88
  89/*
  90 * Wait for the pll to reach the locked state.
  91 * The calling set_rate function is responsible for making sure the
  92 * grf regmap is available.
  93 */
  94static int rockchip_pll_wait_lock(struct rockchip_clk_pll *pll)
  95{
  96        struct regmap *grf = pll->ctx->grf;
  97        unsigned int val;
  98        int delay = 24000000, ret;
  99
 100        while (delay > 0) {
 101                ret = regmap_read(grf, pll->lock_offset, &val);
 102                if (ret) {
 103                        pr_err("%s: failed to read pll lock status: %d\n",
 104                               __func__, ret);
 105                        return ret;
 106                }
 107
 108                if (val & BIT(pll->lock_shift))
 109                        return 0;
 110                delay--;
 111        }
 112
 113        pr_err("%s: timeout waiting for pll to lock\n", __func__);
 114        return -ETIMEDOUT;
 115}
 116
 117/**
 118 * PLL used in RK3036
 119 */
 120
 121#define RK3036_PLLCON(i)                        (i * 0x4)
 122#define RK3036_PLLCON0_FBDIV_MASK               0xfff
 123#define RK3036_PLLCON0_FBDIV_SHIFT              0
 124#define RK3036_PLLCON0_POSTDIV1_MASK            0x7
 125#define RK3036_PLLCON0_POSTDIV1_SHIFT           12
 126#define RK3036_PLLCON1_REFDIV_MASK              0x3f
 127#define RK3036_PLLCON1_REFDIV_SHIFT             0
 128#define RK3036_PLLCON1_POSTDIV2_MASK            0x7
 129#define RK3036_PLLCON1_POSTDIV2_SHIFT           6
 130#define RK3036_PLLCON1_DSMPD_MASK               0x1
 131#define RK3036_PLLCON1_DSMPD_SHIFT              12
 132#define RK3036_PLLCON2_FRAC_MASK                0xffffff
 133#define RK3036_PLLCON2_FRAC_SHIFT               0
 134
 135#define RK3036_PLLCON1_PWRDOWN                  (1 << 13)
 136
 137static void rockchip_rk3036_pll_get_params(struct rockchip_clk_pll *pll,
 138                                        struct rockchip_pll_rate_table *rate)
 139{
 140        u32 pllcon;
 141
 142        pllcon = readl_relaxed(pll->reg_base + RK3036_PLLCON(0));
 143        rate->fbdiv = ((pllcon >> RK3036_PLLCON0_FBDIV_SHIFT)
 144                                & RK3036_PLLCON0_FBDIV_MASK);
 145        rate->postdiv1 = ((pllcon >> RK3036_PLLCON0_POSTDIV1_SHIFT)
 146                                & RK3036_PLLCON0_POSTDIV1_MASK);
 147
 148        pllcon = readl_relaxed(pll->reg_base + RK3036_PLLCON(1));
 149        rate->refdiv = ((pllcon >> RK3036_PLLCON1_REFDIV_SHIFT)
 150                                & RK3036_PLLCON1_REFDIV_MASK);
 151        rate->postdiv2 = ((pllcon >> RK3036_PLLCON1_POSTDIV2_SHIFT)
 152                                & RK3036_PLLCON1_POSTDIV2_MASK);
 153        rate->dsmpd = ((pllcon >> RK3036_PLLCON1_DSMPD_SHIFT)
 154                                & RK3036_PLLCON1_DSMPD_MASK);
 155
 156        pllcon = readl_relaxed(pll->reg_base + RK3036_PLLCON(2));
 157        rate->frac = ((pllcon >> RK3036_PLLCON2_FRAC_SHIFT)
 158                                & RK3036_PLLCON2_FRAC_MASK);
 159}
 160
 161static unsigned long rockchip_rk3036_pll_recalc_rate(struct clk_hw *hw,
 162                                                     unsigned long prate)
 163{
 164        struct rockchip_clk_pll *pll = to_rockchip_clk_pll(hw);
 165        struct rockchip_pll_rate_table cur;
 166        u64 rate64 = prate;
 167
 168        rockchip_rk3036_pll_get_params(pll, &cur);
 169
 170        rate64 *= cur.fbdiv;
 171        do_div(rate64, cur.refdiv);
 172
 173        if (cur.dsmpd == 0) {
 174                /* fractional mode */
 175                u64 frac_rate64 = prate * cur.frac;
 176
 177                do_div(frac_rate64, cur.refdiv);
 178                rate64 += frac_rate64 >> 24;
 179        }
 180
 181        do_div(rate64, cur.postdiv1);
 182        do_div(rate64, cur.postdiv2);
 183
 184        return (unsigned long)rate64;
 185}
 186
 187static int rockchip_rk3036_pll_set_params(struct rockchip_clk_pll *pll,
 188                                const struct rockchip_pll_rate_table *rate)
 189{
 190        const struct clk_ops *pll_mux_ops = pll->pll_mux_ops;
 191        struct clk_mux *pll_mux = &pll->pll_mux;
 192        struct rockchip_pll_rate_table cur;
 193        u32 pllcon;
 194        int rate_change_remuxed = 0;
 195        int cur_parent;
 196        int ret;
 197
 198        pr_debug("%s: rate settings for %lu fbdiv: %d, postdiv1: %d, refdiv: %d, postdiv2: %d, dsmpd: %d, frac: %d\n",
 199                __func__, rate->rate, rate->fbdiv, rate->postdiv1, rate->refdiv,
 200                rate->postdiv2, rate->dsmpd, rate->frac);
 201
 202        rockchip_rk3036_pll_get_params(pll, &cur);
 203        cur.rate = 0;
 204
 205        cur_parent = pll_mux_ops->get_parent(&pll_mux->hw);
 206        if (cur_parent == PLL_MODE_NORM) {
 207                pll_mux_ops->set_parent(&pll_mux->hw, PLL_MODE_SLOW);
 208                rate_change_remuxed = 1;
 209        }
 210
 211        /* update pll values */
 212        writel_relaxed(HIWORD_UPDATE(rate->fbdiv, RK3036_PLLCON0_FBDIV_MASK,
 213                                          RK3036_PLLCON0_FBDIV_SHIFT) |
 214                       HIWORD_UPDATE(rate->postdiv1, RK3036_PLLCON0_POSTDIV1_MASK,
 215                                             RK3036_PLLCON0_POSTDIV1_SHIFT),
 216                       pll->reg_base + RK3036_PLLCON(0));
 217
 218        writel_relaxed(HIWORD_UPDATE(rate->refdiv, RK3036_PLLCON1_REFDIV_MASK,
 219                                                   RK3036_PLLCON1_REFDIV_SHIFT) |
 220                       HIWORD_UPDATE(rate->postdiv2, RK3036_PLLCON1_POSTDIV2_MASK,
 221                                                     RK3036_PLLCON1_POSTDIV2_SHIFT) |
 222                       HIWORD_UPDATE(rate->dsmpd, RK3036_PLLCON1_DSMPD_MASK,
 223                                                  RK3036_PLLCON1_DSMPD_SHIFT),
 224                       pll->reg_base + RK3036_PLLCON(1));
 225
 226        /* GPLL CON2 is not HIWORD_MASK */
 227        pllcon = readl_relaxed(pll->reg_base + RK3036_PLLCON(2));
 228        pllcon &= ~(RK3036_PLLCON2_FRAC_MASK << RK3036_PLLCON2_FRAC_SHIFT);
 229        pllcon |= rate->frac << RK3036_PLLCON2_FRAC_SHIFT;
 230        writel_relaxed(pllcon, pll->reg_base + RK3036_PLLCON(2));
 231
 232        /* wait for the pll to lock */
 233        ret = rockchip_pll_wait_lock(pll);
 234        if (ret) {
 235                pr_warn("%s: pll update unsuccessful, trying to restore old params\n",
 236                        __func__);
 237                rockchip_rk3036_pll_set_params(pll, &cur);
 238        }
 239
 240        if (rate_change_remuxed)
 241                pll_mux_ops->set_parent(&pll_mux->hw, PLL_MODE_NORM);
 242
 243        return ret;
 244}
 245
 246static int rockchip_rk3036_pll_set_rate(struct clk_hw *hw, unsigned long drate,
 247                                        unsigned long prate)
 248{
 249        struct rockchip_clk_pll *pll = to_rockchip_clk_pll(hw);
 250        const struct rockchip_pll_rate_table *rate;
 251
 252        pr_debug("%s: changing %s to %lu with a parent rate of %lu\n",
 253                 __func__, __clk_get_name(hw->clk), drate, prate);
 254
 255        /* Get required rate settings from table */
 256        rate = rockchip_get_pll_settings(pll, drate);
 257        if (!rate) {
 258                pr_err("%s: Invalid rate : %lu for pll clk %s\n", __func__,
 259                        drate, __clk_get_name(hw->clk));
 260                return -EINVAL;
 261        }
 262
 263        return rockchip_rk3036_pll_set_params(pll, rate);
 264}
 265
 266static int rockchip_rk3036_pll_enable(struct clk_hw *hw)
 267{
 268        struct rockchip_clk_pll *pll = to_rockchip_clk_pll(hw);
 269
 270        writel(HIWORD_UPDATE(0, RK3036_PLLCON1_PWRDOWN, 0),
 271               pll->reg_base + RK3036_PLLCON(1));
 272        rockchip_pll_wait_lock(pll);
 273
 274        return 0;
 275}
 276
 277static void rockchip_rk3036_pll_disable(struct clk_hw *hw)
 278{
 279        struct rockchip_clk_pll *pll = to_rockchip_clk_pll(hw);
 280
 281        writel(HIWORD_UPDATE(RK3036_PLLCON1_PWRDOWN,
 282                             RK3036_PLLCON1_PWRDOWN, 0),
 283               pll->reg_base + RK3036_PLLCON(1));
 284}
 285
 286static int rockchip_rk3036_pll_is_enabled(struct clk_hw *hw)
 287{
 288        struct rockchip_clk_pll *pll = to_rockchip_clk_pll(hw);
 289        u32 pllcon = readl(pll->reg_base + RK3036_PLLCON(1));
 290
 291        return !(pllcon & RK3036_PLLCON1_PWRDOWN);
 292}
 293
 294static void rockchip_rk3036_pll_init(struct clk_hw *hw)
 295{
 296        struct rockchip_clk_pll *pll = to_rockchip_clk_pll(hw);
 297        const struct rockchip_pll_rate_table *rate;
 298        struct rockchip_pll_rate_table cur;
 299        unsigned long drate;
 300
 301        if (!(pll->flags & ROCKCHIP_PLL_SYNC_RATE))
 302                return;
 303
 304        drate = clk_hw_get_rate(hw);
 305        rate = rockchip_get_pll_settings(pll, drate);
 306
 307        /* when no rate setting for the current rate, rely on clk_set_rate */
 308        if (!rate)
 309                return;
 310
 311        rockchip_rk3036_pll_get_params(pll, &cur);
 312
 313        pr_debug("%s: pll %s@%lu: Hz\n", __func__, __clk_get_name(hw->clk),
 314                 drate);
 315        pr_debug("old - fbdiv: %d, postdiv1: %d, refdiv: %d, postdiv2: %d, dsmpd: %d, frac: %d\n",
 316                 cur.fbdiv, cur.postdiv1, cur.refdiv, cur.postdiv2,
 317                 cur.dsmpd, cur.frac);
 318        pr_debug("new - fbdiv: %d, postdiv1: %d, refdiv: %d, postdiv2: %d, dsmpd: %d, frac: %d\n",
 319                 rate->fbdiv, rate->postdiv1, rate->refdiv, rate->postdiv2,
 320                 rate->dsmpd, rate->frac);
 321
 322        if (rate->fbdiv != cur.fbdiv || rate->postdiv1 != cur.postdiv1 ||
 323                rate->refdiv != cur.refdiv || rate->postdiv2 != cur.postdiv2 ||
 324                rate->dsmpd != cur.dsmpd ||
 325                (!cur.dsmpd && (rate->frac != cur.frac))) {
 326                struct clk *parent = clk_get_parent(hw->clk);
 327
 328                if (!parent) {
 329                        pr_warn("%s: parent of %s not available\n",
 330                                __func__, __clk_get_name(hw->clk));
 331                        return;
 332                }
 333
 334                pr_debug("%s: pll %s: rate params do not match rate table, adjusting\n",
 335                         __func__, __clk_get_name(hw->clk));
 336                rockchip_rk3036_pll_set_params(pll, rate);
 337        }
 338}
 339
 340static const struct clk_ops rockchip_rk3036_pll_clk_norate_ops = {
 341        .recalc_rate = rockchip_rk3036_pll_recalc_rate,
 342        .enable = rockchip_rk3036_pll_enable,
 343        .disable = rockchip_rk3036_pll_disable,
 344        .is_enabled = rockchip_rk3036_pll_is_enabled,
 345};
 346
 347static const struct clk_ops rockchip_rk3036_pll_clk_ops = {
 348        .recalc_rate = rockchip_rk3036_pll_recalc_rate,
 349        .round_rate = rockchip_pll_round_rate,
 350        .set_rate = rockchip_rk3036_pll_set_rate,
 351        .enable = rockchip_rk3036_pll_enable,
 352        .disable = rockchip_rk3036_pll_disable,
 353        .is_enabled = rockchip_rk3036_pll_is_enabled,
 354        .init = rockchip_rk3036_pll_init,
 355};
 356
 357/**
 358 * PLL used in RK3066, RK3188 and RK3288
 359 */
 360
 361#define RK3066_PLL_RESET_DELAY(nr)      ((nr * 500) / 24 + 1)
 362
 363#define RK3066_PLLCON(i)                (i * 0x4)
 364#define RK3066_PLLCON0_OD_MASK          0xf
 365#define RK3066_PLLCON0_OD_SHIFT         0
 366#define RK3066_PLLCON0_NR_MASK          0x3f
 367#define RK3066_PLLCON0_NR_SHIFT         8
 368#define RK3066_PLLCON1_NF_MASK          0x1fff
 369#define RK3066_PLLCON1_NF_SHIFT         0
 370#define RK3066_PLLCON2_NB_MASK          0xfff
 371#define RK3066_PLLCON2_NB_SHIFT         0
 372#define RK3066_PLLCON3_RESET            (1 << 5)
 373#define RK3066_PLLCON3_PWRDOWN          (1 << 1)
 374#define RK3066_PLLCON3_BYPASS           (1 << 0)
 375
 376static void rockchip_rk3066_pll_get_params(struct rockchip_clk_pll *pll,
 377                                        struct rockchip_pll_rate_table *rate)
 378{
 379        u32 pllcon;
 380
 381        pllcon = readl_relaxed(pll->reg_base + RK3066_PLLCON(0));
 382        rate->nr = ((pllcon >> RK3066_PLLCON0_NR_SHIFT)
 383                                & RK3066_PLLCON0_NR_MASK) + 1;
 384        rate->no = ((pllcon >> RK3066_PLLCON0_OD_SHIFT)
 385                                & RK3066_PLLCON0_OD_MASK) + 1;
 386
 387        pllcon = readl_relaxed(pll->reg_base + RK3066_PLLCON(1));
 388        rate->nf = ((pllcon >> RK3066_PLLCON1_NF_SHIFT)
 389                                & RK3066_PLLCON1_NF_MASK) + 1;
 390
 391        pllcon = readl_relaxed(pll->reg_base + RK3066_PLLCON(2));
 392        rate->nb = ((pllcon >> RK3066_PLLCON2_NB_SHIFT)
 393                                & RK3066_PLLCON2_NB_MASK) + 1;
 394}
 395
 396static unsigned long rockchip_rk3066_pll_recalc_rate(struct clk_hw *hw,
 397                                                     unsigned long prate)
 398{
 399        struct rockchip_clk_pll *pll = to_rockchip_clk_pll(hw);
 400        struct rockchip_pll_rate_table cur;
 401        u64 rate64 = prate;
 402        u32 pllcon;
 403
 404        pllcon = readl_relaxed(pll->reg_base + RK3066_PLLCON(3));
 405        if (pllcon & RK3066_PLLCON3_BYPASS) {
 406                pr_debug("%s: pll %s is bypassed\n", __func__,
 407                        clk_hw_get_name(hw));
 408                return prate;
 409        }
 410
 411        rockchip_rk3066_pll_get_params(pll, &cur);
 412
 413        rate64 *= cur.nf;
 414        do_div(rate64, cur.nr);
 415        do_div(rate64, cur.no);
 416
 417        return (unsigned long)rate64;
 418}
 419
 420static int rockchip_rk3066_pll_set_params(struct rockchip_clk_pll *pll,
 421                                const struct rockchip_pll_rate_table *rate)
 422{
 423        const struct clk_ops *pll_mux_ops = pll->pll_mux_ops;
 424        struct clk_mux *pll_mux = &pll->pll_mux;
 425        struct rockchip_pll_rate_table cur;
 426        int rate_change_remuxed = 0;
 427        int cur_parent;
 428        int ret;
 429
 430        pr_debug("%s: rate settings for %lu (nr, no, nf): (%d, %d, %d)\n",
 431                 __func__, rate->rate, rate->nr, rate->no, rate->nf);
 432
 433        rockchip_rk3066_pll_get_params(pll, &cur);
 434        cur.rate = 0;
 435
 436        cur_parent = pll_mux_ops->get_parent(&pll_mux->hw);
 437        if (cur_parent == PLL_MODE_NORM) {
 438                pll_mux_ops->set_parent(&pll_mux->hw, PLL_MODE_SLOW);
 439                rate_change_remuxed = 1;
 440        }
 441
 442        /* enter reset mode */
 443        writel(HIWORD_UPDATE(RK3066_PLLCON3_RESET, RK3066_PLLCON3_RESET, 0),
 444               pll->reg_base + RK3066_PLLCON(3));
 445
 446        /* update pll values */
 447        writel(HIWORD_UPDATE(rate->nr - 1, RK3066_PLLCON0_NR_MASK,
 448                                           RK3066_PLLCON0_NR_SHIFT) |
 449               HIWORD_UPDATE(rate->no - 1, RK3066_PLLCON0_OD_MASK,
 450                                           RK3066_PLLCON0_OD_SHIFT),
 451               pll->reg_base + RK3066_PLLCON(0));
 452
 453        writel_relaxed(HIWORD_UPDATE(rate->nf - 1, RK3066_PLLCON1_NF_MASK,
 454                                                   RK3066_PLLCON1_NF_SHIFT),
 455                       pll->reg_base + RK3066_PLLCON(1));
 456        writel_relaxed(HIWORD_UPDATE(rate->nb - 1, RK3066_PLLCON2_NB_MASK,
 457                                                   RK3066_PLLCON2_NB_SHIFT),
 458                       pll->reg_base + RK3066_PLLCON(2));
 459
 460        /* leave reset and wait the reset_delay */
 461        writel(HIWORD_UPDATE(0, RK3066_PLLCON3_RESET, 0),
 462               pll->reg_base + RK3066_PLLCON(3));
 463        udelay(RK3066_PLL_RESET_DELAY(rate->nr));
 464
 465        /* wait for the pll to lock */
 466        ret = rockchip_pll_wait_lock(pll);
 467        if (ret) {
 468                pr_warn("%s: pll update unsuccessful, trying to restore old params\n",
 469                        __func__);
 470                rockchip_rk3066_pll_set_params(pll, &cur);
 471        }
 472
 473        if (rate_change_remuxed)
 474                pll_mux_ops->set_parent(&pll_mux->hw, PLL_MODE_NORM);
 475
 476        return ret;
 477}
 478
 479static int rockchip_rk3066_pll_set_rate(struct clk_hw *hw, unsigned long drate,
 480                                        unsigned long prate)
 481{
 482        struct rockchip_clk_pll *pll = to_rockchip_clk_pll(hw);
 483        const struct rockchip_pll_rate_table *rate;
 484
 485        pr_debug("%s: changing %s to %lu with a parent rate of %lu\n",
 486                 __func__, clk_hw_get_name(hw), drate, prate);
 487
 488        /* Get required rate settings from table */
 489        rate = rockchip_get_pll_settings(pll, drate);
 490        if (!rate) {
 491                pr_err("%s: Invalid rate : %lu for pll clk %s\n", __func__,
 492                        drate, clk_hw_get_name(hw));
 493                return -EINVAL;
 494        }
 495
 496        return rockchip_rk3066_pll_set_params(pll, rate);
 497}
 498
 499static int rockchip_rk3066_pll_enable(struct clk_hw *hw)
 500{
 501        struct rockchip_clk_pll *pll = to_rockchip_clk_pll(hw);
 502
 503        writel(HIWORD_UPDATE(0, RK3066_PLLCON3_PWRDOWN, 0),
 504               pll->reg_base + RK3066_PLLCON(3));
 505        rockchip_pll_wait_lock(pll);
 506
 507        return 0;
 508}
 509
 510static void rockchip_rk3066_pll_disable(struct clk_hw *hw)
 511{
 512        struct rockchip_clk_pll *pll = to_rockchip_clk_pll(hw);
 513
 514        writel(HIWORD_UPDATE(RK3066_PLLCON3_PWRDOWN,
 515                             RK3066_PLLCON3_PWRDOWN, 0),
 516               pll->reg_base + RK3066_PLLCON(3));
 517}
 518
 519static int rockchip_rk3066_pll_is_enabled(struct clk_hw *hw)
 520{
 521        struct rockchip_clk_pll *pll = to_rockchip_clk_pll(hw);
 522        u32 pllcon = readl(pll->reg_base + RK3066_PLLCON(3));
 523
 524        return !(pllcon & RK3066_PLLCON3_PWRDOWN);
 525}
 526
 527static void rockchip_rk3066_pll_init(struct clk_hw *hw)
 528{
 529        struct rockchip_clk_pll *pll = to_rockchip_clk_pll(hw);
 530        const struct rockchip_pll_rate_table *rate;
 531        struct rockchip_pll_rate_table cur;
 532        unsigned long drate;
 533
 534        if (!(pll->flags & ROCKCHIP_PLL_SYNC_RATE))
 535                return;
 536
 537        drate = clk_hw_get_rate(hw);
 538        rate = rockchip_get_pll_settings(pll, drate);
 539
 540        /* when no rate setting for the current rate, rely on clk_set_rate */
 541        if (!rate)
 542                return;
 543
 544        rockchip_rk3066_pll_get_params(pll, &cur);
 545
 546        pr_debug("%s: pll %s@%lu: nr (%d:%d); no (%d:%d); nf(%d:%d), nb(%d:%d)\n",
 547                 __func__, clk_hw_get_name(hw), drate, rate->nr, cur.nr,
 548                 rate->no, cur.no, rate->nf, cur.nf, rate->nb, cur.nb);
 549        if (rate->nr != cur.nr || rate->no != cur.no || rate->nf != cur.nf
 550                                                     || rate->nb != cur.nb) {
 551                pr_debug("%s: pll %s: rate params do not match rate table, adjusting\n",
 552                         __func__, clk_hw_get_name(hw));
 553                rockchip_rk3066_pll_set_params(pll, rate);
 554        }
 555}
 556
 557static const struct clk_ops rockchip_rk3066_pll_clk_norate_ops = {
 558        .recalc_rate = rockchip_rk3066_pll_recalc_rate,
 559        .enable = rockchip_rk3066_pll_enable,
 560        .disable = rockchip_rk3066_pll_disable,
 561        .is_enabled = rockchip_rk3066_pll_is_enabled,
 562};
 563
 564static const struct clk_ops rockchip_rk3066_pll_clk_ops = {
 565        .recalc_rate = rockchip_rk3066_pll_recalc_rate,
 566        .round_rate = rockchip_pll_round_rate,
 567        .set_rate = rockchip_rk3066_pll_set_rate,
 568        .enable = rockchip_rk3066_pll_enable,
 569        .disable = rockchip_rk3066_pll_disable,
 570        .is_enabled = rockchip_rk3066_pll_is_enabled,
 571        .init = rockchip_rk3066_pll_init,
 572};
 573
 574/**
 575 * PLL used in RK3399
 576 */
 577
 578#define RK3399_PLLCON(i)                        (i * 0x4)
 579#define RK3399_PLLCON0_FBDIV_MASK               0xfff
 580#define RK3399_PLLCON0_FBDIV_SHIFT              0
 581#define RK3399_PLLCON1_REFDIV_MASK              0x3f
 582#define RK3399_PLLCON1_REFDIV_SHIFT             0
 583#define RK3399_PLLCON1_POSTDIV1_MASK            0x7
 584#define RK3399_PLLCON1_POSTDIV1_SHIFT           8
 585#define RK3399_PLLCON1_POSTDIV2_MASK            0x7
 586#define RK3399_PLLCON1_POSTDIV2_SHIFT           12
 587#define RK3399_PLLCON2_FRAC_MASK                0xffffff
 588#define RK3399_PLLCON2_FRAC_SHIFT               0
 589#define RK3399_PLLCON2_LOCK_STATUS              BIT(31)
 590#define RK3399_PLLCON3_PWRDOWN                  BIT(0)
 591#define RK3399_PLLCON3_DSMPD_MASK               0x1
 592#define RK3399_PLLCON3_DSMPD_SHIFT              3
 593
 594static int rockchip_rk3399_pll_wait_lock(struct rockchip_clk_pll *pll)
 595{
 596        u32 pllcon;
 597        int delay = 24000000;
 598
 599        /* poll check the lock status in rk3399 xPLLCON2 */
 600        while (delay > 0) {
 601                pllcon = readl_relaxed(pll->reg_base + RK3399_PLLCON(2));
 602                if (pllcon & RK3399_PLLCON2_LOCK_STATUS)
 603                        return 0;
 604
 605                delay--;
 606        }
 607
 608        pr_err("%s: timeout waiting for pll to lock\n", __func__);
 609        return -ETIMEDOUT;
 610}
 611
 612static void rockchip_rk3399_pll_get_params(struct rockchip_clk_pll *pll,
 613                                        struct rockchip_pll_rate_table *rate)
 614{
 615        u32 pllcon;
 616
 617        pllcon = readl_relaxed(pll->reg_base + RK3399_PLLCON(0));
 618        rate->fbdiv = ((pllcon >> RK3399_PLLCON0_FBDIV_SHIFT)
 619                                & RK3399_PLLCON0_FBDIV_MASK);
 620
 621        pllcon = readl_relaxed(pll->reg_base + RK3399_PLLCON(1));
 622        rate->refdiv = ((pllcon >> RK3399_PLLCON1_REFDIV_SHIFT)
 623                                & RK3399_PLLCON1_REFDIV_MASK);
 624        rate->postdiv1 = ((pllcon >> RK3399_PLLCON1_POSTDIV1_SHIFT)
 625                                & RK3399_PLLCON1_POSTDIV1_MASK);
 626        rate->postdiv2 = ((pllcon >> RK3399_PLLCON1_POSTDIV2_SHIFT)
 627                                & RK3399_PLLCON1_POSTDIV2_MASK);
 628
 629        pllcon = readl_relaxed(pll->reg_base + RK3399_PLLCON(2));
 630        rate->frac = ((pllcon >> RK3399_PLLCON2_FRAC_SHIFT)
 631                                & RK3399_PLLCON2_FRAC_MASK);
 632
 633        pllcon = readl_relaxed(pll->reg_base + RK3399_PLLCON(3));
 634        rate->dsmpd = ((pllcon >> RK3399_PLLCON3_DSMPD_SHIFT)
 635                                & RK3399_PLLCON3_DSMPD_MASK);
 636}
 637
 638static unsigned long rockchip_rk3399_pll_recalc_rate(struct clk_hw *hw,
 639                                                     unsigned long prate)
 640{
 641        struct rockchip_clk_pll *pll = to_rockchip_clk_pll(hw);
 642        struct rockchip_pll_rate_table cur;
 643        u64 rate64 = prate;
 644
 645        rockchip_rk3399_pll_get_params(pll, &cur);
 646
 647        rate64 *= cur.fbdiv;
 648        do_div(rate64, cur.refdiv);
 649
 650        if (cur.dsmpd == 0) {
 651                /* fractional mode */
 652                u64 frac_rate64 = prate * cur.frac;
 653
 654                do_div(frac_rate64, cur.refdiv);
 655                rate64 += frac_rate64 >> 24;
 656        }
 657
 658        do_div(rate64, cur.postdiv1);
 659        do_div(rate64, cur.postdiv2);
 660
 661        return (unsigned long)rate64;
 662}
 663
 664static int rockchip_rk3399_pll_set_params(struct rockchip_clk_pll *pll,
 665                                const struct rockchip_pll_rate_table *rate)
 666{
 667        const struct clk_ops *pll_mux_ops = pll->pll_mux_ops;
 668        struct clk_mux *pll_mux = &pll->pll_mux;
 669        struct rockchip_pll_rate_table cur;
 670        u32 pllcon;
 671        int rate_change_remuxed = 0;
 672        int cur_parent;
 673        int ret;
 674
 675        pr_debug("%s: rate settings for %lu fbdiv: %d, postdiv1: %d, refdiv: %d, postdiv2: %d, dsmpd: %d, frac: %d\n",
 676                __func__, rate->rate, rate->fbdiv, rate->postdiv1, rate->refdiv,
 677                rate->postdiv2, rate->dsmpd, rate->frac);
 678
 679        rockchip_rk3399_pll_get_params(pll, &cur);
 680        cur.rate = 0;
 681
 682        cur_parent = pll_mux_ops->get_parent(&pll_mux->hw);
 683        if (cur_parent == PLL_MODE_NORM) {
 684                pll_mux_ops->set_parent(&pll_mux->hw, PLL_MODE_SLOW);
 685                rate_change_remuxed = 1;
 686        }
 687
 688        /* update pll values */
 689        writel_relaxed(HIWORD_UPDATE(rate->fbdiv, RK3399_PLLCON0_FBDIV_MASK,
 690                                                  RK3399_PLLCON0_FBDIV_SHIFT),
 691                       pll->reg_base + RK3399_PLLCON(0));
 692
 693        writel_relaxed(HIWORD_UPDATE(rate->refdiv, RK3399_PLLCON1_REFDIV_MASK,
 694                                                   RK3399_PLLCON1_REFDIV_SHIFT) |
 695                       HIWORD_UPDATE(rate->postdiv1, RK3399_PLLCON1_POSTDIV1_MASK,
 696                                                     RK3399_PLLCON1_POSTDIV1_SHIFT) |
 697                       HIWORD_UPDATE(rate->postdiv2, RK3399_PLLCON1_POSTDIV2_MASK,
 698                                                     RK3399_PLLCON1_POSTDIV2_SHIFT),
 699                       pll->reg_base + RK3399_PLLCON(1));
 700
 701        /* xPLL CON2 is not HIWORD_MASK */
 702        pllcon = readl_relaxed(pll->reg_base + RK3399_PLLCON(2));
 703        pllcon &= ~(RK3399_PLLCON2_FRAC_MASK << RK3399_PLLCON2_FRAC_SHIFT);
 704        pllcon |= rate->frac << RK3399_PLLCON2_FRAC_SHIFT;
 705        writel_relaxed(pllcon, pll->reg_base + RK3399_PLLCON(2));
 706
 707        writel_relaxed(HIWORD_UPDATE(rate->dsmpd, RK3399_PLLCON3_DSMPD_MASK,
 708                                            RK3399_PLLCON3_DSMPD_SHIFT),
 709                       pll->reg_base + RK3399_PLLCON(3));
 710
 711        /* wait for the pll to lock */
 712        ret = rockchip_rk3399_pll_wait_lock(pll);
 713        if (ret) {
 714                pr_warn("%s: pll update unsuccessful, trying to restore old params\n",
 715                        __func__);
 716                rockchip_rk3399_pll_set_params(pll, &cur);
 717        }
 718
 719        if (rate_change_remuxed)
 720                pll_mux_ops->set_parent(&pll_mux->hw, PLL_MODE_NORM);
 721
 722        return ret;
 723}
 724
 725static int rockchip_rk3399_pll_set_rate(struct clk_hw *hw, unsigned long drate,
 726                                        unsigned long prate)
 727{
 728        struct rockchip_clk_pll *pll = to_rockchip_clk_pll(hw);
 729        const struct rockchip_pll_rate_table *rate;
 730
 731        pr_debug("%s: changing %s to %lu with a parent rate of %lu\n",
 732                 __func__, __clk_get_name(hw->clk), drate, prate);
 733
 734        /* Get required rate settings from table */
 735        rate = rockchip_get_pll_settings(pll, drate);
 736        if (!rate) {
 737                pr_err("%s: Invalid rate : %lu for pll clk %s\n", __func__,
 738                        drate, __clk_get_name(hw->clk));
 739                return -EINVAL;
 740        }
 741
 742        return rockchip_rk3399_pll_set_params(pll, rate);
 743}
 744
 745static int rockchip_rk3399_pll_enable(struct clk_hw *hw)
 746{
 747        struct rockchip_clk_pll *pll = to_rockchip_clk_pll(hw);
 748
 749        writel(HIWORD_UPDATE(0, RK3399_PLLCON3_PWRDOWN, 0),
 750               pll->reg_base + RK3399_PLLCON(3));
 751        rockchip_rk3399_pll_wait_lock(pll);
 752
 753        return 0;
 754}
 755
 756static void rockchip_rk3399_pll_disable(struct clk_hw *hw)
 757{
 758        struct rockchip_clk_pll *pll = to_rockchip_clk_pll(hw);
 759
 760        writel(HIWORD_UPDATE(RK3399_PLLCON3_PWRDOWN,
 761                             RK3399_PLLCON3_PWRDOWN, 0),
 762               pll->reg_base + RK3399_PLLCON(3));
 763}
 764
 765static int rockchip_rk3399_pll_is_enabled(struct clk_hw *hw)
 766{
 767        struct rockchip_clk_pll *pll = to_rockchip_clk_pll(hw);
 768        u32 pllcon = readl(pll->reg_base + RK3399_PLLCON(3));
 769
 770        return !(pllcon & RK3399_PLLCON3_PWRDOWN);
 771}
 772
 773static void rockchip_rk3399_pll_init(struct clk_hw *hw)
 774{
 775        struct rockchip_clk_pll *pll = to_rockchip_clk_pll(hw);
 776        const struct rockchip_pll_rate_table *rate;
 777        struct rockchip_pll_rate_table cur;
 778        unsigned long drate;
 779
 780        if (!(pll->flags & ROCKCHIP_PLL_SYNC_RATE))
 781                return;
 782
 783        drate = clk_hw_get_rate(hw);
 784        rate = rockchip_get_pll_settings(pll, drate);
 785
 786        /* when no rate setting for the current rate, rely on clk_set_rate */
 787        if (!rate)
 788                return;
 789
 790        rockchip_rk3399_pll_get_params(pll, &cur);
 791
 792        pr_debug("%s: pll %s@%lu: Hz\n", __func__, __clk_get_name(hw->clk),
 793                 drate);
 794        pr_debug("old - fbdiv: %d, postdiv1: %d, refdiv: %d, postdiv2: %d, dsmpd: %d, frac: %d\n",
 795                 cur.fbdiv, cur.postdiv1, cur.refdiv, cur.postdiv2,
 796                 cur.dsmpd, cur.frac);
 797        pr_debug("new - fbdiv: %d, postdiv1: %d, refdiv: %d, postdiv2: %d, dsmpd: %d, frac: %d\n",
 798                 rate->fbdiv, rate->postdiv1, rate->refdiv, rate->postdiv2,
 799                 rate->dsmpd, rate->frac);
 800
 801        if (rate->fbdiv != cur.fbdiv || rate->postdiv1 != cur.postdiv1 ||
 802                rate->refdiv != cur.refdiv || rate->postdiv2 != cur.postdiv2 ||
 803                rate->dsmpd != cur.dsmpd ||
 804                (!cur.dsmpd && (rate->frac != cur.frac))) {
 805                struct clk *parent = clk_get_parent(hw->clk);
 806
 807                if (!parent) {
 808                        pr_warn("%s: parent of %s not available\n",
 809                                __func__, __clk_get_name(hw->clk));
 810                        return;
 811                }
 812
 813                pr_debug("%s: pll %s: rate params do not match rate table, adjusting\n",
 814                         __func__, __clk_get_name(hw->clk));
 815                rockchip_rk3399_pll_set_params(pll, rate);
 816        }
 817}
 818
 819static const struct clk_ops rockchip_rk3399_pll_clk_norate_ops = {
 820        .recalc_rate = rockchip_rk3399_pll_recalc_rate,
 821        .enable = rockchip_rk3399_pll_enable,
 822        .disable = rockchip_rk3399_pll_disable,
 823        .is_enabled = rockchip_rk3399_pll_is_enabled,
 824};
 825
 826static const struct clk_ops rockchip_rk3399_pll_clk_ops = {
 827        .recalc_rate = rockchip_rk3399_pll_recalc_rate,
 828        .round_rate = rockchip_pll_round_rate,
 829        .set_rate = rockchip_rk3399_pll_set_rate,
 830        .enable = rockchip_rk3399_pll_enable,
 831        .disable = rockchip_rk3399_pll_disable,
 832        .is_enabled = rockchip_rk3399_pll_is_enabled,
 833        .init = rockchip_rk3399_pll_init,
 834};
 835
 836/*
 837 * Common registering of pll clocks
 838 */
 839
 840struct clk *rockchip_clk_register_pll(struct rockchip_clk_provider *ctx,
 841                enum rockchip_pll_type pll_type,
 842                const char *name, const char *const *parent_names,
 843                u8 num_parents, int con_offset, int grf_lock_offset,
 844                int lock_shift, int mode_offset, int mode_shift,
 845                struct rockchip_pll_rate_table *rate_table,
 846                unsigned long flags, u8 clk_pll_flags)
 847{
 848        const char *pll_parents[3];
 849        struct clk_init_data init;
 850        struct rockchip_clk_pll *pll;
 851        struct clk_mux *pll_mux;
 852        struct clk *pll_clk, *mux_clk;
 853        char pll_name[20];
 854
 855        if ((pll_type != pll_rk3328 && num_parents != 2) ||
 856            (pll_type == pll_rk3328 && num_parents != 1)) {
 857                pr_err("%s: needs two parent clocks\n", __func__);
 858                return ERR_PTR(-EINVAL);
 859        }
 860
 861        /* name the actual pll */
 862        snprintf(pll_name, sizeof(pll_name), "pll_%s", name);
 863
 864        pll = kzalloc(sizeof(*pll), GFP_KERNEL);
 865        if (!pll)
 866                return ERR_PTR(-ENOMEM);
 867
 868        /* create the mux on top of the real pll */
 869        pll->pll_mux_ops = &clk_mux_ops;
 870        pll_mux = &pll->pll_mux;
 871        pll_mux->reg = ctx->reg_base + mode_offset;
 872        pll_mux->shift = mode_shift;
 873        if (pll_type == pll_rk3328)
 874                pll_mux->mask = PLL_RK3328_MODE_MASK;
 875        else
 876                pll_mux->mask = PLL_MODE_MASK;
 877        pll_mux->flags = 0;
 878        pll_mux->lock = &ctx->lock;
 879        pll_mux->hw.init = &init;
 880
 881        if (pll_type == pll_rk3036 ||
 882            pll_type == pll_rk3066 ||
 883            pll_type == pll_rk3328 ||
 884            pll_type == pll_rk3399)
 885                pll_mux->flags |= CLK_MUX_HIWORD_MASK;
 886
 887        /* the actual muxing is xin24m, pll-output, xin32k */
 888        pll_parents[0] = parent_names[0];
 889        pll_parents[1] = pll_name;
 890        pll_parents[2] = parent_names[1];
 891
 892        init.name = name;
 893        init.flags = CLK_SET_RATE_PARENT;
 894        init.ops = pll->pll_mux_ops;
 895        init.parent_names = pll_parents;
 896        if (pll_type == pll_rk3328)
 897                init.num_parents = 2;
 898        else
 899                init.num_parents = ARRAY_SIZE(pll_parents);
 900
 901        mux_clk = clk_register(NULL, &pll_mux->hw);
 902        if (IS_ERR(mux_clk))
 903                goto err_mux;
 904
 905        /* now create the actual pll */
 906        init.name = pll_name;
 907
 908        /* keep all plls untouched for now */
 909        init.flags = flags | CLK_IGNORE_UNUSED;
 910
 911        init.parent_names = &parent_names[0];
 912        init.num_parents = 1;
 913
 914        if (rate_table) {
 915                int len;
 916
 917                /* find count of rates in rate_table */
 918                for (len = 0; rate_table[len].rate != 0; )
 919                        len++;
 920
 921                pll->rate_count = len;
 922                pll->rate_table = kmemdup(rate_table,
 923                                        pll->rate_count *
 924                                        sizeof(struct rockchip_pll_rate_table),
 925                                        GFP_KERNEL);
 926                WARN(!pll->rate_table,
 927                        "%s: could not allocate rate table for %s\n",
 928                        __func__, name);
 929        }
 930
 931        switch (pll_type) {
 932        case pll_rk3036:
 933        case pll_rk3328:
 934                if (!pll->rate_table || IS_ERR(ctx->grf))
 935                        init.ops = &rockchip_rk3036_pll_clk_norate_ops;
 936                else
 937                        init.ops = &rockchip_rk3036_pll_clk_ops;
 938                break;
 939        case pll_rk3066:
 940                if (!pll->rate_table || IS_ERR(ctx->grf))
 941                        init.ops = &rockchip_rk3066_pll_clk_norate_ops;
 942                else
 943                        init.ops = &rockchip_rk3066_pll_clk_ops;
 944                break;
 945        case pll_rk3399:
 946                if (!pll->rate_table)
 947                        init.ops = &rockchip_rk3399_pll_clk_norate_ops;
 948                else
 949                        init.ops = &rockchip_rk3399_pll_clk_ops;
 950                break;
 951        default:
 952                pr_warn("%s: Unknown pll type for pll clk %s\n",
 953                        __func__, name);
 954        }
 955
 956        pll->hw.init = &init;
 957        pll->type = pll_type;
 958        pll->reg_base = ctx->reg_base + con_offset;
 959        pll->lock_offset = grf_lock_offset;
 960        pll->lock_shift = lock_shift;
 961        pll->flags = clk_pll_flags;
 962        pll->lock = &ctx->lock;
 963        pll->ctx = ctx;
 964
 965        pll_clk = clk_register(NULL, &pll->hw);
 966        if (IS_ERR(pll_clk)) {
 967                pr_err("%s: failed to register pll clock %s : %ld\n",
 968                        __func__, name, PTR_ERR(pll_clk));
 969                goto err_pll;
 970        }
 971
 972        return mux_clk;
 973
 974err_pll:
 975        clk_unregister(mux_clk);
 976        mux_clk = pll_clk;
 977err_mux:
 978        kfree(pll);
 979        return mux_clk;
 980}
 981