Devicetree
 help / color / mirror / Atom feed
* Re: [PATCH 1/1] ARM: Exynos: Add generic compatible string
From: Arnd Bergmann @ 2014-02-20 17:00 UTC (permalink / raw)
  To: Tomasz Figa
  Cc: Sachin Kamat, linux-samsung-soc, Kukjin Kim,
	linux-arm-kernel@lists.infradead.org, Olof Johansson,
	devicetree@vger.kernel.org, Rob Herring, Mark Rutland,
	Grant Likely, Ian Campbell
In-Reply-To: <5306168F.1080400@samsung.com>

On Thursday 20 February 2014, Tomasz Figa wrote:
> On 20.02.2014 05:14, Sachin Kamat wrote:
> > Hi Tomasz,
> >
> > On 19 February 2014 18:15, Tomasz Figa <t.figa@samsung.com> wrote:
> >> Hi Sachin,
> >>
> >> [adding linux-arm-kernel ML to CC list]
> >>
> >>
> >> On 19.02.2014 12:34, Sachin Kamat wrote:
> >>>
> >>> To avoid modifying the kernel every time a new SoC variant
> >>> comes out.
> > <snip>
> >>
> >> Since all Exynos chips can be easily recognized using dedicated chip ID
> >> register, I wonder whether we really need to maintain two distinct board
> >> files for Exynos 4 and 5 series, especially when both of them are doing
> >> mostly the same set up, which can be simply generalized to cover all the
> >> cases.
> >>
> >> Instead of adding just another level of artificially fine grained compatible
> >> strings, I'd rather suggest merging both board files together and adding a
> >> single compatible string identifying all SoCs that can be further
> >> differentiated by using hardware chip ID register.
> >>
> >> What do you think?
> >
> > I agree with your idea of merging both the files as there is very little that is
> > different for now. However I am not really sure if having a single compatible
> > string for all SoCs would be good. What is achieved through compatible string
> > can very well be done using chip ID too. But wouldn't we need to maintain some
> > unique identity for the SoCs in human readable form at the DT level?
> 
> Well, my understanding of Device Tree is that it should provide the 
> information that can't be automatically retrieved from the hardware, not 
> more.
> 
> If you have a PCI or USB bus with enumerable devices, you don't list 
> them in DT, but instead limit the description to just the host 
> controller, if it can't be enumerated.
> 
> Same goes for compatible string. My interpretation of it is that if you 
> can identify the hardware by some automatic means, e.g. querying some ID 
> register, then the compatible should be specific enough to identify the 
> class of devices with the same method of querying such register, with no 
> need for any additional redundant data in DT.

There are some limitations to that, and you also have to apply common
sense and taste. In theory you could argue that a compatible string can
identify a board uniquely the same way that a board number did, and
everything else is implied by that. Clearly that's not what we want.
On the other end of the scale, you could eliminate a lot of compatible
strings if you describe each register or each bit in some cases in
DT properties, and that would be just as wrong.

> Of course nothing stops you from retaining more specific compatible 
> strings. In fact, this is probably the most appropriate solution, 
> because in future you might find out that certain SoCs need some special 
> differentiation, e.g. same ID value on two SoCs.
> 
> So, to apply this to our case, our Exynos 5250 based Arndale board would 
> be changed from
> 
> compatible = "insignal,arndale", "samsung,exynos5260";
> 
> to
> 
> compatible = "insignal,arndale", "samsung,exynos5260", "samsung,exynos";

Right, this would make sense.

> Now, the board file will be able to match simply by "samsung,exynos" 
> compatible string and SoC-specific code in mach-exynos (hopefully none 
> after it gets cleaned up fully) will use soc_is_exynos*() macros (what 
> AFAIK it is already doing at the moment).

On principle, I would not take things out of the match list, if that
would break booting with old DT file that don't list "samsung,exynos"
as compatible. But for new SoCs that would work.

Using soc_is_exynos*() too much of course also isn't good. A lot of
the things tested for should probably be checked from individual DT
properties, but again we have to find the right balance. I wouldn't
mind getting rid of the soc_is_exynos*() macros completely, because
a) we can't use them in device drivers
b) all platform code is supposed to be in drivers
c) both rules are enforced for arm64

> Another benefit of this would be increased safety, because you are 
> reading SoC type from actual hardware, not from externally supplied 
> data. In conjunction with the more specific compatible string (e.g. 
> "samsung,exynos5260") some validation could be performed at boot-up time 
> to make sure that DT for correct SoC is used.

I don't think that's necessary. If you get that part wrong, normally
all your hopes are lost with the rest of the information in DT. ;-)

	Arnd

^ permalink raw reply

* Re: [PATCH 2/2] ARM: dts: OMAP3+: add clock nodes for CPU
From: Tero Kristo @ 2014-02-20 16:57 UTC (permalink / raw)
  To: Nishanth Menon, Benoît Cousson, Tony Lindgren,
	Mike Turquette
  Cc: linux-omap, devicetree, linux-arm-kernel, linux-kernel
In-Reply-To: <1391019557-22313-3-git-send-email-nm@ti.com>

On 01/29/2014 08:19 PM, Nishanth Menon wrote:
> OMAP34xx, AM3517 and OMAP36xx platforms use dpll1 clock.
>
> OMAP443x, OMAP446x, OMAP447x, OMAP5, DRA7, AM43xx platforms use
> dpll_mpu clock.
>
> Latency used is the generic latency defined in omap-cpufreq
> driver.
>
> Signed-off-by: Nishanth Menon <nm@ti.com>

Looks good to me.

Acked-by: Tero Kristo <t-kristo@ti.com>

> ---
>   arch/arm/boot/dts/am33xx.dtsi |    4 ++++
>   arch/arm/boot/dts/am4372.dtsi |    5 +++++
>   arch/arm/boot/dts/dra7.dtsi   |    5 +++++
>   arch/arm/boot/dts/omap3.dtsi  |    5 +++++
>   arch/arm/boot/dts/omap4.dtsi  |    5 +++++
>   arch/arm/boot/dts/omap5.dtsi  |    6 ++++++
>   6 files changed, 30 insertions(+)
>
> diff --git a/arch/arm/boot/dts/am33xx.dtsi b/arch/arm/boot/dts/am33xx.dtsi
> index 6d95d3d..4bbba26 100644
> --- a/arch/arm/boot/dts/am33xx.dtsi
> +++ b/arch/arm/boot/dts/am33xx.dtsi
> @@ -58,6 +58,10 @@
>   				275000  1125000
>   			>;
>   			voltage-tolerance = <2>; /* 2 percentage */
> +
> +			clocks = <&dpll_mpu_ck>;
> +			clock-names = "cpu";
> +
>   			clock-latency = <300000>; /* From omap-cpufreq driver */
>   		};
>   	};
> diff --git a/arch/arm/boot/dts/am4372.dtsi b/arch/arm/boot/dts/am4372.dtsi
> index c6bd4d9..33798d9 100644
> --- a/arch/arm/boot/dts/am4372.dtsi
> +++ b/arch/arm/boot/dts/am4372.dtsi
> @@ -33,6 +33,11 @@
>   			compatible = "arm,cortex-a9";
>   			device_type = "cpu";
>   			reg = <0>;
> +
> +			clocks = <&dpll_mpu_ck>;
> +			clock-names = "cpu";
> +
> +			clock-latency = <300000>; /* From omap-cpufreq driver */
>   		};
>   	};
>
> diff --git a/arch/arm/boot/dts/dra7.dtsi b/arch/arm/boot/dts/dra7.dtsi
> index 1fd75aa..ce591e5 100644
> --- a/arch/arm/boot/dts/dra7.dtsi
> +++ b/arch/arm/boot/dts/dra7.dtsi
> @@ -47,6 +47,11 @@
>   				1000000	1060000
>   				1176000	1160000
>   				>;
> +
> +			clocks = <&dpll_mpu_ck>;
> +			clock-names = "cpu";
> +
> +			clock-latency = <300000>; /* From omap-cpufreq driver */
>   		};
>   		cpu@1 {
>   			device_type = "cpu";
> diff --git a/arch/arm/boot/dts/omap3.dtsi b/arch/arm/boot/dts/omap3.dtsi
> index a5fc83b..01f2b3b 100644
> --- a/arch/arm/boot/dts/omap3.dtsi
> +++ b/arch/arm/boot/dts/omap3.dtsi
> @@ -35,6 +35,11 @@
>   			compatible = "arm,cortex-a8";
>   			device_type = "cpu";
>   			reg = <0x0>;
> +
> +			clocks = <&dpll1_ck>;
> +			clock-names = "cpu";
> +
> +			clock-latency = <300000>; /* From omap-cpufreq driver */
>   		};
>   	};
>
> diff --git a/arch/arm/boot/dts/omap4.dtsi b/arch/arm/boot/dts/omap4.dtsi
> index d3f8a6e..ce87996 100644
> --- a/arch/arm/boot/dts/omap4.dtsi
> +++ b/arch/arm/boot/dts/omap4.dtsi
> @@ -36,6 +36,11 @@
>   			device_type = "cpu";
>   			next-level-cache = <&L2>;
>   			reg = <0x0>;
> +
> +			clocks = <&dpll_mpu_ck>;
> +			clock-names = "cpu";
> +
> +			clock-latency = <300000>; /* From omap-cpufreq driver */
>   		};
>   		cpu@1 {
>   			compatible = "arm,cortex-a9";
> diff --git a/arch/arm/boot/dts/omap5.dtsi b/arch/arm/boot/dts/omap5.dtsi
> index a72813a..8bb4134 100644
> --- a/arch/arm/boot/dts/omap5.dtsi
> +++ b/arch/arm/boot/dts/omap5.dtsi
> @@ -49,6 +49,12 @@
>   				1000000 1060000
>   				1500000 1250000
>   			>;
> +
> +			clocks = <&dpll_mpu_ck>;
> +			clock-names = "cpu";
> +
> +			clock-latency = <300000>; /* From omap-cpufreq driver */
> +
>   			/* cooling options */
>   			cooling-min-level = <0>;
>   			cooling-max-level = <2>;
>

^ permalink raw reply

* [PATCH RESEND] ARM: dts: qcom-msm8960-cdp: Add RNG device tree node
From: Stanimir Varbanov @ 2014-02-20 16:49 UTC (permalink / raw)
  To: devicetree, linux-arm-kernel, linux-arm-msm
  Cc: Kumar Gala, Mark Rutland, Rob Herring, Pawel Moll, Ian Campbell,
	David Brown, Stephen Boyd, Stanimir Varbanov

Add the necessary DT node to probe the rng driver on
msm8960-cdp platform.

Signed-off-by: Stanimir Varbanov <svarbanov@mm-sol.com>
Tested-by: Stephen Boyd <sboyd@codeaurora.org>
---
 arch/arm/boot/dts/qcom-msm8960-cdp.dts | 7 +++++++
 1 file changed, 7 insertions(+)

diff --git a/arch/arm/boot/dts/qcom-msm8960-cdp.dts b/arch/arm/boot/dts/qcom-msm8960-cdp.dts
index 7c30de4fa302..8fda9c90ba97 100644
--- a/arch/arm/boot/dts/qcom-msm8960-cdp.dts
+++ b/arch/arm/boot/dts/qcom-msm8960-cdp.dts
@@ -67,4 +67,11 @@
 		reg = <0x500000 0x1000>;
 		qcom,controller-type = "pmic-arbiter";
 	};
+
+	rng@1a500000 {
+		compatible = "qcom,prng";
+		reg = <0x1a500000 0x200>;
+		clocks = <&gcc PRNG_CLK>;
+		clock-names = "core";
+	};
 };
-- 
1.8.4.4

^ permalink raw reply related

* [PATCH RESEND] ARM: dts: qcom-msm8974: Add RNG device tree node
From: Stanimir Varbanov @ 2014-02-20 16:48 UTC (permalink / raw)
  To: devicetree, linux-arm-kernel, linux-arm-msm
  Cc: Kumar Gala, Mark Rutland, Rob Herring, Pawel Moll, Ian Campbell,
	David Brown, Stephen Boyd, Stanimir Varbanov

Add the necessary DT node to probe the rng driver on
msm8974 platforms.

Signed-off-by: Stanimir Varbanov <svarbanov@mm-sol.com>
Acked-by: Stephen Boyd <sboyd@codeaurora.org>
---
 arch/arm/boot/dts/qcom-msm8974.dtsi | 7 +++++++
 1 file changed, 7 insertions(+)

diff --git a/arch/arm/boot/dts/qcom-msm8974.dtsi b/arch/arm/boot/dts/qcom-msm8974.dtsi
index 9e5dadb101eb..ada0e8216c22 100644
--- a/arch/arm/boot/dts/qcom-msm8974.dtsi
+++ b/arch/arm/boot/dts/qcom-msm8974.dtsi
@@ -117,5 +117,12 @@
 			clocks = <&gcc GCC_BLSP1_UART2_APPS_CLK>, <&gcc GCC_BLSP1_AHB_CLK>;
 			clock-names = "core", "iface";
 		};
+
+		rng@f9bff000 {
+			compatible = "qcom,prng";
+			reg = <0xf9bff000 0x200>;
+			clocks = <&gcc GCC_PRNG_AHB_CLK>;
+			clock-names = "core";
+		};
 	};
 };
-- 
1.8.4.4

^ permalink raw reply related

* Re: [PATCH 1/2] clk: ti: am335x: remove unecessary cpu0 clk node
From: Tero Kristo @ 2014-02-20 16:43 UTC (permalink / raw)
  To: Nishanth Menon, Benoît Cousson, Tony Lindgren,
	Mike Turquette
  Cc: linux-omap, devicetree, linux-arm-kernel, linux-kernel
In-Reply-To: <1391019557-22313-2-git-send-email-nm@ti.com>

On 01/29/2014 08:19 PM, Nishanth Menon wrote:
> cpu0 clock node has no functionality, since cpufreq-cpu0 is already
> capable of picking up the clock from dts.
>
> Signed-off-by: Nishanth Menon <nm@ti.com>

Acked-by: Tero Kristo <t-kristo@ti.com>

> ---
>   drivers/clk/ti/clk-33xx.c |    1 -
>   1 file changed, 1 deletion(-)
>
> diff --git a/drivers/clk/ti/clk-33xx.c b/drivers/clk/ti/clk-33xx.c
> index 776ee45..028b337 100644
> --- a/drivers/clk/ti/clk-33xx.c
> +++ b/drivers/clk/ti/clk-33xx.c
> @@ -34,7 +34,6 @@ static struct ti_dt_clk am33xx_clks[] = {
>   	DT_CLK(NULL, "dpll_core_m5_ck", "dpll_core_m5_ck"),
>   	DT_CLK(NULL, "dpll_core_m6_ck", "dpll_core_m6_ck"),
>   	DT_CLK(NULL, "dpll_mpu_ck", "dpll_mpu_ck"),
> -	DT_CLK("cpu0", NULL, "dpll_mpu_ck"),
>   	DT_CLK(NULL, "dpll_mpu_m2_ck", "dpll_mpu_m2_ck"),
>   	DT_CLK(NULL, "dpll_ddr_ck", "dpll_ddr_ck"),
>   	DT_CLK(NULL, "dpll_ddr_m2_ck", "dpll_ddr_m2_ck"),
>

^ permalink raw reply

* Re: [PATCH 3/4] ARM: dts: OMAP5: Add device nodes for ABB
From: Nishanth Menon @ 2014-02-20 16:36 UTC (permalink / raw)
  To: Benoît Cousson, Tony Lindgren
  Cc: devicetree, linux-arm-kernel, linux-kernel, linux-omap,
	Andrii.Tseglytskyi, Nishanth Menon
In-Reply-To: <1391039177-25284-4-git-send-email-nm@ti.com>

On 01/29/2014 05:46 PM, Nishanth Menon wrote:
> From: "Andrii.Tseglytskyi" <andrii.tseglytskyi@ti.com>
> 
> Add ABB device nodes for OMAP5 family of devices. Data is based on
> OMAP543x Technical Reference Manual revision U (April 2013).
> NOTE: clock node has been disabled in this patch due to the lack of
> OMAP5 clock data.
> 
> [nm@ti.com: co-developer]
> Signed-off-by: Nishanth Menon <nm@ti.com>
> Signed-off-by: Andrii.Tseglytskyi <andrii.tseglytskyi@ti.com>
> ---

I have been informed that there is an fix in TI official documentation
which is due end of this month. So, I have to drop this patch from the
series for the time being - I will refresh this along with necessary
OMAP5 updates once the official documentation is available.

>  arch/arm/boot/dts/omap5.dtsi |   63 ++++++++++++++++++++++++++++++++++++++++++
>  1 file changed, 63 insertions(+)
> 
> diff --git a/arch/arm/boot/dts/omap5.dtsi b/arch/arm/boot/dts/omap5.dtsi
> index a72813a..6159f20 100644
> --- a/arch/arm/boot/dts/omap5.dtsi
> +++ b/arch/arm/boot/dts/omap5.dtsi
> @@ -801,6 +801,69 @@
>  
>  			#thermal-sensor-cells = <1>;
>  		};
> +
> +		abb_mpu: regulator-abb-mpu {
> +			compatible = "ti,abb-v2";
> +			regulator-name = "abb_mpu";
> +			#address-cells = <0>;
> +			#size-cells = <0>;
> +			clocks = <&sys_clkin>;
> +			ti,settling-time = <50>;
> +			ti,clock-cycles = <16>;
> +
> +			reg = <0x4ae07cdc 0x8>, <0x4ae06014 0x4>,
> +			      <0x4a0021ac 0x18>, <0x4ae0C318 0x4>;
> +			reg-names = "base-address", "int-address",
> +				    "efuse-address", "ldo-address";
> +			ti,tranxdone-status-mask = <0x80>;
> +			/* LDOVBBMPU_MUX_CTRL */
> +			ti,ldovbb-override-mask = <0x400>;
> +			/* LDOVBBMPU_VSET_OUT */
> +			ti,ldovbb-vset-mask = <0x1F>;
> +
> +			/*
> +			 * NOTE: only FBB mode used but actual vset will
> +			 * determine final biasing
> +			 */
> +			ti,abb_info = <
> +			/*uV		ABB	efuse	rbb_m fbb_m	vset_m*/
> +			880000		0	0x4	0 0x20000000 0x1F000000
> +			1060000		0	0x8	0 0x20000000 0x1F000000
> +			1250000		0	0x10	0 0x20000000 0x1F000000
> +			1260000		1	0x14	0 0x20000000 0x1F000000
> +			>;
> +		};
> +
> +		abb_mm: regulator-abb-mm {
> +			compatible = "ti,abb-v2";
> +			regulator-name = "abb_mm";
> +			#address-cells = <0>;
> +			#size-cells = <0>;
> +			clocks = <&sys_clkin>;
> +			ti,settling-time = <50>;
> +			ti,clock-cycles = <16>;
> +
> +			reg = <0x4ae07ce4 0x8>, <0x4ae06010 0x4>,
> +			      <0x4a002194 0x14>, <0x4ae0C314 0x4>;
> +			reg-names = "base-address", "int-address",
> +				    "efuse-address", "ldo-address";
> +			ti,tranxdone-status-mask = <0x80000000>;
> +			/* LDOVBBMM_MUX_CTRL */
> +			ti,ldovbb-override-mask = <0x400>;
> +			/* LDOVBBMM_VSET_OUT */
> +			ti,ldovbb-vset-mask = <0x1F>;
> +
> +			/*
> +			 * NOTE: only FBB mode used but actual vset will
> +			 * determine final biasing
> +			 */
> +			ti,abb_info = <
> +			/*uV		ABB	efuse	rbb_m fbb_m	vset_m*/
> +			880000		0	0x4	0 0x20000000 0x1F000000
> +			1025000		0	0x8	0 0x20000000 0x1F000000
> +			1120000		1	0x10	0 0x20000000 0x1F000000
> +			>;
> +		};
>  	};
>  };
>  
> 


-- 
Regards,
Nishanth Menon

^ permalink raw reply

* Re: [PATCH 2/2] arm/xen: Don't use xen DMA ops when the device is protected by an IOMMU
From: Ian Campbell @ 2014-02-20 16:35 UTC (permalink / raw)
  To: Julien Grall
  Cc: linux-kernel-u79uwXL29TY76Z2rM5mHXA,
	stefano.stabellini-mvvWK6WmYclDPfheJLI6IQ,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r,
	xen-devel-GuqFBffKawtpuQazS67q72D2FQJk+8+b, Rob Herring,
	Pawel Moll, Mark Rutland, Ian Campbell, Kumar Gala, Rob Landley,
	Russell King, devicetree-u79uwXL29TY76Z2rM5mHXA
In-Reply-To: <1392913301-25524-1-git-send-email-julien.grall-QSEj5FYQhm4dnm+yROfE0A@public.gmane.org>

On Thu, 2014-02-20 at 16:21 +0000, Julien Grall wrote:
> Only Xen is able to know if a device can safely avoid to use xen-swiotlb.
> This patch introduce a new property "protected-devices" for the hypervisor
> node which list device which the IOMMU are been correctly programmed by Xen.
> 
> During Linux boot, Xen specific code will create an hash table which
> contains all these devices. The hash table will be used in need_xen_dma_ops
> to check if the Xen DMA ops needs to be used for the current device.

Is it out of the question to find a field within struct device itself to
store this e.g. in struct device_dma_parameters perhaps and avoid the
need for a hashtable lookup.

device->iommu_group might be another option, if we can create our own
group?

Ian.

--
To unsubscribe from this list: send the line "unsubscribe devicetree" in
the body of a message to majordomo-u79uwXL29TY76Z2rM5mHXA@public.gmane.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html

^ permalink raw reply

* [PATCH 3/3] iio: adc: fsl,imx25-gcq driver
From: Markus Pargmann @ 2014-02-20 16:21 UTC (permalink / raw)
  To: devicetree-u79uwXL29TY76Z2rM5mHXA,
	linux-input-u79uwXL29TY76Z2rM5mHXA,
	linux-iio-u79uwXL29TY76Z2rM5mHXA
  Cc: Dmitry Torokhov, Samuel Ortiz, Lee Jones, Jonathan Cameron,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r,
	kernel-bIcnvbaLZ9MEGnE8C9+IrQ, Markus Pargmann
In-Reply-To: <1392913312-9030-1-git-send-email-mpa-bIcnvbaLZ9MEGnE8C9+IrQ@public.gmane.org>

This is a conversion queue driver for the mx25 SoC. It uses the central
ADC which is used by two seperate independent queues. This driver
prepares different conversion configurations for each possible input.
For a conversion it creates a conversionqueue of one item with the
correct configuration for the chosen channel. It then executes the queue
once and disables the conversion queue afterwards.

The reference voltages are configurable through devicetree subnodes,
depending on the connections of the ADC inputs.

Signed-off-by: Markus Pargmann <mpa-bIcnvbaLZ9MEGnE8C9+IrQ@public.gmane.org>
---
 .../devicetree/bindings/iio/adc/fsl,imx25-gcq.txt  |  54 ++++
 drivers/iio/adc/Kconfig                            |   7 +
 drivers/iio/adc/Makefile                           |   1 +
 drivers/iio/adc/fsl-imx25-gcq.c                    | 325 +++++++++++++++++++++
 4 files changed, 387 insertions(+)
 create mode 100644 Documentation/devicetree/bindings/iio/adc/fsl,imx25-gcq.txt
 create mode 100644 drivers/iio/adc/fsl-imx25-gcq.c

diff --git a/Documentation/devicetree/bindings/iio/adc/fsl,imx25-gcq.txt b/Documentation/devicetree/bindings/iio/adc/fsl,imx25-gcq.txt
new file mode 100644
index 0000000..333fc55
--- /dev/null
+++ b/Documentation/devicetree/bindings/iio/adc/fsl,imx25-gcq.txt
@@ -0,0 +1,54 @@
+Freescale i.MX25 ADC GCQ device
+
+This is a generic conversion queue device that can convert any of the analog
+inputs using the ADC unit of the i.MX25.
+
+Required properties:
+ - compatible: Should be "fsl,imx25-gcq".
+ - reg: Should be the register range of the module.
+ - interrupts: Should be the interrupt number of the module. Typically this is <1>.
+ - interrupt-parent: phandle to the tsadc module of the i.MX25.
+ - #address-cells: Should be <1> (setting for the subnodes)
+ - #size-cells: Should be <0> (setting for the subnodes)
+
+Optionally you can define subnodes which define the positive and negative
+reference voltage for one of the analog inputs.
+
+Required properties for subnodes:
+ - reg: Should be the number of the analog input.
+     0: xp
+     1: yp
+     2: xn
+     3: yn
+     4: wiper
+     5: inaux0
+     6: inaux1
+     7: inaux2
+ - fsl,adc-refp: Positive reference input
+     0: yp
+     1: xp
+     2: External reference
+     3: Internal reference
+ - fsl,adc-refn: Negative reference input
+     0: xn
+     1: yn
+     2: ngnd_adc
+     3: ngnd_adc
+
+
+Example:
+
+	adc: adc@50030800 {
+		compatible = "fsl,imx25-gcq";
+		reg = <0x50030800 0x60>;
+		interrupt-parent = <&tscadc>;
+		interrupts = <1>;
+		#address-cells = <1>;
+		#size-cells = <0>;
+
+		inaux@5 {
+			reg = <5>;
+			fsl,adc-refp = <3>;
+			fsl,adc-refn = <3>;
+		};
+	};
diff --git a/drivers/iio/adc/Kconfig b/drivers/iio/adc/Kconfig
index 2209f28..a421445 100644
--- a/drivers/iio/adc/Kconfig
+++ b/drivers/iio/adc/Kconfig
@@ -113,6 +113,13 @@ config EXYNOS_ADC
 	  of SoCs for drivers such as the touchscreen and hwmon to use to share
 	  this resource.
 
+config MX25_ADC
+	tristate "Freescale MX25 ADC driver"
+	depends on MFD_MX25_TSADC
+	help
+	  Generic Conversion Queue driver used for general purpose ADC in the
+	  MX25. This driver supports single measurements using the MX25 ADC.
+
 config LP8788_ADC
 	bool "LP8788 ADC driver"
 	depends on MFD_LP8788
diff --git a/drivers/iio/adc/Makefile b/drivers/iio/adc/Makefile
index ba9a10a..63daa2c 100644
--- a/drivers/iio/adc/Makefile
+++ b/drivers/iio/adc/Makefile
@@ -22,3 +22,4 @@ obj-$(CONFIG_TI_ADC081C) += ti-adc081c.o
 obj-$(CONFIG_TI_AM335X_ADC) += ti_am335x_adc.o
 obj-$(CONFIG_TWL6030_GPADC) += twl6030-gpadc.o
 obj-$(CONFIG_VIPERBOARD_ADC) += viperboard_adc.o
+obj-$(CONFIG_MX25_ADC) += fsl-imx25-gcq.o
diff --git a/drivers/iio/adc/fsl-imx25-gcq.c b/drivers/iio/adc/fsl-imx25-gcq.c
new file mode 100644
index 0000000..cc7f87f
--- /dev/null
+++ b/drivers/iio/adc/fsl-imx25-gcq.c
@@ -0,0 +1,325 @@
+/*
+ * Copyright 2014 Markus Pargmann, Pengutronix <mpa-bIcnvbaLZ9MEGnE8C9+IrQ@public.gmane.org>
+ *
+ * The code contained herein is licensed under the GNU General Public
+ * License. You may obtain a copy of the GNU General Public License
+ * Version 2 or later at the following locations:
+ *
+ * http://www.opensource.org/licenses/gpl-license.html
+ * http://www.gnu.org/copyleft/gpl.html
+ *
+ * This is the driver for the imx25 GCQ (Generic Conversion Queue)
+ * connected to the imx25 ADC.
+ */
+
+#include <linux/clk.h>
+#include <linux/interrupt.h>
+#include <linux/iio/iio.h>
+#include <linux/mfd/imx25-tsadc.h>
+#include <linux/module.h>
+#include <linux/of.h>
+#include <linux/platform_device.h>
+#include <linux/regmap.h>
+
+#define MX25_GCQ_TIMEOUT (msecs_to_jiffies(2000))
+
+enum mx25_gcq_cfgs {
+	MX25_CFG_XP = 0,
+	MX25_CFG_YP,
+	MX25_CFG_XN,
+	MX25_CFG_YN,
+	MX25_CFG_WIPER,
+	MX25_CFG_INAUX0,
+	MX25_CFG_INAUX1,
+	MX25_CFG_INAUX2,
+	MX25_NUM_CFGS,
+};
+
+struct mx25_gcq_priv {
+	struct regmap *regs;
+	struct completion completed;
+	unsigned int settling_time;
+	struct clk *clk;
+};
+
+#define MX25_IIO_CHAN(chan, id) {\
+		.type = IIO_VOLTAGE,\
+		.indexed = 1,\
+		.channel = chan,\
+		.address = chan,\
+		.info_mask_separate = BIT(IIO_CHAN_INFO_RAW),	\
+		.datasheet_name = id,				\
+	}
+
+const struct iio_chan_spec mx25_gcq_channels[MX25_NUM_CFGS] = {
+	MX25_IIO_CHAN(0, "xp"),
+	MX25_IIO_CHAN(1, "yp"),
+	MX25_IIO_CHAN(2, "xn"),
+	MX25_IIO_CHAN(3, "yn"),
+	MX25_IIO_CHAN(4, "wiper"),
+	MX25_IIO_CHAN(5, "inaux0"),
+	MX25_IIO_CHAN(6, "inaux1"),
+	MX25_IIO_CHAN(7, "inaux2"),
+};
+
+static void mx25_gcq_disable_eoq(struct mx25_gcq_priv *priv)
+{
+	regmap_update_bits(priv->regs, MX25_ADCQ_MR, MX25_ADCQ_MR_EOQ_IRQ,
+			MX25_ADCQ_MR_EOQ_IRQ);
+}
+
+static void mx25_gcq_enable_eoq(struct mx25_gcq_priv *priv)
+{
+	regmap_update_bits(priv->regs, MX25_ADCQ_MR, MX25_ADCQ_MR_EOQ_IRQ, 0);
+}
+
+static irqreturn_t mx25_gcq_irq(int irq, void *data)
+{
+	struct mx25_gcq_priv *priv = data;
+	u32 stats;
+
+	regmap_read(priv->regs, MX25_ADCQ_SR, &stats);
+
+	if (stats & MX25_ADCQ_SR_EOQ) {
+		mx25_gcq_disable_eoq(priv);
+		complete(&priv->completed);
+	}
+
+	/* Disable conversion queue run */
+	regmap_update_bits(priv->regs, MX25_ADCQ_CR, MX25_ADCQ_CR_FQS, 0);
+
+	/* Acknowledge all possible irqs */
+	regmap_write(priv->regs, MX25_ADCQ_SR, MX25_ADCQ_SR_FRR |
+			MX25_ADCQ_SR_FUR | MX25_ADCQ_SR_FOR | MX25_ADCQ_SR_EOQ |
+			MX25_ADCQ_SR_PD);
+
+	return IRQ_HANDLED;
+}
+
+static int mx25_gcq_read_raw(struct iio_dev *idev,
+		struct iio_chan_spec const *chan, int *val, int *val2,
+		long mask)
+{
+	struct mx25_gcq_priv *priv = iio_priv(idev);
+	unsigned long timeout;
+	u32 data;
+	int ret;
+
+	if (mask != IIO_CHAN_INFO_RAW)
+		return -EINVAL;
+
+	mutex_lock(&idev->mlock);
+
+	/* Setup the configuration we want to use */
+	regmap_write(priv->regs, MX25_ADCQ_ITEM_7_0,
+			MX25_ADCQ_ITEM(0, chan->address));
+
+	mx25_gcq_enable_eoq(priv);
+
+	/* Trigger queue for one run */
+	regmap_update_bits(priv->regs, MX25_ADCQ_CR, MX25_ADCQ_CR_FQS,
+			MX25_ADCQ_CR_FQS);
+
+	timeout = wait_for_completion_interruptible_timeout(&priv->completed,
+			MX25_GCQ_TIMEOUT);
+	if (timeout < 0) {
+		dev_err(&idev->dev, "ADC wait for measurement failed\n");
+		ret = timeout;
+		goto out;
+	} else if (timeout == 0) {
+		dev_err(&idev->dev, "ADC timed out\n");
+		ret = -ETIMEDOUT;
+		goto out;
+	}
+
+	regmap_read(priv->regs, MX25_ADCQ_FIFO, &data);
+	*val = MX25_ADCQ_FIFO_DATA(data);
+
+	ret = IIO_VAL_INT;
+
+out:
+	mutex_unlock(&idev->mlock);
+
+	return ret;
+}
+
+struct iio_info mx25_gcq_iio_info = {
+	.read_raw = mx25_gcq_read_raw,
+};
+
+static struct regmap_config mx25_gcq_regconfig = {
+	.fast_io = true,
+	.max_register = 0x5c,
+	.reg_bits = 32,
+	.val_bits = 32,
+	.reg_stride = 4,
+};
+
+static void mx25_gcq_iio_dev_setup(struct platform_device *pdev,
+		struct iio_dev *idev)
+{
+	idev->dev.parent = &pdev->dev;
+	idev->channels = mx25_gcq_channels;
+	idev->num_channels = ARRAY_SIZE(mx25_gcq_channels);
+	idev->info = &mx25_gcq_iio_info;
+}
+
+static int mx25_gcq_setup_cfgs(struct platform_device *pdev,
+		struct mx25_gcq_priv *priv)
+{
+	struct device_node *np = pdev->dev.of_node;
+	struct device_node *child;
+	struct device *dev = &pdev->dev;
+	int ret;
+	int i;
+
+	/* Setup all configurations registers with a default conversion
+	 * configuration for each input */
+	for (i = 0; i != MX25_NUM_CFGS; ++i)
+		regmap_write(priv->regs, MX25_ADCQ_CFG(i),
+				MX25_ADCQ_CFG_YPLL_OFF |
+				MX25_ADCQ_CFG_XNUR_OFF |
+				MX25_ADCQ_CFG_XPUL_OFF |
+				MX25_ADCQ_CFG_REFP_INT |
+				(i << 4) |
+				MX25_ADCQ_CFG_REFN_NGND2);
+
+	for_each_child_of_node(np, child) {
+		u32 reg;
+		u32 refn;
+		u32 refp;
+
+		ret = of_property_read_u32(child, "reg", &reg);
+		if (ret) {
+			dev_err(dev, "Failed to get reg property\n");
+			return ret;
+		}
+		if (reg > MX25_NUM_CFGS) {
+			dev_err(dev, "reg value is greater than the number of available configuration registers\n");
+			return -EINVAL;
+		}
+
+		ret = of_property_read_u32(child, "fsl,adc-refn", &refn);
+		if (ret) {
+			dev_err(dev, "Failed to get fsl,adc-refn property\n");
+			return ret;
+		}
+
+		ret = of_property_read_u32(child, "fsl,adc-refp", &refp);
+		if (ret) {
+			dev_err(dev, "Failed to get fsl,adc-refp property\n");
+			return ret;
+		}
+
+		regmap_update_bits(priv->regs, MX25_ADCQ_CFG(reg),
+				MX25_ADCQ_CFG_REFP_MASK |
+				MX25_ADCQ_CFG_REFN_MASK,
+				(refp << 7) | (refn << 2));
+	}
+	regmap_update_bits(priv->regs, MX25_ADCQ_CR,
+			MX25_ADCQ_CR_FRST | MX25_ADCQ_CR_QRST,
+			MX25_ADCQ_CR_FRST | MX25_ADCQ_CR_QRST);
+
+	regmap_write(priv->regs, MX25_ADCQ_CR,
+			MX25_ADCQ_CR_PDMSK |
+			MX25_ADCQ_CR_QSM_FQS);
+
+	return 0;
+}
+
+static int mx25_gcq_probe(struct platform_device *pdev)
+{
+	struct iio_dev *idev;
+	struct mx25_gcq_priv *priv;
+	struct resource *res;
+	struct device *dev = &pdev->dev;
+	int ret;
+	int irq;
+	void __iomem *mem;
+
+	idev = devm_iio_device_alloc(&pdev->dev, sizeof(*priv));
+	if (!idev)
+		return -ENOMEM;
+
+	priv = iio_priv(idev);
+
+	res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
+	mem = devm_ioremap_resource(dev, res);
+	if (!mem) {
+		dev_err(dev, "Failed to get iomem");
+		return -ENOMEM;
+	}
+
+	priv->regs = devm_regmap_init_mmio(dev, mem, &mx25_gcq_regconfig);
+	if (IS_ERR(priv->regs)) {
+		dev_err(dev, "Failed to initialize regmap\n");
+		return PTR_ERR(priv->regs);
+	}
+
+	irq = platform_get_irq(pdev, 0);
+	if (irq < 0) {
+		dev_err(dev, "Failed to get IRQ\n");
+		return irq;
+	}
+
+	ret = devm_request_irq(dev, irq, mx25_gcq_irq, IRQF_ONESHOT, pdev->name,
+			priv);
+	if (ret) {
+		dev_err(dev, "Failed requesting IRQ\n");
+		return ret;
+	}
+
+	ret = mx25_gcq_setup_cfgs(pdev, priv);
+	if (ret)
+		return ret;
+
+	mx25_gcq_iio_dev_setup(pdev, idev);
+
+	ret = iio_device_register(idev);
+	if (ret) {
+		dev_err(dev, "Failed to register iio device\n");
+		return ret;
+	}
+
+	init_completion(&priv->completed);
+
+	priv->clk = mx25_tsadc_get_ipg(pdev->dev.parent);
+	ret = clk_prepare_enable(priv->clk);
+	if (ret) {
+		dev_err(dev, "Failed to enable clock\n");
+		return ret;
+	}
+
+	platform_set_drvdata(pdev, priv);
+
+	return 0;
+}
+
+static int mx25_gcq_remove(struct platform_device *pdev)
+{
+	struct mx25_gcq_priv *priv = platform_get_drvdata(pdev);
+
+	clk_disable_unprepare(priv->clk);
+
+	return 0;
+}
+
+static struct of_device_id mx25_gcq_ids[] = {
+	{ .compatible = "fsl,imx25-gcq", },
+	{ /* Senitel */ }
+};
+
+static struct platform_driver mx25_gcq_driver = {
+	.driver		= {
+		.name	= "mx25-gcq",
+		.owner	= THIS_MODULE,
+		.of_match_table = mx25_gcq_ids,
+	},
+	.probe		= mx25_gcq_probe,
+	.remove		= mx25_gcq_remove,
+};
+module_platform_driver(mx25_gcq_driver);
+
+MODULE_DESCRIPTION("ADC driver for Freescale mx25");
+MODULE_AUTHOR("Markus Pargmann <mpa-bIcnvbaLZ9MEGnE8C9+IrQ@public.gmane.org>");
+MODULE_LICENSE("GPL v2");
-- 
1.8.5.3

^ permalink raw reply related

* [PATCH 2/3] input: touchscreen: imx25 tcq driver
From: Markus Pargmann @ 2014-02-20 16:21 UTC (permalink / raw)
  To: devicetree, linux-input, linux-iio
  Cc: Dmitry Torokhov, Samuel Ortiz, Lee Jones, Jonathan Cameron,
	linux-arm-kernel, kernel, Markus Pargmann
In-Reply-To: <1392913312-9030-1-git-send-email-mpa@pengutronix.de>

This is a driver for the imx25 ADC/TSC module. It controls the
touchscreen conversion queue and creates a touchscreen input device.
The driver currently only supports 4 wire touchscreens. The driver uses
a simple conversion queue of precharge, touch detection, X measurement,
Y measurement, precharge and another touch detection.

This driver uses the regmap from the parent to setup some touch specific
settings in the core driver and setup a idle configuration with touch
detection.

Signed-off-by: Markus Pargmann <mpa@pengutronix.de>
---
 .../bindings/input/touchscreen/fsl-mx25-tcq.txt    |  29 +
 drivers/input/touchscreen/Kconfig                  |   6 +
 drivers/input/touchscreen/Makefile                 |   1 +
 drivers/input/touchscreen/fsl-imx25-tcq.c          | 589 +++++++++++++++++++++
 4 files changed, 625 insertions(+)
 create mode 100644 Documentation/devicetree/bindings/input/touchscreen/fsl-mx25-tcq.txt
 create mode 100644 drivers/input/touchscreen/fsl-imx25-tcq.c

diff --git a/Documentation/devicetree/bindings/input/touchscreen/fsl-mx25-tcq.txt b/Documentation/devicetree/bindings/input/touchscreen/fsl-mx25-tcq.txt
new file mode 100644
index 0000000..4214a99
--- /dev/null
+++ b/Documentation/devicetree/bindings/input/touchscreen/fsl-mx25-tcq.txt
@@ -0,0 +1,29 @@
+Freescale mx25 TS conversion queue module
+
+mx25 touchscreen conversion queue module which controls the ADC unit of the
+mx25 for attached touchscreens.
+
+Required properties:
+ - compatible: Should be "fsl,imx25-tcq".
+ - reg: Memory range of the device.
+ - interrupts: Should be the interrupt number associated with this module within
+   the tscadc unit (<0>).
+ - interrupt-parent: Should be a phandle to the tscadc unit.
+ - fsl,wires: Should be '<4>' or '<5>'
+
+Optional properties:
+ - fsl,pen-debounce: Pen debounce time.
+ - fsl,pen-threshold: Pen-down threshold for the touchscreen.
+ - fsl,settling-time: Settling time in nanoseconds.
+
+This device includes two conversion queues which can be added as subnodes.
+The first queue is for the touchscreen, the second for general purpose ADC.
+
+Example:
+	tsc: tcq@50030400 {
+		compatible = "fsl,imx25-tcq";
+		reg = <0x50030400 0x60>;
+		interrupt-parent = <&tscadc>;
+		interrupts = <0>;
+		fsl,wires = <4>;
+	};
diff --git a/drivers/input/touchscreen/Kconfig b/drivers/input/touchscreen/Kconfig
index 07e9e82..d52c055 100644
--- a/drivers/input/touchscreen/Kconfig
+++ b/drivers/input/touchscreen/Kconfig
@@ -715,6 +715,12 @@ config TOUCHSCREEN_USB_COMPOSITE
 	  To compile this driver as a module, choose M here: the
 	  module will be called usbtouchscreen.
 
+config TOUCHSCREEN_MX25
+	tristate "Freescale i.MX25 touchscreen input driver"
+	depends on MFD_MX25_TSADC
+	help
+	  Enable support for touchscreen connected to your i.MX25.
+
 config TOUCHSCREEN_MC13783
 	tristate "Freescale MC13783 touchscreen input driver"
 	depends on MFD_MC13XXX
diff --git a/drivers/input/touchscreen/Makefile b/drivers/input/touchscreen/Makefile
index 62801f2..c891f30 100644
--- a/drivers/input/touchscreen/Makefile
+++ b/drivers/input/touchscreen/Makefile
@@ -38,6 +38,7 @@ obj-$(CONFIG_TOUCHSCREEN_INEXIO)	+= inexio.o
 obj-$(CONFIG_TOUCHSCREEN_INTEL_MID)	+= intel-mid-touch.o
 obj-$(CONFIG_TOUCHSCREEN_LPC32XX)	+= lpc32xx_ts.o
 obj-$(CONFIG_TOUCHSCREEN_MAX11801)	+= max11801_ts.o
+obj-$(CONFIG_TOUCHSCREEN_MX25)		+= fsl-imx25-tcq.o
 obj-$(CONFIG_TOUCHSCREEN_MC13783)	+= mc13783_ts.o
 obj-$(CONFIG_TOUCHSCREEN_MCS5000)	+= mcs5000_ts.o
 obj-$(CONFIG_TOUCHSCREEN_MIGOR)		+= migor_ts.o
diff --git a/drivers/input/touchscreen/fsl-imx25-tcq.c b/drivers/input/touchscreen/fsl-imx25-tcq.c
new file mode 100644
index 0000000..436cc8b
--- /dev/null
+++ b/drivers/input/touchscreen/fsl-imx25-tcq.c
@@ -0,0 +1,589 @@
+/*
+ * Copyright 2014 Markus Pargmann, Pengutronix <mpa@pengutronix.de>
+ * Based on driver from 2011 Juergen Beisert, Pengutronix <kernel@pengutronix.de>
+ *
+ * The code contained herein is licensed under the GNU General Public
+ * License. You may obtain a copy of the GNU General Public License
+ * Version 2 or later at the following locations:
+ *
+ * http://www.opensource.org/licenses/gpl-license.html
+ * http://www.gnu.org/copyleft/gpl.html
+ *
+ * This is the driver for the imx25 TCQ (Touchscreen Conversion Queue)
+ * connected to the imx25 ADC.
+ */
+
+#include <linux/clk.h>
+#include <linux/interrupt.h>
+#include <linux/input.h>
+#include <linux/mfd/imx25-tsadc.h>
+#include <linux/module.h>
+#include <linux/of.h>
+#include <linux/platform_device.h>
+#include <linux/regmap.h>
+
+static const char mx25_tcq_name[] = "mx25-tcq";
+
+enum mx25_tcq_mode {
+	MX25_TS_4WIRE,
+};
+
+struct mx25_tcq_priv {
+	struct regmap *regs;
+	struct regmap *core_regs;
+	struct input_dev *idev;
+	enum mx25_tcq_mode mode;
+	unsigned int pen_threshold;
+	unsigned int sample_count;
+	unsigned int expected_samples;
+	unsigned int repeat_wait;
+	unsigned int pen_debounce;
+	unsigned int settling_time;
+	struct clk *clk;
+};
+
+static struct regmap_config mx25_tcq_regconfig = {
+	.fast_io = true,
+	.max_register = 0x5c,
+	.reg_bits = 32,
+	.val_bits = 32,
+	.reg_stride = 4,
+};
+
+static struct of_device_id mx25_tcq_ids[] = {
+	{ .compatible = "fsl,imx25-tcq", },
+	{ /* Senitel */ }
+};
+
+#define TSC_4WIRE_PRE_INDEX 0
+#define TSC_4WIRE_X_INDEX 1
+#define TSC_4WIRE_Y_INDEX 2
+#define TSC_4WIRE_POST_INDEX 3
+#define TSC_4WIRE_LEAVE 4
+
+#define MX25_TSC_DEF_THRESHOLD 80
+#define TSC_MAX_SAMPLES 16
+
+
+enum mx25_adc_configurations {
+	MX25_CFG_PRECHARGE = 0,
+	MX25_CFG_TOUCH_DETECT,
+	MX25_CFG_X_MEASUREMENT,
+	MX25_CFG_Y_MEASUREMENT,
+};
+
+#define MX25_PRECHARGE_VALUE (\
+			MX25_ADCQ_CFG_YPLL_OFF | \
+			MX25_ADCQ_CFG_XNUR_OFF | \
+			MX25_ADCQ_CFG_XPUL_HIGH | \
+			MX25_ADCQ_CFG_REFP_INT | \
+			MX25_ADCQ_CFG_IN_XP | \
+			MX25_ADCQ_CFG_REFN_NGND2 | \
+			MX25_ADCQ_CFG_IGS)
+
+#define MX25_TOUCH_DETECT_VALUE (\
+			MX25_ADCQ_CFG_YNLR | \
+			MX25_ADCQ_CFG_YPLL_OFF | \
+			MX25_ADCQ_CFG_XNUR_OFF | \
+			MX25_ADCQ_CFG_XPUL_OFF | \
+			MX25_ADCQ_CFG_REFP_INT | \
+			MX25_ADCQ_CFG_IN_XP | \
+			MX25_ADCQ_CFG_REFN_NGND2 | \
+			MX25_ADCQ_CFG_PENIACK)
+
+static void imx25_setup_queue_cfgs(struct mx25_tcq_priv *priv,
+		unsigned int settling_time)
+{
+	u32 precharge_cfg =
+			MX25_PRECHARGE_VALUE |
+			MX25_ADCQ_CFG_SETTLING_TIME(settling_time);
+	u32 touch_detect_cfg =
+			MX25_TOUCH_DETECT_VALUE |
+			MX25_ADCQ_CFG_NOS(1) |
+			MX25_ADCQ_CFG_SETTLING_TIME(settling_time);
+
+	regmap_write(priv->core_regs, MX25_TSC_TICR, precharge_cfg);
+
+	/* PRECHARGE */
+	regmap_write(priv->regs, MX25_ADCQ_CFG(MX25_CFG_PRECHARGE),
+			precharge_cfg);
+
+	/* TOUCH_DETECT */
+	regmap_write(priv->regs, MX25_ADCQ_CFG(MX25_CFG_TOUCH_DETECT),
+			touch_detect_cfg);
+
+	/* X Measurement */
+	regmap_write(priv->regs, MX25_ADCQ_CFG(MX25_CFG_X_MEASUREMENT),
+			MX25_ADCQ_CFG_YPLL_OFF |
+			MX25_ADCQ_CFG_XNUR_LOW |
+			MX25_ADCQ_CFG_XPUL_HIGH |
+			MX25_ADCQ_CFG_REFP_XP |
+			MX25_ADCQ_CFG_IN_YP |
+			MX25_ADCQ_CFG_REFN_XN |
+			MX25_ADCQ_CFG_NOS(priv->sample_count) |
+			MX25_ADCQ_CFG_SETTLING_TIME(settling_time));
+
+	/* Y Measurement */
+	regmap_write(priv->regs, MX25_ADCQ_CFG(MX25_CFG_Y_MEASUREMENT),
+			MX25_ADCQ_CFG_YNLR |
+			MX25_ADCQ_CFG_YPLL_HIGH |
+			MX25_ADCQ_CFG_XNUR_OFF |
+			MX25_ADCQ_CFG_XPUL_OFF |
+			MX25_ADCQ_CFG_REFP_YP |
+			MX25_ADCQ_CFG_IN_XP |
+			MX25_ADCQ_CFG_REFN_YN |
+			MX25_ADCQ_CFG_NOS(priv->sample_count) |
+			MX25_ADCQ_CFG_SETTLING_TIME(settling_time));
+
+	/* Enable the touch detection right now */
+	regmap_write(priv->core_regs, MX25_TSC_TICR, touch_detect_cfg |
+			MX25_ADCQ_CFG_IGS);
+}
+
+static int imx25_setup_queue_4wire(struct mx25_tcq_priv *priv,
+		unsigned settling_time, int *items)
+{
+	imx25_setup_queue_cfgs(priv, settling_time);
+
+	/* Setup the conversion queue */
+	regmap_write(priv->regs, MX25_ADCQ_ITEM_7_0,
+			MX25_ADCQ_ITEM(0, MX25_CFG_PRECHARGE) |
+			MX25_ADCQ_ITEM(1, MX25_CFG_TOUCH_DETECT) |
+			MX25_ADCQ_ITEM(2, MX25_CFG_X_MEASUREMENT) |
+			MX25_ADCQ_ITEM(3, MX25_CFG_Y_MEASUREMENT) |
+			MX25_ADCQ_ITEM(4, MX25_CFG_PRECHARGE) |
+			MX25_ADCQ_ITEM(5, MX25_CFG_TOUCH_DETECT));
+
+	/* We measure X/Y with 'sample_count' number of samples and execute a
+	 * touch detection twice, with 1 sample each */
+	priv->expected_samples = priv->sample_count * 2 + 2;
+	*items = 6;
+
+	return 0;
+}
+
+static void mx25_tcq_disable_touch_irq(struct mx25_tcq_priv *priv)
+{
+	regmap_update_bits(priv->regs, MX25_ADCQ_CR, MX25_ADCQ_CR_PDMSK,
+			MX25_ADCQ_CR_PDMSK);
+}
+
+static void mx25_tcq_enable_touch_irq(struct mx25_tcq_priv *priv)
+{
+	regmap_update_bits(priv->regs, MX25_ADCQ_CR, MX25_ADCQ_CR_PDMSK, 0);
+}
+
+static void mx25_tcq_disable_fifo_irq(struct mx25_tcq_priv *priv)
+{
+	regmap_update_bits(priv->regs, MX25_ADCQ_MR, MX25_ADCQ_MR_FDRY_IRQ,
+			MX25_ADCQ_MR_FDRY_IRQ);
+}
+
+static void mx25_tcq_enable_fifo_irq(struct mx25_tcq_priv *priv)
+{
+	regmap_update_bits(priv->regs, MX25_ADCQ_MR, MX25_ADCQ_MR_FDRY_IRQ, 0);
+}
+
+static void mx25_tcq_force_queue_start(struct mx25_tcq_priv *priv)
+{
+	regmap_update_bits(priv->regs, MX25_ADCQ_CR, MX25_ADCQ_CR_FQS,
+			MX25_ADCQ_CR_FQS);
+
+	regmap_update_bits(priv->regs, MX25_ADCQ_CR, MX25_ADCQ_CR_FQS, 0);
+}
+
+static void mx25_tcq_force_queue_stop(struct mx25_tcq_priv *priv)
+{
+	regmap_update_bits(priv->regs, MX25_ADCQ_CR, MX25_ADCQ_CR_FQS, 0);
+}
+
+static void mx25_tcq_fifo_reset(struct mx25_tcq_priv *priv)
+{
+	u32 tcqcr;
+
+	regmap_read(priv->regs, MX25_ADCQ_CR, &tcqcr);
+	regmap_update_bits(priv->regs, MX25_ADCQ_CR, MX25_ADCQ_CR_FRST,
+			MX25_ADCQ_CR_FRST);
+	regmap_update_bits(priv->regs, MX25_ADCQ_CR, MX25_ADCQ_CR_FRST,
+			0);
+	regmap_write(priv->regs, MX25_ADCQ_CR, tcqcr);
+}
+
+static void mx25_tcq_re_enable_touch_detection(struct mx25_tcq_priv *priv)
+{
+	/* stop the queue from looping */
+	mx25_tcq_force_queue_stop(priv);
+
+	/* for a clean touch detection, preload the X plane */
+	regmap_write(priv->core_regs, MX25_TSC_TICR, MX25_PRECHARGE_VALUE);
+
+	/* waste some time now to pre-load the X plate to high voltage */
+	mx25_tcq_fifo_reset(priv);
+
+	/* re-enable the detection right now */
+	regmap_write(priv->core_regs, MX25_TSC_TICR, MX25_TOUCH_DETECT_VALUE |
+			MX25_ADCQ_CFG_IGS);
+
+	regmap_update_bits(priv->regs, MX25_ADCQ_SR, MX25_ADCQ_SR_PD,
+			MX25_ADCQ_SR_PD);
+
+	/* enable the pen down event to be a source for the interrupt */
+	regmap_update_bits(priv->regs, MX25_ADCQ_MR, MX25_ADCQ_MR_PD_IRQ, 0);
+
+	/* lets fire the next IRQ if someone touches the touchscreen */
+	mx25_tcq_enable_touch_irq(priv);
+}
+
+static int mx25_tcq_create_event_for_4wire(struct mx25_tcq_priv *priv,
+		u32 *sample_buf, int samples)
+{
+	unsigned int x_pos = 0;
+	unsigned int y_pos = 0;
+	unsigned int touch_pre = 0;
+	unsigned int touch_post = 0;
+	unsigned i;
+	int ret = 0;
+
+	for (i = 0; i < samples; i++) {
+		unsigned int index = MX25_ADCQ_FIFO_ID(sample_buf[i]);
+		unsigned int val = MX25_ADCQ_FIFO_DATA(sample_buf[i]);
+
+		switch (index) {
+		case 1:
+			touch_pre = val;
+			break;
+		case 2:
+			x_pos = val;
+			break;
+		case 3:
+			y_pos = val;
+			break;
+		case 5:
+			touch_post = val;
+			break;
+		default:
+			ret = -EINVAL;
+			break;
+		}
+	}
+
+	if (ret == 0 && samples != 0) {
+		/*
+		 * only if both touch measures are below a treshold,
+		 * the position is valid
+		 */
+		if (touch_pre < priv->pen_threshold &&
+					touch_post < priv->pen_threshold) {
+			/* valid samples, generate a report */
+			x_pos /= priv->sample_count;
+			y_pos /= priv->sample_count;
+			input_report_abs(priv->idev, ABS_X, x_pos);
+			input_report_abs(priv->idev, ABS_Y, y_pos);
+			input_report_key(priv->idev, BTN_TOUCH,
+					0xfff - ((touch_pre + touch_post) / 2));
+			input_sync(priv->idev);
+
+			/* get next sample */
+			mx25_tcq_force_queue_start(priv);
+			mx25_tcq_enable_fifo_irq(priv);
+		} else {
+			if (touch_pre >= priv->pen_threshold &&
+					touch_post >= priv->pen_threshold) {
+				/*
+				 * if both samples are invalid,
+				 * generate a release report
+				 */
+				input_report_key(priv->idev, BTN_TOUCH, 0);
+				input_sync(priv->idev);
+				mx25_tcq_re_enable_touch_detection(priv);
+			} else {
+				/*
+				 * if only one of both touch measurements are
+				 * below the threshold, still some bouncing
+				 * happens. Take additional samples in this
+				 * case to be sure
+				 */
+				mx25_tcq_force_queue_start(priv);
+				mx25_tcq_enable_fifo_irq(priv);
+			}
+		}
+	}
+
+	return ret;
+}
+
+static irqreturn_t mx25_tcq_irq_thread(int irq, void *dev_id)
+{
+	struct mx25_tcq_priv *priv = (struct mx25_tcq_priv *) dev_id;
+	u32 sample_buf[TSC_MAX_SAMPLES];
+	int samples = 0;
+
+	/* read all samples */
+	while (1) {
+		u32 stats;
+
+		regmap_read(priv->regs, MX25_ADCQ_SR, &stats);
+		if (stats & MX25_ADCQ_SR_EMPT)
+			break;
+
+		if (samples < TSC_MAX_SAMPLES) {
+			regmap_read(priv->regs, MX25_ADCQ_FIFO,
+					&sample_buf[samples]);
+			++samples;
+		} else {
+			u32 discarded;
+			/* discard samples */
+			regmap_read(priv->regs, MX25_ADCQ_FIFO, &discarded);
+		}
+	}
+
+	mx25_tcq_create_event_for_4wire(priv, sample_buf, samples);
+
+	return IRQ_HANDLED;
+}
+
+static irqreturn_t mx25_tcq_irq(int irq, void *dev_id)
+{
+	struct mx25_tcq_priv *priv = (struct mx25_tcq_priv *)dev_id;
+	u32 stat;
+	int ret = IRQ_HANDLED;
+
+	regmap_read(priv->regs, MX25_ADCQ_SR, &stat);
+
+	if (stat & (MX25_ADCQ_SR_FRR | MX25_ADCQ_SR_FUR | MX25_ADCQ_SR_FOR))
+		mx25_tcq_fifo_reset(priv);
+
+	if (stat & MX25_ADCQ_SR_PD) {
+		mx25_tcq_disable_touch_irq(priv);
+		mx25_tcq_force_queue_start(priv);
+		mx25_tcq_enable_fifo_irq(priv);
+	}
+
+	if (stat & MX25_ADCQ_SR_FDRY) {
+		mx25_tcq_disable_fifo_irq(priv);
+		ret = IRQ_WAKE_THREAD;
+	}
+
+	regmap_update_bits(priv->regs, MX25_ADCQ_SR, MX25_ADCQ_SR_FRR |
+			MX25_ADCQ_SR_FUR | MX25_ADCQ_SR_FOR | MX25_ADCQ_SR_PD |
+			MX25_ADCQ_SR_EOQ,
+			MX25_ADCQ_SR_FRR |
+			MX25_ADCQ_SR_FUR | MX25_ADCQ_SR_FOR | MX25_ADCQ_SR_PD |
+			MX25_ADCQ_SR_EOQ);
+
+	return ret;
+}
+
+/* configure the statemachine for a 4-wire touchscreen */
+static int mx25_tcq_init(struct mx25_tcq_priv *priv)
+{
+	u32 tgcr;
+	unsigned int ipg_div;
+	unsigned int adc_period;
+	unsigned int repeat_wait;
+	unsigned int debounce_cnt;
+	unsigned int settling_time;
+	int itemct;
+	int ret;
+
+	regmap_read(priv->core_regs, MX25_TSC_TGCR, &tgcr);
+	ipg_div = max_t(unsigned int, 4, MX25_TGCR_GET_ADCCLK(tgcr));
+	adc_period = clk_get_rate(priv->clk) / (ipg_div * 2 + 2);
+	repeat_wait = fls(DIV_ROUND_UP(priv->repeat_wait, adc_period));
+	debounce_cnt = DIV_ROUND_UP(priv->pen_debounce, adc_period * 8) - 1;
+	settling_time = DIV_ROUND_UP(priv->settling_time, adc_period);
+
+
+	/* Reset */
+	regmap_write(priv->regs, MX25_ADCQ_CR, MX25_ADCQ_CR_QRST |
+			MX25_ADCQ_CR_FRST);
+	regmap_update_bits(priv->regs, MX25_ADCQ_CR, MX25_ADCQ_CR_QRST |
+			MX25_ADCQ_CR_FRST, 0);
+
+	/* up to 128 * 8 ADC clocks are possible */
+	if (debounce_cnt > 127)
+		debounce_cnt = 127;
+
+	if (repeat_wait > 15)
+		repeat_wait = 15;
+
+	regmap_update_bits(priv->regs, MX25_ADCQ_CR, MX25_ADCQ_CR_RWAIT_MASK,
+			MX25_ADCQ_CR_RWAIT(repeat_wait));
+
+	ret = imx25_setup_queue_4wire(priv, 0x0, &itemct);
+	if (ret)
+		return ret;
+
+	regmap_update_bits(priv->regs, MX25_ADCQ_CR, MX25_ADCQ_CR_LITEMID_MASK |
+			MX25_ADCQ_CR_WMRK_MASK,
+			MX25_ADCQ_CR_LITEMID(itemct - 1) |
+			MX25_ADCQ_CR_WMRK(priv->expected_samples - 1));
+
+	/* setup debounce count */
+	regmap_update_bits(priv->core_regs, MX25_TSC_TGCR,
+			MX25_TGCR_PDBTIME_MASK,
+			MX25_TGCR_PDBTIME(debounce_cnt));
+
+	/* enable debounce */
+	regmap_update_bits(priv->core_regs, MX25_TSC_TGCR, MX25_TGCR_PDBEN,
+			MX25_TGCR_PDBEN);
+	regmap_update_bits(priv->core_regs, MX25_TSC_TGCR, MX25_TGCR_PDEN,
+			MX25_TGCR_PDEN);
+
+	/* enable the engine on demand */
+	regmap_update_bits(priv->regs, MX25_ADCQ_CR, MX25_ADCQ_CR_QSM_FQS,
+			MX25_ADCQ_CR_QSM_FQS);
+
+	mx25_tcq_re_enable_touch_detection(priv);
+
+	return 0;
+}
+
+static int mx25_tcq_parse_dt(struct platform_device *pdev,
+		struct mx25_tcq_priv *priv)
+{
+	struct device_node *np = pdev->dev.of_node;
+	u32 wires;
+	int ret;
+
+	/* Setup defaults */
+	priv->pen_threshold = 500;
+	priv->sample_count = 3;
+	priv->repeat_wait = 15000000;
+	priv->pen_debounce = 1000000;
+	priv->settling_time = 250000;
+
+	ret = of_property_read_u32(np, "fsl,wires", &wires);
+	if (ret) {
+		dev_err(&pdev->dev, "Failed to find fsl,wires properties\n");
+		return ret;
+	}
+
+	if (wires == 4) {
+		priv->mode = MX25_TS_4WIRE;
+	} else {
+		dev_err(&pdev->dev, "%u-wire mode not supported\n", wires);
+		return -EINVAL;
+	}
+
+	/* These are optional, we don't care about the return values */
+	of_property_read_u32(np, "fsl,pen-threshold", &priv->pen_threshold);
+	of_property_read_u32(np, "fsl,settling-time", &priv->settling_time);
+	of_property_read_u32(np, "fsl,pen-debounce", &priv->pen_debounce);
+
+	return 0;
+}
+
+static int mx25_tcq_probe(struct platform_device *pdev)
+{
+	struct device *dev = &pdev->dev;
+	struct input_dev *idev;
+	struct mx25_tcq_priv *priv;
+	struct resource *res;
+	void __iomem *mem;
+	int ret;
+	int irq;
+
+	priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL);
+	if (!priv)
+		return -ENOMEM;
+
+	res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
+	mem = devm_ioremap_resource(dev, res);
+	if (!mem) {
+		dev_err(dev, "Failed to get iomem");
+		return -ENOMEM;
+	}
+
+	ret = mx25_tcq_parse_dt(pdev, priv);
+	if (ret)
+		return ret;
+
+	priv->regs = devm_regmap_init_mmio(dev, mem, &mx25_tcq_regconfig);
+	if (IS_ERR(priv->regs)) {
+		dev_err(dev, "Failed to initialize regmap\n");
+		return PTR_ERR(priv->regs);
+	}
+
+	irq = platform_get_irq(pdev, 0);
+	if (irq < 0) {
+		dev_err(dev, "Failed to get IRQ\n");
+		return irq;
+	}
+
+	ret = devm_request_threaded_irq(dev, irq, mx25_tcq_irq,
+			mx25_tcq_irq_thread, IRQF_ONESHOT, pdev->name, priv);
+	if (ret) {
+		dev_err(dev, "Failed requesting IRQ\n");
+		return ret;
+	}
+
+	idev = devm_input_allocate_device(dev);
+	if (!idev) {
+		dev_err(dev, "Failed to allocate input device\n");
+		return -ENOMEM;
+	}
+
+	idev->name = mx25_tcq_name;
+	idev->evbit[0] = BIT_MASK(EV_KEY) | BIT_MASK(EV_ABS);
+	idev->keybit[BIT_WORD(BTN_TOUCH)] = BIT_MASK(BTN_TOUCH);
+	input_set_abs_params(idev, ABS_X, 0, 0xfff, 0, 0);
+	input_set_abs_params(idev, ABS_Y, 0, 0xfff, 0, 0);
+
+	idev->id.bustype = BUS_HOST;
+
+	ret = input_register_device(idev);
+	if (ret) {
+		dev_err(dev, "Failed to register input device\n");
+		return ret;
+	}
+
+	priv->idev = idev;
+
+	priv->core_regs = mx25_tsadc_get_regmap(pdev->dev.parent);
+	priv->clk = mx25_tsadc_get_ipg(pdev->dev.parent);
+
+	ret = clk_prepare_enable(priv->clk);
+	if (ret) {
+		dev_err(dev, "Failed to enable ipg clock\n");
+		return ret;
+	}
+
+	ret = mx25_tcq_init(priv);
+	if (ret) {
+		dev_err(dev, "Failed to init tcq\n");
+		goto error_tcq_init;
+	}
+
+	platform_set_drvdata(pdev, priv);
+
+	return 0;
+
+error_tcq_init:
+	clk_disable_unprepare(priv->clk);
+	return ret;
+}
+
+static int mx25_tcq_remove(struct platform_device *pdev)
+{
+	struct mx25_tcq_priv *priv = platform_get_drvdata(pdev);
+
+	clk_disable_unprepare(priv->clk);
+
+	return 0;
+}
+
+static struct platform_driver mx25_tcq_driver = {
+	.driver		= {
+		.name	= "mx25-tcq",
+		.owner	= THIS_MODULE,
+		.of_match_table = mx25_tcq_ids,
+	},
+	.probe		= mx25_tcq_probe,
+	.remove		= mx25_tcq_remove,
+};
+module_platform_driver(mx25_tcq_driver);
+
+MODULE_DESCRIPTION("TS input driver for Freescale mx25");
+MODULE_AUTHOR("Markus Pargmann <mpa@pengutronix.de>");
+MODULE_LICENSE("GPL v2");
-- 
1.8.5.3


^ permalink raw reply related

* [PATCH 1/3] mfd: fsl imx25 Touchscreen ADC driver
From: Markus Pargmann @ 2014-02-20 16:21 UTC (permalink / raw)
  To: devicetree, linux-input, linux-iio
  Cc: Dmitry Torokhov, Samuel Ortiz, Lee Jones, Jonathan Cameron,
	linux-arm-kernel, kernel, Markus Pargmann
In-Reply-To: <1392913312-9030-1-git-send-email-mpa@pengutronix.de>

This is the core driver for imx25 touchscreen/adc driver. The module
has one shared ADC and two different conversion queues which use the
ADC. The two queues are identical. Both can be used for general purpose
ADC but one is meant to be used for touchscreens.

This driver is the core which manages the central components and
registers of the TSC/ADC unit. It manages the IRQs and forwards them to
the correct components.

Signed-off-by: Markus Pargmann <mpa@pengutronix.de>
---
 .../devicetree/bindings/mfd/fsl-imx25-tsadc.txt    |  46 ++++
 drivers/mfd/Kconfig                                |   9 +
 drivers/mfd/Makefile                               |   2 +
 drivers/mfd/fsl-imx25-tsadc.c                      | 234 +++++++++++++++++++++
 include/linux/mfd/imx25-tsadc.h                    | 138 ++++++++++++
 5 files changed, 429 insertions(+)
 create mode 100644 Documentation/devicetree/bindings/mfd/fsl-imx25-tsadc.txt
 create mode 100644 drivers/mfd/fsl-imx25-tsadc.c
 create mode 100644 include/linux/mfd/imx25-tsadc.h

diff --git a/Documentation/devicetree/bindings/mfd/fsl-imx25-tsadc.txt b/Documentation/devicetree/bindings/mfd/fsl-imx25-tsadc.txt
new file mode 100644
index 0000000..a857af0e
--- /dev/null
+++ b/Documentation/devicetree/bindings/mfd/fsl-imx25-tsadc.txt
@@ -0,0 +1,46 @@
+Freescale mx25 ADC/TSC multifunction device
+
+This device combines two general purpose conversion queues one used for general
+ADC and the other used for touchscreens.
+
+Required properties:
+ - compatible: Should be "fsl,imx25-tsadc".
+ - reg: Memory range of the device.
+ - interrupts: Interrupt for this device as described in
+   interrupts/interrupts.txt
+ - clocks: An 'ipg' clock defined as described in clocks/clock.txt
+ - interrupt-controller: This device is an interrupt controller. It controls
+   the interrupts of both conversion queues.
+ - #interrupt-cells: Should be '<1>'.
+ - #address-cells: Should be '<1>'.
+ - #size-cells: Should be '<1>'.
+ - ranges
+
+This device includes two conversion queues which can be added as subnodes.
+The first queue is for the touchscreen, the second for general purpose ADC.
+
+Example:
+	tscadc: tscadc@50030000 {
+		compatible = "fsl,imx25-tsadc";
+		reg = <0x50030000 0xc>;
+		interrupts = <46>;
+		clocks = <&clks 119>;
+		clock-names = "ipg";
+		interrupt-controller;
+		#interrupt-cells = <1>;
+		#address-cells = <1>;
+		#size-cells = <1>;
+		ranges;
+
+		tsc: tcq@50030400 {
+			compatible = "fsl,imx25-tcq";
+			reg = <0x50030400 0x60>;
+			...
+		};
+
+		adc: gcq@50030800 {
+			compatible = "fsl,imx25-gcq";
+			reg = <0x50030800 0x60>;
+			...
+		};
+	};
diff --git a/drivers/mfd/Kconfig b/drivers/mfd/Kconfig
index 49bb445..5b43c72 100644
--- a/drivers/mfd/Kconfig
+++ b/drivers/mfd/Kconfig
@@ -163,6 +163,15 @@ config MFD_DA9063
 	  Additional drivers must be enabled in order to use the functionality
 	  of the device.
 
+config MFD_MX25_TSADC
+	depends on ARCH_MXC
+	select REGMAP_MMIO
+	tristate "Freescale i.MX25 integrated Touchscreen and ADC unit"
+	help
+	  Enable support for the integrated Touchscreen and ADC unit of the
+	  i.MX25 processors. They consist of a conversion queue for general
+	  purpose ADC and a queue for Touchscreens.
+
 config MFD_MC13XXX
 	tristate
 	depends on (SPI_MASTER || I2C)
diff --git a/drivers/mfd/Makefile b/drivers/mfd/Makefile
index 5aea5ef..f8c0093 100644
--- a/drivers/mfd/Makefile
+++ b/drivers/mfd/Makefile
@@ -76,6 +76,8 @@ obj-$(CONFIG_TWL4030_POWER)    += twl4030-power.o
 obj-$(CONFIG_MFD_TWL4030_AUDIO)	+= twl4030-audio.o
 obj-$(CONFIG_TWL6040_CORE)	+= twl6040.o
 
+obj-$(CONFIG_MFD_MX25_TSADC)	+= fsl-imx25-tsadc.o
+
 obj-$(CONFIG_MFD_MC13XXX)	+= mc13xxx-core.o
 obj-$(CONFIG_MFD_MC13XXX_SPI)	+= mc13xxx-spi.o
 obj-$(CONFIG_MFD_MC13XXX_I2C)	+= mc13xxx-i2c.o
diff --git a/drivers/mfd/fsl-imx25-tsadc.c b/drivers/mfd/fsl-imx25-tsadc.c
new file mode 100644
index 0000000..549990b
--- /dev/null
+++ b/drivers/mfd/fsl-imx25-tsadc.c
@@ -0,0 +1,234 @@
+/*
+ * Copyright 2014 Markus Pargmann, Pengutronix <mpa@pengutronix.de>
+ *
+ * The code contained herein is licensed under the GNU General Public
+ * License. You may obtain a copy of the GNU General Public License
+ * Version 2 or later at the following locations:
+ *
+ * http://www.opensource.org/licenses/gpl-license.html
+ * http://www.gnu.org/copyleft/gpl.html
+ */
+
+#include <linux/clk.h>
+#include <linux/interrupt.h>
+#include <linux/irq.h>
+#include <linux/irqdesc.h>
+#include <linux/irqdomain.h>
+#include <linux/irqchip/chained_irq.h>
+#include <linux/mfd/imx25-tsadc.h>
+#include <linux/module.h>
+#include <linux/of.h>
+#include <linux/of_platform.h>
+#include <linux/platform_device.h>
+#include <linux/regmap.h>
+
+struct mx25_tsadc_priv {
+	struct regmap *regs;
+	struct irq_domain *domain;
+	struct clk *clk;
+};
+
+static struct regmap_config mx25_tsadc = {
+	.fast_io = true,
+	.max_register = 0x8,
+	.reg_bits = 32,
+	.val_bits = 32,
+	.reg_stride = 4,
+};
+
+struct regmap *mx25_tsadc_get_regmap(struct device *dev)
+{
+	struct platform_device *pdev;
+	struct mx25_tsadc_priv *priv;
+
+	if (!dev)
+		return NULL;
+
+	pdev = container_of(dev, struct platform_device, dev);
+	priv = platform_get_drvdata(pdev);
+	if (IS_ERR_OR_NULL(priv->regs))
+		return NULL;
+
+	return priv->regs;
+}
+EXPORT_SYMBOL(mx25_tsadc_get_regmap);
+
+struct clk *mx25_tsadc_get_ipg(struct device *dev)
+{
+	struct platform_device *pdev;
+	struct mx25_tsadc_priv *priv;
+
+	if (!dev)
+		return NULL;
+
+	pdev = container_of(dev, struct platform_device, dev);
+	priv = platform_get_drvdata(pdev);
+	if (IS_ERR_OR_NULL(priv->clk))
+		return NULL;
+
+	return priv->clk;
+}
+EXPORT_SYMBOL(mx25_tsadc_get_ipg);
+
+static void mx25_tsadc_irq_handler(u32 irq, struct irq_desc *desc)
+{
+	struct mx25_tsadc_priv *priv = irq_desc_get_handler_data(desc);
+	struct irq_chip *chip = irq_get_chip(irq);
+	u32 status;
+
+	chained_irq_enter(chip, desc);
+
+	regmap_read(priv->regs, MX25_TSC_TGSR, &status);
+
+	if (status & MX25_TGSR_GCQ_INT)
+		generic_handle_irq(irq_find_mapping(priv->domain, 1));
+
+	if (status & MX25_TGSR_TCQ_INT)
+		generic_handle_irq(irq_find_mapping(priv->domain, 0));
+
+	chained_irq_exit(chip, desc);
+}
+
+static void mx25_tsadc_nop(struct irq_data *d)
+{
+}
+
+static int mx25_tsadc_set_wake_nop(struct irq_data *d, unsigned int state)
+{
+	return 0;
+}
+
+static struct irq_chip mx25_tsadc_irq_chip = {
+	.name = "mx25-tsadc",
+	.irq_ack = mx25_tsadc_nop,
+	.irq_mask = mx25_tsadc_nop,
+	.irq_unmask = mx25_tsadc_nop,
+	.irq_set_wake = mx25_tsadc_set_wake_nop,
+};
+
+static int mx25_tsadc_domain_map(struct irq_domain *d, unsigned int irq,
+			     irq_hw_number_t hwirq)
+{
+	struct mx25_tsadc_priv *priv = d->host_data;
+
+	irq_set_chip_data(irq, priv);
+	irq_set_chip_and_handler(irq, &mx25_tsadc_irq_chip,
+				 handle_level_irq);
+
+#ifdef CONFIG_ARM
+	set_irq_flags(irq, IRQF_VALID);
+#else
+	irq_set_noprobe(irq);
+#endif
+
+	return 0;
+}
+
+static struct irq_domain_ops mx25_tsadc_domain_ops = {
+	.map = mx25_tsadc_domain_map,
+	.xlate = irq_domain_xlate_onecell,
+};
+
+static int mx25_tsadc_setup_irq(struct platform_device *pdev,
+		struct mx25_tsadc_priv *priv)
+{
+	struct device *dev = &pdev->dev;
+	struct device_node *np = dev->of_node;
+	int irq;
+
+	irq = platform_get_irq(pdev, 0);
+	if (irq < 0) {
+		dev_err(dev, "Failed to get irq\n");
+		return irq;
+	}
+
+	priv->domain = irq_domain_add_simple(np, 2, 0, &mx25_tsadc_domain_ops,
+			priv);
+	if (!priv->domain) {
+		dev_err(dev, "Failed to add irq domain\n");
+		return -ENOMEM;
+	}
+
+	irq_set_chained_handler(irq, mx25_tsadc_irq_handler);
+	irq_set_handler_data(irq, priv);
+
+	return 0;
+}
+
+static int mx25_tsadc_probe(struct platform_device *pdev)
+{
+	struct device *dev = &pdev->dev;
+	struct device_node *np = dev->of_node;
+	struct mx25_tsadc_priv *priv;
+	struct resource *iores;
+	int ret;
+	void __iomem *iomem;
+
+	priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL);
+	if (!priv)
+		return -ENOMEM;
+
+	iores = platform_get_resource(pdev, IORESOURCE_MEM, 0);
+	iomem = devm_ioremap_resource(dev, iores);
+	if (IS_ERR(iomem)) {
+		dev_err(dev, "Failed to remap iomem\n");
+		return PTR_ERR(iomem);
+	}
+
+	priv->regs = regmap_init_mmio(dev, iomem, &mx25_tsadc);
+	if (IS_ERR(priv->regs)) {
+		dev_err(dev, "Failed to initialize regmap\n");
+		return PTR_ERR(priv->regs);
+	}
+
+	priv->clk = devm_clk_get(dev, "ipg");
+	if (IS_ERR(priv->clk)) {
+		dev_err(dev, "Failed to get ipg clock\n");
+		return PTR_ERR(priv->clk);
+	}
+
+	/* Enable clock and reset the component */
+	regmap_update_bits(priv->regs, MX25_TSC_TGCR, MX25_TGCR_CLK_EN,
+			MX25_TGCR_CLK_EN);
+	regmap_update_bits(priv->regs, MX25_TSC_TGCR, MX25_TGCR_TSC_RST,
+			MX25_TGCR_TSC_RST);
+
+	/* Setup powersaving mode, but enable internal reference voltage */
+	regmap_update_bits(priv->regs, MX25_TSC_TGCR, MX25_TGCR_POWERMODE_MASK,
+			MX25_TGCR_POWERMODE_SAVE);
+	regmap_update_bits(priv->regs, MX25_TSC_TGCR, MX25_TGCR_INTREFEN,
+			MX25_TGCR_INTREFEN);
+
+	ret = mx25_tsadc_setup_irq(pdev, priv);
+	if (ret) {
+		dev_err(dev, "Failed to setup irqs\n");
+		return ret;
+	}
+
+	platform_set_drvdata(pdev, priv);
+
+	of_platform_populate(np, NULL, NULL, dev);
+
+	dev_info(dev, "i.MX25/25 Touchscreen and ADC core driver loaded\n");
+
+	return 0;
+}
+
+static const struct of_device_id mx25_tsadc_ids[] = {
+	{ .compatible = "fsl,imx25-tsadc", },
+	{ /* Sentinel */ }
+};
+
+static struct platform_driver mx25_tsadc_driver = {
+	.driver		= {
+		.name	= "mx25-tsadc",
+		.owner	= THIS_MODULE,
+		.of_match_table = mx25_tsadc_ids,
+	},
+	.probe		= mx25_tsadc_probe,
+};
+module_platform_driver(mx25_tsadc_driver);
+
+MODULE_DESCRIPTION("MFD for ADC/TSC for Freescale mx25");
+MODULE_AUTHOR("Markus Pargmann <mpa@pengutronix.de>");
+MODULE_LICENSE("GPL v2");
diff --git a/include/linux/mfd/imx25-tsadc.h b/include/linux/mfd/imx25-tsadc.h
new file mode 100644
index 0000000..6fba341
--- /dev/null
+++ b/include/linux/mfd/imx25-tsadc.h
@@ -0,0 +1,138 @@
+#ifndef _LINUX_INCLUDE_INPUT_IMX25_TSADC_H_
+#define _LINUX_INCLUDE_INPUT_IMX25_TSADC_H_
+
+struct regmap;
+struct device;
+struct clk;
+
+struct regmap *mx25_tsadc_get_regmap(struct device *dev);
+struct clk *mx25_tsadc_get_ipg(struct device *dev);
+
+#define MX25_TSC_TGCR 0x00
+#define MX25_TSC_TGSR 0x04
+#define MX25_TSC_TICR 0x08
+
+/* The same register layout for TC and GC queue */
+#define MX25_ADCQ_FIFO 0x00
+#define MX25_ADCQ_CR 0x04
+#define MX25_ADCQ_SR 0x08
+#define MX25_ADCQ_MR 0x0c
+#define MX25_ADCQ_ITEM_7_0 0x20
+#define MX25_ADCQ_ITEM_15_8 0x24
+#define MX25_ADCQ_CFG(n) (0x40 + ((n) * 0x4))
+
+/* Register values */
+/* Queue Config register */
+#define MX25_ADCQ_MR_MASK 0xffffffff
+
+/* TGCR */
+#define MX25_TGCR_PDBTIME(x) ((x) << 25)
+#define MX25_TGCR_PDBTIME_MASK MX25_TGCR_PDBTIME(0x7f)
+#define MX25_TGCR_PDBEN (1 << 24)
+#define MX25_TGCR_PDEN (1 << 23)
+#define MX25_TGCR_ADCCLKCFG(x) ((x) << 16)
+#define MX25_TGCR_GET_ADCCLK(x) (((x) >> 16) & 0x1f)
+#define MX25_TGCR_INTREFEN (1 << 10)
+#define MX25_TGCR_POWERMODE_MASK (3 << 8)
+#define MX25_TGCR_POWERMODE_SAVE (1 << 8)
+#define MX25_TGCR_POWERMODE_ON (2 << 8)
+#define MX25_TGCR_STLC (1 << 5)
+#define MX25_TGCR_SLPC (1 << 4)
+#define MX25_TGCR_FUNC_RST (1 << 2)
+#define MX25_TGCR_TSC_RST (1 << 1)
+#define MX25_TGCR_CLK_EN (1 << 0)
+
+/* TGSR */
+#define MX25_TGSR_SLP_INT (1 << 2)
+#define MX25_TGSR_GCQ_INT (1 << 1)
+#define MX25_TGSR_TCQ_INT (1 << 0)
+
+/* ADCQ_ITEM_* */
+#define _MX25_ADCQ_ITEM(item, x) ((x) << ((item) * 4))
+#define MX25_ADCQ_ITEM(item, x) ((item) >= 8 ? \
+		_MX25_ADCQ_ITEM((item) - 8, (x)) : _MX25_ADCQ_ITEM((item), (x)))
+
+/* ADCQ_FIFO (TCQFIFO and GCQFIFO) */
+#define MX25_ADCQ_FIFO_DATA(x) (((x) >> 4) & 0xfff)
+#define MX25_ADCQ_FIFO_ID(x) ((x) & 0xf)
+
+/* ADCQ_CR (TCQR and GCQR) */
+#define MX25_ADCQ_CR_PDCFG_LEVEL (1 << 19)
+#define MX25_ADCQ_CR_PDMSK (1 << 18)
+#define MX25_ADCQ_CR_FRST (1 << 17)
+#define MX25_ADCQ_CR_QRST (1 << 16)
+#define MX25_ADCQ_CR_RWAIT_MASK (0xf << 12)
+#define MX25_ADCQ_CR_RWAIT(x) ((x) << 12)
+#define MX25_ADCQ_CR_WMRK_MASK (0xf << 8)
+#define MX25_ADCQ_CR_WMRK(x) ((x) << 8)
+#define MX25_ADCQ_CR_LITEMID_MASK (0xf << 4)
+#define MX25_ADCQ_CR_LITEMID(x) ((x) << 4)
+#define MX25_ADCQ_CR_RPT (1 << 3)
+#define MX25_ADCQ_CR_FQS (1 << 2)
+#define MX25_ADCQ_CR_QSM_MASK 0x3
+#define MX25_ADCQ_CR_QSM_PD 0x1
+#define MX25_ADCQ_CR_QSM_FQS 0x2
+#define MX25_ADCQ_CR_QSM_FQS_PD 0x3
+
+/* ADCQ_SR (TCQSR and GCQSR) */
+#define MX25_ADCQ_SR_FDRY (1 << 15)
+#define MX25_ADCQ_SR_FULL (1 << 14)
+#define MX25_ADCQ_SR_EMPT (1 << 13)
+#define MX25_ADCQ_SR_FDN(x) (((x) >> 8) & 0x1f)
+#define MX25_ADCQ_SR_FRR (1 << 6)
+#define MX25_ADCQ_SR_FUR (1 << 5)
+#define MX25_ADCQ_SR_FOR (1 << 4)
+#define MX25_ADCQ_SR_EOQ (1 << 1)
+#define MX25_ADCQ_SR_PD (1 << 0)
+
+/* ADCQ_MR (TCQMR and GCQMR) */
+#define MX25_ADCQ_MR_FDRY_DMA (1 << 31)
+#define MX25_ADCQ_MR_FER_DMA (1 << 22)
+#define MX25_ADCQ_MR_FUR_DMA (1 << 21)
+#define MX25_ADCQ_MR_FOR_DMA (1 << 20)
+#define MX25_ADCQ_MR_EOQ_DMA (1 << 17)
+#define MX25_ADCQ_MR_PD_DMA (1 << 16)
+#define MX25_ADCQ_MR_FDRY_IRQ (1 << 15)
+#define MX25_ADCQ_MR_FER_IRQ (1 << 6)
+#define MX25_ADCQ_MR_FUR_IRQ (1 << 5)
+#define MX25_ADCQ_MR_FOR_IRQ (1 << 4)
+#define MX25_ADCQ_MR_EOQ_IRQ (1 << 1)
+#define MX25_ADCQ_MR_PD_IRQ (1 << 0)
+
+/* ADCQ_CFG (TICR, TCC0-7,GCC0-7) */
+#define MX25_ADCQ_CFG_SETTLING_TIME(x) ((x) << 24)
+#define MX25_ADCQ_CFG_IGS (1 << 20)
+#define MX25_ADCQ_CFG_NOS_MASK (0xf << 16)
+#define MX25_ADCQ_CFG_NOS(x) (((x) - 1) << 16)
+#define MX25_ADCQ_CFG_WIPER (1 << 15)
+#define MX25_ADCQ_CFG_YNLR (1 << 14)
+#define MX25_ADCQ_CFG_YPLL_HIGH 0
+#define MX25_ADCQ_CFG_YPLL_OFF (1 << 12)
+#define MX25_ADCQ_CFG_YPLL_LOW (3 << 12)
+#define MX25_ADCQ_CFG_XNUR_HIGH 0
+#define MX25_ADCQ_CFG_XNUR_OFF (1 << 10)
+#define MX25_ADCQ_CFG_XNUR_LOW (3 << 10)
+#define MX25_ADCQ_CFG_XPUL_OFF (1 << 9)
+#define MX25_ADCQ_CFG_XPUL_HIGH 0
+#define MX25_ADCQ_CFG_REFP_YP 0
+#define MX25_ADCQ_CFG_REFP_XP (1 << 7)
+#define MX25_ADCQ_CFG_REFP_EXT (2 << 7)
+#define MX25_ADCQ_CFG_REFP_INT (3 << 7)
+#define MX25_ADCQ_CFG_REFP_MASK (3 << 7)
+#define MX25_ADCQ_CFG_IN_XP 0
+#define MX25_ADCQ_CFG_IN_YP (1 << 4)
+#define MX25_ADCQ_CFG_IN_XN (2 << 4)
+#define MX25_ADCQ_CFG_IN_YN (3 << 4)
+#define MX25_ADCQ_CFG_IN_WIPER (4 << 4)
+#define MX25_ADCQ_CFG_IN_AUX0 (5 << 4)
+#define MX25_ADCQ_CFG_IN_AUX1 (6 << 4)
+#define MX25_ADCQ_CFG_IN_AUX2 (7 << 4)
+#define MX25_ADCQ_CFG_REFN_XN 0
+#define MX25_ADCQ_CFG_REFN_YN (1 << 2)
+#define MX25_ADCQ_CFG_REFN_NGND (2 << 2)
+#define MX25_ADCQ_CFG_REFN_NGND2 (3 << 2)
+#define MX25_ADCQ_CFG_REFN_MASK (3 << 2)
+#define MX25_ADCQ_CFG_PENIACK (1 << 1)
+
+
+#endif  /* _LINUX_INCLUDE_INPUT_IMX25_TSADC_H_ */
-- 
1.8.5.3


^ permalink raw reply related

* [PATCH 0/3] arm imx25 touchscreen/ADC drivers
From: Markus Pargmann @ 2014-02-20 16:21 UTC (permalink / raw)
  To: devicetree, linux-input, linux-iio
  Cc: Dmitry Torokhov, Samuel Ortiz, Lee Jones, Jonathan Cameron,
	linux-arm-kernel, kernel, Markus Pargmann

Hi,

This series adds 3 drivers to support the i.MX25 Touchscreen/ADC device.
The device has 3 parts. The core controls some generic functions of the
complete device, including the clock and IRQs. A touchscreen specific
conversion queue that works with the central ADC to detect and convert touch
positions. And a generic conversion queue which is the same hardware as the
touchscreen conversion queue but is supposed to be used for generic ADC
conversions.

There are 3 drivers to support all parts. fsl-imx25-tsadc is a MFD driver which
controls the core. fsl-imx25-tcq is the touchscreen conversion queue driver
which registers a touchscreen input device. fsl-imx25-gcq is the generic
conversion queue driver that registers a iio device for all inputs available.

All drivers are initialized using devicetree bindings.

Regards,

Markus Pargmann


Markus Pargmann (3):
  mfd: fsl imx25 Touchscreen ADC driver
  input: touchscreen: imx25 tcq driver
  iio: adc: fsl,imx25-gcq driver

 .../devicetree/bindings/iio/adc/fsl,imx25-gcq.txt  |  54 ++
 .../bindings/input/touchscreen/fsl-mx25-tcq.txt    |  29 +
 .../devicetree/bindings/mfd/fsl-imx25-tsadc.txt    |  46 ++
 drivers/iio/adc/Kconfig                            |   7 +
 drivers/iio/adc/Makefile                           |   1 +
 drivers/iio/adc/fsl-imx25-gcq.c                    | 325 ++++++++++++
 drivers/input/touchscreen/Kconfig                  |   6 +
 drivers/input/touchscreen/Makefile                 |   1 +
 drivers/input/touchscreen/fsl-imx25-tcq.c          | 589 +++++++++++++++++++++
 drivers/mfd/Kconfig                                |   9 +
 drivers/mfd/Makefile                               |   2 +
 drivers/mfd/fsl-imx25-tsadc.c                      | 234 ++++++++
 include/linux/mfd/imx25-tsadc.h                    | 138 +++++
 13 files changed, 1441 insertions(+)
 create mode 100644 Documentation/devicetree/bindings/iio/adc/fsl,imx25-gcq.txt
 create mode 100644 Documentation/devicetree/bindings/input/touchscreen/fsl-mx25-tcq.txt
 create mode 100644 Documentation/devicetree/bindings/mfd/fsl-imx25-tsadc.txt
 create mode 100644 drivers/iio/adc/fsl-imx25-gcq.c
 create mode 100644 drivers/input/touchscreen/fsl-imx25-tcq.c
 create mode 100644 drivers/mfd/fsl-imx25-tsadc.c
 create mode 100644 include/linux/mfd/imx25-tsadc.h

-- 
1.8.5.3


^ permalink raw reply

* [PATCH 2/2] arm/xen: Don't use xen DMA ops when the device is protected by an IOMMU
From: Julien Grall @ 2014-02-20 16:21 UTC (permalink / raw)
  To: linux-kernel, stefano.stabellini
  Cc: linux-arm-kernel, ian.campbell, xen-devel, Julien Grall,
	Rob Herring, Pawel Moll, Mark Rutland, Ian Campbell, Kumar Gala,
	Rob Landley, Russell King, devicetree

Only Xen is able to know if a device can safely avoid to use xen-swiotlb.
This patch introduce a new property "protected-devices" for the hypervisor
node which list device which the IOMMU are been correctly programmed by Xen.

During Linux boot, Xen specific code will create an hash table which
contains all these devices. The hash table will be used in need_xen_dma_ops
to check if the Xen DMA ops needs to be used for the current device.

Signed-off-by: Julien Grall <julien.grall@linaro.org>
Cc: Rob Herring <robh+dt@kernel.org>
Cc: Pawel Moll <pawel.moll@arm.com>
Cc: Mark Rutland <mark.rutland@arm.com>
Cc: Ian Campbell <ijc+devicetree@hellion.org.uk>
Cc: Kumar Gala <galak@codeaurora.org>
Cc: Rob Landley <rob@landley.net>
Cc: Russell King <linux@arm.linux.org.uk>
Cc: devicetree@vger.kernel.org
---
 Documentation/devicetree/bindings/arm/xen.txt |    2 +
 arch/arm/include/asm/xen/dma-mapping.h        |   11 +++-
 arch/arm/xen/enlighten.c                      |   75 +++++++++++++++++++++++++
 3 files changed, 87 insertions(+), 1 deletion(-)

diff --git a/Documentation/devicetree/bindings/arm/xen.txt b/Documentation/devicetree/bindings/arm/xen.txt
index 0f7b9c2..ee25a57 100644
--- a/Documentation/devicetree/bindings/arm/xen.txt
+++ b/Documentation/devicetree/bindings/arm/xen.txt
@@ -15,6 +15,8 @@ the following properties:
 - interrupts: the interrupt used by Xen to inject event notifications.
   A GIC node is also required.
 
+- protected-devices: (optional) List of phandles to device node where the
+IOMMU has been programmed by Xen.
 
 Example (assuming #address-cells = <2> and #size-cells = <2>):
 
diff --git a/arch/arm/include/asm/xen/dma-mapping.h b/arch/arm/include/asm/xen/dma-mapping.h
index 002fc57..da8e4fe 100644
--- a/arch/arm/include/asm/xen/dma-mapping.h
+++ b/arch/arm/include/asm/xen/dma-mapping.h
@@ -5,9 +5,18 @@
 
 extern struct dma_map_ops *xen_dma_ops;
 
+#ifdef CONFIG_XEN
+bool xen_is_protected_device(const struct device *dev);
+#else
+static inline bool xen_is_protected_device(const struct device *dev)
+{
+	return 0;
+}
+#endif
+
 static inline bool need_xen_dma_ops(struct device *dev)
 {
-	return xen_initial_domain();
+	return xen_initial_domain() && !xen_is_protected_device(dev);
 }
 
 #endif /* _ASM_ARM_XEN_DMA_MAPPING_H */
diff --git a/arch/arm/xen/enlighten.c b/arch/arm/xen/enlighten.c
index b96723e..f124c8c 100644
--- a/arch/arm/xen/enlighten.c
+++ b/arch/arm/xen/enlighten.c
@@ -24,6 +24,7 @@
 #include <linux/cpuidle.h>
 #include <linux/cpufreq.h>
 #include <linux/cpu.h>
+#include <linux/hashtable.h>
 
 #include <linux/mm.h>
 
@@ -53,6 +54,42 @@ EXPORT_SYMBOL_GPL(xen_platform_pci_unplug);
 
 static __read_mostly int xen_events_irq = -1;
 
+/* Hash table for list of devices protected by an IOMMU in Xen */
+#define DEV_HASH_BITS	4
+#define DEV_HASH_SIZE	(1 << DEV_HASH_BITS)
+
+static struct hlist_head *protected_devices;
+
+struct protected_device
+{
+	struct hlist_node hlist;
+	struct device_node *node;
+};
+
+static unsigned long pdev_hash(const struct device_node *node)
+{
+	return (node->phandle % DEV_HASH_SIZE);
+}
+
+bool xen_is_protected_device(const struct device *dev)
+{
+	const struct device_node *node = dev->of_node;
+	unsigned long hash;
+	const struct protected_device *pdev;
+
+	if (!node->phandle)
+		return 0;
+
+	hash = pdev_hash(node);
+
+	hlist_for_each_entry(pdev, &protected_devices[hash], hlist) {
+		if (node == pdev->node)
+			return 1;
+	}
+
+	return 0;
+}
+
 /* map fgmfn of domid to lpfn in the current domain */
 static int map_foreign_page(unsigned long lpfn, unsigned long fgmfn,
 			    unsigned int domid)
@@ -235,6 +272,8 @@ static int __init xen_guest_init(void)
 	const char *xen_prefix = "xen,xen-";
 	struct resource res;
 	phys_addr_t grant_frames;
+	int i = 0;
+	struct device_node *dev;
 
 	node = of_find_compatible_node(NULL, NULL, "xen,xen");
 	if (!node) {
@@ -259,6 +298,31 @@ static int __init xen_guest_init(void)
 	if (xen_events_irq < 0)
 		return -ENODEV;
 
+	protected_devices = kmalloc(DEV_HASH_SIZE * sizeof (*protected_devices),
+				    GFP_KERNEL);
+	if (!protected_devices)
+		return -ENOMEM;
+
+	for (i = 0; i < DEV_HASH_SIZE; i++)
+		INIT_HLIST_HEAD(&protected_devices[i]);
+
+	pr_info("List of protected devices:\n");
+	i = 0;
+	while ((dev = of_parse_phandle(node, "protected-devices", i))) {
+		struct protected_device *pdev;
+		unsigned long hash;
+
+		pr_info(" - %s\n", of_node_full_name(dev));
+		pdev = kmalloc(sizeof (*pdev), GFP_KERNEL);
+		if (!pdev)
+			goto free_hash;
+
+		pdev->node = dev;
+		hash = pdev_hash(dev);
+		hlist_add_head(&pdev->hlist, &protected_devices[hash]);
+		i++;
+	}
+
 	xen_domain_type = XEN_HVM_DOMAIN;
 
 	xen_setup_features();
@@ -324,6 +388,17 @@ static int __init xen_guest_init(void)
 	register_cpu_notifier(&xen_cpu_notifier);
 
 	return 0;
+free_hash:
+	for (i = 0; i < DEV_HASH_SIZE; i++) {
+		struct protected_device *pdev;
+		struct hlist_node *next;
+
+		hlist_for_each_entry_safe(pdev, next, &protected_devices[i],
+					  hlist)
+			kfree(pdev);
+	}
+	kfree(protected_devices);
+	return -ENOMEM;
 }
 early_initcall(xen_guest_init);
 
-- 
1.7.10.4

^ permalink raw reply related

* Re: [PATCH 3/4] tty: serial: bcm63xx_uart: add support for DT probing
From: Florian Fainelli @ 2014-02-20 16:18 UTC (permalink / raw)
  To: Arnd Bergmann, Jonas Gorski
  Cc: linux-serial, devicetree@vger.kernel.org, Maxime Bizon,
	Greg Kroah-Hartman
In-Reply-To: <4709421.TpqQL1VssO@wuerfel>

Hi Arnd,

Le 20/02/2014 04:16, Arnd Bergmann a écrit :
> On Thursday 20 February 2014 11:59:04 Jonas Gorski wrote:
>> On Thu, Feb 20, 2014 at 2:29 AM, Florian Fainelli <f.fainelli@gmail.com> wrote:
>>> 2014-02-19 16:00 GMT-08:00 Jonas Gorski <jogo@openwrt.org>:
>>>> On Thu, Feb 20, 2014 at 12:22 AM, Florian Fainelli <f.fainelli@gmail.com> wrote:
>>>>> @@ -857,6 +861,12 @@ static int bcm_uart_remove(struct platform_device *pdev)
>>>>>          return 0;
>>>>>   }
>>>>>
>>>>> +static const struct of_device_id bcm63xx_of_match[] = {
>>>>> +       { .compatible = "brcm,bcm63xx-uart" },
>>>>
>>>>  From my understanding, this should be "brcm,bcm6345-uart", because
>>>> this kind of uart appeared first on bcm6345 (well, maybe bcm6335, no
>>>> idea which one of these two was first, but the latter was never
>>>> supported in mainline anyway).
>>>
>>> That's right, in fact, I think it might be desirable to handle both
>>> compatible string, just as a hint that it is compatible with the
>>> entire bcm63xx family. Would that work for you?
>>
>> I think using a "generic" compatible string is rather frowned upon
>> (what do you do if there is eventually a bcm63xx chip with an
>> incompatible uart?), but I'm no device tree expert.
>
> It's ok to have a generic name, it's wildcards like the xx above
> that we try to avoid, since that breaks down when you get another
> device in the same SoC family that is not compatible. This is different
> from the Linux way of naming things.
>
> brcm,bcm6345-uart sounds good, if that is the closest we can get
> to a generic name, working under the assumption that it's the oldest
> implementation of this UART. Ideally we'd find someone with access
> to the design documents of the SoC to tell us what the UART is really
> called by whoever designed it (which may not even be Broadcom).

This is just called an uart, it does not have any specific project name 
as far as I could see, and BCM6345 was indeed the very first SoC using it.

>
> If we think there may be some level of variation between the UARTS
> in the various bcm63xx SoCs, it would be good to list both the
> specific model of the SoC as well as the generic name in "compatible",
> so the driver can later detect those differences without requiring
> an updated DT.

Makes sense. So far this UART has been not modified (as far as a 
programmer may be concerned) since its very first design in a BCM6345.

>
> A BCM63138 for instance could list this as
>
> 	compatible = "brcm,bcm62138-uart", "brcm-bcm6345-uart";
>
> 	Arnd
>
--
To unsubscribe from this list: send the line "unsubscribe linux-serial" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html

^ permalink raw reply

* Re: [PATCH 07/10] spi: sh-msiof: Add support for R-Car H2 and M2
From: Geert Uytterhoeven @ 2014-02-20 16:13 UTC (permalink / raw)
  To: Magnus Damm
  Cc: Mark Brown, Takashi Yoshii, linux-spi, SH-Linux, linux-kernel,
	Geert Uytterhoeven, devicetree@vger.kernel.org
In-Reply-To: <CANqRtoQVJzEgo_AdVxrPSRUY6ocyPaQ=RKQJyxoExDrfYxiJ3w@mail.gmail.com>

On Thu, Feb 20, 2014 at 4:41 PM, Magnus Damm <magnus.damm@gmail.com> wrote:
> On thing stuck out a bit with the bindings. I can see that you specify
> both fifo size and use the SoC suffix for the r8a7790 and r8a7791
> bindings. Isn't that a bit of redundant information there, if we know
> that the SoC is r8a7790 or r8a7791 then can't we simply put that
> information in r8a779x_data above and perhaps keep the binding
> simpler? Perhaps same thing applies to other properties as well?

"renesas,tx-fifo-size" and "renesas,rx-fifo-size" are part of the existing
bindings, so I'm a bit reluctant to change these.
Hmm, since the original bindings didn't specify the default values,
I could make them chip-specific, though.

The only other property is "num-cs", which can have any value if you
start using the generic "cs-gpios".

Gr{oetje,eeting}s,

                        Geert

--
Geert Uytterhoeven -- There's lots of Linux beyond ia32 -- geert@linux-m68k.org

In personal conversations with technical people, I call myself a hacker. But
when I'm talking to journalists I just say "programmer" or something like that.
                                -- Linus Torvalds

^ permalink raw reply

* Re: [PATCH v5 2/2] memory: ti-aemif: add bindings for AEMIF driver
From: Ivan Khoronzhuk @ 2014-02-20 15:49 UTC (permalink / raw)
  To: Rob Herring
  Cc: Mark Rutland, devicetree@vger.kernel.org,
	grygorii.strashko@ti.com, linux@arm.linux.org.uk, Pawel Moll,
	swarren@wwwdotorg.org, gregkh@linuxfoundation.org,
	ijc+devicetree@hellion.org.uk, nsekhar@ti.com,
	galak@kernel.crashing.org, rob.herring@calxeda.com,
	linux-kernel@vger.kernel.org, santosh.shilimkar@ti.com,
	rob@landley.net, linux-mtd@lists.infradead.org,
	dwmw2@infradead.org, linux-arm-kernel@lists.infradead.org
In-Reply-To: <CAL_JsqJ5hoQ3vWaQTo8--jiPPQ64OW_b4zKTe7aPLXN0td4DrA@mail.gmail.com>


On 02/20/2014 03:44 PM, Rob Herring wrote:
> On Thu, Feb 20, 2014 at 6:44 AM, Ivan Khoronzhuk <ivan.khoronzhuk@ti.com> wrote:
>> On 02/19/2014 08:11 PM, Mark Rutland wrote:
>>> On Wed, Feb 19, 2014 at 01:40:10PM +0000, Ivan Khoronzhuk wrote:
>>>> Add bindings for TI Async External Memory Interface (AEMIF) controller.
>>>>
>>>> The Async External Memory Interface (EMIF16/AEMIF) controller is intended
>>>> to
>>>> provide a glue-less interface to a variety of asynchronous memory devices
>>>> like
>>>> ASRA M, NOR and NAND memory. A total of 256M bytes of any of these
>>>> memories
>>>> can be accessed via 4 chip selects with 64M byte access per chip select.
>>>>
>>>> We are not encoding CS number in reg property, it's memory partition
>>>> number.
>>>> The CS number is encoded for Davinci NAND node using standalone property
>>>> "ti,davinci-chipselect" and we need to provide two memory ranges to it,
>>>> as result we can't encode CS number in "reg" for AEMIF child devices
>>>> (NAND/NOR/etc), as it will break bindings compatibility.
>>>>
>>>> In this patch, NAND node is used just as an example of child node.
>>>>
>>>> Signed-off-by: Ivan Khoronzhuk <ivan.khoronzhuk@ti.com>
>>>> ---
>>>>    .../bindings/memory-controllers/ti-aemif.txt       | 210
>>>> +++++++++++++++++++++
>>>>    1 file changed, 210 insertions(+)
>>>>    create mode 100644
>>>> Documentation/devicetree/bindings/memory-controllers/ti-aemif.txt
>>> [...]
>>>
>>>> +- ranges:              Contains memory regions. There are two types of
>>>> +                       ranges/partitions:
>>>> +                       - CS-specific partition/range. If continuous,
>>>> must be
>>>> +                       set up to reflect the memory layout for 4
>>>> chipselects,
>>>> +                       if not then additional range/partition can be
>>>> added and
>>>> +                       child device can select the proper one.
>>>> +                       - control partition which is common for all CS
>>>> +                       interfaces.
>>> This really doesn't sound anything like the typical meaning of ranges on
>>> a bus.
>>>
>>> Why isn't this information encoded in reg properties on the child nodes?
>>>
>>> [...]
>>
>> Note that we do not introduce NAND device bindings here.
>> The Davinci NAND bindings was introduced and accepted more then one year
>> ago.
>> And the CS number is encoded for Davinci NAND node using standalone property
>>
>> "ti,davinci-chipselect" and we need to provide two memory ranges to it,
>> as result we can't encode CS number in "reg" for AEMIF child devices
>> (NAND/NOR/etc),
>> as it will break bindings compatibility.
>>
>> In this document, NAND node is used just as an example of child node.
>>
>>
>>>> +- ti,cs-ss:            enable/disable select strobe mode
>>>> +                               In select strobe mode chip select behaves
>>>> as
>>>> +                               the strobe and is active only during the
>>>> strobe
>>>> +                               period. If present then enable.
>>>> +
>>>> +- ti,cs-ew:            enable/disable extended wait mode
>>>> +                               if set, the controller monitors the
>>>> EMIFWAIT pin
>>>> +                               mapped to that chip select to determine
>>>> if the
>>>> +                               device wants to extend the strobe period.
>>>> If
>>>> +                               present then enable.
>>> When would you have these two in the DT and when wouldn't you? Why can't
>>> the driver decide?
>>
>> These are properties of cs node, not the driver itself.
>> The driver cannot know what child device you are going to attach to cs node
>> , as result it cannot decide what settings you are using for particular cs
>> node.
>>
>>
>>> These names are also opaque. We can clearly do better.
>>
>> I propose the following names?:
>>
>> ti,cs-ss  --> ti,cs-select-strobe-mode
>> ti,cs-ew --> ti,cs-extended-waite-mode
>>
>> Are you OK with it?
>>
>>
>>>> +
>>>> +- ti,cs-ta:            minimum turn around time, ns
>>>> +                               Time between the end of one asynchronous
>>>> memory
>>>> +                               access and the start of another
>>>> asynchronous
>>>> +                               memory access. This delay is not incurred
>>>> +                               between a read followed by read or a
>>>> write
>>>> +                               followed by a write to same chip select.
>>> The name is opaque. How about ti,min-turnaround-time-ns ?
>>
>> I like without -ns suffix and with cs- prefix:
>> ti,cs-ta --> ti,cs-min-turnaround-time
>>
>> Is it OK?
>>
>>
>>>> +
>>>> +- ti,cs-rsetup:                read setup width, ns
>>>> +                               Time between the beginning of a memory
>>>> cycle
>>>> +                               and the activation of read strobe.
>>>> +                               Minimum value is 1 (0 treated as 1).
>>>> +
>>>> +- ti,cs-rstobe:                read strobe width, ns
>>>> +                               Time between the activation and
>>>> deactivation of
>>>> +                               the read strobe.
>>>> +                               Minimum value is 1 (0 treated as 1).
>>>> +
>>>> +- ti,cs-rhold:         read hold width, ns
>>>> +                               Time between the deactivation of the read
>>>> +                               strobe and the end of the cycle (which
>>>> may be
>>>> +                               either an address change or the
>>>> deactivation of
>>>> +                               the chip select signal.
>>>> +                               Minimum value is 1 (0 treated as 1).
>>>> +
>>>> +- ti,cs-wsetup:                write setup width, ns
>>>> +                               Time between the beginning of a memory
>>>> cycle
>>>> +                               and the activation of write strobe.
>>>> +                               Minimum value is 1 (0 treated as 1).
>>>> +
>>>> +- ti,cs-wstrobe:       write strobe width, ns
>>>> +                               Time between the activation and
>>>> deactivation of
>>>> +                               the write strobe.
>>>> +                               Minimum value is 1 (0 treated as 1).
>>>> +
>>>> +- ti,cs-whold:         write hold width, ns
>>>> +                               Time between the deactivation of the
>>>> write
>>>> +                               strobe and the end of the cycle (which
>>>> may be
>>>> +                               either an address change or the
>>>> deactivation of
>>>> +                               the chip select signal.
>>>> +                               Minimum value is 1 (0 treated as 1).
>>> Likewise I think these can be given more descriptive names.
>>
>> Ok. How about:
>>
>> ti,cs-rsetup --> ti,cs-read-setup-time
>> ti,cs-rstobe --> ti,cs-read-strobe-time
>> ti,cs-rhold  --> ti,cs-read-hold-time
>> ti,cs-wsetup --> ti,cs-write-setup-time
>> ti,cs-wstrobe --> ti,cs-write-strobe-time
>> ti,cs-whold --> ti,cs-write-hold-time
> Properties that have a unit of measure should have that unit in the
> name. So replace "time" with "ns".
>
> Rob

Ok, I will replace

Thanks!

-- 
Regards,
Ivan Khoronzhuk

^ permalink raw reply

* Re: [PATCH 07/10] spi: sh-msiof: Add support for R-Car H2 and M2
From: Magnus Damm @ 2014-02-20 15:41 UTC (permalink / raw)
  To: Geert Uytterhoeven
  Cc: Mark Brown, Takashi Yoshii, linux-spi-u79uwXL29TY76Z2rM5mHXA,
	SH-Linux, linux-kernel, Geert Uytterhoeven,
	devicetree-u79uwXL29TY76Z2rM5mHXA@public.gmane.org
In-Reply-To: <1392907389-21798-8-git-send-email-geert-Td1EMuHUCqxL1ZNQvxDV9g@public.gmane.org>

On Thu, Feb 20, 2014 at 11:43 PM, Geert Uytterhoeven
<geert-Td1EMuHUCqxL1ZNQvxDV9g@public.gmane.org> wrote:
> From: Geert Uytterhoeven <geert+renesas-Td1EMuHUCqxL1ZNQvxDV9g@public.gmane.org>
>
> Add support for the MSIOF variant in the R-Car H2 (r8a7790) and M2
> (r8a7791) SoCs.
>
> Binding documentation:
>   - Add future-proof "renesas,msiof-<soctype>" compatible values,
>   - Add example bindings.
>
> Implementation:
>   - MSIOF on R-Car H2 and M2 requires the transmission of dummy data if
>     data is being received only (cfr. "Set SICTR.TSCKE to 1" and "Write
>     dummy transmission data to SITFDR" in paragraph "Transmit and Receive
>     Procedures" of the Hardware User's Manual).
>   - As RX depends on TX, MSIOF on R-Car H2 and M2 also lacks the RSCR
>     register (Receive Clock Select Register), and some bits in the RMDR1
>     (Receive Mode Register 1) and TMDR2 (Transmit Mode Register 2)
>     registers.
>   - Use the recently introduced SPI_MASTER_MUST_TX flag to enable support
>     for dummy transmission in the SPI core, and to differentiate from other
>     MSIOF implementations in code paths that need this.
>   - New DT compatible values ("renesas,msiof-r8a7790" and
>     "renesas,msiof-r8a7791") are added, as well as new platform device
>     names ("spi_r8a7790_msiof" and "spi_r8a7791_msiof").
>   - Hardware features are indicated using a new struct sh_msiof_chipdata,
>     which is used for both DT and legacy binding. For now this contains the
>     SPI master flags only.
>
> This is loosely based on a set of patches from Takashi Yoshii
> <takasi-y-nDL5PR/MsHhHfZP73Gtkiw@public.gmane.org>.
>
> Signed-off-by: Geert Uytterhoeven <geert+renesas-Td1EMuHUCqxL1ZNQvxDV9g@public.gmane.org>
> Cc: Takashi Yoshii <takasi-y-nDL5PR/MsHhHfZP73Gtkiw@public.gmane.org>
> Cc: devicetree-u79uwXL29TY76Z2rM5mHXA@public.gmane.org
> ---
>  Documentation/devicetree/bindings/spi/sh-msiof.txt |   21 +++++++-
>  drivers/spi/spi-sh-msiof.c                         |   57 ++++++++++++++++----
>  2 files changed, 66 insertions(+), 12 deletions(-)
>
> diff --git a/drivers/spi/spi-sh-msiof.c b/drivers/spi/spi-sh-msiof.c
> index 92515c1ececa..31624fb4997d 100644
> --- a/drivers/spi/spi-sh-msiof.c
> +++ b/drivers/spi/spi-sh-msiof.c
> @@ -659,6 +671,23 @@ static u32 sh_msiof_spi_txrx_word(struct spi_device *spi, unsigned nsecs,
>  }
>
>  #ifdef CONFIG_OF
> +static const struct sh_msiof_chipdata sh_data = {
> +       .master_flags = 0,
> +};
> +
> +static const struct sh_msiof_chipdata r8a779x_data = {
> +       .master_flags = SPI_MASTER_MUST_TX,
> +};
> +
> +static const struct of_device_id sh_msiof_match[] = {
> +       { .compatible = "renesas,sh-msiof",        .data = &sh_data },
> +       { .compatible = "renesas,sh-mobile-msiof", .data = &sh_data },
> +       { .compatible = "renesas,msiof-r8a7790",   .data = &r8a779x_data },
> +       { .compatible = "renesas,msiof-r8a7791",   .data = &r8a779x_data },
> +       {},
> +};
> +MODULE_DEVICE_TABLE(of, sh_msiof_match);

Hi Geert,

Thanks for your patches. They all look good in general I think.

On thing stuck out a bit with the bindings. I can see that you specify
both fifo size and use the SoC suffix for the r8a7790 and r8a7791
bindings. Isn't that a bit of redundant information there, if we know
that the SoC is r8a7790 or r8a7791 then can't we simply put that
information in r8a779x_data above and perhaps keep the binding
simpler? Perhaps same thing applies to other properties as well?

Cheers,

/ magnus
--
To unsubscribe from this list: send the line "unsubscribe devicetree" in
the body of a message to majordomo-u79uwXL29TY76Z2rM5mHXA@public.gmane.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html

^ permalink raw reply

* Re: [PATCH 0/2] Translate of PCI address without PCI enabled
From: Grant Likely @ 2014-02-20 15:35 UTC (permalink / raw)
  To: Ezequiel Garcia, Gregory CLEMENT
  Cc: Rob Herring, devicetree-u79uwXL29TY76Z2rM5mHXA,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA, Jason Cooper, Andrew Lunn,
	Sebastian Hesselbarth, Thomas Petazzoni,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Lior Amsalem,
	Tawfik Bayouk, Nadav Haklai
In-Reply-To: <20140220005027.GA5721@localhost>

On Wed, 19 Feb 2014 21:50:28 -0300, Ezequiel Garcia <ezequiel.garcia@free-electrons.com> wrote:
> On Wed, Feb 19, 2014 at 11:14:54PM +0100, Gregory CLEMENT wrote:
> > Hello,
> > 
> > This patch set makes the use of the of PCI address translator less
> > restrictive. At the end it will allow to use the mvebu_get_soc_id
> > unconditionally.
> > 
> > The mvebu SoC (such as Kirkwood, Dove or Armada XP for instance) come
> > with an IP of a PCI controller. The ID and the revision of a SoC are
> > stored in the registers of this controller. Being able to get this
> > information allows to deals with errata more dynamically.
> > 
> > To manage to read this information, we need to map the registers, and
> > for this we need to use the of PCI translator which depend of the PCI
> > support.
> > 
> > However there are mvebu board without any PCI devices, and where
> > selecting the PCI support would be useless.
> > 
> > Moreover translating an address from a PCI node of the device-tree
> > into a CPU physical address doesn't require the core PCI
> > support. Those translations are just related to the device tree
> > itself.
> > 
> > The 1st patch introduces a new config symbol: OF_ADDRESS_PCI, which
> > will be selected as soon as PCI will be selected, so we remains in the
> > same situation the current code. It should go to the of tree.
> > 
> > The 2nd patch selects OF_ADDRESS_PCI as soon as ARCH_MVEBU will be
> > selected. This will make mvebu_get_soc_id available even without the
> > PCI support. It should go to the mvebu tree.
> > 
> > Thanks,
> > 
> > Gregory CLEMENT (2):
> >   of: Allows to use the PCI translator without the PCI core
> >   ARM: mvebu: Allows to get the SoC ID even without PCI enabled
> > 
> >  arch/arm/mach-mvebu/Kconfig | 1 +
> >  drivers/of/Kconfig          | 4 ++++
> >  drivers/of/address.c        | 8 +++++---
> >  3 files changed, 10 insertions(+), 3 deletions(-)
> > 
> > -- 
> > 1.8.1.2
> > 
> 
> On XP GP and CONFIG_PCI=n, without the patches I get this:
> 
>   mvebu-soc-id: cannot map registers
> 
> and after applying the patches I have:
> 
>   mvebu-soc-id: MVEBU SoC ID=0x7846, Rev=0x2
> 
> Tested-by: Ezequiel Garcia <ezequiel.garcia-wi1+55ScJUtKEb57/3fJTNBPR1lH4CV8@public.gmane.org>
> Reviewed-by: Ezequiel Garcia <ezequiel.garcia-wi1+55ScJUtKEb57/3fJTNBPR1lH4CV8@public.gmane.org>

Applied both, thanks.

g.

> 
> Thanks for taking care of this.
> -- 
> Ezequiel García, Free Electrons
> Embedded Linux, Kernel and Android Engineering
> http://free-electrons.com

--
To unsubscribe from this list: send the line "unsubscribe devicetree" in
the body of a message to majordomo-u79uwXL29TY76Z2rM5mHXA@public.gmane.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html

^ permalink raw reply

* Re: [PATCH] dt: platform driver: Fill the resources before probe and defer if needed
From: Grant Likely @ 2014-02-20 15:30 UTC (permalink / raw)
  To: gregkh, robh+dt
  Cc: linux-kernel, devicetree, gregory.clement, linux-arm-kernel,
	Jean-Jacques Hiblot
In-Reply-To: <1392285429-9325-1-git-send-email-jjhiblot@traphandler.com>

On Thu, 13 Feb 2014 10:57:09 +0100, Jean-Jacques Hiblot <jjhiblot@traphandler.com> wrote:
> The goal of this patch is to allow drivers to be probed even if at the time of
> the DT parsing some of their ressources are not available yet.
> 
> In the current situation, the resource of a platform device are filled from the
> DT at the time the device is created (of_device_alloc()). The drawbackof this
> is that a device sitting close to the top of the DT (ahb for example) but
> depending on ressources that are initialized later (IRQ domain dynamically
> created for example)  will fail to probe because the ressources don't exist
> at this time.
> 
> This patch fills the resource structure only before the device is probed and
> will defer the probe if the resource are not available yet.
> 
> Signed-off-by: Jean-Jacques Hiblot <jjhiblot@traphandler.com>
> Reviewed-by: Gregory CLEMENT <gregory.clement@free-electrons.com>

Hi Jean-Jacques. Thanks for looking at this, it is a longstanding
problem. However, I'm leary of this approach because it makes failed
probes (which are intended to be cheap) into an expensive operation. If
a device goes through multiple rounds of deferred probe, then every time
it will attempt to decode the needed resources. Parsing 'reg' isn't too
bad, but parsing the interrupts may not be. I think it needs to be more
nuanced and only recalculate the resources that failed in previous
attempts...

...however, the other argument that correctness is more important than
efficiency here and it would be better to completely teardown the
resources table, or at least the interrupt entries, after a failed
probe or driver removal to handle the case where the interrupt
controller is re-bound to its driver and gets a new set of interrupt
numbers...

I think this patch can be reworked into something better though...

> ---
>  drivers/base/platform.c     |  6 ++++
>  drivers/of/platform.c       | 71 +++++++++++++++++++++++++++++----------------
>  include/linux/of_platform.h | 10 +++++++
>  3 files changed, 62 insertions(+), 25 deletions(-)
> 
> diff --git a/drivers/base/platform.c b/drivers/base/platform.c
> index bc78848..8e37d8b 100644
> --- a/drivers/base/platform.c
> +++ b/drivers/base/platform.c
> @@ -481,6 +481,12 @@ static int platform_drv_probe(struct device *_dev)
>  	struct platform_device *dev = to_platform_device(_dev);
>  	int ret;
>  
> +	if (_dev->of_node) {
> +		ret = of_platform_device_populate_resources(dev);
> +		if (ret < 0)
> +			return drv->prevent_deferred_probe ? ret : -EPROBE_DEFER;
> +	}
> +

Get rid of the _dev->of_node() test. It should be embedded in the
function. Also, rename it to: of_platform_device_prepare()

>  	if (ACPI_HANDLE(_dev))
>  		acpi_dev_pm_attach(_dev, true);
>  
> diff --git a/drivers/of/platform.c b/drivers/of/platform.c
> index 404d1da..64a8eb8 100644
> --- a/drivers/of/platform.c
> +++ b/drivers/of/platform.c
> @@ -141,36 +141,11 @@ struct platform_device *of_device_alloc(struct device_node *np,
>  				  struct device *parent)
>  {
>  	struct platform_device *dev;
> -	int rc, i, num_reg = 0, num_irq;
> -	struct resource *res, temp_res;
>  
>  	dev = platform_device_alloc("", -1);
>  	if (!dev)
>  		return NULL;
>  
> -	/* count the io and irq resources */
> -	if (of_can_translate_address(np))
> -		while (of_address_to_resource(np, num_reg, &temp_res) == 0)
> -			num_reg++;
> -	num_irq = of_irq_count(np);
> -
> -	/* Populate the resource table */
> -	if (num_irq || num_reg) {
> -		res = kzalloc(sizeof(*res) * (num_irq + num_reg), GFP_KERNEL);
> -		if (!res) {
> -			platform_device_put(dev);
> -			return NULL;
> -		}
> -
> -		dev->num_resources = num_reg + num_irq;
> -		dev->resource = res;
> -		for (i = 0; i < num_reg; i++, res++) {
> -			rc = of_address_to_resource(np, i, res);
> -			WARN_ON(rc);
> -		}
> -		WARN_ON(of_irq_to_resource_table(np, res, num_irq) != num_irq);
> -	}
> -
>  	dev->dev.of_node = of_node_get(np);
>  #if defined(CONFIG_MICROBLAZE)
>  	dev->dev.dma_mask = &dev->archdata.dma_mask;
> @@ -233,6 +208,52 @@ static struct platform_device *of_platform_device_create_pdata(
>  	return dev;
>  }
>  
> +int of_platform_device_populate_resources(struct platform_device *dev)
> +{
> +	struct device_node *np;
> +	int rc = 0, i, nreg = 0, nirq;
> +
> +	np = dev->dev.of_node;
> +
> +	/* count the io and irq resources */
> +	if (of_can_translate_address(np)) {
> +		struct resource temp_res;
> +		while (of_address_to_resource(np, nreg, &temp_res) == 0)
> +			nreg++;
> +	}

The above snippet should be encapsulated in an of_reg_count() helper function.

> +	nirq = of_irq_count(np);
> +
> +	/* Populate the resource table */
> +	if (nirq || nreg) {
> +		struct resource *res;
> +
> +		res = krealloc(dev->resource, sizeof(*res) * (nirq + nreg),
> +			       GFP_KERNEL);
> +		if (!res) {
> +			kfree(dev->resource);
> +			dev->resource = NULL;
> +			return -ENOMEM;
> +		}
> +		memset(res, 0, sizeof(*res) * (nirq + nreg));
> +		dev->resource = res;
> +		dev->num_resources = nreg + nirq;
> +
> +		if (!rc && of_irq_to_resource_table(np, res, nirq) != nirq) {
> +			rc = -ENOENT;
> +			WARN_ON(rc);
> +		}
> +	}
> +	return rc;
> +}

Reallocation is not necessary. We can know exactly how many tuples are
in the reg and interrupts properties. Once allocated the array will be
the right size. (may need to fix of_irq_count() though).

Also, the reg resources will always be correct. They don't need to be
recalculated each time through. IRQs however are the problem area. A
simplistic implementation which is still better than current mainline
would be the following:

	if (!nirq && !nreg)
		return 0;

	if (!dev->resource) {
		res = kzalloc(dev->resource, sizeof(*res) * (nirq + nreg),
			       GFP_KERNEL);
		if (!res)
			return -ENOMEM;

		for (i = 0; i < nreg; i++, res++) {
			rc = of_address_to_resource(np, i, res);
			if (WARN_ON(rc)) {
				/* THIS IS BAD; don't try to defer probing */
				kfree(res);
				return rc;
			}
		}

		dev->resource = res;
		dev->num_resources = nreg + nirq;

		if (of_irq_to_resource_table(np, dev->resource, nirq) != nirq)
			return -EPROBE_DEFER;

		return 0;
	}

	/* See which IRQ resources need to be redone */
	for (i = 0, res = &dev->resource[nreg]; i < nirq; i++, res++)
		if (!res->flags && !of_irq_to_resource(np, i, res))
			return -EPROBE_DEFER;

	return 0;

It isn't optimal because it cannot handle irq controllers being
replugged, but still better than the current code.

Can you respin and let me know if the above works for you?

Thanks,
g.

> +EXPORT_SYMBOL(of_platform_device_populate_resources);
> +
>  /**
>   * of_platform_device_create - Alloc, initialize and register an of_device
>   * @np: pointer to node to create device for
> diff --git a/include/linux/of_platform.h b/include/linux/of_platform.h
> index 05cb4a9..315e1e3 100644
> --- a/include/linux/of_platform.h
> +++ b/include/linux/of_platform.h
> @@ -53,6 +53,16 @@ struct of_dev_auxdata {
>  
>  extern const struct of_device_id of_default_bus_match_table[];
>  
> +/* Populate the resource for a platform device */
> +#ifdef CONFIG_OF
> +int of_platform_device_populate_resources(struct platform_device *dev);
> +#else
> +static inline int of_platform_device_populate_resources(
> +	struct platform_device *)
> +{
> +	return -ENOSYS;
> +}
> +#endif
>  /* Platform drivers register/unregister */
>  extern struct platform_device *of_device_alloc(struct device_node *np,
>  					 const char *bus_id,
> -- 
> 1.8.5.3
> 

^ permalink raw reply

* Re: [PATCH RFC v1 2/3] of: Add definition of maximum length of a property name
From: Sylwester Nawrocki @ 2014-02-20 15:02 UTC (permalink / raw)
  To: Rob Herring
  Cc: linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r@public.gmane.org,
	devicetree-u79uwXL29TY76Z2rM5mHXA@public.gmane.org,
	Mike Turquette, Russell King - ARM Linux, Rob Herring,
	Grant Likely, Mark Rutland, Kumar Gala, Kyungmin Park,
	sw0312.kim-Sze3O3UU22JBDgjK7y7TUQ, Marek Szyprowski, Tomasz Figa
In-Reply-To: <CAL_Jsq+0pmLHC2Xo=i3kvQMo+uukraK1nRyPZReKtwE_GEaGFQ-JsoAwUIsXosN+BqQ9rBEUg@public.gmane.org>

On 19/02/14 22:42, Rob Herring wrote:
> On Wed, Feb 19, 2014 at 10:58 AM, Sylwester Nawrocki
> <s.nawrocki-Sze3O3UU22JBDgjK7y7TUQ@public.gmane.org> wrote:
>> > Maximum length of a property name is defined by ePAPR (2.2.4.1) as
>> > 31 characters. Add a corresponding definition, including the trailing
>> > null space.
>
> Does dtc enforce this? It would be good to add if not.

As far as I can see there is nothing currently enforcing this in dtc.
There is no related check and too long property names are accepted
silently.
I'll try and see if I can prepare a patch for this, until someone more
familiar with dtc does it.

--
Regards,
Sylwester
--
To unsubscribe from this list: send the line "unsubscribe devicetree" in
the body of a message to majordomo-u79uwXL29TY76Z2rM5mHXA@public.gmane.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html

^ permalink raw reply

* Re: devicetree repository separation/migration
From: Rob Herring @ 2014-02-20 15:01 UTC (permalink / raw)
  To: frowand.list-Re5JQEeQqe8AvxtiuMwx3w
  Cc: Tim Bird, Olof Johansson, Jason Cooper, Sascha Hauer,
	Grant Likely, Ian Campbell, Pawel Moll, Mark Rutland, Kumar Gala,
	Rob Landley, devicetree-u79uwXL29TY76Z2rM5mHXA@public.gmane.org,
	devicetree-spec-u79uwXL29TY76Z2rM5mHXA,
	devicetree-compiler-u79uwXL29TY76Z2rM5mHXA
In-Reply-To: <530522F8.8050102-Re5JQEeQqe8AvxtiuMwx3w@public.gmane.org>

On Wed, Feb 19, 2014 at 3:32 PM, Frank Rowand <frowand.list-Re5JQEeQqe8AvxtiuMwx3w@public.gmane.org> wrote:
> On 2/19/2014 1:12 PM, Rob Herring wrote:
>> On Tue, Feb 18, 2014 at 4:44 PM, Tim Bird <tbird20d-Re5JQEeQqe8AvxtiuMwx3w@public.gmane.org> wrote:
>>> I'm not in favor of separating the device tree information from the kernel.
>>>
>>> If we switch, then whatever synchronization issues other projects
>>> are having now with synching with the device tree info from the kernel will
>>> just then become the problem of the kernel developers, who will then
>>> have to sync with the device tree info from another repository.  If the
>>> sync issues can't be solved now for them, why or how would it be solved
>>> post-separation for us?  (It sounds like a zero-sum game of pain transfer
>>> to me.)
>>>
>>> I'm relatively unfamiliar with the arguments.  Can someone provide
>>> a brief list of reasons this is needed, and how the inconvenience to Linux
>>> kernel developers will be minimized, should it proceed?
>>
>> - Primarily, other projects like u-boot, barebox, FreeBSD and possibly
>> TianoCore (UEFI) are using DT now. Leaving them in the kernel will
>> cause fragmentation. The statements about barebox needing to add
>> barebox properties to the dtb is exactly the kind of fragmentation I'm
>> worried about.
>
> "Devicetree only describes the hardware" (paraphrasing a claim often made).
> If the linux kernel dts files do not fully describe the hardware then it
> is appropriate to add the missing info.

Yes, but if hardware description is what is being added, then that is
not bootloader specific. I would guess this case is not h/w
description, but I don't know as none of it has been posted for
review. The real problem here is adding bindings without review.

Not fully describing the h/w and adding to the dts is common and not
really an issue as long as it is done in an ABI compatible way.

>> - The need to share dts fragments across arches. This is a bit
>> orthogonal, but this restructuring would be easier done outside the
>> kernel tree. Restructuring everything in the kernel tree and then
>> moving it out would be a lot of churn.
>
> The churn will occur no matter what repository the files are in.

Yes, but doing this in the kernel is much harder to coordinate with
Linus and architecture maintainers. I don't think we want to go thru
that process when we plan to just remove everything.

>> - As we add schema checking, we need somewhere to put those.
>
> And why does _that_ need to be in an external repository?

For the same reason as everything else (binding docs, dts files), so
people outside of kernel developers will contribute.

>>
>> One way to minimize the inconvenience is keep versioning and dev
>> cycles in sync with the kernel. We could also start doing things to
>> align the kernel workflow with how things will work when we do have a
>> separate repository.
>
> If you stay in sync with the kernel then you are still tied to the
> linux kernel source repository.  No gain.

The only synchronization would be tagging the repo at the same time
and using the same version numbering. Using that versus working on
master all the time would be completely up to end users. It's really
only encouraging people to test a specific combination of kernel and
dtb. The other option is we simply make up our own tagging/release
scheme.

Rob
--
To unsubscribe from this list: send the line "unsubscribe devicetree-compiler" in
the body of a message to majordomo-u79uwXL29TY76Z2rM5mHXA@public.gmane.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html

^ permalink raw reply

* [PATCH v2 2/2] ARM: shmobile: bockw reference dts: Add SPI FLASH
From: Geert Uytterhoeven @ 2014-02-20 14:57 UTC (permalink / raw)
  To: Simon Horman
  Cc: linux-spi, devicetree, linux-arm-kernel, linux-sh, linux-kernel,
	Geert Uytterhoeven
In-Reply-To: <1392908239-22645-1-git-send-email-geert@linux-m68k.org>

From: Geert Uytterhoeven <geert+renesas@linux-m68k.org>

Add Spansion s25fl008k SPI FLASH and MTD partition, based on bockw legacy
board code.

Signed-off-by: Geert Uytterhoeven <geert+renesas@linux-m68k.org>
Tested-by: Kuninori Morimoto <kuninori.morimoto.gx@renesas.com>
---
v2:
  - Add Tested-by

 arch/arm/boot/dts/r8a7778-bockw-reference.dts |   14 ++++++++++++++
 1 file changed, 14 insertions(+)

diff --git a/arch/arm/boot/dts/r8a7778-bockw-reference.dts b/arch/arm/boot/dts/r8a7778-bockw-reference.dts
index 06cda19dac6a..f76f6ec01e19 100644
--- a/arch/arm/boot/dts/r8a7778-bockw-reference.dts
+++ b/arch/arm/boot/dts/r8a7778-bockw-reference.dts
@@ -109,4 +109,18 @@
 	pinctrl-0 = <&hspi0_pins>;
 	pinctrl-names = "default";
 	status = "okay";
+
+	flash: flash@0 {
+		#address-cells = <1>;
+		#size-cells = <1>;
+		compatible = "spansion,s25fl008k";
+		reg = <0>;
+		spi-max-frequency = <104000000>;
+		m25p,fast-read;
+
+		partition@0 {
+			label = "data(spi)";
+			reg = <0x00000000 0x00100000>;
+		};
+	};
 };
-- 
1.7.9.5


^ permalink raw reply related

* [PATCH v2 1/2] ARM: shmobile: r8a7778/r8a7779 dtsi: Improve and correct HSPI bindings
From: Geert Uytterhoeven @ 2014-02-20 14:57 UTC (permalink / raw)
  To: Simon Horman
  Cc: linux-spi, devicetree, linux-arm-kernel, linux-sh, linux-kernel,
	Geert Uytterhoeven, Mark Brown

From: Geert Uytterhoeven <geert+renesas@linux-m68k.org>

Binding documentation:
  - Add future-proof "renesas,hspi-<soctype>" compatible values,
  - Add "interrupt-parent", "#address-cells" and "#size-cells" properties,
  - Add reference to pinctrl documentation,
  - Add example bindings.

r8a7778 and r8a7779 dtsi:
  - Add "renesas,hspi-r8a7778" resp. "renesas,hspi-r8a7779" compatible
    values,
  - Correct reference to parent interrupt controller
    (use "interrupt-parent" instead of "interrupt-controller"),
  - Add missing "#address-cells" and "#size-cells" properties, which are
    needed when populating the SPI buses.

Signed-off-by: Geert Uytterhoeven <geert+renesas@linux-m68k.org>
Tested-by: Kuninori Morimoto <kuninori.morimoto.gx@renesas.com> [HSPI/BockW]
Cc: Mark Brown <broonie@linaro.org>
---
v2:
  - Add Tested-by
  - List full example compatible properties with soctypes instead of just
    the soctypes, so checkpatch can validate DTSes.

 Documentation/devicetree/bindings/spi/sh-hspi.txt |   28 ++++++++++++++++++---
 arch/arm/boot/dts/r8a7778.dtsi                    |   18 ++++++++-----
 arch/arm/boot/dts/r8a7779.dtsi                    |   18 ++++++++-----
 3 files changed, 49 insertions(+), 15 deletions(-)

diff --git a/Documentation/devicetree/bindings/spi/sh-hspi.txt b/Documentation/devicetree/bindings/spi/sh-hspi.txt
index 30b57b1c8a13..319bad4af875 100644
--- a/Documentation/devicetree/bindings/spi/sh-hspi.txt
+++ b/Documentation/devicetree/bindings/spi/sh-hspi.txt
@@ -1,7 +1,29 @@
 Renesas HSPI.
 
 Required properties:
-- compatible : 	"renesas,hspi"
-- reg : Offset and length of the register set for the device
-- interrupts : interrupt line used by HSPI
+- compatible       : "renesas,hspi-<soctype>", "renesas,hspi" as fallback.
+		     Examples with soctypes are:
+		       - "renesas,hspi-r8a7778" (R-Car M1)
+		       - "renesas,hspi-r8a7779" (R-Car H1)
+- reg              : Offset and length of the register set for the device
+- interrupt-parent : The phandle for the interrupt controller that
+		     services interrupts for this device
+- interrupts       : Interrupt specifier
+- #address-cells   : Must be <1>
+- #size-cells      : Must be <0>
+
+Pinctrl properties might be needed, too.  See
+Documentation/devicetree/bindings/pinctrl/renesas,*.
+
+Example:
+
+	hspi0: spi@fffc7000 {
+		compatible = "renesas,hspi-r8a7778", "renesas,hspi";
+		reg = <0xfffc7000 0x18>;
+		interrupt-parent = <&gic>;
+		interrupts = <0 63 IRQ_TYPE_LEVEL_HIGH>;
+		#address-cells = <1>;
+		#size-cells = <0>;
+		status = "disabled";
+	};
 
diff --git a/arch/arm/boot/dts/r8a7778.dtsi b/arch/arm/boot/dts/r8a7778.dtsi
index 85c5b3b99f5e..3c6fab5c9702 100644
--- a/arch/arm/boot/dts/r8a7778.dtsi
+++ b/arch/arm/boot/dts/r8a7778.dtsi
@@ -204,26 +204,32 @@
 	};
 
 	hspi0: spi@fffc7000 {
-		compatible = "renesas,hspi";
+		compatible = "renesas,hspi-r8a7778", "renesas,hspi";
 		reg = <0xfffc7000 0x18>;
-		interrupt-controller = <&gic>;
+		interrupt-parent = <&gic>;
 		interrupts = <0 63 IRQ_TYPE_LEVEL_HIGH>;
+		#address-cells = <1>;
+		#size-cells = <0>;
 		status = "disabled";
 	};
 
 	hspi1: spi@fffc8000 {
-		compatible = "renesas,hspi";
+		compatible = "renesas,hspi-r8a7778", "renesas,hspi";
 		reg = <0xfffc8000 0x18>;
-		interrupt-controller = <&gic>;
+		interrupt-parent = <&gic>;
 		interrupts = <0 84 IRQ_TYPE_LEVEL_HIGH>;
+		#address-cells = <1>;
+		#size-cells = <0>;
 		status = "disabled";
 	};
 
 	hspi2: spi@fffc6000 {
-		compatible = "renesas,hspi";
+		compatible = "renesas,hspi-r8a7778", "renesas,hspi";
 		reg = <0xfffc6000 0x18>;
-		interrupt-controller = <&gic>;
+		interrupt-parent = <&gic>;
 		interrupts = <0 85 IRQ_TYPE_LEVEL_HIGH>;
+		#address-cells = <1>;
+		#size-cells = <0>;
 		status = "disabled";
 	};
 };
diff --git a/arch/arm/boot/dts/r8a7779.dtsi b/arch/arm/boot/dts/r8a7779.dtsi
index d0561d4c7c46..8b1a336ee401 100644
--- a/arch/arm/boot/dts/r8a7779.dtsi
+++ b/arch/arm/boot/dts/r8a7779.dtsi
@@ -256,26 +256,32 @@
 	};
 
 	hspi0: spi@fffc7000 {
-		compatible = "renesas,hspi";
+		compatible = "renesas,hspi-r8a7779", "renesas,hspi";
 		reg = <0xfffc7000 0x18>;
-		interrupt-controller = <&gic>;
+		interrupt-parent = <&gic>;
 		interrupts = <0 73 IRQ_TYPE_LEVEL_HIGH>;
+		#address-cells = <1>;
+		#size-cells = <0>;
 		status = "disabled";
 	};
 
 	hspi1: spi@fffc8000 {
-		compatible = "renesas,hspi";
+		compatible = "renesas,hspi-r8a7779", "renesas,hspi";
 		reg = <0xfffc8000 0x18>;
-		interrupt-controller = <&gic>;
+		interrupt-parent = <&gic>;
 		interrupts = <0 74 IRQ_TYPE_LEVEL_HIGH>;
+		#address-cells = <1>;
+		#size-cells = <0>;
 		status = "disabled";
 	};
 
 	hspi2: spi@fffc6000 {
-		compatible = "renesas,hspi";
+		compatible = "renesas,hspi-r8a7779", "renesas,hspi";
 		reg = <0xfffc6000 0x18>;
-		interrupt-controller = <&gic>;
+		interrupt-parent = <&gic>;
 		interrupts = <0 75 IRQ_TYPE_LEVEL_HIGH>;
+		#address-cells = <1>;
+		#size-cells = <0>;
 		status = "disabled";
 	};
 };
-- 
1.7.9.5


^ permalink raw reply related

* Re: [PATCH 1/1] ARM: Exynos: Add generic compatible string
From: Tomasz Figa @ 2014-02-20 14:51 UTC (permalink / raw)
  To: Sachin Kamat
  Cc: linux-samsung-soc, Kukjin Kim, Arnd Bergmann,
	linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r@public.gmane.org,
	Olof Johansson,
	devicetree-u79uwXL29TY76Z2rM5mHXA@public.gmane.org, Rob Herring,
	Mark Rutland, Grant Likely, Ian Campbell
In-Reply-To: <CAK9yfHy7YHDLCfUGA-ua4iLzK2PMotVZvC=51t-bMkVZVBQFaA-JsoAwUIsXosN+BqQ9rBEUg@public.gmane.org>

[adding DT ML and DT maintainers on Cc for some discussion]

On 20.02.2014 05:14, Sachin Kamat wrote:
> Hi Tomasz,
>
> On 19 February 2014 18:15, Tomasz Figa <t.figa-Sze3O3UU22JBDgjK7y7TUQ@public.gmane.org> wrote:
>> Hi Sachin,
>>
>> [adding linux-arm-kernel ML to CC list]
>>
>>
>> On 19.02.2014 12:34, Sachin Kamat wrote:
>>>
>>> To avoid modifying the kernel every time a new SoC variant
>>> comes out.
> <snip>
>>
>> Since all Exynos chips can be easily recognized using dedicated chip ID
>> register, I wonder whether we really need to maintain two distinct board
>> files for Exynos 4 and 5 series, especially when both of them are doing
>> mostly the same set up, which can be simply generalized to cover all the
>> cases.
>>
>> Instead of adding just another level of artificially fine grained compatible
>> strings, I'd rather suggest merging both board files together and adding a
>> single compatible string identifying all SoCs that can be further
>> differentiated by using hardware chip ID register.
>>
>> What do you think?
>
> I agree with your idea of merging both the files as there is very little that is
> different for now. However I am not really sure if having a single compatible
> string for all SoCs would be good. What is achieved through compatible string
> can very well be done using chip ID too. But wouldn't we need to maintain some
> unique identity for the SoCs in human readable form at the DT level?

Well, my understanding of Device Tree is that it should provide the 
information that can't be automatically retrieved from the hardware, not 
more.

If you have a PCI or USB bus with enumerable devices, you don't list 
them in DT, but instead limit the description to just the host 
controller, if it can't be enumerated.

Same goes for compatible string. My interpretation of it is that if you 
can identify the hardware by some automatic means, e.g. querying some ID 
register, then the compatible should be specific enough to identify the 
class of devices with the same method of querying such register, with no 
need for any additional redundant data in DT.

Of course nothing stops you from retaining more specific compatible 
strings. In fact, this is probably the most appropriate solution, 
because in future you might find out that certain SoCs need some special 
differentiation, e.g. same ID value on two SoCs.

So, to apply this to our case, our Exynos 5250 based Arndale board would 
be changed from

compatible = "insignal,arndale", "samsung,exynos5260";

to

compatible = "insignal,arndale", "samsung,exynos5260", "samsung,exynos";

Now, the board file will be able to match simply by "samsung,exynos" 
compatible string and SoC-specific code in mach-exynos (hopefully none 
after it gets cleaned up fully) will use soc_is_exynos*() macros (what 
AFAIK it is already doing at the moment).

Another benefit of this would be increased safety, because you are 
reading SoC type from actual hardware, not from externally supplied 
data. In conjunction with the more specific compatible string (e.g. 
"samsung,exynos5260") some validation could be performed at boot-up time 
to make sure that DT for correct SoC is used.

> In the absence
> of any other opinion, can probably experiment with this and see how it
> takes shape.
>
>
>> P.S. Please always keep respective subsystem/arch level MLs on CC list, in
>> this case linux-arm-kernel. The linux-samsung-soc ML is just a convenience
>> tool to group all threads about Samsung SoCs, not a way to bypass respective
>> subsystem MLs.
>
> Nothing to disagree. A valid point at large, but for every trivial or
> exynos specific
> change, including top level MLs would probably amount to spamming :)

I agree that for simple discussion threads samsung-soc list alone might 
be sufficient, but any patches should be subject to broader review, not 
limited to Samsung people.

Best regards,
Tomasz
--
To unsubscribe from this list: send the line "unsubscribe devicetree" in
the body of a message to majordomo-u79uwXL29TY76Z2rM5mHXA@public.gmane.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html

^ permalink raw reply

* [PATCH 11/11] ARM: shmobile: koelsch dts: Add MSIOF nodes
From: Geert Uytterhoeven @ 2014-02-20 14:49 UTC (permalink / raw)
  To: Simon Horman, Magnus Damm
  Cc: linux-sh, linux-arm-kernel, linux-kernel, Geert Uytterhoeven,
	devicetree
In-Reply-To: <1392907779-22053-1-git-send-email-geert@linux-m68k.org>

From: Geert Uytterhoeven <geert+renesas@linux-m68k.org>

Add pinctrl and SPI device for MSIOF on Koelsch.
On this board, only MSIOF0 is in use. Its bus contains a single device
(a Renesas R2A11302FT PMIC), for which no bindings are defined yet.

Signed-off-by: Geert Uytterhoeven <geert+renesas@linux-m68k.org>
Cc: devicetree@vger.kernel.org
---
 arch/arm/boot/dts/r8a7791-koelsch.dts |   21 +++++++++++++++++++++
 1 file changed, 21 insertions(+)

diff --git a/arch/arm/boot/dts/r8a7791-koelsch.dts b/arch/arm/boot/dts/r8a7791-koelsch.dts
index cc6e63914f7c..b29ca85b248f 100644
--- a/arch/arm/boot/dts/r8a7791-koelsch.dts
+++ b/arch/arm/boot/dts/r8a7791-koelsch.dts
@@ -150,6 +150,12 @@
 		renesas,groups = "qspi_ctrl", "qspi_data4";
 		renesas,function = "qspi";
 	};
+
+	msiof0_pins: spi1 {
+		renesas,groups = "msiof0_clk", "msiof0_sync", "msiof0_rx",
+				 "msiof0_tx";
+		renesas,function = "msiof0";
+	};
 };
 
 &sata0 {
@@ -186,3 +192,18 @@
 		};
 	};
 };
+
+&msiof0 {
+	pinctrl-0 = <&msiof0_pins>;
+	pinctrl-names = "default";
+
+	status = "okay";
+
+	pmic: pmic@0 {
+		compatible = "renesas,r2a11302ft";
+		reg = <0>;
+		spi-max-frequency = <6000000>;
+		spi-cpol;
+		spi-cpha;
+	};
+};
-- 
1.7.9.5

^ permalink raw reply related

* [PATCH 10/11] ARM: shmobile: lager dts: Add MSIOF nodes
From: Geert Uytterhoeven @ 2014-02-20 14:49 UTC (permalink / raw)
  To: Simon Horman, Magnus Damm
  Cc: linux-sh, linux-arm-kernel, linux-kernel, Geert Uytterhoeven,
	devicetree
In-Reply-To: <1392907779-22053-1-git-send-email-geert@linux-m68k.org>

From: Geert Uytterhoeven <geert+renesas@linux-m68k.org>

Add pinctrl and SPI device for MSIOF on Lager.
On this board, only MSIOF1 is in use. Its bus contains a single device
(a Renesas R2A11302FT PMIC), for which no bindings are defined yet.

Signed-off-by: Geert Uytterhoeven <geert+renesas@linux-m68k.org>
Cc: devicetree@vger.kernel.org
---
 arch/arm/boot/dts/r8a7790-lager.dts |   22 ++++++++++++++++++++++
 1 file changed, 22 insertions(+)

diff --git a/arch/arm/boot/dts/r8a7790-lager.dts b/arch/arm/boot/dts/r8a7790-lager.dts
index 5d53def10c42..0658c881687e 100644
--- a/arch/arm/boot/dts/r8a7790-lager.dts
+++ b/arch/arm/boot/dts/r8a7790-lager.dts
@@ -148,6 +148,12 @@
 		renesas,groups = "qspi_ctrl", "qspi_data4";
 		renesas,function = "qspi";
 	};
+
+	msiof1_pins: spi2 {
+		renesas,groups = "msiof1_clk", "msiof1_sync", "msiof1_rx",
+				 "msiof1_tx";
+		renesas,function = "msiof1";
+	};
 };
 
 &mmcif1 {
@@ -195,6 +201,22 @@
 	};
 };
 
+&msiof1 {
+	pinctrl-0 = <&msiof1_pins>;
+	pinctrl-names = "default";
+
+	status = "okay";
+
+	pmic: pmic@0 {
+		compatible = "renesas,r2a11302ft";
+		reg = <0>;
+		spi-max-frequency = <6000000>;
+		spi-cpol;
+		spi-cpha;
+	};
+
+};
+
 &sdhi0 {
 	pinctrl-0 = <&sdhi0_pins>;
 	pinctrl-names = "default";
-- 
1.7.9.5


^ permalink raw reply related


This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox