1 // SPDX-License-Identifier: GPL-2.0-only 2 /* 3 * TI Divider Clock 4 * 5 * Copyright (C) 2013 Texas Instruments, Inc. 6 * 7 * Tero Kristo <t-kristo@ti.com> 8 */ 9 10 #include <linux/clk-provider.h> 11 #include <linux/slab.h> 12 #include <linux/err.h> 13 #include <linux/of.h> 14 #include <linux/of_address.h> 15 #include <linux/clk/ti.h> 16 #include "clock.h" 17 18 #undef pr_fmt 19 #define pr_fmt(fmt) "%s: " fmt, __func__ 20 21 static unsigned int _get_table_div(const struct clk_div_table *table, 22 unsigned int val) 23 { 24 const struct clk_div_table *clkt; 25 26 for (clkt = table; clkt->div; clkt++) 27 if (clkt->val == val) 28 return clkt->div; 29 return 0; 30 } 31 32 static void _setup_mask(struct clk_omap_divider *divider) 33 { 34 u16 mask; 35 u32 max_val; 36 const struct clk_div_table *clkt; 37 38 if (divider->table) { 39 max_val = 0; 40 41 for (clkt = divider->table; clkt->div; clkt++) 42 if (clkt->val > max_val) 43 max_val = clkt->val; 44 } else { 45 max_val = divider->max; 46 47 if (!(divider->flags & CLK_DIVIDER_ONE_BASED) && 48 !(divider->flags & CLK_DIVIDER_POWER_OF_TWO)) 49 max_val--; 50 } 51 52 if (divider->flags & CLK_DIVIDER_POWER_OF_TWO) 53 mask = fls(max_val) - 1; 54 else 55 mask = max_val; 56 57 divider->mask = (1 << fls(mask)) - 1; 58 } 59 60 static unsigned int _get_div(struct clk_omap_divider *divider, unsigned int val) 61 { 62 if (divider->flags & CLK_DIVIDER_ONE_BASED) 63 return val; 64 if (divider->flags & CLK_DIVIDER_POWER_OF_TWO) 65 return 1 << val; 66 if (divider->table) 67 return _get_table_div(divider->table, val); 68 return val + 1; 69 } 70 71 static unsigned int _get_table_val(const struct clk_div_table *table, 72 unsigned int div) 73 { 74 const struct clk_div_table *clkt; 75 76 for (clkt = table; clkt->div; clkt++) 77 if (clkt->div == div) 78 return clkt->val; 79 return 0; 80 } 81 82 static unsigned int _get_val(struct clk_omap_divider *divider, u8 div) 83 { 84 if (divider->flags & CLK_DIVIDER_ONE_BASED) 85 return div; 86 if (divider->flags & CLK_DIVIDER_POWER_OF_TWO) 87 return __ffs(div); 88 if (divider->table) 89 return _get_table_val(divider->table, div); 90 return div - 1; 91 } 92 93 static unsigned long ti_clk_divider_recalc_rate(struct clk_hw *hw, 94 unsigned long parent_rate) 95 { 96 struct clk_omap_divider *divider = to_clk_omap_divider(hw); 97 unsigned int div, val; 98 99 val = ti_clk_ll_ops->clk_readl(÷r->reg) >> divider->shift; 100 val &= divider->mask; 101 102 div = _get_div(divider, val); 103 if (!div) { 104 WARN(!(divider->flags & CLK_DIVIDER_ALLOW_ZERO), 105 "%s: Zero divisor and CLK_DIVIDER_ALLOW_ZERO not set\n", 106 clk_hw_get_name(hw)); 107 return parent_rate; 108 } 109 110 return DIV_ROUND_UP(parent_rate, div); 111 } 112 113 /* 114 * The reverse of DIV_ROUND_UP: The maximum number which 115 * divided by m is r 116 */ 117 #define MULT_ROUND_UP(r, m) ((r) * (m) + (m) - 1) 118 119 static bool _is_valid_table_div(const struct clk_div_table *table, 120 unsigned int div) 121 { 122 const struct clk_div_table *clkt; 123 124 for (clkt = table; clkt->div; clkt++) 125 if (clkt->div == div) 126 return true; 127 return false; 128 } 129 130 static bool _is_valid_div(struct clk_omap_divider *divider, unsigned int div) 131 { 132 if (divider->flags & CLK_DIVIDER_POWER_OF_TWO) 133 return is_power_of_2(div); 134 if (divider->table) 135 return _is_valid_table_div(divider->table, div); 136 return true; 137 } 138 139 static int _div_round_up(const struct clk_div_table *table, 140 unsigned long parent_rate, unsigned long rate) 141 { 142 const struct clk_div_table *clkt; 143 int up = INT_MAX; 144 int div = DIV_ROUND_UP_ULL((u64)parent_rate, rate); 145 146 for (clkt = table; clkt->div; clkt++) { 147 if (clkt->div == div) 148 return clkt->div; 149 else if (clkt->div < div) 150 continue; 151 152 if ((clkt->div - div) < (up - div)) 153 up = clkt->div; 154 } 155 156 return up; 157 } 158 159 static int _div_round(const struct clk_div_table *table, 160 unsigned long parent_rate, unsigned long rate) 161 { 162 if (!table) 163 return DIV_ROUND_UP(parent_rate, rate); 164 165 return _div_round_up(table, parent_rate, rate); 166 } 167 168 static int ti_clk_divider_bestdiv(struct clk_hw *hw, unsigned long rate, 169 unsigned long *best_parent_rate) 170 { 171 struct clk_omap_divider *divider = to_clk_omap_divider(hw); 172 int i, bestdiv = 0; 173 unsigned long parent_rate, best = 0, now, maxdiv; 174 unsigned long parent_rate_saved = *best_parent_rate; 175 176 if (!rate) 177 rate = 1; 178 179 maxdiv = divider->max; 180 181 if (!(clk_hw_get_flags(hw) & CLK_SET_RATE_PARENT)) { 182 parent_rate = *best_parent_rate; 183 bestdiv = _div_round(divider->table, parent_rate, rate); 184 bestdiv = bestdiv == 0 ? 1 : bestdiv; 185 bestdiv = bestdiv > maxdiv ? maxdiv : bestdiv; 186 return bestdiv; 187 } 188 189 /* 190 * The maximum divider we can use without overflowing 191 * unsigned long in rate * i below 192 */ 193 maxdiv = min(ULONG_MAX / rate, maxdiv); 194 195 for (i = 1; i <= maxdiv; i++) { 196 if (!_is_valid_div(divider, i)) 197 continue; 198 if (rate * i == parent_rate_saved) { 199 /* 200 * It's the most ideal case if the requested rate can be 201 * divided from parent clock without needing to change 202 * parent rate, so return the divider immediately. 203 */ 204 *best_parent_rate = parent_rate_saved; 205 return i; 206 } 207 parent_rate = clk_hw_round_rate(clk_hw_get_parent(hw), 208 MULT_ROUND_UP(rate, i)); 209 now = DIV_ROUND_UP(parent_rate, i); 210 if (now <= rate && now > best) { 211 bestdiv = i; 212 best = now; 213 *best_parent_rate = parent_rate; 214 } 215 } 216 217 if (!bestdiv) { 218 bestdiv = divider->max; 219 *best_parent_rate = 220 clk_hw_round_rate(clk_hw_get_parent(hw), 1); 221 } 222 223 return bestdiv; 224 } 225 226 static long ti_clk_divider_round_rate(struct clk_hw *hw, unsigned long rate, 227 unsigned long *prate) 228 { 229 int div; 230 div = ti_clk_divider_bestdiv(hw, rate, prate); 231 232 return DIV_ROUND_UP(*prate, div); 233 } 234 235 static int ti_clk_divider_set_rate(struct clk_hw *hw, unsigned long rate, 236 unsigned long parent_rate) 237 { 238 struct clk_omap_divider *divider; 239 unsigned int div, value; 240 u32 val; 241 242 if (!hw || !rate) 243 return -EINVAL; 244 245 divider = to_clk_omap_divider(hw); 246 247 div = DIV_ROUND_UP(parent_rate, rate); 248 249 if (div > divider->max) 250 div = divider->max; 251 if (div < divider->min) 252 div = divider->min; 253 254 value = _get_val(divider, div); 255 256 val = ti_clk_ll_ops->clk_readl(÷r->reg); 257 val &= ~(divider->mask << divider->shift); 258 val |= value << divider->shift; 259 ti_clk_ll_ops->clk_writel(val, ÷r->reg); 260 261 ti_clk_latch(÷r->reg, divider->latch); 262 263 return 0; 264 } 265 266 /** 267 * clk_divider_save_context - Save the divider value 268 * @hw: pointer struct clk_hw 269 * 270 * Save the divider value 271 */ 272 static int clk_divider_save_context(struct clk_hw *hw) 273 { 274 struct clk_omap_divider *divider = to_clk_omap_divider(hw); 275 u32 val; 276 277 val = ti_clk_ll_ops->clk_readl(÷r->reg) >> divider->shift; 278 divider->context = val & divider->mask; 279 280 return 0; 281 } 282 283 /** 284 * clk_divider_restore_context - restore the saved the divider value 285 * @hw: pointer struct clk_hw 286 * 287 * Restore the saved the divider value 288 */ 289 static void clk_divider_restore_context(struct clk_hw *hw) 290 { 291 struct clk_omap_divider *divider = to_clk_omap_divider(hw); 292 u32 val; 293 294 val = ti_clk_ll_ops->clk_readl(÷r->reg); 295 val &= ~(divider->mask << divider->shift); 296 val |= divider->context << divider->shift; 297 ti_clk_ll_ops->clk_writel(val, ÷r->reg); 298 } 299 300 const struct clk_ops ti_clk_divider_ops = { 301 .recalc_rate = ti_clk_divider_recalc_rate, 302 .round_rate = ti_clk_divider_round_rate, 303 .set_rate = ti_clk_divider_set_rate, 304 .save_context = clk_divider_save_context, 305 .restore_context = clk_divider_restore_context, 306 }; 307 308 static struct clk *_register_divider(struct device_node *node, 309 u32 flags, 310 struct clk_omap_divider *div) 311 { 312 struct clk *clk; 313 struct clk_init_data init; 314 const char *parent_name; 315 const char *name; 316 317 parent_name = of_clk_get_parent_name(node, 0); 318 319 name = ti_dt_clk_name(node); 320 init.name = name; 321 init.ops = &ti_clk_divider_ops; 322 init.flags = flags; 323 init.parent_names = (parent_name ? &parent_name : NULL); 324 init.num_parents = (parent_name ? 1 : 0); 325 326 div->hw.init = &init; 327 328 /* register the clock */ 329 clk = ti_clk_register(NULL, &div->hw, name); 330 331 if (IS_ERR(clk)) 332 kfree(div); 333 334 return clk; 335 } 336 337 int ti_clk_parse_divider_data(int *div_table, int num_dividers, int max_div, 338 u8 flags, struct clk_omap_divider *divider) 339 { 340 int valid_div = 0; 341 int i; 342 struct clk_div_table *tmp; 343 u16 min_div = 0; 344 345 if (!div_table) { 346 divider->min = 1; 347 divider->max = max_div; 348 _setup_mask(divider); 349 return 0; 350 } 351 352 i = 0; 353 354 while (!num_dividers || i < num_dividers) { 355 if (div_table[i] == -1) 356 break; 357 if (div_table[i]) 358 valid_div++; 359 i++; 360 } 361 362 num_dividers = i; 363 364 tmp = kcalloc(valid_div + 1, sizeof(*tmp), GFP_KERNEL); 365 if (!tmp) 366 return -ENOMEM; 367 368 valid_div = 0; 369 370 for (i = 0; i < num_dividers; i++) 371 if (div_table[i] > 0) { 372 tmp[valid_div].div = div_table[i]; 373 tmp[valid_div].val = i; 374 valid_div++; 375 if (div_table[i] > max_div) 376 max_div = div_table[i]; 377 if (!min_div || div_table[i] < min_div) 378 min_div = div_table[i]; 379 } 380 381 divider->min = min_div; 382 divider->max = max_div; 383 divider->table = tmp; 384 _setup_mask(divider); 385 386 return 0; 387 } 388 389 static int __init ti_clk_get_div_table(struct device_node *node, 390 struct clk_omap_divider *div) 391 { 392 struct clk_div_table *table; 393 const __be32 *divspec; 394 u32 val; 395 u32 num_div; 396 u32 valid_div; 397 int i; 398 399 divspec = of_get_property(node, "ti,dividers", &num_div); 400 401 if (!divspec) 402 return 0; 403 404 num_div /= 4; 405 406 valid_div = 0; 407 408 /* Determine required size for divider table */ 409 for (i = 0; i < num_div; i++) { 410 of_property_read_u32_index(node, "ti,dividers", i, &val); 411 if (val) 412 valid_div++; 413 } 414 415 if (!valid_div) { 416 pr_err("no valid dividers for %pOFn table\n", node); 417 return -EINVAL; 418 } 419 420 table = kcalloc(valid_div + 1, sizeof(*table), GFP_KERNEL); 421 if (!table) 422 return -ENOMEM; 423 424 valid_div = 0; 425 426 for (i = 0; i < num_div; i++) { 427 of_property_read_u32_index(node, "ti,dividers", i, &val); 428 if (val) { 429 table[valid_div].div = val; 430 table[valid_div].val = i; 431 valid_div++; 432 } 433 } 434 435 div->table = table; 436 437 return 0; 438 } 439 440 static int _populate_divider_min_max(struct device_node *node, 441 struct clk_omap_divider *divider) 442 { 443 u32 min_div = 0; 444 u32 max_div = 0; 445 u32 val; 446 const struct clk_div_table *clkt; 447 448 if (!divider->table) { 449 /* Clk divider table not provided, determine min/max divs */ 450 if (of_property_read_u32(node, "ti,min-div", &min_div)) 451 min_div = 1; 452 453 if (of_property_read_u32(node, "ti,max-div", &max_div)) { 454 pr_err("no max-div for %pOFn!\n", node); 455 return -EINVAL; 456 } 457 } else { 458 459 for (clkt = divider->table; clkt->div; clkt++) { 460 val = clkt->div; 461 if (val > max_div) 462 max_div = val; 463 if (!min_div || val < min_div) 464 min_div = val; 465 } 466 } 467 468 divider->min = min_div; 469 divider->max = max_div; 470 _setup_mask(divider); 471 472 return 0; 473 } 474 475 static int __init ti_clk_divider_populate(struct device_node *node, 476 struct clk_omap_divider *div, 477 u32 *flags) 478 { 479 u32 val; 480 int ret; 481 482 ret = ti_clk_get_reg_addr(node, 0, &div->reg); 483 if (ret) 484 return ret; 485 486 if (!of_property_read_u32(node, "ti,bit-shift", &val)) 487 div->shift = val; 488 else 489 div->shift = 0; 490 491 if (!of_property_read_u32(node, "ti,latch-bit", &val)) 492 div->latch = val; 493 else 494 div->latch = -EINVAL; 495 496 *flags = 0; 497 div->flags = 0; 498 499 if (of_property_read_bool(node, "ti,index-starts-at-one")) 500 div->flags |= CLK_DIVIDER_ONE_BASED; 501 502 if (of_property_read_bool(node, "ti,index-power-of-two")) 503 div->flags |= CLK_DIVIDER_POWER_OF_TWO; 504 505 if (of_property_read_bool(node, "ti,set-rate-parent")) 506 *flags |= CLK_SET_RATE_PARENT; 507 508 ret = ti_clk_get_div_table(node, div); 509 if (ret) 510 return ret; 511 512 return _populate_divider_min_max(node, div); 513 } 514 515 /** 516 * of_ti_divider_clk_setup - Setup function for simple div rate clock 517 * @node: device node for this clock 518 * 519 * Sets up a basic divider clock. 520 */ 521 static void __init of_ti_divider_clk_setup(struct device_node *node) 522 { 523 struct clk *clk; 524 u32 flags = 0; 525 struct clk_omap_divider *div; 526 527 div = kzalloc(sizeof(*div), GFP_KERNEL); 528 if (!div) 529 return; 530 531 if (ti_clk_divider_populate(node, div, &flags)) 532 goto cleanup; 533 534 clk = _register_divider(node, flags, div); 535 if (!IS_ERR(clk)) { 536 of_clk_add_provider(node, of_clk_src_simple_get, clk); 537 of_ti_clk_autoidle_setup(node); 538 return; 539 } 540 541 cleanup: 542 kfree(div->table); 543 kfree(div); 544 } 545 CLK_OF_DECLARE(divider_clk, "ti,divider-clock", of_ti_divider_clk_setup); 546 547 static void __init of_ti_composite_divider_clk_setup(struct device_node *node) 548 { 549 struct clk_omap_divider *div; 550 u32 tmp; 551 552 div = kzalloc(sizeof(*div), GFP_KERNEL); 553 if (!div) 554 return; 555 556 if (ti_clk_divider_populate(node, div, &tmp)) 557 goto cleanup; 558 559 if (!ti_clk_add_component(node, &div->hw, CLK_COMPONENT_TYPE_DIVIDER)) 560 return; 561 562 cleanup: 563 kfree(div->table); 564 kfree(div); 565 } 566 CLK_OF_DECLARE(ti_composite_divider_clk, "ti,composite-divider-clock", 567 of_ti_composite_divider_clk_setup); 568