2015-12-11 22:46:00

by Marcus Weseloh

[permalink] [raw]
Subject: [PATCH v2] spi: dts: sun4i: Add support for inter-word wait cycles using the SPI Wait Clock Register

Adds support and binding documentation for a new slave device property
"sun4i,spi-word-wait-ns" that allows to set a hardware based delay
between the transmission of words using the SPI Wait Clock Register.
The SPI hardware needs 3 clock cycles to set up the delay, which makes
the minimum non-zero wait time 4 clock cycles.

Signed-off-by: Marcus Weseloh <[email protected]>
---
Changes from v1:
* renamed the property for more clarity
* wait time is set in nanoseconds instead of number of clock cycles
* transparently handle the 3 setup clock cycles

There is one review comment that I didn't address: Rob Herring suggested
that this should be in the core-binding rather than in sun4i. I checked
many of the hardware manuals of other SPI drivers and it looks to me like
this hardware based inter-word delay is a feature that not many SPI
controllers offer. And the SPI core currently has no way to control an
inter-word delay, only inter-message. So I would like to propose this again
as a sun4i binding, as it targets a sun4i (or sunxi?) specific hardware
feature.
---
.../devicetree/bindings/spi/spi-sun4i.txt | 11 +++++++++++
drivers/spi/spi-sun4i.c | 23 ++++++++++++++++++++++
2 files changed, 34 insertions(+)

diff --git a/Documentation/devicetree/bindings/spi/spi-sun4i.txt b/Documentation/devicetree/bindings/spi/spi-sun4i.txt
index de827f5..d6c55fc 100644
--- a/Documentation/devicetree/bindings/spi/spi-sun4i.txt
+++ b/Documentation/devicetree/bindings/spi/spi-sun4i.txt
@@ -10,6 +10,10 @@ Required properties:
- "mod": the parent module clock
- clock-names: Must contain the clock names described just above

+Optional properties for slave devices:
+- sun4i,spi-word-wait-ns: hardware based delay in nanoseconds between
+ transmission of words
+
Example:

spi1: spi@01c06000 {
@@ -21,4 +25,11 @@ spi1: spi@01c06000 {
status = "disabled";
#address-cells = <1>;
#size-cells = <0>;
+
+ spi1_0 {
+ compatible = "example,dummy";
+ reg = <0>;
+ spi-max-frequency = <1000000>;
+ sun4i,spi-word-wait-ns = <12000>;
+ };
};
diff --git a/drivers/spi/spi-sun4i.c b/drivers/spi/spi-sun4i.c
index f60a6d6..8cfd96c 100644
--- a/drivers/spi/spi-sun4i.c
+++ b/drivers/spi/spi-sun4i.c
@@ -19,6 +19,7 @@
#include <linux/module.h>
#include <linux/platform_device.h>
#include <linux/pm_runtime.h>
+#include <linux/of.h>

#include <linux/spi/spi.h>

@@ -173,6 +174,9 @@ static int sun4i_spi_transfer_one(struct spi_master *master,
unsigned int tx_len = 0;
int ret = 0;
u32 reg;
+ u32 wait_ns = 0;
+ int wait_clk = 0;
+ int clk_ns = 0;

/* We don't support transfer larger than the FIFO */
if (tfr->len > SUN4I_FIFO_DEPTH)
@@ -261,6 +265,25 @@ static int sun4i_spi_transfer_one(struct spi_master *master,

sun4i_spi_write(sspi, SUN4I_CLK_CTL_REG, reg);

+ /* Setup wait time beteen words */
+ of_property_read_u32(spi->dev.of_node, "sun4i,spi-word-wait-ns",
+ &wait_ns);
+ if (wait_ns) {
+ /* The wait time is set in SPI_CLK cycles. The SPI hardware
+ * needs 3 additional cycles to setup the wait counter, so
+ * the minimum delay time is 4 cycles.
+ */
+ clk_ns = DIV_ROUND_UP(1000000000, tfr->speed_hz);
+ wait_clk = DIV_ROUND_UP(wait_ns, clk_ns) - 3;
+ if (wait_clk < 1) {
+ wait_clk = 1;
+ dev_info(&spi->dev,
+ "using minimum of 4 word wait cycles (%uns)",
+ 4 * clk_ns);
+ }
+ }
+ sun4i_spi_write(sspi, SUN4I_WAIT_REG, (u16)wait_clk);
+
/* Setup the transfer now... */
if (sspi->tx_buf)
tx_len = tfr->len;
--
1.9.1


2015-12-12 09:20:20

by Priit Laes

[permalink] [raw]
Subject: Re: [linux-sunxi] [PATCH v2] spi: dts: sun4i: Add support for inter-word wait cycles using the SPI Wait Clock Register

On Fri, 2015-12-11 at 23:45 +0100, Marcus Weseloh wrote:

[...]
>
> diff --git a/Documentation/devicetree/bindings/spi/spi-sun4i.txt b/Documentation/devicetree/bindings/spi/spi-sun4i.txt
> index de827f5..d6c55fc 100644
> --- a/Documentation/devicetree/bindings/spi/spi-sun4i.txt
> +++ b/Documentation/devicetree/bindings/spi/spi-sun4i.txt
> @@ -10,6 +10,10 @@ Required properties:
>    - "mod": the parent module clock
>  - clock-names: Must contain the clock names described just above
>  
> +Optional properties for slave devices:
> +- sun4i,spi-word-wait-ns: hardware based delay in nanoseconds between
> +   transmission of words

Should be 'allwinner,spi-word-wait-ns'

Vendor prefix do come from:
Documentation/devicetree/bindings/vendor-prefixes.txt

> +
>  Example:
>  
>  spi1: spi@01c06000 {
> @@ -21,4 +25,11 @@ spi1: spi@01c06000 {
>   status = "disabled";
>   #address-cells = <1>;
>   #size-cells = <0>;
> +
> + spi1_0 {
> + compatible = "example,dummy";
> + reg = <0>;
> + spi-max-frequency = <1000000>;
> + sun4i,spi-word-wait-ns = <12000>;
> + };
>  };
> diff --git a/drivers/spi/spi-sun4i.c b/drivers/spi/spi-sun4i.c
> index f60a6d6..8cfd96c 100644
> --- a/drivers/spi/spi-sun4i.c
> +++ b/drivers/spi/spi-sun4i.c
> @@ -19,6 +19,7 @@
>  #include
>  #include
>  #include
> +#include
>  
>  #include
>  
> @@ -173,6 +174,9 @@ static int sun4i_spi_transfer_one(struct spi_master *master,
>   unsigned int tx_len = 0;
>   int ret = 0;
>   u32 reg;
> + u32 wait_ns = 0;
> + int wait_clk = 0;
> + int clk_ns = 0;
>  
>   /* We don't support transfer larger than the FIFO */
>   if (tfr->len > SUN4I_FIFO_DEPTH)
> @@ -261,6 +265,25 @@ static int sun4i_spi_transfer_one(struct spi_master *master,
>  
>   sun4i_spi_write(sspi, SUN4I_CLK_CTL_REG, reg);
>  
> + /* Setup wait time beteen words */
typo

> + of_property_read_u32(spi->dev.of_node, "sun4i,spi-word-wait-ns",
> +      &wait_ns);
> + if (wait_ns) {
> + /* The wait time is set in SPI_CLK cycles. The SPI hardware
> +  * needs 3 additional cycles to setup the wait counter, so
> +  * the minimum delay time is 4 cycles.
> +  */
> + clk_ns = DIV_ROUND_UP(1000000000, tfr->speed_hz);
> + wait_clk = DIV_ROUND_UP(wait_ns, clk_ns) - 3;
> + if (wait_clk < 1) {
> + wait_clk = 1;
> + dev_info(&spi->dev,
> +  "using minimum of 4 word wait cycles (%uns)",
> +  4 * clk_ns);
> + }
> + }
> + sun4i_spi_write(sspi, SUN4I_WAIT_REG, (u16)wait_clk);
> +
>   /* Setup the transfer now... */
>   if (sspi->tx_buf)
>   tx_len = tfr->len;
> -- 
> 1.9.1
>

2015-12-12 10:44:50

by Marcus Weseloh

[permalink] [raw]
Subject: Re: [linux-sunxi] [PATCH v2] spi: dts: sun4i: Add support for inter-word wait cycles using the SPI Wait Clock Register

2015-12-12 10:19 GMT+01:00 Priit Laes <[email protected]>:
> On Fri, 2015-12-11 at 23:45 +0100, Marcus Weseloh wrote:
> [...]
>> +- sun4i,spi-word-wait-ns: hardware based delay in nanoseconds between
>> + transmission of words
>
> Should be 'allwinner,spi-word-wait-ns'

Thanks for the review, I will change the prefix.

> [...]
>> + /* Setup wait time beteen words */
> typo

Ah, yes. I will wait for more review comments and post a v3 after that.

Cheers,

Marcus

2015-12-13 21:07:23

by Maxime Ripard

[permalink] [raw]
Subject: Re: [PATCH v2] spi: dts: sun4i: Add support for inter-word wait cycles using the SPI Wait Clock Register

Hi,

On Fri, Dec 11, 2015 at 11:45:39PM +0100, Marcus Weseloh wrote:
> Adds support and binding documentation for a new slave device property
> "sun4i,spi-word-wait-ns" that allows to set a hardware based delay
> between the transmission of words using the SPI Wait Clock Register.
> The SPI hardware needs 3 clock cycles to set up the delay, which makes
> the minimum non-zero wait time 4 clock cycles.
>
> Signed-off-by: Marcus Weseloh <[email protected]>
> ---
> Changes from v1:
> * renamed the property for more clarity
> * wait time is set in nanoseconds instead of number of clock cycles
> * transparently handle the 3 setup clock cycles
>
> There is one review comment that I didn't address: Rob Herring suggested
> that this should be in the core-binding rather than in sun4i. I checked
> many of the hardware manuals of other SPI drivers and it looks to me like
> this hardware based inter-word delay is a feature that not many SPI
> controllers offer. And the SPI core currently has no way to control an
> inter-word delay, only inter-message. So I would like to propose this again
> as a sun4i binding, as it targets a sun4i (or sunxi?) specific hardware
> feature.

Only a few of them justify to have this in the framework. There's a
bunch of controllers that support such a feature, and it definitely
belongs in the core.

The point of the framework is not to be the least common denominator,
it's about having as much code in common as possible, and it
definitely falls into that category.

Thanks,
Maxime

--
Maxime Ripard, Free Electrons
Embedded Linux, Kernel and Android engineering
http://free-electrons.com


Attachments:
(No filename) (1.60 kB)
signature.asc (819.00 B)
Digital signature
Download all attachments

2015-12-13 21:52:16

by Marcus Weseloh

[permalink] [raw]
Subject: Re: [PATCH v2] spi: dts: sun4i: Add support for inter-word wait cycles using the SPI Wait Clock Register

2015-12-13 22:07 GMT+01:00 Maxime Ripard <[email protected]>:
[...]
>> There is one review comment that I didn't address: Rob Herring suggested
>> that this should be in the core-binding rather than in sun4i. I checked
>> many of the hardware manuals of other SPI drivers and it looks to me like
>> this hardware based inter-word delay is a feature that not many SPI
>> controllers offer. And the SPI core currently has no way to control an
>> inter-word delay, only inter-message. So I would like to propose this again
>> as a sun4i binding, as it targets a sun4i (or sunxi?) specific hardware
>> feature.
>
> Only a few of them justify to have this in the framework. There's a
> bunch of controllers that support such a feature, and it definitely
> belongs in the core.
>
> The point of the framework is not to be the least common denominator,
> it's about having as much code in common as possible, and it
> definitely falls into that category.

Ok, now I understand. I did indeed think that the SPI core is more
like a least common denominator. So I will add the property to the
spi-core binding, as initially requested by Rob and send a v3.

Thanks for the review, Maxime!

Marcus

2015-12-13 23:04:48

by Marcus Weseloh

[permalink] [raw]
Subject: [PATCH v3] spi: dts: sun4i: Add support for hardware-based wait time between words

Adds a new property "spi-word-wait-ns" to the spi-bus binding that allows
SPI slave devices to set a hardware based wait time between the
transmission of words. Also modifies the sun4i SPI master driver to make
use of the new property. This specific SPI controller needs 3 clock
cycles to set up the delay, which makes the minimum non-zero wait time
on this hardware 4 clock cycles.

Signed-off-by: Marcus Weseloh <[email protected]>
---
Changes from v1:
* renamed the property for more clarity
* wait time is set in nanoseconds instead of number of clock cycles
* transparently handle the 3 setup clock cycles

Changes from v2:
* fixed typo in comment
* moved parameter to spi-bus binding, dropping the vendor prefix
* changed commit summary and description to reflect the changes
---
Documentation/devicetree/bindings/spi/spi-bus.txt | 2 ++
drivers/spi/spi-sun4i.c | 23 +++++++++++++++++++++++
2 files changed, 25 insertions(+)

diff --git a/Documentation/devicetree/bindings/spi/spi-bus.txt b/Documentation/devicetree/bindings/spi/spi-bus.txt
index bbaa857..2d6034f 100644
--- a/Documentation/devicetree/bindings/spi/spi-bus.txt
+++ b/Documentation/devicetree/bindings/spi/spi-bus.txt
@@ -61,6 +61,8 @@ contain the following properties.
used for MOSI. Defaults to 1 if not present.
- spi-rx-bus-width - (optional) The bus width(number of data wires) that
used for MISO. Defaults to 1 if not present.
+- spi-word-wait-ns - (optional) Hardware based delay between transmission of
+ words in nanoseconds

Some SPI controllers and devices support Dual and Quad SPI transfer mode.
It allows data in the SPI system to be transferred in 2 wires(DUAL) or 4 wires(QUAD).
diff --git a/drivers/spi/spi-sun4i.c b/drivers/spi/spi-sun4i.c
index f60a6d6..73995a1 100644
--- a/drivers/spi/spi-sun4i.c
+++ b/drivers/spi/spi-sun4i.c
@@ -19,6 +19,7 @@
#include <linux/module.h>
#include <linux/platform_device.h>
#include <linux/pm_runtime.h>
+#include <linux/of.h>

#include <linux/spi/spi.h>

@@ -173,6 +174,9 @@ static int sun4i_spi_transfer_one(struct spi_master *master,
unsigned int tx_len = 0;
int ret = 0;
u32 reg;
+ u32 wait_ns = 0;
+ int wait_clk = 0;
+ int clk_ns = 0;

/* We don't support transfer larger than the FIFO */
if (tfr->len > SUN4I_FIFO_DEPTH)
@@ -261,6 +265,25 @@ static int sun4i_spi_transfer_one(struct spi_master *master,

sun4i_spi_write(sspi, SUN4I_CLK_CTL_REG, reg);

+ /* Setup wait time between words */
+ of_property_read_u32(spi->dev.of_node, "spi-word-wait-ns",
+ &wait_ns);
+ if (wait_ns) {
+ /* The wait time is set in SPI_CLK cycles. The SPI hardware
+ * needs 3 additional cycles to setup the wait counter, so
+ * the minimum delay time is 4 cycles.
+ */
+ clk_ns = DIV_ROUND_UP(1000000000, tfr->speed_hz);
+ wait_clk = DIV_ROUND_UP(wait_ns, clk_ns) - 3;
+ if (wait_clk < 1) {
+ wait_clk = 1;
+ dev_info(&spi->dev,
+ "using minimum of 4 word wait cycles (%uns)",
+ 4 * clk_ns);
+ }
+ }
+ sun4i_spi_write(sspi, SUN4I_WAIT_REG, (u16)wait_clk);
+
/* Setup the transfer now... */
if (sspi->tx_buf)
tx_len = tfr->len;
--
1.9.1

2015-12-13 23:09:06

by Mark Brown

[permalink] [raw]
Subject: Re: [PATCH v3] spi: dts: sun4i: Add support for hardware-based wait time between words

On Mon, Dec 14, 2015 at 12:04:11AM +0100, Marcus Weseloh wrote:
> Adds a new property "spi-word-wait-ns" to the spi-bus binding that allows

Please don't bury patches in reply to existing serieses, it makes it
hard to follow what's going on with regard to which versions are current
and so on.


Attachments:
(No filename) (294.00 B)
signature.asc (473.00 B)
Download all attachments

2015-12-13 23:23:33

by Marcus Weseloh

[permalink] [raw]
Subject: Re: [PATCH v3] spi: dts: sun4i: Add support for hardware-based wait time between words

2015-12-14 0:08 GMT+01:00 Mark Brown <[email protected]>:
> Please don't bury patches in reply to existing serieses, it makes it
> hard to follow what's going on with regard to which versions are current
> and so on.

Thanks for the pointer, I will send patches like you ask from now on.
Should I resend the patch?

Cheers,

Marcus

2015-12-14 01:29:44

by Rob Herring (Arm)

[permalink] [raw]
Subject: Re: [PATCH v3] spi: dts: sun4i: Add support for hardware-based wait time between words

On Mon, Dec 14, 2015 at 12:04:11AM +0100, Marcus Weseloh wrote:
> Adds a new property "spi-word-wait-ns" to the spi-bus binding that allows
> SPI slave devices to set a hardware based wait time between the
> transmission of words. Also modifies the sun4i SPI master driver to make
> use of the new property. This specific SPI controller needs 3 clock
> cycles to set up the delay, which makes the minimum non-zero wait time
> on this hardware 4 clock cycles.
>
> Signed-off-by: Marcus Weseloh <[email protected]>
> ---
> Changes from v1:
> * renamed the property for more clarity
> * wait time is set in nanoseconds instead of number of clock cycles
> * transparently handle the 3 setup clock cycles
>
> Changes from v2:
> * fixed typo in comment
> * moved parameter to spi-bus binding, dropping the vendor prefix
> * changed commit summary and description to reflect the changes
> ---
> Documentation/devicetree/bindings/spi/spi-bus.txt | 2 ++
> drivers/spi/spi-sun4i.c | 23 +++++++++++++++++++++++
> 2 files changed, 25 insertions(+)
>
> diff --git a/Documentation/devicetree/bindings/spi/spi-bus.txt b/Documentation/devicetree/bindings/spi/spi-bus.txt
> index bbaa857..2d6034f 100644
> --- a/Documentation/devicetree/bindings/spi/spi-bus.txt
> +++ b/Documentation/devicetree/bindings/spi/spi-bus.txt
> @@ -61,6 +61,8 @@ contain the following properties.
> used for MOSI. Defaults to 1 if not present.
> - spi-rx-bus-width - (optional) The bus width(number of data wires) that
> used for MISO. Defaults to 1 if not present.
> +- spi-word-wait-ns - (optional) Hardware based delay between transmission of
> + words in nanoseconds

Could be a software delay if the h/w doesn't support delays.

> Some SPI controllers and devices support Dual and Quad SPI transfer mode.
> It allows data in the SPI system to be transferred in 2 wires(DUAL) or 4 wires(QUAD).
> diff --git a/drivers/spi/spi-sun4i.c b/drivers/spi/spi-sun4i.c
> index f60a6d6..73995a1 100644
> --- a/drivers/spi/spi-sun4i.c
> +++ b/drivers/spi/spi-sun4i.c
> @@ -19,6 +19,7 @@
> #include <linux/module.h>
> #include <linux/platform_device.h>
> #include <linux/pm_runtime.h>
> +#include <linux/of.h>
>
> #include <linux/spi/spi.h>
>
> @@ -173,6 +174,9 @@ static int sun4i_spi_transfer_one(struct spi_master *master,
> unsigned int tx_len = 0;
> int ret = 0;
> u32 reg;
> + u32 wait_ns = 0;
> + int wait_clk = 0;
> + int clk_ns = 0;
>
> /* We don't support transfer larger than the FIFO */
> if (tfr->len > SUN4I_FIFO_DEPTH)
> @@ -261,6 +265,25 @@ static int sun4i_spi_transfer_one(struct spi_master *master,
>
> sun4i_spi_write(sspi, SUN4I_CLK_CTL_REG, reg);
>
> + /* Setup wait time between words */
> + of_property_read_u32(spi->dev.of_node, "spi-word-wait-ns",
> + &wait_ns);

Read this in probe and save the value rather than fetching every
transfer.

> + if (wait_ns) {
> + /* The wait time is set in SPI_CLK cycles. The SPI hardware
> + * needs 3 additional cycles to setup the wait counter, so
> + * the minimum delay time is 4 cycles.
> + */
> + clk_ns = DIV_ROUND_UP(1000000000, tfr->speed_hz);
> + wait_clk = DIV_ROUND_UP(wait_ns, clk_ns) - 3;
> + if (wait_clk < 1) {
> + wait_clk = 1;
> + dev_info(&spi->dev,
> + "using minimum of 4 word wait cycles (%uns)",
> + 4 * clk_ns);
> + }
> + }
> + sun4i_spi_write(sspi, SUN4I_WAIT_REG, (u16)wait_clk);
> +
> /* Setup the transfer now... */
> if (sspi->tx_buf)
> tx_len = tfr->len;
> --
> 1.9.1
>

2015-12-14 07:31:59

by Marcus Weseloh

[permalink] [raw]
Subject: Re: [PATCH v3] spi: dts: sun4i: Add support for hardware-based wait time between words

Hi,

2015-12-14 2:29 GMT+01:00 Rob Herring <[email protected]>:
> On Mon, Dec 14, 2015 at 12:04:11AM +0100, Marcus Weseloh wrote:
>> Adds a new property "spi-word-wait-ns" to the spi-bus binding that allows
[...]
>> diff --git a/Documentation/devicetree/bindings/spi/spi-bus.txt b/Documentation/devicetree/bindings/spi/spi-bus.txt
>> index bbaa857..2d6034f 100644
>> --- a/Documentation/devicetree/bindings/spi/spi-bus.txt
>> +++ b/Documentation/devicetree/bindings/spi/spi-bus.txt
>> @@ -61,6 +61,8 @@ contain the following properties.
>> used for MOSI. Defaults to 1 if not present.
>> - spi-rx-bus-width - (optional) The bus width(number of data wires) that
>> used for MISO. Defaults to 1 if not present.
>> +- spi-word-wait-ns - (optional) Hardware based delay between transmission of
>> + words in nanoseconds
>
> Could be a software delay if the h/w doesn't support delays.

Of course, I was still trapped in my sun4i specific thinking. Will
remove the hardware reference.

[...]
>> + /* Setup wait time between words */
>> + of_property_read_u32(spi->dev.of_node, "spi-word-wait-ns",
>> + &wait_ns);
>
> Read this in probe and save the value rather than fetching every
> transfer.

But this is a slave property I'm using here. If I read and store it in
probe in the spi-sun4i driver, I won't have access to the slave node
property, will I?

Cheers,

Marcus

2015-12-14 08:08:13

by Marcus Weseloh

[permalink] [raw]
Subject: Re: [PATCH v3] spi: dts: sun4i: Add support for hardware-based wait time between words

2015-12-14 8:31 GMT+01:00 Marcus Weseloh <[email protected]>:
> [...]
>>> + /* Setup wait time between words */
>>> + of_property_read_u32(spi->dev.of_node, "spi-word-wait-ns",
>>> + &wait_ns);
>>
>> Read this in probe and save the value rather than fetching every
>> transfer.
>
> But this is a slave property I'm using here. If I read and store it in
> probe in the spi-sun4i driver, I won't have access to the slave node
> property, will I?

Sorry, I think I get it now. I would need to read the value in SPI
core, when the slave device gets probed. I will send an updated patch.

Thanks,

Marcus

2015-12-14 10:58:17

by Mark Brown

[permalink] [raw]
Subject: Re: [PATCH v3] spi: dts: sun4i: Add support for hardware-based wait time between words

On Mon, Dec 14, 2015 at 12:23:29AM +0100, Marcus Weseloh wrote:

> Should I resend the patch?

No, it's OK.


Attachments:
(No filename) (108.00 B)
signature.asc (473.00 B)
Download all attachments