Commit 67d4c879 authored by Linus Torvalds's avatar Linus Torvalds
Browse files

Merge tag 'clk-fixes-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/clk/linux

Pull clk fixes from Stephen Boyd:
 "Three fixes, one for the clk framework and two for clk drivers:

   - Avoid an oops in possible_parent_show() by checking for no parent
     properly when a DT index based lookup is used

   - Handle errors returned from divider_ro_round_rate() in
     clk_stm32_composite_determine_rate()

   - Fix clk_ops::determine_rate() implementation of socfpga's
     gateclk_ops that was ruining uart output because the divider
     was forgotten about"

* tag 'clk-fixes-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/clk/linux:
  clk: stm32: Fix a signedness issue in clk_stm32_composite_determine_rate()
  clk: Sanitize possible_parent_show to Handle Return Value of of_clk_get_parent_name
  clk: socfpga: gate: Account for the divider in determine_rate
parents d1b0949f 790437bb
Loading
Loading
Loading
Loading
+12 −9
Original line number Diff line number Diff line
@@ -3416,6 +3416,7 @@ static void possible_parent_show(struct seq_file *s, struct clk_core *core,
				 unsigned int i, char terminator)
{
	struct clk_core *parent;
	const char *name = NULL;

	/*
	 * Go through the following options to fetch a parent's name.
@@ -3430,18 +3431,20 @@ static void possible_parent_show(struct seq_file *s, struct clk_core *core,
	 * registered (yet).
	 */
	parent = clk_core_get_parent_by_index(core, i);
	if (parent)
	if (parent) {
		seq_puts(s, parent->name);
	else if (core->parents[i].name)
	} else if (core->parents[i].name) {
		seq_puts(s, core->parents[i].name);
	else if (core->parents[i].fw_name)
	} else if (core->parents[i].fw_name) {
		seq_printf(s, "<%s>(fw)", core->parents[i].fw_name);
	else if (core->parents[i].index >= 0)
		seq_puts(s,
			 of_clk_get_parent_name(core->of_node,
						core->parents[i].index));
	else
		seq_puts(s, "(missing)");
	} else {
		if (core->parents[i].index >= 0)
			name = of_clk_get_parent_name(core->of_node, core->parents[i].index);
		if (!name)
			name = "(missing)";

		seq_puts(s, name);
	}

	seq_putc(s, terminator);
}
+23 −4
Original line number Diff line number Diff line
@@ -87,10 +87,8 @@ static int socfpga_clk_set_parent(struct clk_hw *hwclk, u8 parent)
	return 0;
}

static unsigned long socfpga_clk_recalc_rate(struct clk_hw *hwclk,
	unsigned long parent_rate)
static u32 socfpga_clk_get_div(struct socfpga_gate_clk *socfpgaclk)
{
	struct socfpga_gate_clk *socfpgaclk = to_socfpga_gate_clk(hwclk);
	u32 div = 1, val;

	if (socfpgaclk->fixed_div)
@@ -105,12 +103,33 @@ static unsigned long socfpga_clk_recalc_rate(struct clk_hw *hwclk,
			div = (1 << val);
	}

	return div;
}

static unsigned long socfpga_clk_recalc_rate(struct clk_hw *hwclk,
					     unsigned long parent_rate)
{
	struct socfpga_gate_clk *socfpgaclk = to_socfpga_gate_clk(hwclk);
	u32 div = socfpga_clk_get_div(socfpgaclk);

	return parent_rate / div;
}


static int socfpga_clk_determine_rate(struct clk_hw *hwclk,
				      struct clk_rate_request *req)
{
	struct socfpga_gate_clk *socfpgaclk = to_socfpga_gate_clk(hwclk);
	u32 div = socfpga_clk_get_div(socfpgaclk);

	req->rate = req->best_parent_rate / div;

	return 0;
}

static struct clk_ops gateclk_ops = {
	.recalc_rate = socfpga_clk_recalc_rate,
	.determine_rate = clk_hw_determine_rate_no_reparent,
	.determine_rate = socfpga_clk_determine_rate,
	.get_parent = socfpga_clk_get_parent,
	.set_parent = socfpga_clk_set_parent,
};
+1 −1
Original line number Diff line number Diff line
@@ -431,7 +431,7 @@ static int clk_stm32_composite_determine_rate(struct clk_hw *hw,
{
	struct clk_stm32_composite *composite = to_clk_stm32_composite(hw);
	const struct stm32_div_cfg *divider;
	unsigned long rate;
	long rate;

	if (composite->div_id == NO_STM32_DIV)
		return 0;