All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH v2 0/3] add support for Allwinner R40 CAN controller
@ 2022-01-11 15:57 ` Evgeny Boger
  0 siblings, 0 replies; 14+ messages in thread
From: Evgeny Boger @ 2022-01-11 15:57 UTC (permalink / raw)
  To: Maxime Ripard, Chen-Yu Tsai, linux-arm-kernel
  Cc: Evgeny Boger, devicetree, linux-sunxi, linux-can,
	Wolfgang Grandegger, Marc Kleine-Budde, David S . Miller,
	Jeroen Hofstee, Gerhard Bertelsmann

Allwinner R40 (also known as A40i, T3, V40) has a CAN controller. The
controller is the same as in earlier A10 and A20 SoCs, but needs reset
line to be deasserted before use.

This patch series introduce new compatible for R40 CAN controller,
add support for reset line in driver and add the corresponding nodes
to the SoC .dtsi file.

The CAN IP was documented in early V40 datasheet [1]. It also fully
supported in vendor BSP. However, CAN description was removed from
more recent A40i, T3 and R40 user manuals and datasheets.
Anyway, we verified that the CAN controller is indeed there and tested
it extensively on A40i-based custom hardware [2].

[1] https://linux-sunxi.org/File:Allwinner_V40_Datasheet_V1.0.pdf
[2] https://wirenboard.com/en/product/wiren-board-7/

Changes in v2:
  - sort pinmux nodes alphabetically and mark them with omit-if-no-ref

Evgeny Boger (3):
  dt-bindings: net: can: add support for Allwinner R40 CAN controller
  can: sun4i_can: add support for R40 CAN controller
  ARM: dts: sun8i: r40: add node for CAN controller

 .../net/can/allwinner,sun4i-a10-can.yaml      | 24 ++++++++
 arch/arm/boot/dts/sun8i-r40.dtsi              | 21 +++++++
 drivers/net/can/sun4i_can.c                   | 61 ++++++++++++++++++-
 3 files changed, 105 insertions(+), 1 deletion(-)

-- 
2.25.1

^ permalink raw reply	[flat|nested] 14+ messages in thread

* [PATCH v2 0/3] add support for Allwinner R40 CAN controller
@ 2022-01-11 15:57 ` Evgeny Boger
  0 siblings, 0 replies; 14+ messages in thread
From: Evgeny Boger @ 2022-01-11 15:57 UTC (permalink / raw)
  To: Maxime Ripard, Chen-Yu Tsai, linux-arm-kernel
  Cc: Evgeny Boger, devicetree, linux-sunxi, linux-can,
	Wolfgang Grandegger, Marc Kleine-Budde, David S . Miller,
	Jeroen Hofstee, Gerhard Bertelsmann

Allwinner R40 (also known as A40i, T3, V40) has a CAN controller. The
controller is the same as in earlier A10 and A20 SoCs, but needs reset
line to be deasserted before use.

This patch series introduce new compatible for R40 CAN controller,
add support for reset line in driver and add the corresponding nodes
to the SoC .dtsi file.

The CAN IP was documented in early V40 datasheet [1]. It also fully
supported in vendor BSP. However, CAN description was removed from
more recent A40i, T3 and R40 user manuals and datasheets.
Anyway, we verified that the CAN controller is indeed there and tested
it extensively on A40i-based custom hardware [2].

[1] https://linux-sunxi.org/File:Allwinner_V40_Datasheet_V1.0.pdf
[2] https://wirenboard.com/en/product/wiren-board-7/

Changes in v2:
  - sort pinmux nodes alphabetically and mark them with omit-if-no-ref

Evgeny Boger (3):
  dt-bindings: net: can: add support for Allwinner R40 CAN controller
  can: sun4i_can: add support for R40 CAN controller
  ARM: dts: sun8i: r40: add node for CAN controller

 .../net/can/allwinner,sun4i-a10-can.yaml      | 24 ++++++++
 arch/arm/boot/dts/sun8i-r40.dtsi              | 21 +++++++
 drivers/net/can/sun4i_can.c                   | 61 ++++++++++++++++++-
 3 files changed, 105 insertions(+), 1 deletion(-)

-- 
2.25.1

_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply	[flat|nested] 14+ messages in thread

* [PATCH v2 1/3] dt-bindings: net: can: add support for Allwinner R40 CAN controller
  2022-01-11 15:57 ` Evgeny Boger
@ 2022-01-11 15:57   ` Evgeny Boger
  -1 siblings, 0 replies; 14+ messages in thread
From: Evgeny Boger @ 2022-01-11 15:57 UTC (permalink / raw)
  To: Maxime Ripard, Chen-Yu Tsai, linux-arm-kernel
  Cc: Evgeny Boger, devicetree, linux-sunxi, linux-can,
	Wolfgang Grandegger, Marc Kleine-Budde, David S . Miller,
	Jeroen Hofstee, Gerhard Bertelsmann

Allwinner R40 (also known as A40i, T3, V40) has a CAN controller. The
controller is the same as in earlier A10 and A20 SoCs, but needs reset
line to be deasserted before use.

This patch Introduces new compatible for R40 CAN controller with
required resets property.

Signed-off-by: Evgeny Boger <boger@wirenboard.com>
---
 .../net/can/allwinner,sun4i-a10-can.yaml      | 24 +++++++++++++++++++
 1 file changed, 24 insertions(+)

diff --git a/Documentation/devicetree/bindings/net/can/allwinner,sun4i-a10-can.yaml b/Documentation/devicetree/bindings/net/can/allwinner,sun4i-a10-can.yaml
index a95960ee3feb..c93fe9d3ea82 100644
--- a/Documentation/devicetree/bindings/net/can/allwinner,sun4i-a10-can.yaml
+++ b/Documentation/devicetree/bindings/net/can/allwinner,sun4i-a10-can.yaml
@@ -17,6 +17,7 @@ properties:
           - const: allwinner,sun7i-a20-can
           - const: allwinner,sun4i-a10-can
       - const: allwinner,sun4i-a10-can
+      - const: allwinner,sun8i-r40-can
 
   reg:
     maxItems: 1
@@ -27,6 +28,19 @@ properties:
   clocks:
     maxItems: 1
 
+  resets:
+    maxItems: 1
+
+if:
+  properties:
+    compatible:
+      contains:
+        const: allwinner,sun8i-r40-can
+
+then:
+  required:
+    - resets
+
 required:
   - compatible
   - reg
@@ -47,5 +61,15 @@ examples:
         interrupts = <GIC_SPI 26 IRQ_TYPE_LEVEL_HIGH>;
         clocks = <&ccu CLK_APB1_CAN>;
     };
+  - |
+    #define RST_BUS_CAN		68
+    #define CLK_BUS_CAN		91
+    can1: can@1c2bc00 {
+        compatible = "allwinner,sun8i-r40-can";
+        reg = <0x01c2bc00 0x400>;
+        interrupts = <GIC_SPI 26 IRQ_TYPE_LEVEL_HIGH>;
+        clocks = <&ccu CLK_BUS_CAN>;
+        resets = <&ccu RST_BUS_CAN>;
+    };
 
 ...
-- 
2.25.1


^ permalink raw reply related	[flat|nested] 14+ messages in thread

* [PATCH v2 1/3] dt-bindings: net: can: add support for Allwinner R40 CAN controller
@ 2022-01-11 15:57   ` Evgeny Boger
  0 siblings, 0 replies; 14+ messages in thread
From: Evgeny Boger @ 2022-01-11 15:57 UTC (permalink / raw)
  To: Maxime Ripard, Chen-Yu Tsai, linux-arm-kernel
  Cc: Evgeny Boger, devicetree, linux-sunxi, linux-can,
	Wolfgang Grandegger, Marc Kleine-Budde, David S . Miller,
	Jeroen Hofstee, Gerhard Bertelsmann

Allwinner R40 (also known as A40i, T3, V40) has a CAN controller. The
controller is the same as in earlier A10 and A20 SoCs, but needs reset
line to be deasserted before use.

This patch Introduces new compatible for R40 CAN controller with
required resets property.

Signed-off-by: Evgeny Boger <boger@wirenboard.com>
---
 .../net/can/allwinner,sun4i-a10-can.yaml      | 24 +++++++++++++++++++
 1 file changed, 24 insertions(+)

diff --git a/Documentation/devicetree/bindings/net/can/allwinner,sun4i-a10-can.yaml b/Documentation/devicetree/bindings/net/can/allwinner,sun4i-a10-can.yaml
index a95960ee3feb..c93fe9d3ea82 100644
--- a/Documentation/devicetree/bindings/net/can/allwinner,sun4i-a10-can.yaml
+++ b/Documentation/devicetree/bindings/net/can/allwinner,sun4i-a10-can.yaml
@@ -17,6 +17,7 @@ properties:
           - const: allwinner,sun7i-a20-can
           - const: allwinner,sun4i-a10-can
       - const: allwinner,sun4i-a10-can
+      - const: allwinner,sun8i-r40-can
 
   reg:
     maxItems: 1
@@ -27,6 +28,19 @@ properties:
   clocks:
     maxItems: 1
 
+  resets:
+    maxItems: 1
+
+if:
+  properties:
+    compatible:
+      contains:
+        const: allwinner,sun8i-r40-can
+
+then:
+  required:
+    - resets
+
 required:
   - compatible
   - reg
@@ -47,5 +61,15 @@ examples:
         interrupts = <GIC_SPI 26 IRQ_TYPE_LEVEL_HIGH>;
         clocks = <&ccu CLK_APB1_CAN>;
     };
+  - |
+    #define RST_BUS_CAN		68
+    #define CLK_BUS_CAN		91
+    can1: can@1c2bc00 {
+        compatible = "allwinner,sun8i-r40-can";
+        reg = <0x01c2bc00 0x400>;
+        interrupts = <GIC_SPI 26 IRQ_TYPE_LEVEL_HIGH>;
+        clocks = <&ccu CLK_BUS_CAN>;
+        resets = <&ccu RST_BUS_CAN>;
+    };
 
 ...
-- 
2.25.1


_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply related	[flat|nested] 14+ messages in thread

* [PATCH v2 2/3] can: sun4i_can: add support for R40 CAN controller
  2022-01-11 15:57 ` Evgeny Boger
@ 2022-01-11 15:57   ` Evgeny Boger
  -1 siblings, 0 replies; 14+ messages in thread
From: Evgeny Boger @ 2022-01-11 15:57 UTC (permalink / raw)
  To: Maxime Ripard, Chen-Yu Tsai, linux-arm-kernel
  Cc: Evgeny Boger, devicetree, linux-sunxi, linux-can,
	Wolfgang Grandegger, Marc Kleine-Budde, David S . Miller,
	Jeroen Hofstee, Gerhard Bertelsmann

Allwinner R40 (also known as A40i, T3, V40) has a CAN controller. The
controller is the same as in earlier A10 and A20 SoCs, but needs reset
line to be deasserted before use.

This patch adds a new compatible for R40 CAN controller. Depending
on the compatible, reset line can be requested from DT.

Signed-off-by: Evgeny Boger <boger@wirenboard.com>
---
 drivers/net/can/sun4i_can.c | 61 ++++++++++++++++++++++++++++++++++++-
 1 file changed, 60 insertions(+), 1 deletion(-)

diff --git a/drivers/net/can/sun4i_can.c b/drivers/net/can/sun4i_can.c
index 54aa7c25c4de..24a61326915e 100644
--- a/drivers/net/can/sun4i_can.c
+++ b/drivers/net/can/sun4i_can.c
@@ -61,6 +61,7 @@
 #include <linux/of.h>
 #include <linux/of_device.h>
 #include <linux/platform_device.h>
+#include <linux/reset.h>
 
 #define DRV_NAME "sun4i_can"
 
@@ -200,10 +201,20 @@
 #define SUN4I_CAN_MAX_IRQ	20
 #define SUN4I_MODE_MAX_RETRIES	100
 
+/**
+ * struct sun4ican_quirks - Differences between SoC variants.
+ *
+ * @has_reset: SoC needs reset deasserted.
+ */
+struct sun4ican_quirks {
+	bool		has_reset;
+};
+
 struct sun4ican_priv {
 	struct can_priv can;
 	void __iomem *base;
 	struct clk *clk;
+	struct reset_control *reset;
 	spinlock_t cmdreg_lock;	/* lock for concurrent cmd register writes */
 };
 
@@ -702,6 +713,13 @@ static int sun4ican_open(struct net_device *dev)
 		goto exit_irq;
 	}
 
+	/* software reset deassert */
+	err = reset_control_deassert(priv->reset);
+	if (err) {
+		netdev_err(dev, "could not deassert CAN reset\n");
+		goto exit_soft_reset;
+	}
+
 	/* turn on clocking for CAN peripheral block */
 	err = clk_prepare_enable(priv->clk);
 	if (err) {
@@ -723,6 +741,8 @@ static int sun4ican_open(struct net_device *dev)
 exit_can_start:
 	clk_disable_unprepare(priv->clk);
 exit_clock:
+	reset_control_assert(priv->reset);
+exit_soft_reset:
 	free_irq(dev->irq, dev);
 exit_irq:
 	close_candev(dev);
@@ -736,6 +756,7 @@ static int sun4ican_close(struct net_device *dev)
 	netif_stop_queue(dev);
 	sun4i_can_stop(dev);
 	clk_disable_unprepare(priv->clk);
+	reset_control_assert(priv->reset);
 
 	free_irq(dev->irq, dev);
 	close_candev(dev);
@@ -750,8 +771,27 @@ static const struct net_device_ops sun4ican_netdev_ops = {
 	.ndo_start_xmit = sun4ican_start_xmit,
 };
 
+static const struct sun4ican_quirks sun4ican_quirks_a10 = {
+	.has_reset = false,
+};
+
+static const struct sun4ican_quirks sun4ican_quirks_r40 = {
+	.has_reset = true,
+};
+
 static const struct of_device_id sun4ican_of_match[] = {
-	{.compatible = "allwinner,sun4i-a10-can"},
+	{
+		.compatible = "allwinner,sun4i-a10-can",
+		.data = &sun4ican_quirks_a10
+	},
+	{
+		.compatible = "allwinner,sun7i-a20-can",
+		.data = &sun4ican_quirks_a10
+	},
+	{
+		.compatible = "allwinner,sun8i-r40-can",
+		.data = &sun4ican_quirks_r40
+	},
 	{},
 };
 
@@ -771,10 +811,28 @@ static int sun4ican_probe(struct platform_device *pdev)
 {
 	struct device_node *np = pdev->dev.of_node;
 	struct clk *clk;
+	struct reset_control *reset = NULL;
 	void __iomem *addr;
 	int err, irq;
 	struct net_device *dev;
 	struct sun4ican_priv *priv;
+	const struct sun4ican_quirks *quirks;
+
+	quirks = of_device_get_match_data(&pdev->dev);
+	if (!quirks) {
+		dev_err(&pdev->dev, "failed to determine the quirks to use\n");
+		err = -ENODEV;
+		goto exit;
+	}
+
+	if (quirks->has_reset) {
+		reset = devm_reset_control_get_exclusive(&pdev->dev, NULL);
+		if (IS_ERR(reset)) {
+			dev_err(&pdev->dev, "unable to request reset\n");
+			err = PTR_ERR(reset);
+			goto exit;
+		}
+	}
 
 	clk = of_clk_get(np, 0);
 	if (IS_ERR(clk)) {
@@ -818,6 +876,7 @@ static int sun4ican_probe(struct platform_device *pdev)
 				       CAN_CTRLMODE_3_SAMPLES;
 	priv->base = addr;
 	priv->clk = clk;
+	priv->reset = reset;
 	spin_lock_init(&priv->cmdreg_lock);
 
 	platform_set_drvdata(pdev, dev);
-- 
2.25.1


^ permalink raw reply related	[flat|nested] 14+ messages in thread

* [PATCH v2 2/3] can: sun4i_can: add support for R40 CAN controller
@ 2022-01-11 15:57   ` Evgeny Boger
  0 siblings, 0 replies; 14+ messages in thread
From: Evgeny Boger @ 2022-01-11 15:57 UTC (permalink / raw)
  To: Maxime Ripard, Chen-Yu Tsai, linux-arm-kernel
  Cc: Evgeny Boger, devicetree, linux-sunxi, linux-can,
	Wolfgang Grandegger, Marc Kleine-Budde, David S . Miller,
	Jeroen Hofstee, Gerhard Bertelsmann

Allwinner R40 (also known as A40i, T3, V40) has a CAN controller. The
controller is the same as in earlier A10 and A20 SoCs, but needs reset
line to be deasserted before use.

This patch adds a new compatible for R40 CAN controller. Depending
on the compatible, reset line can be requested from DT.

Signed-off-by: Evgeny Boger <boger@wirenboard.com>
---
 drivers/net/can/sun4i_can.c | 61 ++++++++++++++++++++++++++++++++++++-
 1 file changed, 60 insertions(+), 1 deletion(-)

diff --git a/drivers/net/can/sun4i_can.c b/drivers/net/can/sun4i_can.c
index 54aa7c25c4de..24a61326915e 100644
--- a/drivers/net/can/sun4i_can.c
+++ b/drivers/net/can/sun4i_can.c
@@ -61,6 +61,7 @@
 #include <linux/of.h>
 #include <linux/of_device.h>
 #include <linux/platform_device.h>
+#include <linux/reset.h>
 
 #define DRV_NAME "sun4i_can"
 
@@ -200,10 +201,20 @@
 #define SUN4I_CAN_MAX_IRQ	20
 #define SUN4I_MODE_MAX_RETRIES	100
 
+/**
+ * struct sun4ican_quirks - Differences between SoC variants.
+ *
+ * @has_reset: SoC needs reset deasserted.
+ */
+struct sun4ican_quirks {
+	bool		has_reset;
+};
+
 struct sun4ican_priv {
 	struct can_priv can;
 	void __iomem *base;
 	struct clk *clk;
+	struct reset_control *reset;
 	spinlock_t cmdreg_lock;	/* lock for concurrent cmd register writes */
 };
 
@@ -702,6 +713,13 @@ static int sun4ican_open(struct net_device *dev)
 		goto exit_irq;
 	}
 
+	/* software reset deassert */
+	err = reset_control_deassert(priv->reset);
+	if (err) {
+		netdev_err(dev, "could not deassert CAN reset\n");
+		goto exit_soft_reset;
+	}
+
 	/* turn on clocking for CAN peripheral block */
 	err = clk_prepare_enable(priv->clk);
 	if (err) {
@@ -723,6 +741,8 @@ static int sun4ican_open(struct net_device *dev)
 exit_can_start:
 	clk_disable_unprepare(priv->clk);
 exit_clock:
+	reset_control_assert(priv->reset);
+exit_soft_reset:
 	free_irq(dev->irq, dev);
 exit_irq:
 	close_candev(dev);
@@ -736,6 +756,7 @@ static int sun4ican_close(struct net_device *dev)
 	netif_stop_queue(dev);
 	sun4i_can_stop(dev);
 	clk_disable_unprepare(priv->clk);
+	reset_control_assert(priv->reset);
 
 	free_irq(dev->irq, dev);
 	close_candev(dev);
@@ -750,8 +771,27 @@ static const struct net_device_ops sun4ican_netdev_ops = {
 	.ndo_start_xmit = sun4ican_start_xmit,
 };
 
+static const struct sun4ican_quirks sun4ican_quirks_a10 = {
+	.has_reset = false,
+};
+
+static const struct sun4ican_quirks sun4ican_quirks_r40 = {
+	.has_reset = true,
+};
+
 static const struct of_device_id sun4ican_of_match[] = {
-	{.compatible = "allwinner,sun4i-a10-can"},
+	{
+		.compatible = "allwinner,sun4i-a10-can",
+		.data = &sun4ican_quirks_a10
+	},
+	{
+		.compatible = "allwinner,sun7i-a20-can",
+		.data = &sun4ican_quirks_a10
+	},
+	{
+		.compatible = "allwinner,sun8i-r40-can",
+		.data = &sun4ican_quirks_r40
+	},
 	{},
 };
 
@@ -771,10 +811,28 @@ static int sun4ican_probe(struct platform_device *pdev)
 {
 	struct device_node *np = pdev->dev.of_node;
 	struct clk *clk;
+	struct reset_control *reset = NULL;
 	void __iomem *addr;
 	int err, irq;
 	struct net_device *dev;
 	struct sun4ican_priv *priv;
+	const struct sun4ican_quirks *quirks;
+
+	quirks = of_device_get_match_data(&pdev->dev);
+	if (!quirks) {
+		dev_err(&pdev->dev, "failed to determine the quirks to use\n");
+		err = -ENODEV;
+		goto exit;
+	}
+
+	if (quirks->has_reset) {
+		reset = devm_reset_control_get_exclusive(&pdev->dev, NULL);
+		if (IS_ERR(reset)) {
+			dev_err(&pdev->dev, "unable to request reset\n");
+			err = PTR_ERR(reset);
+			goto exit;
+		}
+	}
 
 	clk = of_clk_get(np, 0);
 	if (IS_ERR(clk)) {
@@ -818,6 +876,7 @@ static int sun4ican_probe(struct platform_device *pdev)
 				       CAN_CTRLMODE_3_SAMPLES;
 	priv->base = addr;
 	priv->clk = clk;
+	priv->reset = reset;
 	spin_lock_init(&priv->cmdreg_lock);
 
 	platform_set_drvdata(pdev, dev);
-- 
2.25.1


_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply related	[flat|nested] 14+ messages in thread

* [PATCH v2 3/3] ARM: dts: sun8i: r40: add node for CAN controller
  2022-01-11 15:57 ` Evgeny Boger
@ 2022-01-11 15:57   ` Evgeny Boger
  -1 siblings, 0 replies; 14+ messages in thread
From: Evgeny Boger @ 2022-01-11 15:57 UTC (permalink / raw)
  To: Maxime Ripard, Chen-Yu Tsai, linux-arm-kernel
  Cc: Evgeny Boger, devicetree, linux-sunxi, linux-can,
	Wolfgang Grandegger, Marc Kleine-Budde, David S . Miller,
	Jeroen Hofstee, Gerhard Bertelsmann

Allwinner R40 (also known as A40i, T3, V40) has a CAN controller. The
controller is the same as in earlier A10 and A20 SoCs, but needs reset
line to be deasserted before use.

This patch adds a CAN node and the corresponding pinctrl descriptions.

Signed-off-by: Evgeny Boger <boger@wirenboard.com>
---
 arch/arm/boot/dts/sun8i-r40.dtsi | 21 +++++++++++++++++++++
 1 file changed, 21 insertions(+)

diff --git a/arch/arm/boot/dts/sun8i-r40.dtsi b/arch/arm/boot/dts/sun8i-r40.dtsi
index 1d87fc0c24ee..2ba0e681a7ac 100644
--- a/arch/arm/boot/dts/sun8i-r40.dtsi
+++ b/arch/arm/boot/dts/sun8i-r40.dtsi
@@ -511,6 +511,18 @@ pio: pinctrl@1c20800 {
 			#interrupt-cells = <3>;
 			#gpio-cells = <3>;
 
+			/omit-if-no-ref/
+			can_pa_pins: can-pa-pins {
+				pins = "PA16", "PA17";
+				function = "can";
+			};
+
+			/omit-if-no-ref/
+			can_ph_pins: can-ph-pins {
+				pins = "PH20", "PH21";
+				function = "can";
+			};
+
 			clk_out_a_pin: clk-out-a-pin {
 				pins = "PI12";
 				function = "clk_out_a";
@@ -926,6 +938,15 @@ i2c3: i2c@1c2b800 {
 			#size-cells = <0>;
 		};
 
+		can0: can@1c2bc00 {
+			compatible = "allwinner,sun8i-r40-can";
+			reg = <0x01c2bc00 0x400>;
+			interrupts = <GIC_SPI 26 IRQ_TYPE_LEVEL_HIGH>;
+			clocks = <&ccu CLK_BUS_CAN>;
+			resets = <&ccu RST_BUS_CAN>;
+			status = "disabled";
+		};
+
 		i2c4: i2c@1c2c000 {
 			compatible = "allwinner,sun6i-a31-i2c";
 			reg = <0x01c2c000 0x400>;
-- 
2.25.1


^ permalink raw reply related	[flat|nested] 14+ messages in thread

* [PATCH v2 3/3] ARM: dts: sun8i: r40: add node for CAN controller
@ 2022-01-11 15:57   ` Evgeny Boger
  0 siblings, 0 replies; 14+ messages in thread
From: Evgeny Boger @ 2022-01-11 15:57 UTC (permalink / raw)
  To: Maxime Ripard, Chen-Yu Tsai, linux-arm-kernel
  Cc: Evgeny Boger, devicetree, linux-sunxi, linux-can,
	Wolfgang Grandegger, Marc Kleine-Budde, David S . Miller,
	Jeroen Hofstee, Gerhard Bertelsmann

Allwinner R40 (also known as A40i, T3, V40) has a CAN controller. The
controller is the same as in earlier A10 and A20 SoCs, but needs reset
line to be deasserted before use.

This patch adds a CAN node and the corresponding pinctrl descriptions.

Signed-off-by: Evgeny Boger <boger@wirenboard.com>
---
 arch/arm/boot/dts/sun8i-r40.dtsi | 21 +++++++++++++++++++++
 1 file changed, 21 insertions(+)

diff --git a/arch/arm/boot/dts/sun8i-r40.dtsi b/arch/arm/boot/dts/sun8i-r40.dtsi
index 1d87fc0c24ee..2ba0e681a7ac 100644
--- a/arch/arm/boot/dts/sun8i-r40.dtsi
+++ b/arch/arm/boot/dts/sun8i-r40.dtsi
@@ -511,6 +511,18 @@ pio: pinctrl@1c20800 {
 			#interrupt-cells = <3>;
 			#gpio-cells = <3>;
 
+			/omit-if-no-ref/
+			can_pa_pins: can-pa-pins {
+				pins = "PA16", "PA17";
+				function = "can";
+			};
+
+			/omit-if-no-ref/
+			can_ph_pins: can-ph-pins {
+				pins = "PH20", "PH21";
+				function = "can";
+			};
+
 			clk_out_a_pin: clk-out-a-pin {
 				pins = "PI12";
 				function = "clk_out_a";
@@ -926,6 +938,15 @@ i2c3: i2c@1c2b800 {
 			#size-cells = <0>;
 		};
 
+		can0: can@1c2bc00 {
+			compatible = "allwinner,sun8i-r40-can";
+			reg = <0x01c2bc00 0x400>;
+			interrupts = <GIC_SPI 26 IRQ_TYPE_LEVEL_HIGH>;
+			clocks = <&ccu CLK_BUS_CAN>;
+			resets = <&ccu RST_BUS_CAN>;
+			status = "disabled";
+		};
+
 		i2c4: i2c@1c2c000 {
 			compatible = "allwinner,sun6i-a31-i2c";
 			reg = <0x01c2c000 0x400>;
-- 
2.25.1


_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply related	[flat|nested] 14+ messages in thread

* Re: [PATCH v2 2/3] can: sun4i_can: add support for R40 CAN controller
  2022-01-11 15:57   ` Evgeny Boger
@ 2022-01-11 16:24     ` Andre Przywara
  -1 siblings, 0 replies; 14+ messages in thread
From: Andre Przywara @ 2022-01-11 16:24 UTC (permalink / raw)
  To: Evgeny Boger
  Cc: Maxime Ripard, Chen-Yu Tsai, linux-arm-kernel, devicetree,
	linux-sunxi, linux-can, Wolfgang Grandegger, Marc Kleine-Budde,
	David S . Miller, Jeroen Hofstee, Gerhard Bertelsmann

On Tue, 11 Jan 2022 18:57:08 +0300
Evgeny Boger <boger@wirenboard.com> wrote:

Hi,

> Allwinner R40 (also known as A40i, T3, V40) has a CAN controller. The
> controller is the same as in earlier A10 and A20 SoCs, but needs reset
> line to be deasserted before use.
> 
> This patch adds a new compatible for R40 CAN controller. Depending
> on the compatible, reset line can be requested from DT.
> 
> Signed-off-by: Evgeny Boger <boger@wirenboard.com>
> ---
>  drivers/net/can/sun4i_can.c | 61 ++++++++++++++++++++++++++++++++++++-
>  1 file changed, 60 insertions(+), 1 deletion(-)
> 
> diff --git a/drivers/net/can/sun4i_can.c b/drivers/net/can/sun4i_can.c
> index 54aa7c25c4de..24a61326915e 100644
> --- a/drivers/net/can/sun4i_can.c
> +++ b/drivers/net/can/sun4i_can.c
> @@ -61,6 +61,7 @@
>  #include <linux/of.h>
>  #include <linux/of_device.h>
>  #include <linux/platform_device.h>
> +#include <linux/reset.h>
>  
>  #define DRV_NAME "sun4i_can"
>  
> @@ -200,10 +201,20 @@
>  #define SUN4I_CAN_MAX_IRQ	20
>  #define SUN4I_MODE_MAX_RETRIES	100
>  
> +/**
> + * struct sun4ican_quirks - Differences between SoC variants.
> + *
> + * @has_reset: SoC needs reset deasserted.
> + */
> +struct sun4ican_quirks {
> +	bool		has_reset;
> +};
> +
>  struct sun4ican_priv {
>  	struct can_priv can;
>  	void __iomem *base;
>  	struct clk *clk;
> +	struct reset_control *reset;
>  	spinlock_t cmdreg_lock;	/* lock for concurrent cmd register writes */
>  };
>  
> @@ -702,6 +713,13 @@ static int sun4ican_open(struct net_device *dev)
>  		goto exit_irq;
>  	}
>  
> +	/* software reset deassert */
> +	err = reset_control_deassert(priv->reset);
> +	if (err) {
> +		netdev_err(dev, "could not deassert CAN reset\n");
> +		goto exit_soft_reset;
> +	}
> +
>  	/* turn on clocking for CAN peripheral block */
>  	err = clk_prepare_enable(priv->clk);
>  	if (err) {
> @@ -723,6 +741,8 @@ static int sun4ican_open(struct net_device *dev)
>  exit_can_start:
>  	clk_disable_unprepare(priv->clk);
>  exit_clock:
> +	reset_control_assert(priv->reset);
> +exit_soft_reset:
>  	free_irq(dev->irq, dev);
>  exit_irq:
>  	close_candev(dev);
> @@ -736,6 +756,7 @@ static int sun4ican_close(struct net_device *dev)
>  	netif_stop_queue(dev);
>  	sun4i_can_stop(dev);
>  	clk_disable_unprepare(priv->clk);
> +	reset_control_assert(priv->reset);
>  
>  	free_irq(dev->irq, dev);
>  	close_candev(dev);
> @@ -750,8 +771,27 @@ static const struct net_device_ops sun4ican_netdev_ops = {
>  	.ndo_start_xmit = sun4ican_start_xmit,
>  };
>  
> +static const struct sun4ican_quirks sun4ican_quirks_a10 = {
> +	.has_reset = false,
> +};
> +
> +static const struct sun4ican_quirks sun4ican_quirks_r40 = {
> +	.has_reset = true,
> +};
> +
>  static const struct of_device_id sun4ican_of_match[] = {
> -	{.compatible = "allwinner,sun4i-a10-can"},
> +	{
> +		.compatible = "allwinner,sun4i-a10-can",
> +		.data = &sun4ican_quirks_a10
> +	},
> +	{
> +		.compatible = "allwinner,sun7i-a20-can",
> +		.data = &sun4ican_quirks_a10
> +	},

This one looks unnecessary, the binding says that it must be paired with
the A10 fallback.
We should only add an A20 compatible match if there is really a reason,
otherwise it encourages people to produce DTs with *only* the A20
compatible (violating the binding).

Cheers,
Andre

> +	{
> +		.compatible = "allwinner,sun8i-r40-can",
> +		.data = &sun4ican_quirks_r40
> +	},
>  	{},
>  };
>  
> @@ -771,10 +811,28 @@ static int sun4ican_probe(struct platform_device *pdev)
>  {
>  	struct device_node *np = pdev->dev.of_node;
>  	struct clk *clk;
> +	struct reset_control *reset = NULL;
>  	void __iomem *addr;
>  	int err, irq;
>  	struct net_device *dev;
>  	struct sun4ican_priv *priv;
> +	const struct sun4ican_quirks *quirks;
> +
> +	quirks = of_device_get_match_data(&pdev->dev);
> +	if (!quirks) {
> +		dev_err(&pdev->dev, "failed to determine the quirks to use\n");
> +		err = -ENODEV;
> +		goto exit;
> +	}
> +
> +	if (quirks->has_reset) {
> +		reset = devm_reset_control_get_exclusive(&pdev->dev, NULL);
> +		if (IS_ERR(reset)) {
> +			dev_err(&pdev->dev, "unable to request reset\n");
> +			err = PTR_ERR(reset);
> +			goto exit;
> +		}
> +	}
>  
>  	clk = of_clk_get(np, 0);
>  	if (IS_ERR(clk)) {
> @@ -818,6 +876,7 @@ static int sun4ican_probe(struct platform_device *pdev)
>  				       CAN_CTRLMODE_3_SAMPLES;
>  	priv->base = addr;
>  	priv->clk = clk;
> +	priv->reset = reset;
>  	spin_lock_init(&priv->cmdreg_lock);
>  
>  	platform_set_drvdata(pdev, dev);


^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: [PATCH v2 2/3] can: sun4i_can: add support for R40 CAN controller
@ 2022-01-11 16:24     ` Andre Przywara
  0 siblings, 0 replies; 14+ messages in thread
From: Andre Przywara @ 2022-01-11 16:24 UTC (permalink / raw)
  To: Evgeny Boger
  Cc: Maxime Ripard, Chen-Yu Tsai, linux-arm-kernel, devicetree,
	linux-sunxi, linux-can, Wolfgang Grandegger, Marc Kleine-Budde,
	David S . Miller, Jeroen Hofstee, Gerhard Bertelsmann

On Tue, 11 Jan 2022 18:57:08 +0300
Evgeny Boger <boger@wirenboard.com> wrote:

Hi,

> Allwinner R40 (also known as A40i, T3, V40) has a CAN controller. The
> controller is the same as in earlier A10 and A20 SoCs, but needs reset
> line to be deasserted before use.
> 
> This patch adds a new compatible for R40 CAN controller. Depending
> on the compatible, reset line can be requested from DT.
> 
> Signed-off-by: Evgeny Boger <boger@wirenboard.com>
> ---
>  drivers/net/can/sun4i_can.c | 61 ++++++++++++++++++++++++++++++++++++-
>  1 file changed, 60 insertions(+), 1 deletion(-)
> 
> diff --git a/drivers/net/can/sun4i_can.c b/drivers/net/can/sun4i_can.c
> index 54aa7c25c4de..24a61326915e 100644
> --- a/drivers/net/can/sun4i_can.c
> +++ b/drivers/net/can/sun4i_can.c
> @@ -61,6 +61,7 @@
>  #include <linux/of.h>
>  #include <linux/of_device.h>
>  #include <linux/platform_device.h>
> +#include <linux/reset.h>
>  
>  #define DRV_NAME "sun4i_can"
>  
> @@ -200,10 +201,20 @@
>  #define SUN4I_CAN_MAX_IRQ	20
>  #define SUN4I_MODE_MAX_RETRIES	100
>  
> +/**
> + * struct sun4ican_quirks - Differences between SoC variants.
> + *
> + * @has_reset: SoC needs reset deasserted.
> + */
> +struct sun4ican_quirks {
> +	bool		has_reset;
> +};
> +
>  struct sun4ican_priv {
>  	struct can_priv can;
>  	void __iomem *base;
>  	struct clk *clk;
> +	struct reset_control *reset;
>  	spinlock_t cmdreg_lock;	/* lock for concurrent cmd register writes */
>  };
>  
> @@ -702,6 +713,13 @@ static int sun4ican_open(struct net_device *dev)
>  		goto exit_irq;
>  	}
>  
> +	/* software reset deassert */
> +	err = reset_control_deassert(priv->reset);
> +	if (err) {
> +		netdev_err(dev, "could not deassert CAN reset\n");
> +		goto exit_soft_reset;
> +	}
> +
>  	/* turn on clocking for CAN peripheral block */
>  	err = clk_prepare_enable(priv->clk);
>  	if (err) {
> @@ -723,6 +741,8 @@ static int sun4ican_open(struct net_device *dev)
>  exit_can_start:
>  	clk_disable_unprepare(priv->clk);
>  exit_clock:
> +	reset_control_assert(priv->reset);
> +exit_soft_reset:
>  	free_irq(dev->irq, dev);
>  exit_irq:
>  	close_candev(dev);
> @@ -736,6 +756,7 @@ static int sun4ican_close(struct net_device *dev)
>  	netif_stop_queue(dev);
>  	sun4i_can_stop(dev);
>  	clk_disable_unprepare(priv->clk);
> +	reset_control_assert(priv->reset);
>  
>  	free_irq(dev->irq, dev);
>  	close_candev(dev);
> @@ -750,8 +771,27 @@ static const struct net_device_ops sun4ican_netdev_ops = {
>  	.ndo_start_xmit = sun4ican_start_xmit,
>  };
>  
> +static const struct sun4ican_quirks sun4ican_quirks_a10 = {
> +	.has_reset = false,
> +};
> +
> +static const struct sun4ican_quirks sun4ican_quirks_r40 = {
> +	.has_reset = true,
> +};
> +
>  static const struct of_device_id sun4ican_of_match[] = {
> -	{.compatible = "allwinner,sun4i-a10-can"},
> +	{
> +		.compatible = "allwinner,sun4i-a10-can",
> +		.data = &sun4ican_quirks_a10
> +	},
> +	{
> +		.compatible = "allwinner,sun7i-a20-can",
> +		.data = &sun4ican_quirks_a10
> +	},

This one looks unnecessary, the binding says that it must be paired with
the A10 fallback.
We should only add an A20 compatible match if there is really a reason,
otherwise it encourages people to produce DTs with *only* the A20
compatible (violating the binding).

Cheers,
Andre

> +	{
> +		.compatible = "allwinner,sun8i-r40-can",
> +		.data = &sun4ican_quirks_r40
> +	},
>  	{},
>  };
>  
> @@ -771,10 +811,28 @@ static int sun4ican_probe(struct platform_device *pdev)
>  {
>  	struct device_node *np = pdev->dev.of_node;
>  	struct clk *clk;
> +	struct reset_control *reset = NULL;
>  	void __iomem *addr;
>  	int err, irq;
>  	struct net_device *dev;
>  	struct sun4ican_priv *priv;
> +	const struct sun4ican_quirks *quirks;
> +
> +	quirks = of_device_get_match_data(&pdev->dev);
> +	if (!quirks) {
> +		dev_err(&pdev->dev, "failed to determine the quirks to use\n");
> +		err = -ENODEV;
> +		goto exit;
> +	}
> +
> +	if (quirks->has_reset) {
> +		reset = devm_reset_control_get_exclusive(&pdev->dev, NULL);
> +		if (IS_ERR(reset)) {
> +			dev_err(&pdev->dev, "unable to request reset\n");
> +			err = PTR_ERR(reset);
> +			goto exit;
> +		}
> +	}
>  
>  	clk = of_clk_get(np, 0);
>  	if (IS_ERR(clk)) {
> @@ -818,6 +876,7 @@ static int sun4ican_probe(struct platform_device *pdev)
>  				       CAN_CTRLMODE_3_SAMPLES;
>  	priv->base = addr;
>  	priv->clk = clk;
> +	priv->reset = reset;
>  	spin_lock_init(&priv->cmdreg_lock);
>  
>  	platform_set_drvdata(pdev, dev);


_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: [PATCH v2 2/3] can: sun4i_can: add support for R40 CAN controller
  2022-01-11 16:24     ` Andre Przywara
@ 2022-01-11 16:58       ` Evgeny Boger
  -1 siblings, 0 replies; 14+ messages in thread
From: Evgeny Boger @ 2022-01-11 16:58 UTC (permalink / raw)
  To: Andre Przywara
  Cc: Maxime Ripard, Chen-Yu Tsai, linux-arm-kernel, devicetree,
	linux-sunxi, linux-can, Wolfgang Grandegger, Marc Kleine-Budde,
	David S . Miller, Jeroen Hofstee, Gerhard Bertelsmann

11.01.2022 19:24, Andre Przywara пишет:
> On Tue, 11 Jan 2022 18:57:08 +0300
> Evgeny Boger <boger@wirenboard.com> wrote:
>
> Hi,
>
>> Allwinner R40 (also known as A40i, T3, V40) has a CAN controller. The
>> controller is the same as in earlier A10 and A20 SoCs, but needs reset
>> line to be deasserted before use.
>>
>> This patch adds a new compatible for R40 CAN controller. Depending
>> on the compatible, reset line can be requested from DT.
>>
>> Signed-off-by: Evgeny Boger <boger@wirenboard.com>
>> ---
>>   drivers/net/can/sun4i_can.c | 61 ++++++++++++++++++++++++++++++++++++-
>>   1 file changed, 60 insertions(+), 1 deletion(-)
>>
>> diff --git a/drivers/net/can/sun4i_can.c b/drivers/net/can/sun4i_can.c
>> index 54aa7c25c4de..24a61326915e 100644
>> --- a/drivers/net/can/sun4i_can.c
>> +++ b/drivers/net/can/sun4i_can.c
>> @@ -61,6 +61,7 @@
>>   #include <linux/of.h>
>>   #include <linux/of_device.h>
>>   #include <linux/platform_device.h>
>> +#include <linux/reset.h>
>>   
>>   #define DRV_NAME "sun4i_can"
>>   
>> @@ -200,10 +201,20 @@
>>   #define SUN4I_CAN_MAX_IRQ	20
>>   #define SUN4I_MODE_MAX_RETRIES	100
>>   
>> +/**
>> + * struct sun4ican_quirks - Differences between SoC variants.
>> + *
>> + * @has_reset: SoC needs reset deasserted.
>> + */
>> +struct sun4ican_quirks {
>> +	bool		has_reset;
>> +};
>> +
>>   struct sun4ican_priv {
>>   	struct can_priv can;
>>   	void __iomem *base;
>>   	struct clk *clk;
>> +	struct reset_control *reset;
>>   	spinlock_t cmdreg_lock;	/* lock for concurrent cmd register writes */
>>   };
>>   
>> @@ -702,6 +713,13 @@ static int sun4ican_open(struct net_device *dev)
>>   		goto exit_irq;
>>   	}
>>   
>> +	/* software reset deassert */
>> +	err = reset_control_deassert(priv->reset);
>> +	if (err) {
>> +		netdev_err(dev, "could not deassert CAN reset\n");
>> +		goto exit_soft_reset;
>> +	}
>> +
>>   	/* turn on clocking for CAN peripheral block */
>>   	err = clk_prepare_enable(priv->clk);
>>   	if (err) {
>> @@ -723,6 +741,8 @@ static int sun4ican_open(struct net_device *dev)
>>   exit_can_start:
>>   	clk_disable_unprepare(priv->clk);
>>   exit_clock:
>> +	reset_control_assert(priv->reset);
>> +exit_soft_reset:
>>   	free_irq(dev->irq, dev);
>>   exit_irq:
>>   	close_candev(dev);
>> @@ -736,6 +756,7 @@ static int sun4ican_close(struct net_device *dev)
>>   	netif_stop_queue(dev);
>>   	sun4i_can_stop(dev);
>>   	clk_disable_unprepare(priv->clk);
>> +	reset_control_assert(priv->reset);
>>   
>>   	free_irq(dev->irq, dev);
>>   	close_candev(dev);
>> @@ -750,8 +771,27 @@ static const struct net_device_ops sun4ican_netdev_ops = {
>>   	.ndo_start_xmit = sun4ican_start_xmit,
>>   };
>>   
>> +static const struct sun4ican_quirks sun4ican_quirks_a10 = {
>> +	.has_reset = false,
>> +};
>> +
>> +static const struct sun4ican_quirks sun4ican_quirks_r40 = {
>> +	.has_reset = true,
>> +};
>> +
>>   static const struct of_device_id sun4ican_of_match[] = {
>> -	{.compatible = "allwinner,sun4i-a10-can"},
>> +	{
>> +		.compatible = "allwinner,sun4i-a10-can",
>> +		.data = &sun4ican_quirks_a10
>> +	},
>> +	{
>> +		.compatible = "allwinner,sun7i-a20-can",
>> +		.data = &sun4ican_quirks_a10
>> +	},
> This one looks unnecessary, the binding says that it must be paired with
> the A10 fallback.
> We should only add an A20 compatible match if there is really a reason,
> otherwise it encourages people to produce DTs with *only* the A20
> compatible (violating the binding).

Right, thank you! Since this series has been around for a couple of 
months already,
and changes in v2 are trivial, would it make sense to submit v3 right away?


> Cheers,
> Andre
>
>> +	{
>> +		.compatible = "allwinner,sun8i-r40-can",
>> +		.data = &sun4ican_quirks_r40
>> +	},
>>   	{},
>>   };
>>   
>> @@ -771,10 +811,28 @@ static int sun4ican_probe(struct platform_device *pdev)
>>   {
>>   	struct device_node *np = pdev->dev.of_node;
>>   	struct clk *clk;
>> +	struct reset_control *reset = NULL;
>>   	void __iomem *addr;
>>   	int err, irq;
>>   	struct net_device *dev;
>>   	struct sun4ican_priv *priv;
>> +	const struct sun4ican_quirks *quirks;
>> +
>> +	quirks = of_device_get_match_data(&pdev->dev);
>> +	if (!quirks) {
>> +		dev_err(&pdev->dev, "failed to determine the quirks to use\n");
>> +		err = -ENODEV;
>> +		goto exit;
>> +	}
>> +
>> +	if (quirks->has_reset) {
>> +		reset = devm_reset_control_get_exclusive(&pdev->dev, NULL);
>> +		if (IS_ERR(reset)) {
>> +			dev_err(&pdev->dev, "unable to request reset\n");
>> +			err = PTR_ERR(reset);
>> +			goto exit;
>> +		}
>> +	}
>>   
>>   	clk = of_clk_get(np, 0);
>>   	if (IS_ERR(clk)) {
>> @@ -818,6 +876,7 @@ static int sun4ican_probe(struct platform_device *pdev)
>>   				       CAN_CTRLMODE_3_SAMPLES;
>>   	priv->base = addr;
>>   	priv->clk = clk;
>> +	priv->reset = reset;
>>   	spin_lock_init(&priv->cmdreg_lock);
>>   
>>   	platform_set_drvdata(pdev, dev);


^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: [PATCH v2 2/3] can: sun4i_can: add support for R40 CAN controller
@ 2022-01-11 16:58       ` Evgeny Boger
  0 siblings, 0 replies; 14+ messages in thread
From: Evgeny Boger @ 2022-01-11 16:58 UTC (permalink / raw)
  To: Andre Przywara
  Cc: Maxime Ripard, Chen-Yu Tsai, linux-arm-kernel, devicetree,
	linux-sunxi, linux-can, Wolfgang Grandegger, Marc Kleine-Budde,
	David S . Miller, Jeroen Hofstee, Gerhard Bertelsmann

11.01.2022 19:24, Andre Przywara пишет:
> On Tue, 11 Jan 2022 18:57:08 +0300
> Evgeny Boger <boger@wirenboard.com> wrote:
>
> Hi,
>
>> Allwinner R40 (also known as A40i, T3, V40) has a CAN controller. The
>> controller is the same as in earlier A10 and A20 SoCs, but needs reset
>> line to be deasserted before use.
>>
>> This patch adds a new compatible for R40 CAN controller. Depending
>> on the compatible, reset line can be requested from DT.
>>
>> Signed-off-by: Evgeny Boger <boger@wirenboard.com>
>> ---
>>   drivers/net/can/sun4i_can.c | 61 ++++++++++++++++++++++++++++++++++++-
>>   1 file changed, 60 insertions(+), 1 deletion(-)
>>
>> diff --git a/drivers/net/can/sun4i_can.c b/drivers/net/can/sun4i_can.c
>> index 54aa7c25c4de..24a61326915e 100644
>> --- a/drivers/net/can/sun4i_can.c
>> +++ b/drivers/net/can/sun4i_can.c
>> @@ -61,6 +61,7 @@
>>   #include <linux/of.h>
>>   #include <linux/of_device.h>
>>   #include <linux/platform_device.h>
>> +#include <linux/reset.h>
>>   
>>   #define DRV_NAME "sun4i_can"
>>   
>> @@ -200,10 +201,20 @@
>>   #define SUN4I_CAN_MAX_IRQ	20
>>   #define SUN4I_MODE_MAX_RETRIES	100
>>   
>> +/**
>> + * struct sun4ican_quirks - Differences between SoC variants.
>> + *
>> + * @has_reset: SoC needs reset deasserted.
>> + */
>> +struct sun4ican_quirks {
>> +	bool		has_reset;
>> +};
>> +
>>   struct sun4ican_priv {
>>   	struct can_priv can;
>>   	void __iomem *base;
>>   	struct clk *clk;
>> +	struct reset_control *reset;
>>   	spinlock_t cmdreg_lock;	/* lock for concurrent cmd register writes */
>>   };
>>   
>> @@ -702,6 +713,13 @@ static int sun4ican_open(struct net_device *dev)
>>   		goto exit_irq;
>>   	}
>>   
>> +	/* software reset deassert */
>> +	err = reset_control_deassert(priv->reset);
>> +	if (err) {
>> +		netdev_err(dev, "could not deassert CAN reset\n");
>> +		goto exit_soft_reset;
>> +	}
>> +
>>   	/* turn on clocking for CAN peripheral block */
>>   	err = clk_prepare_enable(priv->clk);
>>   	if (err) {
>> @@ -723,6 +741,8 @@ static int sun4ican_open(struct net_device *dev)
>>   exit_can_start:
>>   	clk_disable_unprepare(priv->clk);
>>   exit_clock:
>> +	reset_control_assert(priv->reset);
>> +exit_soft_reset:
>>   	free_irq(dev->irq, dev);
>>   exit_irq:
>>   	close_candev(dev);
>> @@ -736,6 +756,7 @@ static int sun4ican_close(struct net_device *dev)
>>   	netif_stop_queue(dev);
>>   	sun4i_can_stop(dev);
>>   	clk_disable_unprepare(priv->clk);
>> +	reset_control_assert(priv->reset);
>>   
>>   	free_irq(dev->irq, dev);
>>   	close_candev(dev);
>> @@ -750,8 +771,27 @@ static const struct net_device_ops sun4ican_netdev_ops = {
>>   	.ndo_start_xmit = sun4ican_start_xmit,
>>   };
>>   
>> +static const struct sun4ican_quirks sun4ican_quirks_a10 = {
>> +	.has_reset = false,
>> +};
>> +
>> +static const struct sun4ican_quirks sun4ican_quirks_r40 = {
>> +	.has_reset = true,
>> +};
>> +
>>   static const struct of_device_id sun4ican_of_match[] = {
>> -	{.compatible = "allwinner,sun4i-a10-can"},
>> +	{
>> +		.compatible = "allwinner,sun4i-a10-can",
>> +		.data = &sun4ican_quirks_a10
>> +	},
>> +	{
>> +		.compatible = "allwinner,sun7i-a20-can",
>> +		.data = &sun4ican_quirks_a10
>> +	},
> This one looks unnecessary, the binding says that it must be paired with
> the A10 fallback.
> We should only add an A20 compatible match if there is really a reason,
> otherwise it encourages people to produce DTs with *only* the A20
> compatible (violating the binding).

Right, thank you! Since this series has been around for a couple of 
months already,
and changes in v2 are trivial, would it make sense to submit v3 right away?


> Cheers,
> Andre
>
>> +	{
>> +		.compatible = "allwinner,sun8i-r40-can",
>> +		.data = &sun4ican_quirks_r40
>> +	},
>>   	{},
>>   };
>>   
>> @@ -771,10 +811,28 @@ static int sun4ican_probe(struct platform_device *pdev)
>>   {
>>   	struct device_node *np = pdev->dev.of_node;
>>   	struct clk *clk;
>> +	struct reset_control *reset = NULL;
>>   	void __iomem *addr;
>>   	int err, irq;
>>   	struct net_device *dev;
>>   	struct sun4ican_priv *priv;
>> +	const struct sun4ican_quirks *quirks;
>> +
>> +	quirks = of_device_get_match_data(&pdev->dev);
>> +	if (!quirks) {
>> +		dev_err(&pdev->dev, "failed to determine the quirks to use\n");
>> +		err = -ENODEV;
>> +		goto exit;
>> +	}
>> +
>> +	if (quirks->has_reset) {
>> +		reset = devm_reset_control_get_exclusive(&pdev->dev, NULL);
>> +		if (IS_ERR(reset)) {
>> +			dev_err(&pdev->dev, "unable to request reset\n");
>> +			err = PTR_ERR(reset);
>> +			goto exit;
>> +		}
>> +	}
>>   
>>   	clk = of_clk_get(np, 0);
>>   	if (IS_ERR(clk)) {
>> @@ -818,6 +876,7 @@ static int sun4ican_probe(struct platform_device *pdev)
>>   				       CAN_CTRLMODE_3_SAMPLES;
>>   	priv->base = addr;
>>   	priv->clk = clk;
>> +	priv->reset = reset;
>>   	spin_lock_init(&priv->cmdreg_lock);
>>   
>>   	platform_set_drvdata(pdev, dev);


_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: [PATCH v2 0/3] add support for Allwinner R40 CAN controller
  2022-01-11 15:57 ` Evgeny Boger
@ 2022-01-12  6:51   ` Evgeny Boger
  -1 siblings, 0 replies; 14+ messages in thread
From: Evgeny Boger @ 2022-01-12  6:51 UTC (permalink / raw)
  To: Maxime Ripard, Chen-Yu Tsai, linux-arm-kernel
  Cc: devicetree, linux-sunxi, linux-can, Wolfgang Grandegger,
	Marc Kleine-Budde, David S . Miller, Jeroen Hofstee,
	Gerhard Bertelsmann

11.01.2022 18:57, Evgeny Boger пишет:
> Allwinner R40 (also known as A40i, T3, V40) has a CAN controller. The
> controller is the same as in earlier A10 and A20 SoCs, but needs reset
> line to be deasserted before use.
>
> This patch series introduce new compatible for R40 CAN controller,
> add support for reset line in driver and add the corresponding nodes
> to the SoC .dtsi file.
>
> The CAN IP was documented in early V40 datasheet [1]. It also fully
> supported in vendor BSP. However, CAN description was removed from
> more recent A40i, T3 and R40 user manuals and datasheets.
> Anyway, we verified that the CAN controller is indeed there and tested
> it extensively on A40i-based custom hardware [2].
>
> [1] https://linux-sunxi.org/File:Allwinner_V40_Datasheet_V1.0.pdf
> [2] https://wirenboard.com/en/product/wiren-board-7/
>
> Changes in v2:
>    - sort pinmux nodes alphabetically and mark them with omit-if-no-ref
>
> Evgeny Boger (3):
>    dt-bindings: net: can: add support for Allwinner R40 CAN controller
>    can: sun4i_can: add support for R40 CAN controller
>    ARM: dts: sun8i: r40: add node for CAN controller
>
>   .../net/can/allwinner,sun4i-a10-can.yaml      | 24 ++++++++
>   arch/arm/boot/dts/sun8i-r40.dtsi              | 21 +++++++
>   drivers/net/can/sun4i_can.c                   | 61 ++++++++++++++++++-
>   3 files changed, 105 insertions(+), 1 deletion(-)
>
oh, v1 is already in Linus' tree. Please ignore this series then.

I'll send patches addressing the comments soon.



^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: [PATCH v2 0/3] add support for Allwinner R40 CAN controller
@ 2022-01-12  6:51   ` Evgeny Boger
  0 siblings, 0 replies; 14+ messages in thread
From: Evgeny Boger @ 2022-01-12  6:51 UTC (permalink / raw)
  To: Maxime Ripard, Chen-Yu Tsai, linux-arm-kernel
  Cc: devicetree, linux-sunxi, linux-can, Wolfgang Grandegger,
	Marc Kleine-Budde, David S . Miller, Jeroen Hofstee,
	Gerhard Bertelsmann

11.01.2022 18:57, Evgeny Boger пишет:
> Allwinner R40 (also known as A40i, T3, V40) has a CAN controller. The
> controller is the same as in earlier A10 and A20 SoCs, but needs reset
> line to be deasserted before use.
>
> This patch series introduce new compatible for R40 CAN controller,
> add support for reset line in driver and add the corresponding nodes
> to the SoC .dtsi file.
>
> The CAN IP was documented in early V40 datasheet [1]. It also fully
> supported in vendor BSP. However, CAN description was removed from
> more recent A40i, T3 and R40 user manuals and datasheets.
> Anyway, we verified that the CAN controller is indeed there and tested
> it extensively on A40i-based custom hardware [2].
>
> [1] https://linux-sunxi.org/File:Allwinner_V40_Datasheet_V1.0.pdf
> [2] https://wirenboard.com/en/product/wiren-board-7/
>
> Changes in v2:
>    - sort pinmux nodes alphabetically and mark them with omit-if-no-ref
>
> Evgeny Boger (3):
>    dt-bindings: net: can: add support for Allwinner R40 CAN controller
>    can: sun4i_can: add support for R40 CAN controller
>    ARM: dts: sun8i: r40: add node for CAN controller
>
>   .../net/can/allwinner,sun4i-a10-can.yaml      | 24 ++++++++
>   arch/arm/boot/dts/sun8i-r40.dtsi              | 21 +++++++
>   drivers/net/can/sun4i_can.c                   | 61 ++++++++++++++++++-
>   3 files changed, 105 insertions(+), 1 deletion(-)
>
oh, v1 is already in Linus' tree. Please ignore this series then.

I'll send patches addressing the comments soon.



_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply	[flat|nested] 14+ messages in thread

end of thread, other threads:[~2022-01-12  6:52 UTC | newest]

Thread overview: 14+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2022-01-11 15:57 [PATCH v2 0/3] add support for Allwinner R40 CAN controller Evgeny Boger
2022-01-11 15:57 ` Evgeny Boger
2022-01-11 15:57 ` [PATCH v2 1/3] dt-bindings: net: can: " Evgeny Boger
2022-01-11 15:57   ` Evgeny Boger
2022-01-11 15:57 ` [PATCH v2 2/3] can: sun4i_can: add support for " Evgeny Boger
2022-01-11 15:57   ` Evgeny Boger
2022-01-11 16:24   ` Andre Przywara
2022-01-11 16:24     ` Andre Przywara
2022-01-11 16:58     ` Evgeny Boger
2022-01-11 16:58       ` Evgeny Boger
2022-01-11 15:57 ` [PATCH v2 3/3] ARM: dts: sun8i: r40: add node for " Evgeny Boger
2022-01-11 15:57   ` Evgeny Boger
2022-01-12  6:51 ` [PATCH v2 0/3] add support for Allwinner R40 " Evgeny Boger
2022-01-12  6:51   ` Evgeny Boger

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.