From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
To: Geert Uytterhoeven <geert+renesas@glider.be>
Cc: Greg Kroah-Hartman <gregkh@linuxfoundation.org>,
Simon Horman <horms@verge.net.au>,
Magnus Damm <magnus.damm@gmail.com>,
Yoshinori Sato <ysato@users.sourceforge.jp>,
linux-serial@vger.kernel.org, linux-sh@vger.kernel.org,
linux-kernel@vger.kernel.org
Subject: Re: [PATCH 18/25] serial: sh-sci: Prepare for multiple clocks and baud rate generators
Date: Thu, 19 Nov 2015 21:04:02 +0000 [thread overview]
Message-ID: <3383903.1R72kZGx62@avalon> (raw)
In-Reply-To: <1447958344-836-19-git-send-email-geert+renesas@glider.be>
Hi Geert,
Thank you for the patch.
On Thursday 19 November 2015 19:38:57 Geert Uytterhoeven wrote:
> Refactor the clock and baud rate parameter code to ease adding support
> for multiple clocks and baud rate generators later.
> sci_scbrr_calc() now returns the bit rate error, so it can be compared
> to the bit rate error for other baud rate generators.
>
> Signed-off-by: Geert Uytterhoeven <geert+renesas@glider.be>
> ---
> drivers/tty/serial/sh-sci.c | 176 +++++++++++++++++++++++++++--------------
> 1 file changed, 120 insertions(+), 56 deletions(-)
>
> diff --git a/drivers/tty/serial/sh-sci.c b/drivers/tty/serial/sh-sci.c
> index 726c96d5a511c222..12800e52f41953dc 100644
> --- a/drivers/tty/serial/sh-sci.c
> +++ b/drivers/tty/serial/sh-sci.c
> @@ -2,6 +2,7 @@
> * SuperH on-chip serial module support. (SCI with no FIFO / with FIFO)
> *
> * Copyright (C) 2002 - 2011 Paul Mundt
> + * Copyright (C) 2015 Glider bvba
> * Modified to support SH7720 SCIF. Markus Brunner, Mark Jonas (Jul 2007).
> *
> * based off of the old drivers/char/sh-sci.c by:
> @@ -76,6 +77,11 @@ enum {
> ((port)->irqs[SCIx_ERI_IRQ] && \
> ((port)->irqs[SCIx_RXI_IRQ] < 0))
>
> +enum SCI_CLKS {
> + SCI_FCK, /* Functional Clock */
> + SCI_NUM_CLKS
> +};
> +
> struct sci_port {
> struct uart_port port;
>
> @@ -92,8 +98,9 @@ struct sci_port {
> struct timer_list break_timer;
> int break_flag;
>
> - /* Function clock */
> - struct clk *fclk;
> + /* Clocks */
> + struct clk *clks[SCI_NUM_CLKS];
> + unsigned long clk_rates[SCI_NUM_CLKS];
>
> int irqs[SCIx_NR_IRQS];
> char *irqstr[SCIx_NR_IRQS];
> @@ -496,17 +503,24 @@ static int sci_probe_regmap(struct plat_sci_port *cfg)
>
> static void sci_port_enable(struct sci_port *sci_port)
> {
> + unsigned int i;
> +
> if (!sci_port->port.dev)
> return;
>
> pm_runtime_get_sync(sci_port->port.dev);
>
> - clk_prepare_enable(sci_port->fclk);
> - sci_port->port.uartclk = clk_get_rate(sci_port->fclk);
> + for (i = 0; i < SCI_NUM_CLKS; i++) {
> + clk_prepare_enable(sci_port->clks[i]);
> + sci_port->clk_rates[i] = clk_get_rate(sci_port->clks[i]);
> + }
> + sci_port->port.uartclk = sci_port->clk_rates[SCI_FCK];
> }
>
> static void sci_port_disable(struct sci_port *sci_port)
> {
> + unsigned int i;
> +
> if (!sci_port->port.dev)
> return;
>
> @@ -518,7 +532,8 @@ static void sci_port_disable(struct sci_port *sci_port)
> del_timer_sync(&sci_port->break_timer);
> sci_port->break_flag = 0;
>
> - clk_disable_unprepare(sci_port->fclk);
> + for (i = SCI_NUM_CLKS; i-- > 0; )
> + clk_disable_unprepare(sci_port->clks[i]);
>
> pm_runtime_put_sync(sci_port->port.dev);
> }
> @@ -1657,6 +1672,7 @@ static int sci_notifier(struct notifier_block *self,
> {
> struct sci_port *sci_port;
> unsigned long flags;
> + unsigned int i;
>
> sci_port = container_of(self, struct sci_port, freq_transition);
>
> @@ -1664,7 +1680,9 @@ static int sci_notifier(struct notifier_block *self,
> struct uart_port *port = &sci_port->port;
>
> spin_lock_irqsave(&port->lock, flags);
> - port->uartclk = clk_get_rate(sci_port->fclk);
> + for (i = 0; i < SCI_NUM_CLKS; i++)
> + sci_port->clk_rates[i] > + clk_get_rate(sci_port->clks[i]);
> spin_unlock_irqrestore(&port->lock, flags);
> }
>
> @@ -1907,11 +1925,12 @@ static void sci_shutdown(struct uart_port *port)
> }
>
> /* calculate sample rate, BRR, and clock select */
> -static void sci_scbrr_calc(struct sci_port *s, unsigned int bps,
> - unsigned long freq, int *brr, unsigned int *srr,
> - unsigned int *cks)
> +static int sci_scbrr_calc(struct sci_port *s, unsigned int bps,
> + unsigned int *brr, unsigned int *srr,
> + unsigned int *cks)
> {
> unsigned int min_sr, max_sr, shift, sr, br, a, b, c;
> + unsigned long freq = s->clk_rates[SCI_FCK];
> int err, min_err = INT_MAX;
>
> if (s->sampling_rate) {
> @@ -1963,6 +1982,7 @@ static void sci_scbrr_calc(struct sci_port *s,
> unsigned int bps,
>
> dev_dbg(s->port.dev, "BRR: %u%+d bps using N %u SR %u cks %u\n", bps,
> min_err, *brr, *srr + 1, *cks);
> + return min_err;
> }
>
> static void sci_reset(struct uart_port *port)
> @@ -1984,11 +2004,14 @@ static void sci_reset(struct uart_port *port)
> static void sci_set_termios(struct uart_port *port, struct ktermios
> *termios, struct ktermios *old)
> {
> + unsigned int baud, smr_val = 0, scr_val = 0, i;
> + unsigned int brr = 255, cks = 0, srr = 15;
> + unsigned int brr1 = 255, cks1 = 0, srr1 = 15;
> struct sci_port *s = to_sci_port(port);
> const struct plat_sci_reg *reg;
> - unsigned int baud, smr_val = 0, max_baud, cks = 0;
> - int t = -1;
> - unsigned int srr = 15;
> + int min_err = INT_MAX, err;
> + unsigned long max_freq = 0;
> + int best_clk = -1;
>
> if ((termios->c_cflag & CSIZE) = CS7)
> smr_val |= SCSMR_CHR;
> @@ -2007,35 +2030,59 @@ static void sci_set_termios(struct uart_port *port,
> struct ktermios *termios, * that the previous boot loader has enabled
> required clocks and * setup the baud rate generator hardware for us
> already.
> */
> - if (port->uartclk)
> - max_baud = port->uartclk / max(s->sampling_rate, 8U);
> - else
> - max_baud = 115200;
> + if (!port->uartclk) {
> + baud = uart_get_baud_rate(port, termios, old, 0, 115200);
> + goto done;
> + }
>
> - baud = uart_get_baud_rate(port, termios, old, 0, max_baud);
> - if (likely(baud && port->uartclk))
> - sci_scbrr_calc(s, baud, port->uartclk, &t, &srr, &cks);
> + for (i = 0; i < SCI_NUM_CLKS; i++)
> + max_freq = max(max_freq, s->clk_rates[i]);
> +
> + baud = uart_get_baud_rate(port, termios, old, 0,
> + max_freq / max(s->sampling_rate, 8U));
> + if (!baud)
> + goto done;
> +
> + /* Functional Clock and standard Bit Rate Register */
> + err = sci_scbrr_calc(s, baud, &brr1, &srr1, &cks1);
> + if (abs(err) < abs(min_err)) {
> + best_clk = SCI_FCK;
> + min_err = err;
> + brr = brr1;
> + srr = srr1;
> + cks = cks1;
> + }
> +
> +done:
> + if (best_clk >= 0)
> + dev_dbg(port->dev, "Using clk %pC for %u%+d bps\n",
> + s->clks[best_clk], baud, min_err);
>
> sci_port_enable(s);
>
> sci_reset(port);
>
> - smr_val |= serial_port_in(port, SCSMR) & SCSMR_CKS;
> -
> uart_update_timeout(port, termios->c_cflag, baud);
>
> - dev_dbg(port->dev, "%s: SMR %x, cks %x, t %x, SCSCR %x\n",
> - __func__, smr_val, cks, t, s->cfg->scscr);
> -
> - if (t >= 0) {
> - serial_port_out(port, SCSMR, (smr_val & ~SCSMR_CKS) | cks);
> - serial_port_out(port, SCBRR, t);
> - reg = sci_getreg(port, HSSRR);
> - if (reg->size)
> + if (best_clk >= 0) {
> + smr_val |= cks;
> + dev_dbg(port->dev, "SMR 0x%x BRR %u SRR %u\n", smr_val, brr,
> + srr);
> + serial_port_out(port, SCSMR, smr_val);
> + serial_port_out(port, SCBRR, brr);
> + if (sci_getreg(port, HSSRR)->size)
> serial_port_out(port, HSSRR, srr | HSCIF_SRE);
> - udelay((1000000+(baud-1)) / baud); /* Wait one bit interval */
> - } else
> +
> + /* Wait one bit interval */
> + udelay((1000000 + (baud - 1)) / baud);
> + } else {
> + /* Don't touch the bit rate configuration */
> + scr_val = s->cfg->scscr & (SCSCR_CKE1 | SCSCR_CKE0);
> + smr_val |= serial_port_in(port, SCSMR) & SCSMR_CKS;
> + dev_dbg(port->dev, "SCR 0x%x SMR 0x%x\n", scr_val, smr_val);
> + serial_port_out(port, SCSCR, scr_val);
> serial_port_out(port, SCSMR, smr_val);
> + }
>
> sci_init_pins(port, termios->c_cflag);
>
> @@ -2060,7 +2107,9 @@ static void sci_set_termios(struct uart_port *port,
> struct ktermios *termios, serial_port_out(port, SCFCR, ctrl);
> }
>
> - serial_port_out(port, SCSCR, s->cfg->scscr);
> + scr_val |= s->cfg->scscr & ~(SCSCR_CKE1 | SCSCR_CKE0);
> + dev_dbg(port->dev, "SCSCR 0x%x\n", scr_val);
> + serial_port_out(port, SCSCR, scr_val);
>
> #ifdef CONFIG_SERIAL_SH_SCI_DMA
> /*
> @@ -2252,33 +2301,48 @@ static struct uart_ops sci_uart_ops = {
>
> static int sci_init_clocks(struct sci_port *sci_port, struct device *dev)
> {
> - /* Get the SCI functional clock. It's called "fck" on ARM. */
> - sci_port->fclk = devm_clk_get(dev, "fck");
> - if (PTR_ERR(sci_port->fclk) = -EPROBE_DEFER)
> - return -EPROBE_DEFER;
> - if (!IS_ERR(sci_port->fclk))
> - return 0;
> + const char *clk_names[] = {
> + [SCI_FCK] = "fck",
> + };
> + struct clk *clk;
> + unsigned int i;
>
> - /*
> - * But it used to be called "sci_ick", and we need to maintain DT
> - * backward compatibility.
> - */
> - sci_port->fclk = devm_clk_get(dev, "sci_ick");
> - if (PTR_ERR(sci_port->fclk) = -EPROBE_DEFER)
> - return -EPROBE_DEFER;
> - if (!IS_ERR(sci_port->fclk))
> - return 0;
> + for (i = 0; i < SCI_NUM_CLKS; i++) {
> + clk = devm_clk_get(dev, clk_names[i]);
> + if (PTR_ERR(clk) = -EPROBE_DEFER)
> + return -EPROBE_DEFER;
>
> - /*
> - * Not all SH platforms declare a clock lookup entry for SCI devices,
> - * in which case we need to get the global "peripheral_clk" clock.
> - */
> - sci_port->fclk = devm_clk_get(dev, "peripheral_clk");
> - if (!IS_ERR(sci_port->fclk))
> - return 0;
> + if (IS_ERR(clk) && i = SCI_FCK) {
> + /*
> + * "fck" used to be called "sci_ick", and we need to
> + * maintain DT backward compatibility.
> + */
> + clk = devm_clk_get(dev, "sci_ick");
> + if (PTR_ERR(clk) = -EPROBE_DEFER)
> + return -EPROBE_DEFER;
> +
> + if (!IS_ERR(clk))
> + goto found;
> +
> + /*
> + * Not all SH platforms declare a clock lookup entry
> + * for SCI devices, in which case we need to get the
> + * global "peripheral_clk" clock.
> + */
> + clk = devm_clk_get(dev, "peripheral_clk");
> + if (!IS_ERR(clk))
> + goto found;
> +
> + dev_err(dev, "failed to get functional clock\n");
> + return PTR_ERR(clk);
> + }
>
> - dev_err(dev, "failed to get functional clock\n");
> - return PTR_ERR(sci_port->fclk);
> +found:
> + if (!IS_ERR(clk))
> + dev_dbg(dev, "clk %u is %pC rate %pCr\n", i, clk, clk);
> + sci_port->clks[i] = IS_ERR(clk) ? NULL : clk;
Isn't it an issue that we can't tell apart the case where there is no clock
specified in DT and the case where we can't get the clock due to another error
?
> + }
> + return 0;
> }
>
> static int sci_init_single(struct platform_device *dev,
--
Regards,
Laurent Pinchart
WARNING: multiple messages have this Message-ID (diff)
From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
To: Geert Uytterhoeven <geert+renesas@glider.be>
Cc: Greg Kroah-Hartman <gregkh@linuxfoundation.org>,
Simon Horman <horms@verge.net.au>,
Magnus Damm <magnus.damm@gmail.com>,
Yoshinori Sato <ysato@users.sourceforge.jp>,
linux-serial@vger.kernel.org, linux-sh@vger.kernel.org,
linux-kernel@vger.kernel.org
Subject: Re: [PATCH 18/25] serial: sh-sci: Prepare for multiple clocks and baud rate generators
Date: Thu, 19 Nov 2015 23:04:02 +0200 [thread overview]
Message-ID: <3383903.1R72kZGx62@avalon> (raw)
In-Reply-To: <1447958344-836-19-git-send-email-geert+renesas@glider.be>
Hi Geert,
Thank you for the patch.
On Thursday 19 November 2015 19:38:57 Geert Uytterhoeven wrote:
> Refactor the clock and baud rate parameter code to ease adding support
> for multiple clocks and baud rate generators later.
> sci_scbrr_calc() now returns the bit rate error, so it can be compared
> to the bit rate error for other baud rate generators.
>
> Signed-off-by: Geert Uytterhoeven <geert+renesas@glider.be>
> ---
> drivers/tty/serial/sh-sci.c | 176 +++++++++++++++++++++++++++--------------
> 1 file changed, 120 insertions(+), 56 deletions(-)
>
> diff --git a/drivers/tty/serial/sh-sci.c b/drivers/tty/serial/sh-sci.c
> index 726c96d5a511c222..12800e52f41953dc 100644
> --- a/drivers/tty/serial/sh-sci.c
> +++ b/drivers/tty/serial/sh-sci.c
> @@ -2,6 +2,7 @@
> * SuperH on-chip serial module support. (SCI with no FIFO / with FIFO)
> *
> * Copyright (C) 2002 - 2011 Paul Mundt
> + * Copyright (C) 2015 Glider bvba
> * Modified to support SH7720 SCIF. Markus Brunner, Mark Jonas (Jul 2007).
> *
> * based off of the old drivers/char/sh-sci.c by:
> @@ -76,6 +77,11 @@ enum {
> ((port)->irqs[SCIx_ERI_IRQ] && \
> ((port)->irqs[SCIx_RXI_IRQ] < 0))
>
> +enum SCI_CLKS {
> + SCI_FCK, /* Functional Clock */
> + SCI_NUM_CLKS
> +};
> +
> struct sci_port {
> struct uart_port port;
>
> @@ -92,8 +98,9 @@ struct sci_port {
> struct timer_list break_timer;
> int break_flag;
>
> - /* Function clock */
> - struct clk *fclk;
> + /* Clocks */
> + struct clk *clks[SCI_NUM_CLKS];
> + unsigned long clk_rates[SCI_NUM_CLKS];
>
> int irqs[SCIx_NR_IRQS];
> char *irqstr[SCIx_NR_IRQS];
> @@ -496,17 +503,24 @@ static int sci_probe_regmap(struct plat_sci_port *cfg)
>
> static void sci_port_enable(struct sci_port *sci_port)
> {
> + unsigned int i;
> +
> if (!sci_port->port.dev)
> return;
>
> pm_runtime_get_sync(sci_port->port.dev);
>
> - clk_prepare_enable(sci_port->fclk);
> - sci_port->port.uartclk = clk_get_rate(sci_port->fclk);
> + for (i = 0; i < SCI_NUM_CLKS; i++) {
> + clk_prepare_enable(sci_port->clks[i]);
> + sci_port->clk_rates[i] = clk_get_rate(sci_port->clks[i]);
> + }
> + sci_port->port.uartclk = sci_port->clk_rates[SCI_FCK];
> }
>
> static void sci_port_disable(struct sci_port *sci_port)
> {
> + unsigned int i;
> +
> if (!sci_port->port.dev)
> return;
>
> @@ -518,7 +532,8 @@ static void sci_port_disable(struct sci_port *sci_port)
> del_timer_sync(&sci_port->break_timer);
> sci_port->break_flag = 0;
>
> - clk_disable_unprepare(sci_port->fclk);
> + for (i = SCI_NUM_CLKS; i-- > 0; )
> + clk_disable_unprepare(sci_port->clks[i]);
>
> pm_runtime_put_sync(sci_port->port.dev);
> }
> @@ -1657,6 +1672,7 @@ static int sci_notifier(struct notifier_block *self,
> {
> struct sci_port *sci_port;
> unsigned long flags;
> + unsigned int i;
>
> sci_port = container_of(self, struct sci_port, freq_transition);
>
> @@ -1664,7 +1680,9 @@ static int sci_notifier(struct notifier_block *self,
> struct uart_port *port = &sci_port->port;
>
> spin_lock_irqsave(&port->lock, flags);
> - port->uartclk = clk_get_rate(sci_port->fclk);
> + for (i = 0; i < SCI_NUM_CLKS; i++)
> + sci_port->clk_rates[i] =
> + clk_get_rate(sci_port->clks[i]);
> spin_unlock_irqrestore(&port->lock, flags);
> }
>
> @@ -1907,11 +1925,12 @@ static void sci_shutdown(struct uart_port *port)
> }
>
> /* calculate sample rate, BRR, and clock select */
> -static void sci_scbrr_calc(struct sci_port *s, unsigned int bps,
> - unsigned long freq, int *brr, unsigned int *srr,
> - unsigned int *cks)
> +static int sci_scbrr_calc(struct sci_port *s, unsigned int bps,
> + unsigned int *brr, unsigned int *srr,
> + unsigned int *cks)
> {
> unsigned int min_sr, max_sr, shift, sr, br, a, b, c;
> + unsigned long freq = s->clk_rates[SCI_FCK];
> int err, min_err = INT_MAX;
>
> if (s->sampling_rate) {
> @@ -1963,6 +1982,7 @@ static void sci_scbrr_calc(struct sci_port *s,
> unsigned int bps,
>
> dev_dbg(s->port.dev, "BRR: %u%+d bps using N %u SR %u cks %u\n", bps,
> min_err, *brr, *srr + 1, *cks);
> + return min_err;
> }
>
> static void sci_reset(struct uart_port *port)
> @@ -1984,11 +2004,14 @@ static void sci_reset(struct uart_port *port)
> static void sci_set_termios(struct uart_port *port, struct ktermios
> *termios, struct ktermios *old)
> {
> + unsigned int baud, smr_val = 0, scr_val = 0, i;
> + unsigned int brr = 255, cks = 0, srr = 15;
> + unsigned int brr1 = 255, cks1 = 0, srr1 = 15;
> struct sci_port *s = to_sci_port(port);
> const struct plat_sci_reg *reg;
> - unsigned int baud, smr_val = 0, max_baud, cks = 0;
> - int t = -1;
> - unsigned int srr = 15;
> + int min_err = INT_MAX, err;
> + unsigned long max_freq = 0;
> + int best_clk = -1;
>
> if ((termios->c_cflag & CSIZE) == CS7)
> smr_val |= SCSMR_CHR;
> @@ -2007,35 +2030,59 @@ static void sci_set_termios(struct uart_port *port,
> struct ktermios *termios, * that the previous boot loader has enabled
> required clocks and * setup the baud rate generator hardware for us
> already.
> */
> - if (port->uartclk)
> - max_baud = port->uartclk / max(s->sampling_rate, 8U);
> - else
> - max_baud = 115200;
> + if (!port->uartclk) {
> + baud = uart_get_baud_rate(port, termios, old, 0, 115200);
> + goto done;
> + }
>
> - baud = uart_get_baud_rate(port, termios, old, 0, max_baud);
> - if (likely(baud && port->uartclk))
> - sci_scbrr_calc(s, baud, port->uartclk, &t, &srr, &cks);
> + for (i = 0; i < SCI_NUM_CLKS; i++)
> + max_freq = max(max_freq, s->clk_rates[i]);
> +
> + baud = uart_get_baud_rate(port, termios, old, 0,
> + max_freq / max(s->sampling_rate, 8U));
> + if (!baud)
> + goto done;
> +
> + /* Functional Clock and standard Bit Rate Register */
> + err = sci_scbrr_calc(s, baud, &brr1, &srr1, &cks1);
> + if (abs(err) < abs(min_err)) {
> + best_clk = SCI_FCK;
> + min_err = err;
> + brr = brr1;
> + srr = srr1;
> + cks = cks1;
> + }
> +
> +done:
> + if (best_clk >= 0)
> + dev_dbg(port->dev, "Using clk %pC for %u%+d bps\n",
> + s->clks[best_clk], baud, min_err);
>
> sci_port_enable(s);
>
> sci_reset(port);
>
> - smr_val |= serial_port_in(port, SCSMR) & SCSMR_CKS;
> -
> uart_update_timeout(port, termios->c_cflag, baud);
>
> - dev_dbg(port->dev, "%s: SMR %x, cks %x, t %x, SCSCR %x\n",
> - __func__, smr_val, cks, t, s->cfg->scscr);
> -
> - if (t >= 0) {
> - serial_port_out(port, SCSMR, (smr_val & ~SCSMR_CKS) | cks);
> - serial_port_out(port, SCBRR, t);
> - reg = sci_getreg(port, HSSRR);
> - if (reg->size)
> + if (best_clk >= 0) {
> + smr_val |= cks;
> + dev_dbg(port->dev, "SMR 0x%x BRR %u SRR %u\n", smr_val, brr,
> + srr);
> + serial_port_out(port, SCSMR, smr_val);
> + serial_port_out(port, SCBRR, brr);
> + if (sci_getreg(port, HSSRR)->size)
> serial_port_out(port, HSSRR, srr | HSCIF_SRE);
> - udelay((1000000+(baud-1)) / baud); /* Wait one bit interval */
> - } else
> +
> + /* Wait one bit interval */
> + udelay((1000000 + (baud - 1)) / baud);
> + } else {
> + /* Don't touch the bit rate configuration */
> + scr_val = s->cfg->scscr & (SCSCR_CKE1 | SCSCR_CKE0);
> + smr_val |= serial_port_in(port, SCSMR) & SCSMR_CKS;
> + dev_dbg(port->dev, "SCR 0x%x SMR 0x%x\n", scr_val, smr_val);
> + serial_port_out(port, SCSCR, scr_val);
> serial_port_out(port, SCSMR, smr_val);
> + }
>
> sci_init_pins(port, termios->c_cflag);
>
> @@ -2060,7 +2107,9 @@ static void sci_set_termios(struct uart_port *port,
> struct ktermios *termios, serial_port_out(port, SCFCR, ctrl);
> }
>
> - serial_port_out(port, SCSCR, s->cfg->scscr);
> + scr_val |= s->cfg->scscr & ~(SCSCR_CKE1 | SCSCR_CKE0);
> + dev_dbg(port->dev, "SCSCR 0x%x\n", scr_val);
> + serial_port_out(port, SCSCR, scr_val);
>
> #ifdef CONFIG_SERIAL_SH_SCI_DMA
> /*
> @@ -2252,33 +2301,48 @@ static struct uart_ops sci_uart_ops = {
>
> static int sci_init_clocks(struct sci_port *sci_port, struct device *dev)
> {
> - /* Get the SCI functional clock. It's called "fck" on ARM. */
> - sci_port->fclk = devm_clk_get(dev, "fck");
> - if (PTR_ERR(sci_port->fclk) == -EPROBE_DEFER)
> - return -EPROBE_DEFER;
> - if (!IS_ERR(sci_port->fclk))
> - return 0;
> + const char *clk_names[] = {
> + [SCI_FCK] = "fck",
> + };
> + struct clk *clk;
> + unsigned int i;
>
> - /*
> - * But it used to be called "sci_ick", and we need to maintain DT
> - * backward compatibility.
> - */
> - sci_port->fclk = devm_clk_get(dev, "sci_ick");
> - if (PTR_ERR(sci_port->fclk) == -EPROBE_DEFER)
> - return -EPROBE_DEFER;
> - if (!IS_ERR(sci_port->fclk))
> - return 0;
> + for (i = 0; i < SCI_NUM_CLKS; i++) {
> + clk = devm_clk_get(dev, clk_names[i]);
> + if (PTR_ERR(clk) == -EPROBE_DEFER)
> + return -EPROBE_DEFER;
>
> - /*
> - * Not all SH platforms declare a clock lookup entry for SCI devices,
> - * in which case we need to get the global "peripheral_clk" clock.
> - */
> - sci_port->fclk = devm_clk_get(dev, "peripheral_clk");
> - if (!IS_ERR(sci_port->fclk))
> - return 0;
> + if (IS_ERR(clk) && i == SCI_FCK) {
> + /*
> + * "fck" used to be called "sci_ick", and we need to
> + * maintain DT backward compatibility.
> + */
> + clk = devm_clk_get(dev, "sci_ick");
> + if (PTR_ERR(clk) == -EPROBE_DEFER)
> + return -EPROBE_DEFER;
> +
> + if (!IS_ERR(clk))
> + goto found;
> +
> + /*
> + * Not all SH platforms declare a clock lookup entry
> + * for SCI devices, in which case we need to get the
> + * global "peripheral_clk" clock.
> + */
> + clk = devm_clk_get(dev, "peripheral_clk");
> + if (!IS_ERR(clk))
> + goto found;
> +
> + dev_err(dev, "failed to get functional clock\n");
> + return PTR_ERR(clk);
> + }
>
> - dev_err(dev, "failed to get functional clock\n");
> - return PTR_ERR(sci_port->fclk);
> +found:
> + if (!IS_ERR(clk))
> + dev_dbg(dev, "clk %u is %pC rate %pCr\n", i, clk, clk);
> + sci_port->clks[i] = IS_ERR(clk) ? NULL : clk;
Isn't it an issue that we can't tell apart the case where there is no clock
specified in DT and the case where we can't get the clock due to another error
?
> + }
> + return 0;
> }
>
> static int sci_init_single(struct platform_device *dev,
--
Regards,
Laurent Pinchart
next prev parent reply other threads:[~2015-11-19 21:04 UTC|newest]
Thread overview: 151+ messages / expand[flat|nested] mbox.gz Atom feed top
2015-11-19 18:38 [PATCH 00/25] serial: sh-sci: Add external clock and BRG Support Geert Uytterhoeven
2015-11-19 18:38 ` Geert Uytterhoeven
[not found] ` <1447958344-836-1-git-send-email-geert+renesas-gXvu3+zWzMSzQB+pC5nmwQ@public.gmane.org>
2015-11-19 18:38 ` [PATCH 01/25] serial: sh-sci: Update DT binding documentation for external clock input Geert Uytterhoeven
2015-11-19 18:38 ` Geert Uytterhoeven
2015-11-19 18:38 ` Geert Uytterhoeven
[not found] ` <1447958344-836-2-git-send-email-geert+renesas-gXvu3+zWzMSzQB+pC5nmwQ@public.gmane.org>
2015-11-19 20:19 ` Laurent Pinchart
2015-11-19 20:19 ` Laurent Pinchart
2015-11-19 20:19 ` Laurent Pinchart
2015-11-19 20:27 ` Laurent Pinchart
2015-11-19 20:27 ` Laurent Pinchart
2015-11-19 20:39 ` Geert Uytterhoeven
2015-11-19 20:39 ` Geert Uytterhoeven
2015-11-19 20:39 ` Geert Uytterhoeven
[not found] ` <CAMuHMdUnT2zCnj9QBVgxJaHV2fk5iuc7cxq=fh+fVTv3toOVaQ-JsoAwUIsXosN+BqQ9rBEUg@public.gmane.org>
2015-11-19 21:17 ` Laurent Pinchart
2015-11-19 21:17 ` Laurent Pinchart
2015-11-19 21:17 ` Laurent Pinchart
2015-11-20 8:00 ` Geert Uytterhoeven
2015-11-20 8:00 ` Geert Uytterhoeven
2015-11-19 20:33 ` Geert Uytterhoeven
2015-11-19 20:33 ` Geert Uytterhoeven
[not found] ` <CAMuHMdX4ToefbBLR6o2AMuzCMoKcYo9XRZOzHJzgtQn552vmNg-JsoAwUIsXosN+BqQ9rBEUg@public.gmane.org>
2015-12-21 14:20 ` Geert Uytterhoeven
2015-12-21 14:20 ` Geert Uytterhoeven
2015-12-21 14:20 ` Geert Uytterhoeven
2015-11-19 18:38 ` [PATCH 02/25] serial: sh-sci: Update DT binding documentation for BRG support Geert Uytterhoeven
2015-11-19 18:38 ` Geert Uytterhoeven
2015-11-19 18:38 ` Geert Uytterhoeven
2015-11-19 20:26 ` Laurent Pinchart
2015-11-19 20:26 ` Laurent Pinchart
2015-11-19 20:44 ` Geert Uytterhoeven
2015-11-19 20:44 ` Geert Uytterhoeven
[not found] ` <CAMuHMdWHbc1kK7MipyZ_M_C6gPyPqvC4H35eZLXQezjbQNK2Jw-JsoAwUIsXosN+BqQ9rBEUg@public.gmane.org>
2015-11-19 21:13 ` Laurent Pinchart
2015-11-19 21:13 ` Laurent Pinchart
2015-11-19 21:13 ` Laurent Pinchart
2015-11-20 7:58 ` Geert Uytterhoeven
2015-11-20 7:58 ` Geert Uytterhoeven
2015-11-19 18:38 ` [PATCH 03/25] serial: sh-sci: Drop useless check for zero sampling_rate Geert Uytterhoeven
2015-11-19 18:38 ` Geert Uytterhoeven
2015-11-19 18:38 ` [PATCH 04/25] serial: sh-sci: Grammar s/Get ... for/Get ... from/ Geert Uytterhoeven
2015-11-19 18:38 ` Geert Uytterhoeven
2015-11-19 18:38 ` [PATCH 05/25] serial: sh-sci: Drop unused frame_len parameter for sci_baud_calc_hscif() Geert Uytterhoeven
2015-11-19 18:38 ` Geert Uytterhoeven
2015-11-19 18:38 ` [PATCH 06/25] serial: sh-sci: Don't overwrite clock selection in serial_console_write() Geert Uytterhoeven
2015-11-19 18:38 ` Geert Uytterhoeven
2015-11-19 18:38 ` [PATCH 07/25] serial: sh-sci: Convert from clk_get() to devm_clk_get() Geert Uytterhoeven
2015-11-19 18:38 ` Geert Uytterhoeven
2015-11-19 20:38 ` Laurent Pinchart
2015-11-19 20:38 ` Laurent Pinchart
2015-12-10 12:30 ` Geert Uytterhoeven
2015-12-10 12:30 ` Geert Uytterhoeven
2015-12-13 19:39 ` Laurent Pinchart
2015-12-13 19:39 ` Laurent Pinchart
2015-12-14 10:34 ` Geert Uytterhoeven
2015-12-14 10:34 ` Geert Uytterhoeven
2015-12-14 15:47 ` Laurent Pinchart
2015-12-14 15:47 ` Laurent Pinchart
2015-11-19 18:38 ` [PATCH 08/25] serial: sh-sci: Make unsigned values in sci_baud_calc_hscif() unsigned Geert Uytterhoeven
2015-11-19 18:38 ` Geert Uytterhoeven
2015-11-19 20:36 ` Laurent Pinchart
2015-11-19 20:36 ` Laurent Pinchart
2015-11-19 20:49 ` Geert Uytterhoeven
2015-11-19 20:49 ` Geert Uytterhoeven
2015-11-19 18:38 ` [PATCH 09/25] serial: sh-sci: Avoid overflow in sci_baud_calc_hscif() Geert Uytterhoeven
2015-11-19 18:38 ` Geert Uytterhoeven
2015-11-19 20:37 ` Laurent Pinchart
2015-11-19 20:37 ` Laurent Pinchart
2015-11-19 20:50 ` Geert Uytterhoeven
2015-11-19 20:50 ` Geert Uytterhoeven
2015-11-19 18:38 ` [PATCH 10/25] serial: sh-sci: Improve bit rate error calculation for HSCIF Geert Uytterhoeven
2015-11-19 18:38 ` Geert Uytterhoeven
2015-11-19 18:38 ` [PATCH 11/25] serial: sh-sci: Avoid calculating the receive margin " Geert Uytterhoeven
2015-11-19 18:38 ` Geert Uytterhoeven
2015-11-19 18:38 ` [PATCH 12/25] serial: sh-sci: Merge sci_scbrr_calc() and sci_baud_calc_hscif() Geert Uytterhoeven
2015-11-19 18:38 ` Geert Uytterhoeven
2015-11-19 18:38 ` [PATCH 13/25] serial: sh-sci: Take into account sampling rate for max baud rate Geert Uytterhoeven
2015-11-19 18:38 ` Geert Uytterhoeven
2015-11-19 18:38 ` [PATCH 14/25] serial: sh-sci: Add BRG register definitions Geert Uytterhoeven
2015-11-19 18:38 ` Geert Uytterhoeven
2015-11-19 20:45 ` Laurent Pinchart
2015-11-19 20:45 ` Laurent Pinchart
2015-11-19 18:38 ` [PATCH 15/25] serial: sh-sci: Replace struct sci_port_info by type/regtype encoding Geert Uytterhoeven
2015-11-19 18:38 ` Geert Uytterhoeven
2015-11-19 18:38 ` [PATCH 16/25] serial: sh-sci: Correct SCIF type on RZ/A1H Geert Uytterhoeven
2015-11-19 18:38 ` Geert Uytterhoeven
2015-11-19 18:38 ` [PATCH 17/25] serial: sh-sci: Correct SCIF type on R-Car for BRG Geert Uytterhoeven
2015-11-19 18:38 ` Geert Uytterhoeven
2015-11-19 20:55 ` Laurent Pinchart
2015-11-19 20:55 ` Laurent Pinchart
2015-11-20 7:46 ` Geert Uytterhoeven
2015-11-20 7:46 ` Geert Uytterhoeven
2015-11-20 14:52 ` Laurent Pinchart
2015-11-20 14:52 ` Laurent Pinchart
2015-11-20 15:30 ` Geert Uytterhoeven
2015-11-20 15:30 ` Geert Uytterhoeven
2015-11-20 15:33 ` Laurent Pinchart
2015-11-20 15:33 ` Laurent Pinchart
2015-12-10 9:21 ` Geert Uytterhoeven
2015-12-10 9:21 ` Geert Uytterhoeven
2015-12-11 1:12 ` Simon Horman
2015-12-11 1:12 ` Simon Horman
2015-12-13 19:18 ` Laurent Pinchart
2015-12-13 19:18 ` Laurent Pinchart
2015-11-19 18:38 ` [PATCH 18/25] serial: sh-sci: Prepare for multiple clocks and baud rate generators Geert Uytterhoeven
2015-11-19 18:38 ` Geert Uytterhoeven
2015-11-19 21:04 ` Laurent Pinchart [this message]
2015-11-19 21:04 ` Laurent Pinchart
2015-11-20 7:52 ` Geert Uytterhoeven
2015-11-20 7:52 ` Geert Uytterhoeven
2015-11-20 14:47 ` Laurent Pinchart
2015-11-20 14:47 ` Laurent Pinchart
2015-11-20 15:17 ` Geert Uytterhoeven
2015-11-20 15:17 ` Geert Uytterhoeven
2015-11-20 15:31 ` Laurent Pinchart
2015-11-20 15:31 ` Laurent Pinchart
2015-11-19 18:38 ` [PATCH 19/25] serial: sh-sci: Add support for optional external (H)SCK input Geert Uytterhoeven
2015-11-19 18:38 ` Geert Uytterhoeven
2015-11-19 18:38 ` [PATCH 20/25] serial: sh-sci: Add support for optional BRG on (H)SCIF Geert Uytterhoeven
2015-11-19 18:38 ` Geert Uytterhoeven
2015-11-19 18:39 ` [PATCH 21/25] ARM: shmobile: r8a7791 dtsi: Add BRG support for (H)SCIF Geert Uytterhoeven
2015-11-19 18:39 ` Geert Uytterhoeven
2015-11-19 18:39 ` [PATCH 22/25] ARM: shmobile: koelsch dts: Enable SCIF_CLK frequency and pins Geert Uytterhoeven
2015-11-19 18:39 ` Geert Uytterhoeven
2015-11-19 18:39 ` [PATCH 23/25] arm64: renesas: r8a7795 dtsi: Add BRG support for (H)SCIF Geert Uytterhoeven
2015-11-19 18:39 ` Geert Uytterhoeven
2015-11-19 21:07 ` Laurent Pinchart
2015-11-19 21:07 ` Laurent Pinchart
2015-11-20 8:17 ` Geert Uytterhoeven
2015-11-20 8:17 ` Geert Uytterhoeven
2015-11-19 18:39 ` [PATCH 24/25] arm64: renesas: salvator-x dts: Enable SCIF_CLK frequency and pins Geert Uytterhoeven
2015-11-19 18:39 ` Geert Uytterhoeven
2015-11-19 18:39 ` [PATCH 25/25] sh: sh7734: Correct SCIF type for BRG Geert Uytterhoeven
2015-11-19 18:39 ` Geert Uytterhoeven
2015-11-19 21:08 ` [PATCH 00/25] serial: sh-sci: Add external clock and BRG Support Laurent Pinchart
2015-11-19 21:08 ` Laurent Pinchart
2015-11-20 8:22 ` Geert Uytterhoeven
2015-11-20 8:22 ` Geert Uytterhoeven
2015-11-20 8:58 ` Laurent Pinchart
2015-11-20 8:58 ` Laurent Pinchart
2015-11-20 9:07 ` Geert Uytterhoeven
2015-11-20 9:07 ` Geert Uytterhoeven
2015-11-20 14:50 ` Laurent Pinchart
2015-11-20 14:50 ` Laurent Pinchart
2015-11-20 15:31 ` Geert Uytterhoeven
2015-11-20 15:31 ` Geert Uytterhoeven
2015-11-20 9:09 ` Geert Uytterhoeven
2015-11-20 9:09 ` Geert Uytterhoeven
2015-12-13 6:43 ` Greg Kroah-Hartman
2015-12-13 6:43 ` Greg Kroah-Hartman
2015-12-13 9:09 ` Geert Uytterhoeven
2015-12-13 9:09 ` Geert Uytterhoeven
2015-11-24 2:43 ` Simon Horman
2015-11-24 2:43 ` Simon Horman
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=3383903.1R72kZGx62@avalon \
--to=laurent.pinchart@ideasonboard.com \
--cc=geert+renesas@glider.be \
--cc=gregkh@linuxfoundation.org \
--cc=horms@verge.net.au \
--cc=linux-kernel@vger.kernel.org \
--cc=linux-serial@vger.kernel.org \
--cc=linux-sh@vger.kernel.org \
--cc=magnus.damm@gmail.com \
--cc=ysato@users.sourceforge.jp \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.