Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

clk: divider: Add hw based registration APIs

Add registration APIs in the clk divider code to return struct
clk_hw pointers instead of struct clk pointers. This way we hide
the struct clk pointer from providers unless they need to use
consumer facing APIs.

Signed-off-by: Stephen Boyd <sboyd@codeaurora.org>

+93 -8
+83 -8
drivers/clk/clk-divider.c
··· 426 426 }; 427 427 EXPORT_SYMBOL_GPL(clk_divider_ro_ops); 428 428 429 - static struct clk *_register_divider(struct device *dev, const char *name, 429 + static struct clk_hw *_register_divider(struct device *dev, const char *name, 430 430 const char *parent_name, unsigned long flags, 431 431 void __iomem *reg, u8 shift, u8 width, 432 432 u8 clk_divider_flags, const struct clk_div_table *table, 433 433 spinlock_t *lock) 434 434 { 435 435 struct clk_divider *div; 436 - struct clk *clk; 436 + struct clk_hw *hw; 437 437 struct clk_init_data init; 438 + int ret; 438 439 439 440 if (clk_divider_flags & CLK_DIVIDER_HIWORD_MASK) { 440 441 if (width + shift > 16) { ··· 468 467 div->table = table; 469 468 470 469 /* register the clock */ 471 - clk = clk_register(dev, &div->hw); 472 - 473 - if (IS_ERR(clk)) 470 + hw = &div->hw; 471 + ret = clk_hw_register(dev, hw); 472 + if (ret) { 474 473 kfree(div); 474 + hw = ERR_PTR(ret); 475 + } 475 476 476 - return clk; 477 + return hw; 477 478 } 478 479 479 480 /** ··· 495 492 void __iomem *reg, u8 shift, u8 width, 496 493 u8 clk_divider_flags, spinlock_t *lock) 497 494 { 495 + struct clk_hw *hw; 496 + 497 + hw = _register_divider(dev, name, parent_name, flags, reg, shift, 498 + width, clk_divider_flags, NULL, lock); 499 + if (IS_ERR(hw)) 500 + return ERR_CAST(hw); 501 + return hw->clk; 502 + } 503 + EXPORT_SYMBOL_GPL(clk_register_divider); 504 + 505 + /** 506 + * clk_hw_register_divider - register a divider clock with the clock framework 507 + * @dev: device registering this clock 508 + * @name: name of this clock 509 + * @parent_name: name of clock's parent 510 + * @flags: framework-specific flags 511 + * @reg: register address to adjust divider 512 + * @shift: number of bits to shift the bitfield 513 + * @width: width of the bitfield 514 + * @clk_divider_flags: divider-specific flags for this clock 515 + * @lock: shared register lock for this clock 516 + */ 517 + struct clk_hw *clk_hw_register_divider(struct device *dev, const char *name, 518 + const char *parent_name, unsigned long flags, 519 + void __iomem *reg, u8 shift, u8 width, 520 + u8 clk_divider_flags, spinlock_t *lock) 521 + { 498 522 return _register_divider(dev, name, parent_name, flags, reg, shift, 499 523 width, clk_divider_flags, NULL, lock); 500 524 } 501 - EXPORT_SYMBOL_GPL(clk_register_divider); 525 + EXPORT_SYMBOL_GPL(clk_hw_register_divider); 502 526 503 527 /** 504 528 * clk_register_divider_table - register a table based divider clock with ··· 547 517 u8 clk_divider_flags, const struct clk_div_table *table, 548 518 spinlock_t *lock) 549 519 { 520 + struct clk_hw *hw; 521 + 522 + hw = _register_divider(dev, name, parent_name, flags, reg, shift, 523 + width, clk_divider_flags, table, lock); 524 + if (IS_ERR(hw)) 525 + return ERR_CAST(hw); 526 + return hw->clk; 527 + } 528 + EXPORT_SYMBOL_GPL(clk_register_divider_table); 529 + 530 + /** 531 + * clk_hw_register_divider_table - register a table based divider clock with 532 + * the clock framework 533 + * @dev: device registering this clock 534 + * @name: name of this clock 535 + * @parent_name: name of clock's parent 536 + * @flags: framework-specific flags 537 + * @reg: register address to adjust divider 538 + * @shift: number of bits to shift the bitfield 539 + * @width: width of the bitfield 540 + * @clk_divider_flags: divider-specific flags for this clock 541 + * @table: array of divider/value pairs ending with a div set to 0 542 + * @lock: shared register lock for this clock 543 + */ 544 + struct clk_hw *clk_hw_register_divider_table(struct device *dev, 545 + const char *name, const char *parent_name, unsigned long flags, 546 + void __iomem *reg, u8 shift, u8 width, 547 + u8 clk_divider_flags, const struct clk_div_table *table, 548 + spinlock_t *lock) 549 + { 550 550 return _register_divider(dev, name, parent_name, flags, reg, shift, 551 551 width, clk_divider_flags, table, lock); 552 552 } 553 - EXPORT_SYMBOL_GPL(clk_register_divider_table); 553 + EXPORT_SYMBOL_GPL(clk_hw_register_divider_table); 554 554 555 555 void clk_unregister_divider(struct clk *clk) 556 556 { ··· 597 537 kfree(div); 598 538 } 599 539 EXPORT_SYMBOL_GPL(clk_unregister_divider); 540 + 541 + /** 542 + * clk_hw_unregister_divider - unregister a clk divider 543 + * @hw: hardware-specific clock data to unregister 544 + */ 545 + void clk_hw_unregister_divider(struct clk_hw *hw) 546 + { 547 + struct clk_divider *div; 548 + 549 + div = to_clk_divider(hw); 550 + 551 + clk_hw_unregister(hw); 552 + kfree(div); 553 + } 554 + EXPORT_SYMBOL_GPL(clk_hw_unregister_divider);
+10
include/linux/clk-provider.h
··· 407 407 const char *parent_name, unsigned long flags, 408 408 void __iomem *reg, u8 shift, u8 width, 409 409 u8 clk_divider_flags, spinlock_t *lock); 410 + struct clk_hw *clk_hw_register_divider(struct device *dev, const char *name, 411 + const char *parent_name, unsigned long flags, 412 + void __iomem *reg, u8 shift, u8 width, 413 + u8 clk_divider_flags, spinlock_t *lock); 410 414 struct clk *clk_register_divider_table(struct device *dev, const char *name, 411 415 const char *parent_name, unsigned long flags, 412 416 void __iomem *reg, u8 shift, u8 width, 413 417 u8 clk_divider_flags, const struct clk_div_table *table, 414 418 spinlock_t *lock); 419 + struct clk_hw *clk_hw_register_divider_table(struct device *dev, 420 + const char *name, const char *parent_name, unsigned long flags, 421 + void __iomem *reg, u8 shift, u8 width, 422 + u8 clk_divider_flags, const struct clk_div_table *table, 423 + spinlock_t *lock); 415 424 void clk_unregister_divider(struct clk *clk); 425 + void clk_hw_unregister_divider(struct clk_hw *hw); 416 426 417 427 /** 418 428 * struct clk_mux - multiplexer clock