ARM: sunxi: SRAM mapping support
Subsystems (2)
v3 cover ARM: sunxi: SRAM mapping support
Hi,
The Allwinner SoCs all have a bunch of SRAMs (the exact number depending on the SoC itself) that can have various sections mapped to the CPU or to a bunch of devices, each section having different possible devices to be mapped to.
Since this SRAM setup is highly SoC dependent, and that we could have multiple drivers trying to map a section for their own use, relying on syscon would put to much duplicated logic to devices that are using these SRAMs, among which the USB OTG and EMAC controllers, while not guaranteeing any kind of exclusive use of that section.
To do this, we introduce a custom API to control the mapping of the sections in a SoC independent way, and a SoC driver to implement it.
Let me know what you think,
Maxime
Changes from v2:
- Changed the DT bindings to have an explicit relationship between "client" devices, the controller, and the SRAM sections it controls
- Changed the interface to not rely on private structures anymore but only the client's struct device
- Fixed a bug in the claiming logic
Maxime Ripard (4):
drivers: soc: sunxi: Introduce SoC driver to map SRAMs
ARM: dts: sun4i: Add A10 SRAM and SRAM controller
ARM: dts: sun5i: Add A10s and A13 SRAM and SRAM controller
ARM: dts: sun7i: Add A20 SRAM and SRAM controller
.../devicetree/bindings/soc/sunxi/sram.txt | 72 ++++++ arch/arm/boot/dts/sun4i-a10-a1000.dts | 4 + arch/arm/boot/dts/sun4i-a10-ba10-tvbox.dts | 4 + arch/arm/boot/dts/sun4i-a10-cubieboard.dts | 4 + arch/arm/boot/dts/sun4i-a10-hackberry.dts | 4 + arch/arm/boot/dts/sun4i-a10-jesurun-q5.dts | 4 + arch/arm/boot/dts/sun4i-a10-marsboard.dts | 4 + arch/arm/boot/dts/sun4i-a10-olinuxino-lime.dts | 4 + arch/arm/boot/dts/sun4i-a10-pcduino.dts | 4 + arch/arm/boot/dts/sun4i-a10.dtsi | 37 +++ arch/arm/boot/dts/sun5i-a10s-olinuxino-micro.dts | 4 + arch/arm/boot/dts/sun5i-a10s.dtsi | 9 + arch/arm/boot/dts/sun5i.dtsi | 30 +++ arch/arm/boot/dts/sun7i-a20.dtsi | 37 +++ drivers/soc/Kconfig | 1 + drivers/soc/Makefile | 1 + drivers/soc/sunxi/Kconfig | 10 + drivers/soc/sunxi/Makefile | 1 + drivers/soc/sunxi/sunxi_sram.c | 284 +++++++++++++++++++++ include/linux/soc/sunxi/sunxi_sram.h | 19 ++ 20 files changed, 537 insertions(+) create mode 100644 Documentation/devicetree/bindings/soc/sunxi/sram.txt create mode 100644 drivers/soc/sunxi/Kconfig create mode 100644 drivers/soc/sunxi/Makefile create mode 100644 drivers/soc/sunxi/sunxi_sram.c create mode 100644 include/linux/soc/sunxi/sunxi_sram.h
Signature · 1 line
2.4.1
PATCH v3 1/4 drivers: soc: sunxi: Introduce SoC driver to map SRAMs
The Allwinner SoCs have a handful of SRAM that can be either mapped to be accessible by devices or the CPU.
That mapping is controlled by an SRAM controller, and that mapping might not be set by the bootloader, for example if the device wasn't used at all, or if we're using solutions like the U-Boot's Falcon Boot.
We could also imagine changing this at runtime for example to change the mapping of these SRAMs to use them for suspend/resume or runtime memory rate change, if that ever happens.
These use cases require some API in the kernel to control that mapping, exported through a drivers/soc driver.
This driver also implement a debugfs file that shows the SRAM found in the system, the current mapping and the SRAM that have been claimed by some drivers in the kernel.
[hdegoede at redhat.com: Changed compat string to sun4i-a10-sram-controller, as
the sram controller is identical on sun4i, sun5i & sun7i, added devicetree binding documentation, fixed some checkpatch warnings]
--- .../devicetree/bindings/soc/sunxi/sram.txt | 72 ++++++ drivers/soc/Kconfig | 1 + drivers/soc/Makefile | 1 + drivers/soc/sunxi/Kconfig | 10 + drivers/soc/sunxi/Makefile | 1 + drivers/soc/sunxi/sunxi_sram.c | 284 +++++++++++++++++++++ include/linux/soc/sunxi/sunxi_sram.h | 19 ++ 7 files changed, 388 insertions(+) create mode 100644 Documentation/devicetree/bindings/soc/sunxi/sram.txt create mode 100644 drivers/soc/sunxi/Kconfig create mode 100644 drivers/soc/sunxi/Makefile create mode 100644 drivers/soc/sunxi/sunxi_sram.c create mode 100644 include/linux/soc/sunxi/sunxi_sram.h
Documentation/devicetree/bindings/soc/sunxi/sram.txt new file +72 -0
@@ -0,0 +1,72 @@ +Allwinnner SoC SRAM controllers +----------------------------------------------------- + +The SRAM controller found on most Allwinner devices is represented by +a regular node for the SRAM controller itself, with sub-nodes +reprensenting the SRAM handled by the SRAM controller. + +Controller Node +--------------- + +Required properties: +- compatible : "allwinner,sun4i-a10-sram-controller" +- reg : sram controller register offset + length + +SRAM nodes +---------- + +Each SRAM is described using the mmio-sram bindings documented in +Documentation/devicetree/bindings/misc/sram.txt + +Each SRAM will have SRAM sections that are going to be handled by the +SRAM controller as subnodes. These sections are represented following +once again the representation described in the mmio-sram binding. + +The valid sections compatible are: + - allwinner,sun4i-a10-sram-a3-a4 + - allwinner,sun4i-a10-sram-d + +Devices using SRAM sections +--------------------------- + +Some devices need to request to the SRAM controller to map an SRAM for +their exclusive use. + +The relationship between such a device and an SRAM section is +expressed through the allwinner,sram property, that will take a +phandle and an argument. + +This valid values for this argument are: + - 0: CPU + - 1: Device + +Example +------- +sram-controller at 01c00000 { + compatible = "allwinner,sun4i-a10-sram-controller"; + reg = <0x01c00000 0x30>; + #address-cells = <1>; + #size-cells = <1>; + ranges; + + sram_a: sram at 00000000 { + compatible = "mmio-sram"; + reg = <0x00000000 0xc000>; + #address-cells = <1>; + #size-cells = <1>; + ranges = <0 0x00000000 0xc000>; + + emac_sram: sram-section at 8000 { + compatible = "allwinner,sun4i-a10-sram-a3-a4"; + reg = <0x8000 0x4000>; + status = "disabled"; + }; + }; +}; + +emac: ethernet at 01c0b000 { + compatible = "allwinner,sun4i-a10-emac"; + ... + + allwinner,sram = <&emac_sram 1>; +};
drivers/soc/Kconfig +1 -0
@@ -2,6 +2,7 @@ menu "SOC (System On Chip) specific Drivers" source "drivers/soc/mediatek/Kconfig" source "drivers/soc/qcom/Kconfig" +source "drivers/soc/sunxi/Kconfig" source "drivers/soc/ti/Kconfig" source "drivers/soc/versatile/Kconfig"
drivers/soc/Makefile +1 -0
@@ -4,6 +4,7 @@ obj-$(CONFIG_ARCH_MEDIATEK) += mediatek/ obj-$(CONFIG_ARCH_QCOM) += qcom/ +obj-$(CONFIG_ARCH_SUNXI) += sunxi/ obj-$(CONFIG_ARCH_TEGRA) += tegra/ obj-$(CONFIG_SOC_TI) += ti/ obj-$(CONFIG_PLAT_VERSATILE) += versatile/
drivers/soc/sunxi/Kconfig new file +10 -0
@@ -0,0 +1,10 @@ +# +# Allwinner sunXi SoC drivers +# +config SUNXI_SRAM + bool + default ARCH_SUNXI + help + Say y here to enable the SRAM controller support. This + device is responsible on mapping the SRAM in the sunXi SoCs + whether to the CPU/DMA, or to the devices.
drivers/soc/sunxi/Makefile new file +1 -0
@@ -0,0 +1 @@ +obj-$(CONFIG_SUNXI_SRAM) += sunxi_sram.o
drivers/soc/sunxi/sunxi_sram.c new file +284 -0
284 lines not on this page · raw message
include/linux/soc/sunxi/sunxi_sram.h new file +19 -0
@@ -0,0 +1,19 @@ +/* +* Allwinner SoCs SRAM Controller Driver +* +* Copyright (C) 2015 Maxime Ripard +* +* Author: Maxime Ripard <[email protected]> +* +* This file is licensed under the terms of the GNU General Public +* License version 2. This program is licensed "as is" without any +* warranty of any kind, whether express or implied. +*/ + +#ifndef _SUNXI_SRAM_H_ +#define _SUNXI_SRAM_H_ + +int sunxi_sram_claim (struct device *dev); +int sunxi_sram_release (struct device *dev); + +#endif /* _SUNXI_SRAM_H_ */
Signature · 1 line
2.4.1
PATCH v3 2/4 ARM: dts: sun4i: Add A10 SRAM and SRAM controller
In reply to Maxime RipardThe A10 has a few SRAM that can be mapped either to a device or to the CPU, with the mapping being controlled by a SRAM controller.
Add the SRAM controller, the SRAM that it drives and the section that can be used by the various devices.
--- arch/arm/boot/dts/sun4i-a10-a1000.dts | 4 +++ arch/arm/boot/dts/sun4i-a10-ba10-tvbox.dts | 4 +++ arch/arm/boot/dts/sun4i-a10-cubieboard.dts | 4 +++ arch/arm/boot/dts/sun4i-a10-hackberry.dts | 4 +++ arch/arm/boot/dts/sun4i-a10-jesurun-q5.dts | 4 +++ arch/arm/boot/dts/sun4i-a10-marsboard.dts | 4 +++ arch/arm/boot/dts/sun4i-a10-olinuxino-lime.dts | 4 +++ arch/arm/boot/dts/sun4i-a10-pcduino.dts | 4 +++ arch/arm/boot/dts/sun4i-a10.dtsi | 37 ++++++++++++++++++++++++++ 9 files changed, 69 insertions(+)
arch/arm/boot/dts/sun4i-a10-a1000.dts +4 -0
@@ -108,6 +108,10 @@ status = "okay"; }; +&emac_sram { + status = "okay"; +}; + &i2c0 { pinctrl-names = "default"; pinctrl-0 = <&i2c0_pins_a>;
arch/arm/boot/dts/sun4i-a10-ba10-tvbox.dts +4 -0
@@ -74,6 +74,10 @@ status = "okay"; }; +&emac_sram { + status = "okay"; +}; + &i2c0 { pinctrl-names = "default"; pinctrl-0 = <&i2c0_pins_a>;
arch/arm/boot/dts/sun4i-a10-cubieboard.dts +4 -0
@@ -102,6 +102,10 @@ status = "okay"; }; +&emac_sram { + status = "okay"; +}; + &i2c0 { pinctrl-names = "default"; pinctrl-0 = <&i2c0_pins_a>;
arch/arm/boot/dts/sun4i-a10-hackberry.dts +4 -0
@@ -86,6 +86,10 @@ status = "okay"; }; +&emac_sram { + status = "okay"; +}; + &ir0 { pinctrl-names = "default"; pinctrl-0 = <&ir0_rx_pins_a>;
arch/arm/boot/dts/sun4i-a10-jesurun-q5.dts +4 -0
@@ -104,6 +104,10 @@ status = "okay"; }; +&emac_sram { + status = "okay"; +}; + &i2c0 { pinctrl-names = "default"; pinctrl-0 = <&i2c0_pins_a>;
arch/arm/boot/dts/sun4i-a10-marsboard.dts +4 -0
@@ -99,6 +99,10 @@ status = "okay"; }; +&emac_sram { + status = "okay"; +}; + &emac { pinctrl-names = "default"; pinctrl-0 = <&emac_pins_a>;
arch/arm/boot/dts/sun4i-a10-olinuxino-lime.dts +4 -0
@@ -105,6 +105,10 @@ status = "okay"; }; +&emac_sram { + status = "okay"; +}; + &i2c0 { pinctrl-names = "default"; pinctrl-0 = <&i2c0_pins_a>;
arch/arm/boot/dts/sun4i-a10-pcduino.dts +4 -0
@@ -119,6 +119,10 @@ status = "okay"; }; +&emac_sram { + status = "okay"; +}; + &i2c0 { pinctrl-names = "default"; pinctrl-0 = <&i2c0_pins_a>;
arch/arm/boot/dts/sun4i-a10.dtsi +37 -0
@@ -454,6 +454,42 @@ #size-cells = <1>; ranges; + sram-controller at 01c00000 { + compatible = "allwinner,sun4i-a10-sram-controller"; + reg = <0x01c00000 0x30>; + #address-cells = <1>; + #size-cells = <1>; + ranges; + + sram_a: sram at 00000000 { + compatible = "mmio-sram"; + reg = <0x00000000 0xc000>; + #address-cells = <1>; + #size-cells = <1>; + ranges = <0 0x00000000 0xc000>; + + emac_sram: sram-section at 8000 { + compatible = "allwinner,sun4i-a10-sram-a3-a4"; + reg = <0x8000 0x4000>; + status = "disabled"; + }; + }; + + sram_d: sram at 00010000 { + compatible = "mmio-sram"; + reg = <0x00010000 0x1000>; + #address-cells = <1>; + #size-cells = <1>; + ranges = <0 0x00010000 0x1000>; + + otg_sram: sram-section at 0000 { + compatible = "allwinner,sun4i-a10-sram-d"; + reg = <0x0000 0x1000>; + status = "disabled"; + }; + }; + }; + dma: dma-controller at 01c02000 { compatible = "allwinner,sun4i-a10-dma"; reg = <0x01c02000 0x1000>;
@@ -495,6 +531,7 @@ reg = <0x01c0b000 0x1000>; interrupts = <55>; clocks = <&ahb_gates 17>; + allwinner,sram = <&emac_sram 1>; status = "disabled"; };
Signature · 1 line
2.4.1
PATCH v3 3/4 ARM: dts: sun5i: Add A10s and A13 SRAM and SRAM controller
In reply to Maxime RipardThe A10s and A13 have a few SRAM that can be mapped either to a device or to the CPU, with the mapping being controlled by a SRAM controller.
Add the SRAM controller, the SRAM that it drives and the section that can be used by the various devices.
--- arch/arm/boot/dts/sun5i-a10s-olinuxino-micro.dts | 4 ++++ arch/arm/boot/dts/sun5i-a10s.dtsi | 9 +++++++ arch/arm/boot/dts/sun5i.dtsi | 30 ++++++++++++++++++++++++ 3 files changed, 43 insertions(+)
arch/arm/boot/dts/sun5i-a10s-olinuxino-micro.dts +4 -0
@@ -88,6 +88,10 @@ status = "okay"; }; +&emac_sram { + status = "okay"; +}; + &i2c0 { pinctrl-names = "default"; pinctrl-0 = <&i2c0_pins_a>;
arch/arm/boot/dts/sun5i-a10s.dtsi +9 -0
@@ -125,6 +125,7 @@ reg = <0x01c0b000 0x1000>; interrupts = <55>; clocks = <&ahb_gates 17>; + allwinner,sram = <&emac_sram 1>; status = "disabled"; };
@@ -201,3 +202,11 @@ allwinner,pull = <SUN4I_PINCTRL_NO_PULL>; }; }; + +&sram_a { + emac_sram: sram-section at 8000 { + compatible = "allwinner,sun4i-a10-sram-a3-a4"; + reg = <0x8000 0x4000>; + status = "disabled"; + }; +};
arch/arm/boot/dts/sun5i.dtsi +30 -0
@@ -299,6 +299,36 @@ #size-cells = <1>; ranges; + sram-controller at 01c00000 { + compatible = "allwinner,sun4i-a10-sram-controller"; + reg = <0x01c00000 0x30>; + #address-cells = <1>; + #size-cells = <1>; + ranges; + + sram_a: sram at 00000000 { + compatible = "mmio-sram"; + reg = <0x00000000 0xc000>; + #address-cells = <1>; + #size-cells = <1>; + ranges = <0 0x00000000 0xc000>; + }; + + sram_d: sram at 00010000 { + compatible = "mmio-sram"; + reg = <0x00010000 0x1000>; + #address-cells = <1>; + #size-cells = <1>; + ranges = <0 0x00010000 0x1000>; + + otg_sram: sram-section at 0000 { + compatible = "allwinner,sun4i-a10-sram-d"; + reg = <0x0000 0x1000>; + status = "disabled"; + }; + }; + }; + dma: dma-controller at 01c02000 { compatible = "allwinner,sun4i-a10-dma"; reg = <0x01c02000 0x1000>;
Signature · 1 line
2.4.1
PATCH v3 4/4 ARM: dts: sun7i: Add A20 SRAM and SRAM controller
In reply to Maxime RipardThe A20 has a few SRAM that can be mapped either to a device or to the CPU, with the mapping being controlled by a SRAM controller.
Add the SRAM controller, the SRAM that it drives and the section that can be used by the various devices.
--- arch/arm/boot/dts/sun7i-a20.dtsi | 37 +++++++++++++++++++++++++++++++++++++ 1 file changed, 37 insertions(+)
arch/arm/boot/dts/sun7i-a20.dtsi +37 -0
@@ -534,6 +534,42 @@ #size-cells = <1>; ranges; + sram-controller at 01c00000 { + compatible = "allwinner,sun4i-a10-sram-controller"; + reg = <0x01c00000 0x30>; + #address-cells = <1>; + #size-cells = <1>; + ranges; + + sram_a: sram at 00000000 { + compatible = "mmio-sram"; + reg = <0x00000000 0xc000>; + #address-cells = <1>; + #size-cells = <1>; + ranges = <0 0x00000000 0xc000>; + + emac_sram: sram-section at 8000 { + compatible = "allwinner,sun4i-a10-sram-a3-a4"; + reg = <0x8000 0x4000>; + status = "disabled"; + }; + }; + + sram_d: sram at 00010000 { + compatible = "mmio-sram"; + reg = <0x00010000 0x1000>; + #address-cells = <1>; + #size-cells = <1>; + ranges = <0 0x00010000 0x1000>; + + otg_sram: sram-section at 0000 { + compatible = "allwinner,sun4i-a10-sram-d"; + reg = <0x0000 0x1000>; + status = "disabled"; + }; + }; + }; + nmi_intc: interrupt-controller at 01c00030 { compatible = "allwinner,sun7i-a20-sc-nmi"; interrupt-controller;
@@ -583,6 +619,7 @@ reg = <0x01c0b000 0x1000>; interrupts = <GIC_SPI 55 IRQ_TYPE_LEVEL_HIGH>; clocks = <&ahb_gates 17>; + allwinner,sram = <&emac_sram 1>; status = "disabled"; };
Signature · 1 line
2.4.1
v3 cover ARM: sunxi: SRAM mapping support
In reply to Maxime RipardHi,
Quoted 13 lines · Maxime Ripard
Hi,
The Allwinner SoCs all have a bunch of SRAMs (the exact number depending on the SoC itself) that can have various sections mapped to the CPU or to a bunch of devices, each section having different possible devices to be mapped to.
Since this SRAM setup is highly SoC dependent, and that we could have multiple drivers trying to map a section for their own use, relying on syscon would put to much duplicated logic to devices that are using these SRAMs, among which the USB OTG and EMAC controllers, while not guaranteeing any kind of exclusive use of that section.
Quoted 4 lines
To do this, we introduce a custom API to control the mapping of the sections in a SoC independent way, and a SoC driver to implement it.
Let me know what you think,
Looks good, thanks for your work on this.
One small nitpick:
+static struct sunxi_sram_desc sun4i_a10_sram_a3_a4 = {
+ .data = SUNXI_SRAM_DATA("A3-A4", 0x4, 0x4, 1,
+ SUNXI_SRAM_MAP(0, "cpu"),
+ SUNXI_SRAM_MAP(1, "emac")),
+};
According to the A10 datasheet bits 4 and 5 control the A3-A4 mapping, with values 2 and 3 being reserved, so the first line here should be:
+ .data = SUNXI_SRAM_DATA("A3-A4", 0x4, 0x4, 2,
Other then that this looks good and is:
Regards,
Hans
Quoted 43 lines
Maxime
Changes from v2:
- Changed the DT bindings to have an explicit relationship between "client" devices, the controller, and the SRAM sections it controls
- Changed the interface to not rely on private structures anymore but only the client's struct device
- Fixed a bug in the claiming logicMaxime Ripard (4):
drivers: soc: sunxi: Introduce SoC driver to map SRAMs
ARM: dts: sun4i: Add A10 SRAM and SRAM controller
ARM: dts: sun5i: Add A10s and A13 SRAM and SRAM controller
ARM: dts: sun7i: Add A20 SRAM and SRAM controller.../devicetree/bindings/soc/sunxi/sram.txt | 72 ++++++ arch/arm/boot/dts/sun4i-a10-a1000.dts | 4 + arch/arm/boot/dts/sun4i-a10-ba10-tvbox.dts | 4 + arch/arm/boot/dts/sun4i-a10-cubieboard.dts | 4 + arch/arm/boot/dts/sun4i-a10-hackberry.dts | 4 + arch/arm/boot/dts/sun4i-a10-jesurun-q5.dts | 4 + arch/arm/boot/dts/sun4i-a10-marsboard.dts | 4 + arch/arm/boot/dts/sun4i-a10-olinuxino-lime.dts | 4 + arch/arm/boot/dts/sun4i-a10-pcduino.dts | 4 + arch/arm/boot/dts/sun4i-a10.dtsi | 37 +++ arch/arm/boot/dts/sun5i-a10s-olinuxino-micro.dts | 4 + arch/arm/boot/dts/sun5i-a10s.dtsi | 9 + arch/arm/boot/dts/sun5i.dtsi | 30 +++ arch/arm/boot/dts/sun7i-a20.dtsi | 37 +++ drivers/soc/Kconfig | 1 + drivers/soc/Makefile | 1 + drivers/soc/sunxi/Kconfig | 10 + drivers/soc/sunxi/Makefile | 1 + drivers/soc/sunxi/sunxi_sram.c | 284 +++++++++++++++++++++ include/linux/soc/sunxi/sunxi_sram.h | 19 ++ 20 files changed, 537 insertions(+)create mode 100644
Documentation/devicetree/bindings/soc/sunxi/sram.txtcreate mode 100644drivers/soc/sunxi/Kconfig
create mode 100644drivers/soc/sunxi/Makefile
create mode 100644drivers/soc/sunxi/sunxi_sram.c
create mode 100644include/linux/soc/sunxi/sunxi_sram.h