^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2) * SCI Clock driver for keystone based devices
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4) * Copyright (C) 2015-2016 Texas Instruments Incorporated - https://www.ti.com/
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5) * Tero Kristo <t-kristo@ti.com>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 6) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 7) * This program is free software; you can redistribute it and/or modify
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 8) * it under the terms of the GNU General Public License version 2 as
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 9) * published by the Free Software Foundation.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 10) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 11) * This program is distributed "as is" WITHOUT ANY WARRANTY of any
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 12) * kind, whether express or implied; without even the implied warranty
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 13) * of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 14) * GNU General Public License for more details.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 15) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 16) #include <linux/clk-provider.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 17) #include <linux/err.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 18) #include <linux/io.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 19) #include <linux/module.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 20) #include <linux/of_address.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 21) #include <linux/of_device.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 22) #include <linux/platform_device.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 23) #include <linux/slab.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 24) #include <linux/soc/ti/ti_sci_protocol.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 25) #include <linux/bsearch.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 26) #include <linux/list_sort.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 27)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 28) #define SCI_CLK_SSC_ENABLE BIT(0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 29) #define SCI_CLK_ALLOW_FREQ_CHANGE BIT(1)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 30) #define SCI_CLK_INPUT_TERMINATION BIT(2)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 31)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 32) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 33) * struct sci_clk_provider - TI SCI clock provider representation
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 34) * @sci: Handle to the System Control Interface protocol handler
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 35) * @ops: Pointer to the SCI ops to be used by the clocks
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 36) * @dev: Device pointer for the clock provider
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 37) * @clocks: Clocks array for this device
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 38) * @num_clocks: Total number of clocks for this provider
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 39) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 40) struct sci_clk_provider {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 41) const struct ti_sci_handle *sci;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 42) const struct ti_sci_clk_ops *ops;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 43) struct device *dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 44) struct sci_clk **clocks;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 45) int num_clocks;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 46) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 47)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 48) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 49) * struct sci_clk - TI SCI clock representation
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 50) * @hw: Hardware clock cookie for common clock framework
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 51) * @dev_id: Device index
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 52) * @clk_id: Clock index
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 53) * @num_parents: Number of parents for this clock
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 54) * @provider: Master clock provider
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 55) * @flags: Flags for the clock
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 56) * @node: Link for handling clocks probed via DT
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 57) * @cached_req: Cached requested freq for determine rate calls
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 58) * @cached_res: Cached result freq for determine rate calls
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 59) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 60) struct sci_clk {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 61) struct clk_hw hw;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 62) u16 dev_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 63) u32 clk_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 64) u32 num_parents;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 65) struct sci_clk_provider *provider;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 66) u8 flags;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 67) struct list_head node;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 68) unsigned long cached_req;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 69) unsigned long cached_res;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 70) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 71)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 72) #define to_sci_clk(_hw) container_of(_hw, struct sci_clk, hw)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 73)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 74) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 75) * sci_clk_prepare - Prepare (enable) a TI SCI clock
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 76) * @hw: clock to prepare
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 77) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 78) * Prepares a clock to be actively used. Returns the SCI protocol status.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 79) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 80) static int sci_clk_prepare(struct clk_hw *hw)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 81) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 82) struct sci_clk *clk = to_sci_clk(hw);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 83) bool enable_ssc = clk->flags & SCI_CLK_SSC_ENABLE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 84) bool allow_freq_change = clk->flags & SCI_CLK_ALLOW_FREQ_CHANGE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 85) bool input_termination = clk->flags & SCI_CLK_INPUT_TERMINATION;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 86)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 87) return clk->provider->ops->get_clock(clk->provider->sci, clk->dev_id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 88) clk->clk_id, enable_ssc,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 89) allow_freq_change,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 90) input_termination);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 91) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 92)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 93) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 94) * sci_clk_unprepare - Un-prepares (disables) a TI SCI clock
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 95) * @hw: clock to unprepare
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 96) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 97) * Un-prepares a clock from active state.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 98) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 99) static void sci_clk_unprepare(struct clk_hw *hw)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 100) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 101) struct sci_clk *clk = to_sci_clk(hw);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 102) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 103)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 104) ret = clk->provider->ops->put_clock(clk->provider->sci, clk->dev_id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 105) clk->clk_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 106) if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 107) dev_err(clk->provider->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 108) "unprepare failed for dev=%d, clk=%d, ret=%d\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 109) clk->dev_id, clk->clk_id, ret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 110) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 111)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 112) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 113) * sci_clk_is_prepared - Check if a TI SCI clock is prepared or not
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 114) * @hw: clock to check status for
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 115) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 116) * Checks if a clock is prepared (enabled) in hardware. Returns non-zero
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 117) * value if clock is enabled, zero otherwise.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 118) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 119) static int sci_clk_is_prepared(struct clk_hw *hw)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 120) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 121) struct sci_clk *clk = to_sci_clk(hw);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 122) bool req_state, current_state;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 123) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 124)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 125) ret = clk->provider->ops->is_on(clk->provider->sci, clk->dev_id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 126) clk->clk_id, &req_state,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 127) ¤t_state);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 128) if (ret) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 129) dev_err(clk->provider->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 130) "is_prepared failed for dev=%d, clk=%d, ret=%d\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 131) clk->dev_id, clk->clk_id, ret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 132) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 133) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 134)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 135) return req_state;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 136) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 137)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 138) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 139) * sci_clk_recalc_rate - Get clock rate for a TI SCI clock
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 140) * @hw: clock to get rate for
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 141) * @parent_rate: parent rate provided by common clock framework, not used
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 142) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 143) * Gets the current clock rate of a TI SCI clock. Returns the current
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 144) * clock rate, or zero in failure.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 145) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 146) static unsigned long sci_clk_recalc_rate(struct clk_hw *hw,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 147) unsigned long parent_rate)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 148) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 149) struct sci_clk *clk = to_sci_clk(hw);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 150) u64 freq;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 151) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 152)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 153) ret = clk->provider->ops->get_freq(clk->provider->sci, clk->dev_id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 154) clk->clk_id, &freq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 155) if (ret) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 156) dev_err(clk->provider->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 157) "recalc-rate failed for dev=%d, clk=%d, ret=%d\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 158) clk->dev_id, clk->clk_id, ret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 159) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 160) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 161)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 162) return freq;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 163) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 164)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 165) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 166) * sci_clk_determine_rate - Determines a clock rate a clock can be set to
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 167) * @hw: clock to change rate for
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 168) * @req: requested rate configuration for the clock
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 169) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 170) * Determines a suitable clock rate and parent for a TI SCI clock.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 171) * The parent handling is un-used, as generally the parent clock rates
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 172) * are not known by the kernel; instead these are internally handled
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 173) * by the firmware. Returns 0 on success, negative error value on failure.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 174) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 175) static int sci_clk_determine_rate(struct clk_hw *hw,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 176) struct clk_rate_request *req)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 177) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 178) struct sci_clk *clk = to_sci_clk(hw);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 179) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 180) u64 new_rate;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 181)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 182) if (clk->cached_req && clk->cached_req == req->rate) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 183) req->rate = clk->cached_res;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 184) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 185) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 186)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 187) ret = clk->provider->ops->get_best_match_freq(clk->provider->sci,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 188) clk->dev_id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 189) clk->clk_id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 190) req->min_rate,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 191) req->rate,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 192) req->max_rate,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 193) &new_rate);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 194) if (ret) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 195) dev_err(clk->provider->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 196) "determine-rate failed for dev=%d, clk=%d, ret=%d\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 197) clk->dev_id, clk->clk_id, ret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 198) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 199) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 200)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 201) clk->cached_req = req->rate;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 202) clk->cached_res = new_rate;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 203)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 204) req->rate = new_rate;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 205)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 206) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 207) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 208)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 209) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 210) * sci_clk_set_rate - Set rate for a TI SCI clock
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 211) * @hw: clock to change rate for
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 212) * @rate: target rate for the clock
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 213) * @parent_rate: rate of the clock parent, not used for TI SCI clocks
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 214) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 215) * Sets a clock frequency for a TI SCI clock. Returns the TI SCI
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 216) * protocol status.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 217) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 218) static int sci_clk_set_rate(struct clk_hw *hw, unsigned long rate,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 219) unsigned long parent_rate)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 220) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 221) struct sci_clk *clk = to_sci_clk(hw);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 222)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 223) return clk->provider->ops->set_freq(clk->provider->sci, clk->dev_id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 224) clk->clk_id, rate / 10 * 9, rate,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 225) rate / 10 * 11);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 226) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 227)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 228) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 229) * sci_clk_get_parent - Get the current parent of a TI SCI clock
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 230) * @hw: clock to get parent for
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 231) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 232) * Returns the index of the currently selected parent for a TI SCI clock.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 233) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 234) static u8 sci_clk_get_parent(struct clk_hw *hw)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 235) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 236) struct sci_clk *clk = to_sci_clk(hw);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 237) u32 parent_id = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 238) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 239)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 240) ret = clk->provider->ops->get_parent(clk->provider->sci, clk->dev_id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 241) clk->clk_id, (void *)&parent_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 242) if (ret) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 243) dev_err(clk->provider->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 244) "get-parent failed for dev=%d, clk=%d, ret=%d\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 245) clk->dev_id, clk->clk_id, ret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 246) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 247) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 248)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 249) parent_id = parent_id - clk->clk_id - 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 250)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 251) return (u8)parent_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 252) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 253)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 254) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 255) * sci_clk_set_parent - Set the parent of a TI SCI clock
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 256) * @hw: clock to set parent for
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 257) * @index: new parent index for the clock
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 258) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 259) * Sets the parent of a TI SCI clock. Return TI SCI protocol status.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 260) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 261) static int sci_clk_set_parent(struct clk_hw *hw, u8 index)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 262) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 263) struct sci_clk *clk = to_sci_clk(hw);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 264)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 265) clk->cached_req = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 266)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 267) return clk->provider->ops->set_parent(clk->provider->sci, clk->dev_id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 268) clk->clk_id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 269) index + 1 + clk->clk_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 270) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 271)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 272) static const struct clk_ops sci_clk_ops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 273) .prepare = sci_clk_prepare,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 274) .unprepare = sci_clk_unprepare,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 275) .is_prepared = sci_clk_is_prepared,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 276) .recalc_rate = sci_clk_recalc_rate,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 277) .determine_rate = sci_clk_determine_rate,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 278) .set_rate = sci_clk_set_rate,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 279) .get_parent = sci_clk_get_parent,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 280) .set_parent = sci_clk_set_parent,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 281) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 282)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 283) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 284) * _sci_clk_get - Gets a handle for an SCI clock
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 285) * @provider: Handle to SCI clock provider
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 286) * @sci_clk: Handle to the SCI clock to populate
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 287) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 288) * Gets a handle to an existing TI SCI hw clock, or builds a new clock
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 289) * entry and registers it with the common clock framework. Called from
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 290) * the common clock framework, when a corresponding of_clk_get call is
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 291) * executed, or recursively from itself when parsing parent clocks.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 292) * Returns 0 on success, negative error code on failure.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 293) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 294) static int _sci_clk_build(struct sci_clk_provider *provider,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 295) struct sci_clk *sci_clk)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 296) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 297) struct clk_init_data init = { NULL };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 298) char *name = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 299) char **parent_names = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 300) int i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 301) int ret = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 302)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 303) name = kasprintf(GFP_KERNEL, "clk:%d:%d", sci_clk->dev_id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 304) sci_clk->clk_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 305)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 306) init.name = name;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 307)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 308) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 309) * From kernel point of view, we only care about a clocks parents,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 310) * if it has more than 1 possible parent. In this case, it is going
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 311) * to have mux functionality. Otherwise it is going to act as a root
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 312) * clock.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 313) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 314) if (sci_clk->num_parents < 2)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 315) sci_clk->num_parents = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 316)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 317) if (sci_clk->num_parents) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 318) parent_names = kcalloc(sci_clk->num_parents, sizeof(char *),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 319) GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 320)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 321) if (!parent_names) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 322) ret = -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 323) goto err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 324) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 325)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 326) for (i = 0; i < sci_clk->num_parents; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 327) char *parent_name;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 328)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 329) parent_name = kasprintf(GFP_KERNEL, "clk:%d:%d",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 330) sci_clk->dev_id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 331) sci_clk->clk_id + 1 + i);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 332) if (!parent_name) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 333) ret = -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 334) goto err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 335) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 336) parent_names[i] = parent_name;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 337) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 338) init.parent_names = (void *)parent_names;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 339) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 340)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 341) init.ops = &sci_clk_ops;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 342) init.num_parents = sci_clk->num_parents;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 343) sci_clk->hw.init = &init;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 344)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 345) ret = devm_clk_hw_register(provider->dev, &sci_clk->hw);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 346) if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 347) dev_err(provider->dev, "failed clk register with %d\n", ret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 348)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 349) err:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 350) if (parent_names) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 351) for (i = 0; i < sci_clk->num_parents; i++)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 352) kfree(parent_names[i]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 353)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 354) kfree(parent_names);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 355) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 356)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 357) kfree(name);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 358)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 359) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 360) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 361)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 362) static int _cmp_sci_clk(const void *a, const void *b)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 363) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 364) const struct sci_clk *ca = a;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 365) const struct sci_clk *cb = *(struct sci_clk **)b;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 366)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 367) if (ca->dev_id == cb->dev_id && ca->clk_id == cb->clk_id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 368) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 369) if (ca->dev_id > cb->dev_id ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 370) (ca->dev_id == cb->dev_id && ca->clk_id > cb->clk_id))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 371) return 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 372) return -1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 373) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 374)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 375) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 376) * sci_clk_get - Xlate function for getting clock handles
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 377) * @clkspec: device tree clock specifier
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 378) * @data: pointer to the clock provider
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 379) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 380) * Xlate function for retrieving clock TI SCI hw clock handles based on
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 381) * device tree clock specifier. Called from the common clock framework,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 382) * when a corresponding of_clk_get call is executed. Returns a pointer
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 383) * to the TI SCI hw clock struct, or ERR_PTR value in failure.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 384) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 385) static struct clk_hw *sci_clk_get(struct of_phandle_args *clkspec, void *data)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 386) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 387) struct sci_clk_provider *provider = data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 388) struct sci_clk **clk;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 389) struct sci_clk key;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 390)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 391) if (clkspec->args_count != 2)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 392) return ERR_PTR(-EINVAL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 393)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 394) key.dev_id = clkspec->args[0];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 395) key.clk_id = clkspec->args[1];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 396)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 397) clk = bsearch(&key, provider->clocks, provider->num_clocks,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 398) sizeof(clk), _cmp_sci_clk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 399)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 400) if (!clk)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 401) return ERR_PTR(-ENODEV);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 402)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 403) return &(*clk)->hw;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 404) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 405)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 406) static int ti_sci_init_clocks(struct sci_clk_provider *p)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 407) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 408) int i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 409) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 410)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 411) for (i = 0; i < p->num_clocks; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 412) ret = _sci_clk_build(p, p->clocks[i]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 413) if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 414) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 415) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 416)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 417) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 418) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 419)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 420) static const struct of_device_id ti_sci_clk_of_match[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 421) { .compatible = "ti,k2g-sci-clk" },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 422) { /* Sentinel */ },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 423) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 424) MODULE_DEVICE_TABLE(of, ti_sci_clk_of_match);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 425)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 426) #ifdef CONFIG_TI_SCI_CLK_PROBE_FROM_FW
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 427) static int ti_sci_scan_clocks_from_fw(struct sci_clk_provider *provider)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 428) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 429) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 430) int num_clks = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 431) struct sci_clk **clks = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 432) struct sci_clk **tmp_clks;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 433) struct sci_clk *sci_clk;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 434) int max_clks = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 435) int clk_id = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 436) int dev_id = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 437) u32 num_parents = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 438) int gap_size = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 439) struct device *dev = provider->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 440)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 441) while (1) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 442) ret = provider->ops->get_num_parents(provider->sci, dev_id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 443) clk_id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 444) (void *)&num_parents);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 445) if (ret) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 446) gap_size++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 447) if (!clk_id) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 448) if (gap_size >= 5)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 449) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 450) dev_id++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 451) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 452) if (gap_size >= 2) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 453) dev_id++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 454) clk_id = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 455) gap_size = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 456) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 457) clk_id++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 458) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 459) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 460) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 461) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 462)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 463) gap_size = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 464)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 465) if (num_clks == max_clks) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 466) tmp_clks = devm_kmalloc_array(dev, max_clks + 64,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 467) sizeof(sci_clk),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 468) GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 469) memcpy(tmp_clks, clks, max_clks * sizeof(sci_clk));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 470) if (max_clks)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 471) devm_kfree(dev, clks);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 472) max_clks += 64;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 473) clks = tmp_clks;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 474) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 475)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 476) sci_clk = devm_kzalloc(dev, sizeof(*sci_clk), GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 477) if (!sci_clk)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 478) return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 479) sci_clk->dev_id = dev_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 480) sci_clk->clk_id = clk_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 481) sci_clk->provider = provider;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 482) sci_clk->num_parents = num_parents;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 483)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 484) clks[num_clks] = sci_clk;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 485)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 486) clk_id++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 487) num_clks++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 488) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 489)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 490) provider->clocks = devm_kmalloc_array(dev, num_clks, sizeof(sci_clk),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 491) GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 492) if (!provider->clocks)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 493) return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 494)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 495) memcpy(provider->clocks, clks, num_clks * sizeof(sci_clk));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 496)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 497) provider->num_clocks = num_clks;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 498)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 499) devm_kfree(dev, clks);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 500)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 501) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 502) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 503)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 504) #else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 505)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 506) static int _cmp_sci_clk_list(void *priv, struct list_head *a,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 507) struct list_head *b)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 508) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 509) struct sci_clk *ca = container_of(a, struct sci_clk, node);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 510) struct sci_clk *cb = container_of(b, struct sci_clk, node);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 511)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 512) return _cmp_sci_clk(ca, &cb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 513) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 514)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 515) static int ti_sci_scan_clocks_from_dt(struct sci_clk_provider *provider)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 516) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 517) struct device *dev = provider->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 518) struct device_node *np = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 519) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 520) int index;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 521) struct of_phandle_args args;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 522) struct list_head clks;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 523) struct sci_clk *sci_clk, *prev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 524) int num_clks = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 525) int num_parents;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 526) int clk_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 527) const char * const clk_names[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 528) "clocks", "assigned-clocks", "assigned-clock-parents", NULL
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 529) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 530) const char * const *clk_name;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 531)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 532) INIT_LIST_HEAD(&clks);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 533)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 534) clk_name = clk_names;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 535)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 536) while (*clk_name) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 537) np = of_find_node_with_property(np, *clk_name);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 538) if (!np) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 539) clk_name++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 540) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 541) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 542)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 543) if (!of_device_is_available(np))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 544) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 545)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 546) index = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 547)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 548) do {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 549) ret = of_parse_phandle_with_args(np, *clk_name,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 550) "#clock-cells", index,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 551) &args);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 552) if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 553) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 554)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 555) if (args.args_count == 2 && args.np == dev->of_node) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 556) sci_clk = devm_kzalloc(dev, sizeof(*sci_clk),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 557) GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 558) if (!sci_clk)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 559) return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 560)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 561) sci_clk->dev_id = args.args[0];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 562) sci_clk->clk_id = args.args[1];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 563) sci_clk->provider = provider;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 564) provider->ops->get_num_parents(provider->sci,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 565) sci_clk->dev_id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 566) sci_clk->clk_id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 567) (void *)&sci_clk->num_parents);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 568) list_add_tail(&sci_clk->node, &clks);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 569)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 570) num_clks++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 571)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 572) num_parents = sci_clk->num_parents;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 573) if (num_parents == 1)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 574) num_parents = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 575)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 576) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 577) * Linux kernel has inherent limitation
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 578) * of 255 clock parents at the moment.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 579) * Right now, it is not expected that
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 580) * any mux clock from sci-clk driver
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 581) * would exceed that limit either, but
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 582) * the ABI basically provides that
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 583) * possibility. Print out a warning if
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 584) * this happens for any clock.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 585) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 586) if (num_parents >= 255) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 587) dev_warn(dev, "too many parents for dev=%d, clk=%d (%d), cropping to 255.\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 588) sci_clk->dev_id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 589) sci_clk->clk_id, num_parents);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 590) num_parents = 255;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 591) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 592)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 593) clk_id = args.args[1] + 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 594)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 595) while (num_parents--) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 596) sci_clk = devm_kzalloc(dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 597) sizeof(*sci_clk),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 598) GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 599) if (!sci_clk)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 600) return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 601) sci_clk->dev_id = args.args[0];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 602) sci_clk->clk_id = clk_id++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 603) sci_clk->provider = provider;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 604) list_add_tail(&sci_clk->node, &clks);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 605)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 606) num_clks++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 607) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 608) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 609)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 610) index++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 611) } while (args.np);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 612) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 613)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 614) list_sort(NULL, &clks, _cmp_sci_clk_list);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 615)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 616) provider->clocks = devm_kmalloc_array(dev, num_clks, sizeof(sci_clk),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 617) GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 618) if (!provider->clocks)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 619) return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 620)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 621) num_clks = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 622) prev = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 623)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 624) list_for_each_entry(sci_clk, &clks, node) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 625) if (prev && prev->dev_id == sci_clk->dev_id &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 626) prev->clk_id == sci_clk->clk_id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 627) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 628)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 629) provider->clocks[num_clks++] = sci_clk;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 630) prev = sci_clk;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 631) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 632)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 633) provider->num_clocks = num_clks;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 634)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 635) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 636) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 637) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 638)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 639) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 640) * ti_sci_clk_probe - Probe function for the TI SCI clock driver
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 641) * @pdev: platform device pointer to be probed
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 642) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 643) * Probes the TI SCI clock device. Allocates a new clock provider
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 644) * and registers this to the common clock framework. Also applies
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 645) * any required flags to the identified clocks via clock lists
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 646) * supplied from DT. Returns 0 for success, negative error value
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 647) * for failure.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 648) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 649) static int ti_sci_clk_probe(struct platform_device *pdev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 650) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 651) struct device *dev = &pdev->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 652) struct device_node *np = dev->of_node;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 653) struct sci_clk_provider *provider;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 654) const struct ti_sci_handle *handle;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 655) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 656)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 657) handle = devm_ti_sci_get_handle(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 658) if (IS_ERR(handle))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 659) return PTR_ERR(handle);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 660)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 661) provider = devm_kzalloc(dev, sizeof(*provider), GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 662) if (!provider)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 663) return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 664)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 665) provider->sci = handle;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 666) provider->ops = &handle->ops.clk_ops;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 667) provider->dev = dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 668)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 669) #ifdef CONFIG_TI_SCI_CLK_PROBE_FROM_FW
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 670) ret = ti_sci_scan_clocks_from_fw(provider);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 671) if (ret) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 672) dev_err(dev, "scan clocks from FW failed: %d\n", ret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 673) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 674) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 675) #else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 676) ret = ti_sci_scan_clocks_from_dt(provider);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 677) if (ret) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 678) dev_err(dev, "scan clocks from DT failed: %d\n", ret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 679) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 680) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 681) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 682)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 683) ret = ti_sci_init_clocks(provider);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 684) if (ret) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 685) pr_err("ti-sci-init-clocks failed.\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 686) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 687) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 688)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 689) return of_clk_add_hw_provider(np, sci_clk_get, provider);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 690) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 691)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 692) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 693) * ti_sci_clk_remove - Remove TI SCI clock device
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 694) * @pdev: platform device pointer for the device to be removed
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 695) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 696) * Removes the TI SCI device. Unregisters the clock provider registered
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 697) * via common clock framework. Any memory allocated for the device will
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 698) * be free'd silently via the devm framework. Returns 0 always.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 699) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 700) static int ti_sci_clk_remove(struct platform_device *pdev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 701) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 702) of_clk_del_provider(pdev->dev.of_node);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 703)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 704) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 705) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 706)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 707) static struct platform_driver ti_sci_clk_driver = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 708) .probe = ti_sci_clk_probe,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 709) .remove = ti_sci_clk_remove,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 710) .driver = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 711) .name = "ti-sci-clk",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 712) .of_match_table = of_match_ptr(ti_sci_clk_of_match),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 713) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 714) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 715) module_platform_driver(ti_sci_clk_driver);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 716)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 717) MODULE_LICENSE("GPL v2");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 718) MODULE_DESCRIPTION("TI System Control Interface(SCI) Clock driver");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 719) MODULE_AUTHOR("Tero Kristo");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 720) MODULE_ALIAS("platform:ti-sci-clk");