Skip to content

Commit

Permalink
clk: use data types with preknown length
Browse files Browse the repository at this point in the history
This commit replaces all platform-dependent data types with fix-sized
types, and unifies the return values of interfaces as signed integers.
The return value 0 indicates the success on the request to clock driver,
and negative values indicate the failure reasons.

Signed-off-by: Terry Bai <[email protected]>
  • Loading branch information
terryzbai committed Nov 18, 2024
1 parent 1acc8de commit 2007cd7
Show file tree
Hide file tree
Showing 10 changed files with 135 additions and 118 deletions.
28 changes: 14 additions & 14 deletions drivers/clk/clk-operations.c
Original file line number Diff line number Diff line change
Expand Up @@ -122,8 +122,8 @@ const struct clk_ops clk_gate_ro_ops = {
.is_enabled = clk_gate_is_enabled,
};

static inline unsigned long clk_div_recalc_rate(const struct clk *clk,
unsigned long prate)
static inline uint64_t clk_div_recalc_rate(const struct clk *clk,
uint64_t prate)
{

struct clk_div_data *data = (struct clk_div_data *)(clk->data);
Expand All @@ -144,8 +144,8 @@ static inline unsigned long clk_div_recalc_rate(const struct clk *clk,
return DIV_ROUND_UP_ULL((uint64_t)prate, div);
}

static inline int clk_div_set_rate(const struct clk *clk, uint32_t rate,
uint32_t parent_rate)
static inline int clk_div_set_rate(const struct clk *clk, uint64_t rate,
uint64_t parent_rate)
{
struct clk_div_data *data = (struct clk_div_data *)(clk->data);
uint32_t div = DIV_ROUND_UP(parent_rate, rate);
Expand Down Expand Up @@ -212,7 +212,7 @@ static inline int clk_mux_set_parent(struct clk *clk, uint8_t index)
struct clk_mux_data *data = (struct clk_mux_data *)(clk->data);

if (data->table) {
unsigned int val = data->table[index];
uint32_t val = data->table[index];
regmap_mux_update_bits(clk->base, data->offset, data->shift, data->mask,
val);
}
Expand All @@ -231,16 +231,16 @@ const struct clk_ops clk_mux_ro_ops = {
.get_parent = clk_mux_get_parent,
};

static inline unsigned long clk_factor_recalc_rate(const struct clk *clk,
unsigned long parent_rate)
static inline uint64_t clk_factor_recalc_rate(const struct clk *clk,
uint64_t parent_rate)
{
struct clk_fixed_factor_data *data =
(struct clk_fixed_factor_data *)(clk->data);
unsigned long long int rate;
uint64_t rate;

rate = (unsigned long long int)parent_rate * data->mult;
rate = (uint64_t)parent_rate * data->mult;
do_div(rate, data->div);
return (unsigned long)rate;
return (uint64_t)rate;
}

const struct clk_ops clk_fixed_factor_ops = {
Expand All @@ -250,17 +250,17 @@ const struct clk_ops clk_fixed_factor_ops = {
/* .recalc_accuracy = clk_factor_recalc_accuracy, */
};

static inline int clk_source_set_rate(const struct clk *clk, uint32_t rate,
uint32_t parent_rate)
static inline int clk_source_set_rate(const struct clk *clk, uint64_t rate,
uint64_t parent_rate)
{
struct clk_source_data *data = (struct clk_source_data *)(clk->data);
data->rate = rate;

return 0;
}

static inline unsigned long clk_source_get_rate(const struct clk *clk,
unsigned long prate)
static inline uint64_t clk_source_get_rate(const struct clk *clk,
uint64_t prate)
{
struct clk_source_data *data = (struct clk_source_data *)(clk->data);

Expand Down
10 changes: 5 additions & 5 deletions drivers/clk/clk-operations.h
Original file line number Diff line number Diff line change
Expand Up @@ -8,11 +8,11 @@
#include <clk.h>
#include <utils.h>

#define CLK_INCORRECT_ARGS 1
#define CLK_INVALID_OP 2
#define CLK_INVALID_ID 3
#define CLK_UNKNOWN_REQ 4
#define CLK_UNKNOWN_TARGET 5
#define CLK_INCORRECT_ARGS -1
#define CLK_INVALID_OP -2
#define CLK_INVALID_ID -3
#define CLK_UNKNOWN_REQ -4
#define CLK_UNKNOWN_TARGET -5

static inline int reg_write(uint64_t base, uint32_t offset, uint32_t val)
{
Expand Down
38 changes: 7 additions & 31 deletions drivers/clk/clk.h
Original file line number Diff line number Diff line change
Expand Up @@ -70,8 +70,7 @@ struct clk_init_data;
* clk_foo's clk_ops
*
* @init: pointer to struct clk_init_data that contains the init data shared
* with the common clock framework. This pointer will be set to NULL once
* a clk_register() variant is called on this clk_hw pointer.
* with the common clock framework.
*/
struct clk_hw {
struct clk *clk;
Expand All @@ -83,20 +82,6 @@ struct clk_hw {
* be provided by the clock implementation, and will be called by drivers
* through the clk_* api.
*
* @prepare: Prepare the clock for enabling. This must not return until
* the clock is fully prepared, and it's safe to call clk_enable.
* This callback is intended to allow clock implementations to
* do any initialisation that may sleep. Called with
* prepare_lock held.
*
* @unprepare: Release the clock from its prepared state. This will typically
* undo any work done in the @prepare callback. Called with
* prepare_lock held.
*
* @is_prepared: Queries the hardware to determine if the clock is prepared.
* This function is allowed to sleep. Optional, if this op is not
* set then the prepare count will be used.
*
* @enable: Enable the clock atomically. This must not return until the
* clock is generating a valid clock signal, usable by consumer
* devices. Called with enable_lock held. This function must not
Expand All @@ -109,11 +94,6 @@ struct clk_hw {
* This function must not sleep. Optional, if this op is not
* set then the enable count will be used.
*
* @disable_unused: Disable the clock atomically. Only called from
* clk_disable_unused for gate clocks with special needs.
* Called with enable_lock held. This function must not
* sleep.
*
* @recalc_rate: Recalculate the rate of this clock, by querying hardware. The
* parent rate is an input parameter. It is up to the caller to
* ensure that the prepare_mutex is held across this call. If the
Expand Down Expand Up @@ -165,9 +145,8 @@ struct clk_hw {
struct clk_ops {
uint8_t (*get_parent)(const struct clk *clk);
int (*set_parent)(struct clk *clk, uint8_t index);
unsigned long (*recalc_rate)(const struct clk *clk,
unsigned long parent_rate);
int (*set_rate)(const struct clk *clk, uint32_t rate, uint32_t parent_rate);
uint64_t (*recalc_rate)(const struct clk *clk, uint64_t parent_rate);
int (*set_rate)(const struct clk *clk, uint64_t rate, uint64_t parent_rate);
void (*init)(struct clk *clk);
int (*enable)(struct clk *clk);
int (*disable)(struct clk *clk);
Expand Down Expand Up @@ -334,9 +313,6 @@ struct clk_fixed_factor_data {
* .get_parent clk_op.
* CLK_MUX_ROUND_CLOSEST - Use the parent rate that is closest to the desired
* frequency.
* CLK_MUX_BIG_ENDIAN - By default little endian register accesses are used for
* the mux register. Setting this flag makes the register accesses big
* endian.
*/
struct clk_mux_data {
uint32_t offset;
Expand Down Expand Up @@ -368,21 +344,21 @@ const struct clk *get_parent(const struct clk *clk);
* @clk: pointer to the current clk
*
*/
uint32_t clk_get_rate(const struct clk *clk, uint64_t *rate);
int clk_get_rate(const struct clk *clk, uint64_t *rate);

/**
* function clk_enable() - enable the target clock signal
*
* @clk: pointer to the current clk
*/
uint32_t clk_enable(struct clk *clk);
int clk_enable(struct clk *clk);

/**
* function clk_disable() - disable the target clock signal
*
* @clk: pointer to the current clk
*/
uint32_t clk_disable(struct clk *clk);
int clk_disable(struct clk *clk);

/**
* function clk_set_rate() - set the nearest rate to the requested rate for
Expand All @@ -392,4 +368,4 @@ uint32_t clk_disable(struct clk *clk);
* @req_rate: request rate
* @rate: pointer to result variable
*/
uint32_t clk_set_rate(struct clk *clk, uint64_t req_rate, uint64_t *rate);
int clk_set_rate(struct clk *clk, uint64_t req_rate, uint64_t *rate);
24 changes: 10 additions & 14 deletions drivers/clk/imx/clk-imx.c
Original file line number Diff line number Diff line change
Expand Up @@ -69,8 +69,7 @@ const struct clk_ops clk_gate2_ops = {
.is_enabled = clk_gate2_is_enabled,
};

static unsigned long clk_pll_recalc_rate(const struct clk *clk,
unsigned long prate)
static uint64_t clk_pll_recalc_rate(const struct clk *clk, uint64_t prate)
{
/* TODO: This function is derived from Linux codebase, but seems wrong
* according to the datasheet as PLL_REFCLK_DIV_VAL[5:10] is never used. */
Expand Down Expand Up @@ -112,8 +111,7 @@ const struct clk_ops clk_frac_pll_ops = {
/* .set_rate = clk_pll_set_rate, */
};

static unsigned long clk_sscg_pll_recalc_rate(const struct clk *clk,
unsigned long prate)
static uint64_t clk_sscg_pll_recalc_rate(const struct clk *clk, uint64_t prate)
{
struct clk_sscg_pll_data *data = (struct clk_sscg_pll_data *)(clk->data);
uint64_t temp_rate = prate;
Expand Down Expand Up @@ -173,8 +171,8 @@ const struct clk_ops clk_sscg_pll_ops = {
/* .determine_rate = clk_sscg_pll_determine_rate, */
};

static unsigned long imx8m_clk_core_slice_recalc_rate(const struct clk *clk,
unsigned long prate)
static uint64_t imx8m_clk_core_slice_recalc_rate(const struct clk *clk,
uint64_t prate)
{
struct clk_core_slice_data *data =
(struct clk_core_slice_data *)(clk->data);
Expand Down Expand Up @@ -226,17 +224,16 @@ const struct clk_ops clk_core_slice_ops = {
.set_parent = imx8m_clk_core_slice_set_parent,
};

static unsigned long imx8m_clk_common_slice_recalc_rate(const struct clk *clk,
unsigned long prate)
static uint64_t imx8m_clk_common_slice_recalc_rate(const struct clk *clk,
uint64_t prate)
{
struct clk_common_slice_data *data =
(struct clk_common_slice_data *)(clk->data);

uint32_t prediv_val = regmap_read_bits(
clk->base, data->offset, data->prevdiv_shift, data->prevdiv_width);
/* Divider value is n+1 */
unsigned long prediv_rate = DIV_ROUND_UP_ULL((uint64_t)prate,
prediv_val + 1);
uint64_t prediv_rate = DIV_ROUND_UP_ULL((uint64_t)prate, prediv_val + 1);

uint32_t postdiv_val = regmap_read_bits(
clk->base, data->offset, data->postdiv_shift, data->postdiv_width);
Expand Down Expand Up @@ -285,16 +282,15 @@ const struct clk_ops clk_common_slice_ops = {
.set_parent = imx8m_clk_common_slice_set_parent,
};

static unsigned long imx8m_clk_bus_slice_recalc_rate(const struct clk *clk,
unsigned long prate)
static uint64_t imx8m_clk_bus_slice_recalc_rate(const struct clk *clk,
uint64_t prate)
{
struct clk_bus_slice_data *data = (struct clk_bus_slice_data *)(clk->data);

uint32_t prediv_val = regmap_read_bits(
clk->base, data->offset, data->prevdiv_shift, data->prevdiv_width);
/* Divider value is n+1 */
unsigned long prediv_rate = DIV_ROUND_UP_ULL((uint64_t)prate,
prediv_val + 1);
uint64_t prediv_rate = DIV_ROUND_UP_ULL((uint64_t)prate, prediv_val + 1);

uint32_t postdiv_val = regmap_read_bits(
clk->base, data->offset, data->postdiv_shift, data->postdiv_width);
Expand Down
19 changes: 10 additions & 9 deletions drivers/clk/imx/clk.c
Original file line number Diff line number Diff line change
Expand Up @@ -98,14 +98,14 @@ const struct clk *get_parent(const struct clk *clk)

/* TODO: Should be just read from the structure, but need to update everytime when */
/* related clocks are modified */
uint32_t clk_get_rate(const struct clk *clk, uint64_t *rate)
int clk_get_rate(const struct clk *clk, uint64_t *rate)
{
if (!clk)
return CLK_UNKNOWN_TARGET;

const struct clk_init_data *init = (struct clk_init_data *)clk->hw.init;
uint64_t parent_rate = 0;
uint32_t err = 0;
int err = 0;

const struct clk *parent_clk = get_parent(clk);

Expand All @@ -124,7 +124,7 @@ uint32_t clk_get_rate(const struct clk *clk, uint64_t *rate)
return 0;
}

uint32_t clk_enable(struct clk *clk)
int clk_enable(struct clk *clk)
{
if (!clk)
return CLK_UNKNOWN_TARGET;
Expand All @@ -136,7 +136,7 @@ uint32_t clk_enable(struct clk *clk)
return CLK_INVALID_OP;
}

uint32_t clk_disable(struct clk *clk)
int clk_disable(struct clk *clk)
{
if (!clk)
return CLK_UNKNOWN_TARGET;
Expand All @@ -148,7 +148,7 @@ uint32_t clk_disable(struct clk *clk)
return CLK_INVALID_OP;
}

uint32_t clk_set_rate(struct clk *clk, uint64_t req_rate, uint64_t *rate)
int clk_set_rate(struct clk *clk, uint64_t req_rate, uint64_t *rate)
{
if (!clk)
return CLK_UNKNOWN_TARGET;
Expand All @@ -161,7 +161,7 @@ uint32_t clk_set_rate(struct clk *clk, uint64_t req_rate, uint64_t *rate)

const struct clk *pclk = get_parent(clk);
uint64_t prate = 0;
uint32_t err = clk_get_rate(pclk, &prate);
int err = clk_get_rate(pclk, &prate);
if (err) {
LOG_DRIVER_ERR("Failed to get parent clock's rate\n");
return err;
Expand All @@ -174,7 +174,7 @@ uint32_t clk_set_rate(struct clk *clk, uint64_t req_rate, uint64_t *rate)
if (pclk && pclk->hw.init->ops->set_rate) {
const struct clk *ppclk = get_parent(pclk);
uint64_t pprate = 0;
uint32_t err = clk_get_rate(ppclk, &pprate);
int err = clk_get_rate(ppclk, &pprate);
if (!err) {
pclk->hw.init->ops->set_rate(pclk, prate, pprate);
return 0;
Expand All @@ -190,7 +190,7 @@ int clk_msr_stat()
#ifdef DEBUG_DRIVER
int i;
uint64_t rate = 0;
uint32_t err;
int err;

LOG_DRIVER("-------Expected clock rates------\n");
for (i = 0; i < NUM_CLK_LIST; i++) {
Expand All @@ -199,6 +199,7 @@ int clk_msr_stat()
if (err) {
LOG_DRIVER_ERR("Failed to get rate of %s: -%u\n",
clk_list[i]->hw.init->name, err);
return err;
}
LOG_DRIVER("[%4d][%10luHz] %s\n", i, rate,
clk_list[i]->hw.init->name);
Expand Down Expand Up @@ -244,7 +245,7 @@ void init(void)

microkit_msginfo protected(microkit_channel ch, microkit_msginfo msginfo)
{
uint32_t err = 0;
int err = 0;
uint32_t argc = microkit_msginfo_get_count(msginfo);

/* TODO: Check if the channel is valid */
Expand Down
3 changes: 1 addition & 2 deletions drivers/clk/imx/include/clk-imx.h
Original file line number Diff line number Diff line change
Expand Up @@ -244,8 +244,7 @@ struct clk _name = { \
}, \
}

#define IMX_CLK_GATE2_FLAGS(_name, _parent_clks, _base, _offset, _shift, \
_flags) \
#define IMX_CLK_GATE2_FLAGS(_name, _parent_clks, _base, _offset, _shift, _flags) \
struct clk _name = { \
.base = (_base), \
.data = &(struct clk_gate_data) { \
Expand Down
13 changes: 6 additions & 7 deletions drivers/clk/meson/clk-meson.c
Original file line number Diff line number Diff line change
Expand Up @@ -220,8 +220,7 @@ const struct clk_ops meson_clk_pll_ro_ops = {
#define N2_MIN 4
#define N2_MAX 511

static unsigned long mpll_recalc_rate(const struct clk *clk,
unsigned long prate)
static uint64_t mpll_recalc_rate(const struct clk *clk, uint64_t prate)
{
struct meson_clk_mpll_data *data =
(struct meson_clk_mpll_data *)(clk->data);
Expand All @@ -239,8 +238,8 @@ static unsigned long mpll_recalc_rate(const struct clk *clk,
return DIV_ROUND_UP_ULL((uint64_t)prate * SDM_DEN, divisor);
}

static int mpll_set_rate(const struct clk *clk, uint32_t rate,
uint32_t parent_rate)
static int mpll_set_rate(const struct clk *clk, uint64_t rate,
uint64_t parent_rate)
{
struct meson_clk_mpll_data *data =
(struct meson_clk_mpll_data *)(clk->data);
Expand Down Expand Up @@ -291,7 +290,7 @@ static void mpll_init(struct clk *clk)
data->sdm_en.width, 1);

/* Set spread spectrum if possible */
unsigned int ss = data->flags & CLK_MESON_MPLL_SPREAD_SPECTRUM ? 1 : 0;
uint32_t ss = data->flags & CLK_MESON_MPLL_SPREAD_SPECTRUM ? 1 : 0;
regmap_update_bits(clk->base, data->ssen.reg_off, data->ssen.shift,
data->ssen.width, ss);
}
Expand Down Expand Up @@ -457,8 +456,8 @@ static unsigned long meson_vclk_div_recalc_rate(const struct clk *clk,
return DIV_ROUND_UP_ULL((uint64_t)prate, div);
}

static int meson_vclk_div_set_rate(const struct clk *clk, uint32_t rate,
uint32_t parent_rate)
static int meson_vclk_div_set_rate(const struct clk *clk, uint64_t rate,
uint64_t parent_rate)
{
struct meson_vclk_div_data *data =
(struct meson_vclk_div_data *)(clk->data);
Expand Down
Loading

0 comments on commit 2007cd7

Please sign in to comment.