* Re: [v11, 7/8] base: soc: introduce soc_device_match() interface
From: Ulf Hansson @ 2016-09-06 11:44 UTC (permalink / raw)
To: Yangbo Lu
Cc: linux-mmc, Scott Wood, Arnd Bergmann,
linuxppc-dev-uLR06cmDAlY/bJ5BZ2RsiQ@public.gmane.org,
devicetree-u79uwXL29TY76Z2rM5mHXA@public.gmane.org,
linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r@public.gmane.org,
linux-kernel-u79uwXL29TY76Z2rM5mHXA@public.gmane.org, linux-clk,
linux-i2c-u79uwXL29TY76Z2rM5mHXA@public.gmane.org,
iommu-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA,
netdev-u79uwXL29TY76Z2rM5mHXA, Mark Rutland, Rob Herring,
Russell King, Jochen Friedrich, Joerg Roedel, Claudiu Manoil,
Bhupesh Sharma <bhupe>
In-Reply-To: <1473150503-9550-8-git-send-email-yangbo.lu-3arQi8VN3Tc@public.gmane.org>
On 6 September 2016 at 10:28, Yangbo Lu <yangbo.lu-3arQi8VN3Tc@public.gmane.org> wrote:
> We keep running into cases where device drivers want to know the exact
> version of the a SoC they are currently running on. In the past, this has
> usually been done through a vendor specific API that can be called by a
> driver, or by directly accessing some kind of version register that is
> not part of the device itself but that belongs to a global register area
> of the chip.
>
> Common reasons for doing this include:
>
> - A machine is not using devicetree or similar for passing data about
> on-chip devices, but just announces their presence using boot-time
> platform devices, and the machine code itself does not care about the
> revision.
>
> - There is existing firmware or boot loaders with existing DT binaries
> with generic compatible strings that do not identify the particular
> revision of each device, but the driver knows which SoC revisions
> include which part.
>
> - A prerelease version of a chip has some quirks and we are using the same
> version of the bootloader and the DT blob on both the prerelease and the
> final version. An update of the DT binding seems inappropriate because
> that would involve maintaining multiple copies of the dts and/or
> bootloader.
>
> This patch introduces the soc_device_match() interface that is meant to
> work like of_match_node() but instead of identifying the version of a
> device, it identifies the SoC itself using a vendor-agnostic interface.
>
> Unlike of_match_node(), we do not do an exact string compare but instead
> use glob_match() to allow wildcards in strings.
Overall, this change make sense to me, although some minor comment below.
>
> Signed-off-by: Arnd Bergmann <arnd-r2nGTMty4D4@public.gmane.org>
> Signed-off-by: Yangbo Lu <yangbo.lu-3arQi8VN3Tc@public.gmane.org>
> ---
> Changes for v11:
> - Added this patch for soc match
> ---
> drivers/base/Kconfig | 1 +
> drivers/base/soc.c | 61 +++++++++++++++++++++++++++++++++++++++++++++++++
> include/linux/sys_soc.h | 3 +++
> 3 files changed, 65 insertions(+)
>
> diff --git a/drivers/base/Kconfig b/drivers/base/Kconfig
> index 98504ec..f1591ad2 100644
> --- a/drivers/base/Kconfig
> +++ b/drivers/base/Kconfig
> @@ -225,6 +225,7 @@ config GENERIC_CPU_AUTOPROBE
>
> config SOC_BUS
> bool
> + select GLOB
>
> source "drivers/base/regmap/Kconfig"
>
> diff --git a/drivers/base/soc.c b/drivers/base/soc.c
> index 75b98aa..5c4e84a 100644
> --- a/drivers/base/soc.c
> +++ b/drivers/base/soc.c
> @@ -14,6 +14,7 @@
> #include <linux/spinlock.h>
> #include <linux/sys_soc.h>
> #include <linux/err.h>
> +#include <linux/glob.h>
>
> static DEFINE_IDA(soc_ida);
>
> @@ -168,3 +169,63 @@ static void __exit soc_bus_unregister(void)
> bus_unregister(&soc_bus_type);
> }
> module_exit(soc_bus_unregister);
> +
> +static int soc_device_match_one(struct device *dev, void *arg)
> +{
> + struct soc_device *soc_dev = container_of(dev, struct soc_device, dev);
> + const struct soc_device_attribute *match = arg;
> +
> + if (match->machine &&
> + !glob_match(match->machine, soc_dev->attr->machine))
> + return 0;
> +
> + if (match->family &&
> + !glob_match(match->family, soc_dev->attr->family))
> + return 0;
> +
> + if (match->revision &&
> + !glob_match(match->revision, soc_dev->attr->revision))
> + return 0;
> +
> + if (match->soc_id &&
> + !glob_match(match->soc_id, soc_dev->attr->soc_id))
> + return 0;
> +
> + return 1;
> +}
> +
> +/*
> + * soc_device_match - identify the SoC in the machine
> + * @matches: zero-terminated array of possible matches
Perhaps also express the constraint on the matching entries. As you
need at least one of the ->machine(), ->family(), ->revision() or
->soc_id() callbacks implemented, right!?
> + *
> + * returns the first matching entry of the argument array, or NULL
> + * if none of them match.
> + *
> + * This function is meant as a helper in place of of_match_node()
> + * in cases where either no device tree is available or the information
> + * in a device node is insufficient to identify a particular variant
> + * by its compatible strings or other properties. For new devices,
> + * the DT binding should always provide unique compatible strings
> + * that allow the use of of_match_node() instead.
> + *
> + * The calling function can use the .data entry of the
> + * soc_device_attribute to pass a structure or function pointer for
> + * each entry.
I don't get the use case behind this, could you elaborate?
Perhaps we should postpone adding the .data entry until we actually
see a need for it?
> + */
> +const struct soc_device_attribute *soc_device_match(
> + const struct soc_device_attribute *matches)
> +{
> + struct device *dev;
> + int ret;
> +
> + for (ret = 0; ret == 0; matches++) {
This loop looks a bit weird and unsafe.
1) Perhaps using a while loop makes this more readable?
2) As this is an exported API, I guess validation of the ->matches
pointer needs to be done before accessing it.
> + if (!(matches->machine || matches->family ||
> + matches->revision || matches->soc_id))
> + return NULL;
> + dev = NULL;
There's no need to use a struct device just to assign it to NULL.
Instead just provide the function below with NULL.
> + ret = bus_for_each_dev(&soc_bus_type, dev, (void *)matches,
> + soc_device_match_one);
> + }
> + return matches;
> +}
> +EXPORT_SYMBOL_GPL(soc_device_match);
> diff --git a/include/linux/sys_soc.h b/include/linux/sys_soc.h
> index 2739ccb..9f5eb06 100644
> --- a/include/linux/sys_soc.h
> +++ b/include/linux/sys_soc.h
> @@ -13,6 +13,7 @@ struct soc_device_attribute {
> const char *family;
> const char *revision;
> const char *soc_id;
> + const void *data;
> };
>
> /**
> @@ -34,4 +35,6 @@ void soc_device_unregister(struct soc_device *soc_dev);
> */
> struct device *soc_device_to_device(struct soc_device *soc);
>
> +const struct soc_device_attribute *soc_device_match(
> + const struct soc_device_attribute *matches);
> #endif /* __SOC_BUS_H */
> --
> 2.1.0.27.g96db324
>
Kind regards
Uffe
--
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 2/2] i2c: mux: mellanox: add driver
From: Peter Rosin @ 2016-09-06 11:00 UTC (permalink / raw)
To: vadimp, wsa; +Cc: linux-i2c, linux-kernel, jiri, Michael Shych
In-Reply-To: <1472492176-195844-1-git-send-email-vadimp@mellanox.com>
On 2016-08-29 19:36, vadimp@mellanox.com wrote:
> From: Vadim Pasternak <vadimp@mellanox.com>
>
> This driver allows I2C routing controlled through CPLD select registers on
> wide range of Mellanox systems (CPLD Lattice device).
> MUX selection is provided by digital and analog HW. Analog part is not
> under SW control.
> Digital part is under CPLD control (channel selection/de-selection).
>
> Connectivity schema.
> i2c-mlxcpld Digital Analog
> driver
> *--------* * -> mux1 (virt bus2) -> mux ->|
> | I2CLPC | i2c physical * -> mux2 (virt bus3) -> mux ->|
> | bridge | bus 1 *---------* |
> | logic |---------------------> * mux reg * |
> | in CPLD| *---------* |
> *--------* i2c-mux-mlxpcld ^ * -> muxn (virt busn) -> mux ->|
> | driver | |
> | *---------------* | Devices
> | * CPLD (LPC bus)* select |
> | * registers for *--------*
> | * mux selection * deselect
> | *---------------*
> | |
> <--------> <----------->
> i2c cntrl Board cntrl reg
> reg space space (mux select,
> | IO, LED, WD, info)
> | | *-----* *-----*
> *------------- LPC bus --------------| PCH |---| CPU |
> *-----* *-----*
>
> i2c-mux-mlxpcld does not necessary required i2c-mlxcpld. It can be use
> along with another bus driver, and still control i2c routing through CPLD
> mux selection, in case the system is equipped with CPLD capable of mux
> selection control.
>
> The Kconfig currently controlling compilation of this code is:
> drivers/i2c/muxes/Kconfig:config I2C_MUX_MLXCPLD
>
> Signed-off-by: Michael Shych <michaelsh@mellanox.com>
> Signed-off-by: Vadim Pasternak <vadimp@mellanox.com>
> Reviewed-by: Jiri Pirko <jiri@mellanox.com>
BTW, it just occurred to me that you could perhaps use (and extend if
needed) the i2c_mux_reg driver for the lpc_access cases. Have you
explored that option? It looks like a nice fit, and limiting this new
driver to i2c_access would make it significantly simpler with only
one device (mux module) and one access method (i2c) to support.
Cheers,
Peter
^ permalink raw reply
* Re: [PATCH V2 0/9] Some Tegra I2C Updates
From: Jon Hunter @ 2016-09-06 9:52 UTC (permalink / raw)
To: Wolfram Sang
Cc: Laxman Dewangan, Stephen Warren, Thierry Reding,
Alexandre Courbot, linux-i2c-u79uwXL29TY76Z2rM5mHXA,
linux-tegra-u79uwXL29TY76Z2rM5mHXA,
linux-kernel-u79uwXL29TY76Z2rM5mHXA
In-Reply-To: <20160830203844.GD3645@katana>
On 30/08/16 21:38, Wolfram Sang wrote:
> * PGP Signed by an unknown key
>
> On Fri, Aug 26, 2016 at 02:08:56PM +0100, Jon Hunter wrote:
>> Add runtime-pm and pinctrl support for Tegra I2C driver.
>>
>> The first 6 patches are trivial clean-up/simplification changes.
>>
>> Changes since V1:
>> - Fixed cppcheck warning reported by Wolfram
>> - Added 3 more clean-up patches to fix some checkpatch issues
>>
>> Jon Hunter (9):
>> i2c: tegra: Fix lines over 80 characters
>> i2c: tegra: Use BIT macro
>> i2c: tegra: Fix missing blank lines after declarations
>> i2c: tegra: Add missing new line characters
>> i2c: tegra: Remove non device-tree support
>> i2c: tegra: Use device name for adapter name
>> i2c: tegra: Simplify I2C resume
>> i2c: tegra: Add runtime power-management support
>> i2c: tegra: Add pinctrl support
>>
>
> Applied to for-next, thanks!
>
> If you are in for some more cleanups ;)
>
> SPATCH
> drivers/i2c/busses/i2c-tegra.c:529:2-23: WARNING: Assignment of bool to 0/1
> drivers/i2c/busses/i2c-tegra.c:555:3-24: WARNING: Assignment of bool to 0/1
Thanks! I have sent a patch to fix these.
Cheers
Jon
--
nvpublic
^ permalink raw reply
* [PATCH] i2c: tegra: Fix assignment of boolean variables
From: Jon Hunter @ 2016-09-06 9:50 UTC (permalink / raw)
To: Wolfram Sang
Cc: Laxman Dewangan, linux-i2c-u79uwXL29TY76Z2rM5mHXA,
linux-tegra-u79uwXL29TY76Z2rM5mHXA, Jon Hunter
Fix the following warnings reported by coccinelle for the Tegra I2C
driver.
drivers/i2c/busses/i2c-tegra.c:513:2-23: WARNING: Assignment of bool to 0/1
drivers/i2c/busses/i2c-tegra.c:539:3-24: WARNING: Assignment of bool to 0/1
Reported-by: Wolfram Sang <wsa-z923LK4zBo2bacvFa/9K2g@public.gmane.org>
Signed-off-by: Jon Hunter <jonathanh-DDmLM1+adcrQT0dZR+AlfA@public.gmane.org>
---
drivers/i2c/busses/i2c-tegra.c | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/drivers/i2c/busses/i2c-tegra.c b/drivers/i2c/busses/i2c-tegra.c
index d86a993b75d6..7398930172f3 100644
--- a/drivers/i2c/busses/i2c-tegra.c
+++ b/drivers/i2c/busses/i2c-tegra.c
@@ -510,7 +510,7 @@ static int tegra_i2c_init(struct tegra_i2c_dev *i2c_dev)
}
if (i2c_dev->irq_disabled) {
- i2c_dev->irq_disabled = 0;
+ i2c_dev->irq_disabled = false;
enable_irq(i2c_dev->irq);
}
@@ -536,7 +536,7 @@ static irqreturn_t tegra_i2c_isr(int irq, void *dev_id)
if (!i2c_dev->irq_disabled) {
disable_irq_nosync(i2c_dev->irq);
- i2c_dev->irq_disabled = 1;
+ i2c_dev->irq_disabled = true;
}
goto err;
}
--
2.1.4
^ permalink raw reply related
* [v11, 8/8] mmc: sdhci-of-esdhc: fix host version for T4240-R1.0-R2.0
From: Yangbo Lu @ 2016-09-06 8:28 UTC (permalink / raw)
To: linux-mmc-u79uwXL29TY76Z2rM5mHXA,
ulf.hansson-QSEj5FYQhm4dnm+yROfE0A, Scott Wood, Arnd Bergmann
Cc: Mark Rutland, devicetree-u79uwXL29TY76Z2rM5mHXA, Russell King,
Yangbo Lu, Bhupesh Sharma, netdev-u79uwXL29TY76Z2rM5mHXA,
Santosh Shilimkar, linux-kernel-u79uwXL29TY76Z2rM5mHXA,
Jochen Friedrich, xiaobo.xie-3arQi8VN3Tc,
iommu-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA, Rob Herring,
linux-i2c-u79uwXL29TY76Z2rM5mHXA, Claudiu Manoil, Kumar Gala,
leoyang.li-3arQi8VN3Tc, linuxppc-dev-uLR06cmDAlY/bJ5BZ2RsiQ,
linux-clk-u79uwXL29TY76Z2rM5mHXA,
linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Qiang Zhao
In-Reply-To: <1473150503-9550-1-git-send-email-yangbo.lu-3arQi8VN3Tc@public.gmane.org>
The eSDHC of T4240-R1.0-R2.0 has incorrect vender version and spec version.
Acturally the right version numbers should be VVN=0x13 and SVN = 0x1.
This patch adds the GUTS driver support for eSDHC driver to match SoC.
And fix host version to avoid that incorrect version numbers break down
the ADMA data transfer.
Signed-off-by: Yangbo Lu <yangbo.lu-3arQi8VN3Tc@public.gmane.org>
Acked-by: Ulf Hansson <ulf.hansson-QSEj5FYQhm4dnm+yROfE0A@public.gmane.org>
Acked-by: Scott Wood <oss-fOR+EgIDQEHk1uMJSBkQmQ@public.gmane.org>
---
Changes for v2:
- Got SVR through iomap instead of dts
Changes for v3:
- Managed GUTS through syscon instead of iomap in eSDHC driver
Changes for v4:
- Got SVR by GUTS driver instead of SYSCON
Changes for v5:
- Changed to get SVR through API fsl_guts_get_svr()
- Combined patch 4, patch 5 and patch 6 into one
Changes for v6:
- Added 'Acked-by: Ulf Hansson'
Changes for v7:
- None
Changes for v8:
- Added 'Acked-by: Scott Wood'
Changes for v9:
- None
Changes for v10:
- None
Changes for v11:
- Changed to use soc_device_match
---
drivers/mmc/host/Kconfig | 1 +
drivers/mmc/host/sdhci-of-esdhc.c | 20 ++++++++++++++++++++
2 files changed, 21 insertions(+)
diff --git a/drivers/mmc/host/Kconfig b/drivers/mmc/host/Kconfig
index 5274f50..a1135a9 100644
--- a/drivers/mmc/host/Kconfig
+++ b/drivers/mmc/host/Kconfig
@@ -144,6 +144,7 @@ config MMC_SDHCI_OF_ESDHC
depends on MMC_SDHCI_PLTFM
depends on PPC || ARCH_MXC || ARCH_LAYERSCAPE
select MMC_SDHCI_IO_ACCESSORS
+ select FSL_GUTS
help
This selects the Freescale eSDHC controller support.
diff --git a/drivers/mmc/host/sdhci-of-esdhc.c b/drivers/mmc/host/sdhci-of-esdhc.c
index fb71c86..0a31aa5 100644
--- a/drivers/mmc/host/sdhci-of-esdhc.c
+++ b/drivers/mmc/host/sdhci-of-esdhc.c
@@ -18,6 +18,7 @@
#include <linux/of.h>
#include <linux/delay.h>
#include <linux/module.h>
+#include <linux/sys_soc.h>
#include <linux/mmc/host.h>
#include "sdhci-pltfm.h"
#include "sdhci-esdhc.h"
@@ -28,6 +29,7 @@
struct sdhci_esdhc {
u8 vendor_ver;
u8 spec_ver;
+ bool quirk_incorrect_hostver;
};
/**
@@ -73,6 +75,8 @@ static u32 esdhc_readl_fixup(struct sdhci_host *host,
static u16 esdhc_readw_fixup(struct sdhci_host *host,
int spec_reg, u32 value)
{
+ struct sdhci_pltfm_host *pltfm_host = sdhci_priv(host);
+ struct sdhci_esdhc *esdhc = sdhci_pltfm_priv(pltfm_host);
u16 ret;
int shift = (spec_reg & 0x2) * 8;
@@ -80,6 +84,12 @@ static u16 esdhc_readw_fixup(struct sdhci_host *host,
ret = value & 0xffff;
else
ret = (value >> shift) & 0xffff;
+ /* Workaround for T4240-R1.0-R2.0 eSDHC which has incorrect
+ * vendor version and spec version information.
+ */
+ if ((spec_reg == SDHCI_HOST_VERSION) &&
+ (esdhc->quirk_incorrect_hostver))
+ ret = (VENDOR_V_23 << SDHCI_VENDOR_VER_SHIFT) | SDHCI_SPEC_200;
return ret;
}
@@ -558,6 +568,12 @@ static const struct sdhci_pltfm_data sdhci_esdhc_le_pdata = {
.ops = &sdhci_esdhc_le_ops,
};
+static struct soc_device_attribute soc_incorrect_hostver[] = {
+ { .soc_id = "*name:T4240*", .revision = "1.0", },
+ { .soc_id = "*name:T4240*", .revision = "2.0", },
+ { },
+};
+
static void esdhc_init(struct platform_device *pdev, struct sdhci_host *host)
{
struct sdhci_pltfm_host *pltfm_host;
@@ -571,6 +587,10 @@ static void esdhc_init(struct platform_device *pdev, struct sdhci_host *host)
esdhc->vendor_ver = (host_ver & SDHCI_VENDOR_VER_MASK) >>
SDHCI_VENDOR_VER_SHIFT;
esdhc->spec_ver = host_ver & SDHCI_SPEC_VER_MASK;
+ if (soc_device_match(soc_incorrect_hostver))
+ esdhc->quirk_incorrect_hostver = true;
+ else
+ esdhc->quirk_incorrect_hostver = false;
}
static int sdhci_esdhc_probe(struct platform_device *pdev)
--
2.1.0.27.g96db324
^ permalink raw reply related
* [v11, 7/8] base: soc: introduce soc_device_match() interface
From: Yangbo Lu @ 2016-09-06 8:28 UTC (permalink / raw)
To: linux-mmc-u79uwXL29TY76Z2rM5mHXA,
ulf.hansson-QSEj5FYQhm4dnm+yROfE0A, Scott Wood, Arnd Bergmann
Cc: Mark Rutland, devicetree-u79uwXL29TY76Z2rM5mHXA, Russell King,
Yangbo Lu, Bhupesh Sharma, netdev-u79uwXL29TY76Z2rM5mHXA,
Santosh Shilimkar, linux-kernel-u79uwXL29TY76Z2rM5mHXA,
Jochen Friedrich, xiaobo.xie-3arQi8VN3Tc,
iommu-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA, Rob Herring,
linux-i2c-u79uwXL29TY76Z2rM5mHXA, Claudiu Manoil, Kumar Gala,
leoyang.li-3arQi8VN3Tc, linuxppc-dev-uLR06cmDAlY/bJ5BZ2RsiQ,
linux-clk-u79uwXL29TY76Z2rM5mHXA,
linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Qiang Zhao
In-Reply-To: <1473150503-9550-1-git-send-email-yangbo.lu-3arQi8VN3Tc@public.gmane.org>
We keep running into cases where device drivers want to know the exact
version of the a SoC they are currently running on. In the past, this has
usually been done through a vendor specific API that can be called by a
driver, or by directly accessing some kind of version register that is
not part of the device itself but that belongs to a global register area
of the chip.
Common reasons for doing this include:
- A machine is not using devicetree or similar for passing data about
on-chip devices, but just announces their presence using boot-time
platform devices, and the machine code itself does not care about the
revision.
- There is existing firmware or boot loaders with existing DT binaries
with generic compatible strings that do not identify the particular
revision of each device, but the driver knows which SoC revisions
include which part.
- A prerelease version of a chip has some quirks and we are using the same
version of the bootloader and the DT blob on both the prerelease and the
final version. An update of the DT binding seems inappropriate because
that would involve maintaining multiple copies of the dts and/or
bootloader.
This patch introduces the soc_device_match() interface that is meant to
work like of_match_node() but instead of identifying the version of a
device, it identifies the SoC itself using a vendor-agnostic interface.
Unlike of_match_node(), we do not do an exact string compare but instead
use glob_match() to allow wildcards in strings.
Signed-off-by: Arnd Bergmann <arnd-r2nGTMty4D4@public.gmane.org>
Signed-off-by: Yangbo Lu <yangbo.lu-3arQi8VN3Tc@public.gmane.org>
---
Changes for v11:
- Added this patch for soc match
---
drivers/base/Kconfig | 1 +
drivers/base/soc.c | 61 +++++++++++++++++++++++++++++++++++++++++++++++++
include/linux/sys_soc.h | 3 +++
3 files changed, 65 insertions(+)
diff --git a/drivers/base/Kconfig b/drivers/base/Kconfig
index 98504ec..f1591ad2 100644
--- a/drivers/base/Kconfig
+++ b/drivers/base/Kconfig
@@ -225,6 +225,7 @@ config GENERIC_CPU_AUTOPROBE
config SOC_BUS
bool
+ select GLOB
source "drivers/base/regmap/Kconfig"
diff --git a/drivers/base/soc.c b/drivers/base/soc.c
index 75b98aa..5c4e84a 100644
--- a/drivers/base/soc.c
+++ b/drivers/base/soc.c
@@ -14,6 +14,7 @@
#include <linux/spinlock.h>
#include <linux/sys_soc.h>
#include <linux/err.h>
+#include <linux/glob.h>
static DEFINE_IDA(soc_ida);
@@ -168,3 +169,63 @@ static void __exit soc_bus_unregister(void)
bus_unregister(&soc_bus_type);
}
module_exit(soc_bus_unregister);
+
+static int soc_device_match_one(struct device *dev, void *arg)
+{
+ struct soc_device *soc_dev = container_of(dev, struct soc_device, dev);
+ const struct soc_device_attribute *match = arg;
+
+ if (match->machine &&
+ !glob_match(match->machine, soc_dev->attr->machine))
+ return 0;
+
+ if (match->family &&
+ !glob_match(match->family, soc_dev->attr->family))
+ return 0;
+
+ if (match->revision &&
+ !glob_match(match->revision, soc_dev->attr->revision))
+ return 0;
+
+ if (match->soc_id &&
+ !glob_match(match->soc_id, soc_dev->attr->soc_id))
+ return 0;
+
+ return 1;
+}
+
+/*
+ * soc_device_match - identify the SoC in the machine
+ * @matches: zero-terminated array of possible matches
+ *
+ * returns the first matching entry of the argument array, or NULL
+ * if none of them match.
+ *
+ * This function is meant as a helper in place of of_match_node()
+ * in cases where either no device tree is available or the information
+ * in a device node is insufficient to identify a particular variant
+ * by its compatible strings or other properties. For new devices,
+ * the DT binding should always provide unique compatible strings
+ * that allow the use of of_match_node() instead.
+ *
+ * The calling function can use the .data entry of the
+ * soc_device_attribute to pass a structure or function pointer for
+ * each entry.
+ */
+const struct soc_device_attribute *soc_device_match(
+ const struct soc_device_attribute *matches)
+{
+ struct device *dev;
+ int ret;
+
+ for (ret = 0; ret == 0; matches++) {
+ if (!(matches->machine || matches->family ||
+ matches->revision || matches->soc_id))
+ return NULL;
+ dev = NULL;
+ ret = bus_for_each_dev(&soc_bus_type, dev, (void *)matches,
+ soc_device_match_one);
+ }
+ return matches;
+}
+EXPORT_SYMBOL_GPL(soc_device_match);
diff --git a/include/linux/sys_soc.h b/include/linux/sys_soc.h
index 2739ccb..9f5eb06 100644
--- a/include/linux/sys_soc.h
+++ b/include/linux/sys_soc.h
@@ -13,6 +13,7 @@ struct soc_device_attribute {
const char *family;
const char *revision;
const char *soc_id;
+ const void *data;
};
/**
@@ -34,4 +35,6 @@ void soc_device_unregister(struct soc_device *soc_dev);
*/
struct device *soc_device_to_device(struct soc_device *soc);
+const struct soc_device_attribute *soc_device_match(
+ const struct soc_device_attribute *matches);
#endif /* __SOC_BUS_H */
--
2.1.0.27.g96db324
^ permalink raw reply related
* [v11, 6/8] MAINTAINERS: add entry for Freescale SoC drivers
From: Yangbo Lu @ 2016-09-06 8:28 UTC (permalink / raw)
To: linux-mmc-u79uwXL29TY76Z2rM5mHXA,
ulf.hansson-QSEj5FYQhm4dnm+yROfE0A, Scott Wood, Arnd Bergmann
Cc: Mark Rutland, devicetree-u79uwXL29TY76Z2rM5mHXA, Russell King,
Yangbo Lu, Bhupesh Sharma, netdev-u79uwXL29TY76Z2rM5mHXA,
Santosh Shilimkar, linux-kernel-u79uwXL29TY76Z2rM5mHXA,
Jochen Friedrich, xiaobo.xie-3arQi8VN3Tc,
iommu-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA, Rob Herring,
linux-i2c-u79uwXL29TY76Z2rM5mHXA, Claudiu Manoil, Kumar Gala,
leoyang.li-3arQi8VN3Tc, linuxppc-dev-uLR06cmDAlY/bJ5BZ2RsiQ,
linux-clk-u79uwXL29TY76Z2rM5mHXA,
linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Qiang Zhao
In-Reply-To: <1473150503-9550-1-git-send-email-yangbo.lu-3arQi8VN3Tc@public.gmane.org>
Add maintainer entry for Freescale SoC drivers including
the QE library and the GUTS driver now. Also add maintainer
for QE library.
Signed-off-by: Yangbo Lu <yangbo.lu-3arQi8VN3Tc@public.gmane.org>
Acked-by: Scott Wood <oss-fOR+EgIDQEHk1uMJSBkQmQ@public.gmane.org>
Acked-by: Qiang Zhao <qiang.zhao-3arQi8VN3Tc@public.gmane.org>
---
Changes for v8:
- Added this patch
Changes for v9:
- Added linux-arm mail list
- Removed GUTS driver entry
Changes for v10:
- Changed 'DRIVER' to 'DRIVERS'
- Added 'Acked-by' of Scott and Qiang
Changes for v11:
- None
---
MAINTAINERS | 11 ++++++++++-
1 file changed, 10 insertions(+), 1 deletion(-)
diff --git a/MAINTAINERS b/MAINTAINERS
index 71aa5da..3954c0c 100644
--- a/MAINTAINERS
+++ b/MAINTAINERS
@@ -4969,9 +4969,18 @@ F: drivers/net/ethernet/freescale/fec_ptp.c
F: drivers/net/ethernet/freescale/fec.h
F: Documentation/devicetree/bindings/net/fsl-fec.txt
+FREESCALE SOC DRIVERS
+M: Scott Wood <oss-fOR+EgIDQEHk1uMJSBkQmQ@public.gmane.org>
+L: linuxppc-dev-uLR06cmDAlY/bJ5BZ2RsiQ@public.gmane.org
+L: linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r@public.gmane.org
+S: Maintained
+F: drivers/soc/fsl/
+F: include/linux/fsl/
+
FREESCALE QUICC ENGINE LIBRARY
+M: Qiang Zhao <qiang.zhao-3arQi8VN3Tc@public.gmane.org>
L: linuxppc-dev-uLR06cmDAlY/bJ5BZ2RsiQ@public.gmane.org
-S: Orphan
+S: Maintained
F: drivers/soc/fsl/qe/
F: include/soc/fsl/*qe*.h
F: include/soc/fsl/*ucc*.h
--
2.1.0.27.g96db324
^ permalink raw reply related
* [v11, 5/8] soc: fsl: add GUTS driver for QorIQ platforms
From: Yangbo Lu @ 2016-09-06 8:28 UTC (permalink / raw)
To: linux-mmc-u79uwXL29TY76Z2rM5mHXA,
ulf.hansson-QSEj5FYQhm4dnm+yROfE0A, Scott Wood, Arnd Bergmann
Cc: Mark Rutland, devicetree-u79uwXL29TY76Z2rM5mHXA, Russell King,
Yangbo Lu, Bhupesh Sharma, netdev-u79uwXL29TY76Z2rM5mHXA,
Santosh Shilimkar, linux-kernel-u79uwXL29TY76Z2rM5mHXA,
Jochen Friedrich, xiaobo.xie-3arQi8VN3Tc,
iommu-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA, Rob Herring,
linux-i2c-u79uwXL29TY76Z2rM5mHXA, Claudiu Manoil, Kumar Gala,
leoyang.li-3arQi8VN3Tc, linuxppc-dev-uLR06cmDAlY/bJ5BZ2RsiQ,
linux-clk-u79uwXL29TY76Z2rM5mHXA,
linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Qiang Zhao
In-Reply-To: <1473150503-9550-1-git-send-email-yangbo.lu-3arQi8VN3Tc@public.gmane.org>
The global utilities block controls power management, I/O device
enabling, power-onreset(POR) configuration monitoring, alternate
function selection for multiplexed signals,and clock control.
This patch adds a driver to manage and access global utilities block.
Initially only reading SVR and registering soc device are supported.
Other guts accesses, such as reading RCW, should eventually be moved
into this driver as well.
Signed-off-by: Yangbo Lu <yangbo.lu-3arQi8VN3Tc@public.gmane.org>
Signed-off-by: Scott Wood <oss-fOR+EgIDQEHk1uMJSBkQmQ@public.gmane.org>
---
Changes for v4:
- Added this patch
Changes for v5:
- Modified copyright info
- Changed MODULE_LICENSE to GPL
- Changed EXPORT_SYMBOL_GPL to EXPORT_SYMBOL
- Made FSL_GUTS user-invisible
- Added a complete compatible list for GUTS
- Stored guts info in file-scope variable
- Added mfspr() getting SVR
- Redefined GUTS APIs
- Called fsl_guts_init rather than using platform driver
- Removed useless parentheses
- Removed useless 'extern' key words
Changes for v6:
- Made guts thread safe in fsl_guts_init
Changes for v7:
- Removed 'ifdef' for function declaration in guts.h
Changes for v8:
- Fixes lines longer than 80 characters checkpatch issue
- Added 'Acked-by: Scott Wood'
Changes for v9:
- None
Changes for v10:
- None
Changes for v11:
- Changed to platform driver
- Registered soc device
---
drivers/soc/Kconfig | 2 +-
drivers/soc/fsl/Kconfig | 20 ++
drivers/soc/fsl/Makefile | 1 +
drivers/soc/fsl/guts.c | 483 +++++++++++++++++++++++++++++++++++++++++++++++
include/linux/fsl/guts.h | 127 ++++++++-----
5 files changed, 584 insertions(+), 49 deletions(-)
create mode 100644 drivers/soc/fsl/Kconfig
create mode 100644 drivers/soc/fsl/guts.c
diff --git a/drivers/soc/Kconfig b/drivers/soc/Kconfig
index fe42a2f..f31bceb 100644
--- a/drivers/soc/Kconfig
+++ b/drivers/soc/Kconfig
@@ -1,7 +1,7 @@
menu "SOC (System On Chip) specific Drivers"
source "drivers/soc/bcm/Kconfig"
-source "drivers/soc/fsl/qe/Kconfig"
+source "drivers/soc/fsl/Kconfig"
source "drivers/soc/mediatek/Kconfig"
source "drivers/soc/qcom/Kconfig"
source "drivers/soc/rockchip/Kconfig"
diff --git a/drivers/soc/fsl/Kconfig b/drivers/soc/fsl/Kconfig
new file mode 100644
index 0000000..439998d
--- /dev/null
+++ b/drivers/soc/fsl/Kconfig
@@ -0,0 +1,20 @@
+#
+# Freescale SOC drivers
+#
+
+source "drivers/soc/fsl/qe/Kconfig"
+
+config FSL_GUTS
+ bool "Freescale QorIQ GUTS driver"
+ select SOC_BUS
+ select GLOB
+ help
+ The global utilities block controls power management, I/O device
+ enabling, power-onreset(POR) configuration monitoring, alternate
+ function selection for multiplexed signals,and clock control.
+ This driver is to manage and access global utilities block.
+ Initially only reading SVR and registering soc device are supported.
+ Other guts accesses, such as reading RCW, should eventually be moved
+ into this driver as well.
+
+ If you want GUTS driver support, you should say Y here.
diff --git a/drivers/soc/fsl/Makefile b/drivers/soc/fsl/Makefile
index 203307f..02afb7f 100644
--- a/drivers/soc/fsl/Makefile
+++ b/drivers/soc/fsl/Makefile
@@ -4,3 +4,4 @@
obj-$(CONFIG_QUICC_ENGINE) += qe/
obj-$(CONFIG_CPM) += qe/
+obj-$(CONFIG_FSL_GUTS) += guts.o
diff --git a/drivers/soc/fsl/guts.c b/drivers/soc/fsl/guts.c
new file mode 100644
index 0000000..93c39315
--- /dev/null
+++ b/drivers/soc/fsl/guts.c
@@ -0,0 +1,483 @@
+/*
+ * Freescale QorIQ Platforms GUTS Driver
+ *
+ * Copyright (C) 2016 Freescale Semiconductor, Inc.
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ */
+
+#include <linux/io.h>
+#include <linux/slab.h>
+#include <linux/module.h>
+#include <linux/of_fdt.h>
+#include <linux/sys_soc.h>
+#include <linux/of_address.h>
+#include <linux/platform_device.h>
+#include <linux/glob.h>
+#include <linux/fsl/guts.h>
+#include <linux/fsl/svr.h>
+
+struct guts {
+ struct ccsr_guts __iomem *regs;
+ bool little_endian;
+};
+
+static struct guts *guts;
+static struct soc_device_attribute *soc_dev_attr;
+static struct soc_device *soc_dev;
+
+
+/* SoC attribute definition for QorIQ platform */
+static const struct soc_device_attribute qoriq_soc[] = {
+#ifdef CONFIG_PPC
+ /*
+ * Power Architecture-based SoCs T Series
+ */
+
+ /* SoC: T1024/T1014/T1023/T1013 Rev: 1.0 */
+ { .soc_id = "svr:0x85400010,name:T1024,die:T1024",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x85480010,name:T1024E,die:T1024",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x85440010,name:T1014,die:T1024",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x854C0010,name:T1014E,die:T1024",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x85410010,name:T1023,die:T1024",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x85490010,name:T1023E,die:T1024",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x85450010,name:T1013,die:T1024",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x854D0010,name:T1013E,die:T1024",
+ .revision = "1.0",
+ },
+ /* SoC: T1040/T1020/T1042/T1022 Rev: 1.0/1.1 */
+ { .soc_id = "svr:0x85200010,name:T1040,die:T1040",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x85280010,name:T1040E,die:T1040",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x85210010,name:T1020,die:T1040",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x85290010,name:T1020E,die:T1040",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x85200210,name:T1042,die:T1040",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x85280210,name:T1042E,die:T1040",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x85210210,name:T1022,die:T1040",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x85290210,name:T1022E,die:T1040",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x85200011,name:T1040,die:T1040",
+ .revision = "1.1",
+ },
+ { .soc_id = "svr:0x85280011,name:T1040E,die:T1040",
+ .revision = "1.1",
+ },
+ { .soc_id = "svr:0x85210011,name:T1020,die:T1040",
+ .revision = "1.1",
+ },
+ { .soc_id = "svr:0x85290011,name:T1020E,die:T1040",
+ .revision = "1.1",
+ },
+ { .soc_id = "svr:0x85200211,name:T1042,die:T1040",
+ .revision = "1.1",
+ },
+ { .soc_id = "svr:0x85280211,name:T1042E,die:T1040",
+ .revision = "1.1",
+ },
+ { .soc_id = "svr:0x85210211,name:T1022,die:T1040",
+ .revision = "1.1",
+ },
+ { .soc_id = "svr:0x85290211,name:T1022E,die:T1040",
+ .revision = "1.1",
+ },
+ /* SoC: T2080/T2081 Rev: 1.0/1.1 */
+ { .soc_id = "svr:0x85300010,name:T2080,die:T2080",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x85380010,name:T2080E,die:T2080",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x85310010,name:T2081,die:T2080",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x85390010,name:T2081E,die:T2080",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x85300011,name:T2080,die:T2080",
+ .revision = "1.1",
+ },
+ { .soc_id = "svr:0x85380011,name:T2080E,die:T2080",
+ .revision = "1.1",
+ },
+ { .soc_id = "svr:0x85310011,name:T2081,die:T2080",
+ .revision = "1.1",
+ },
+ { .soc_id = "svr:0x85390011,name:T2081E,die:T2080",
+ .revision = "1.1",
+ },
+ /* SoC: T4240/T4160/T4080 Rev: 1.0/2.0 */
+ { .soc_id = "svr:0x82400010,name:T4240,die:T4240",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x82480010,name:T4240E,die:T4240",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x82410010,name:T4160,die:T4240",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x82490010,name:T4160E,die:T4240",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x82400020,name:T4240,die:T4240",
+ .revision = "2.0",
+ },
+ { .soc_id = "svr:0x82480020,name:T4240E,die:T4240",
+ .revision = "2.0",
+ },
+ { .soc_id = "svr:0x82410020,name:T4160,die:T4240",
+ .revision = "2.0",
+ },
+ { .soc_id = "svr:0x82490020,name:T4160E,die:T4240",
+ .revision = "2.0",
+ },
+ { .soc_id = "svr:0x82410220,name:T4080,die:T4240",
+ .revision = "2.0",
+ },
+ { .soc_id = "svr:0x82490220,name:T4080E,die:T4240",
+ .revision = "2.0",
+ },
+#endif /* CONFIG_PPC */
+#if defined(CONFIG_ARCH_MXC) || defined(CONFIG_ARCH_LAYERSCAPE)
+ /*
+ * ARM-based SoCs LS Series
+ */
+
+ /* SoC: LS1021A/LS1020A/LS1022A Rev: 1.0/2.0 */
+ { .soc_id = "svr:0x87001110,name:LS1021A,die:LS1021A",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x87081110,name:LS1021AE,die:LS1021A",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x87001010,name:LS1020A,die:LS1021A",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x87081010,name:LS1020AE,die:LS1021A",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x87001210,name:LS1022A,die:LS1021A",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x87081210,name:LS1022AE,die:LS1021A",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x87001120,name:LS1021A,die:LS1021A",
+ .revision = "2.0",
+ },
+ { .soc_id = "svr:0x87081120,name:LS1021AE,die:LS1021A",
+ .revision = "2.0",
+ },
+ { .soc_id = "svr:0x87001020,name:LS1020A,die:LS1021A",
+ .revision = "2.0",
+ },
+ { .soc_id = "svr:0x87081020,name:LS1020AE,die:LS1021A",
+ .revision = "2.0",
+ },
+ { .soc_id = "svr:0x87001220,name:LS1022A,die:LS1021A",
+ .revision = "2.0",
+ },
+ { .soc_id = "svr:0x87081220,name:LS1022AE,die:LS1021A",
+ .revision = "2.0",
+ },
+ /* SoC: LS1046A/LS1026A Rev: 1.0 */
+ { .soc_id = "svr:0x87070110,name:LS1046A,die:LS1046A",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x87070010,name:LS1046AE,die:LS1046A",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x87070910,name:LS1026A,die:LS1046A",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x87070810,name:LS1026AE,die:LS1046A",
+ .revision = "1.0",
+ },
+ /* SoC: LS1043A/LS1023A Rev: 1.0 Package: 21*21 */
+ { .soc_id = "svr:0x87920110,name:LS1043A,die:LS1043A",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x87920010,name:LS1043AE,die:LS1043A",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x87920910,name:LS1023A,die:LS1043A",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x87920810,name:LS1023AE,die:LS1043A",
+ .revision = "1.0",
+ },
+ /* SoC: LS1043A/LS1023A Rev: 1.0 Package: 23*23 */
+ { .soc_id = "svr:0x87920310,name:LS1043A,die:LS1043A",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x87920210,name:LS1043AE,die:LS1043A",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x87920B10,name:LS1023A,die:LS1043A",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x87920A10,name:LS1023AE,die:LS1043A",
+ .revision = "1.0",
+ },
+ /* SoC: LS1012A Rev: 1.0 */
+ { .soc_id = "svr:0x87040110,name:LS1012A,die:LS1012A",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x87040010,name:LS1012AE,die:LS1012A",
+ .revision = "1.0",
+ },
+ /* SoC: LS2088A/LS2048A/LS2084A/LS2044A Rev: 1.0 */
+ { .soc_id = "svr:0x87090110,name:LS2088A,die:LS2088A",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x87090010,name:LS2088AE,die:LS2088A",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x87092110,name:LS2048A,die:LS2088A",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x87092010,name:LS2048AE,die:LS2088A",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x87091110,name:LS2084A,die:LS2088A",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x87091010,name:LS2084AE,die:LS2088A",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x87093110,name:LS2044A,die:LS2088A",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x87093010,name:LS2044AE,die:LS2088A",
+ .revision = "1.0",
+ },
+ /* SoC: LS2080A/LS2040A Rev: 1.0 */
+ { .soc_id = "svr:0x87011010,name:LS2080AE,die:LS2080A",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x87013010,name:LS2040AE,die:LS2080A",
+ .revision = "1.0",
+ },
+ /* SoC: LS2085A Rev: 1.0 */
+ { .soc_id = "svr:0x87010110,name:LS2085A,die:LS2085A",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x87010010,name:LS2085AE,die:LS2085A",
+ .revision = "1.0",
+ },
+ /* SoC: LS1088A/LS1048A/LS1084A/LS1044A Rev: 1.0 */
+ { .soc_id = "svr:0x87030110,name:LS1088A,die:LS1088A",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x87030010,name:LS1088AE,die:LS1088A",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x87032110,name:LS1048A,die:LS1088A",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x87032010,name:LS1048AE,die:LS1088A",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x87030310,name:LS1084A,die:LS1088A",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x87030210,name:LS1084AE,die:LS1088A",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x87032310,name:LS1044A,die:LS1088A",
+ .revision = "1.0",
+ },
+ { .soc_id = "svr:0x87032210,name:LS1044AE,die:LS1088A",
+ .revision = "1.0",
+ },
+#endif /* CONFIG_ARCH_MXC || CONFIG_ARCH_LAYERSCAPE */
+ { },
+};
+
+static const struct soc_device_attribute *fsl_soc_device_match(
+ unsigned int svr, const struct soc_device_attribute *matches)
+{
+ char svr_match[50];
+ int n;
+
+ n = sprintf(svr_match, "*%08x*", svr);
+
+ do {
+ if (!matches->soc_id)
+ return NULL;
+ if (glob_match(svr_match, matches->soc_id))
+ break;
+ } while (matches++);
+
+ return matches;
+}
+
+unsigned int fsl_guts_get_svr(void)
+{
+ unsigned int svr = 0;
+
+ if (!guts || !guts->regs)
+ return svr;
+
+ if (guts->little_endian)
+ svr = ioread32(&guts->regs->svr);
+ else
+ svr = ioread32be(&guts->regs->svr);
+
+ return svr;
+}
+EXPORT_SYMBOL(fsl_guts_get_svr);
+
+static int fsl_guts_probe(struct platform_device *pdev)
+{
+ struct device_node *np;
+ const struct soc_device_attribute *fsl_soc;
+ const char *machine;
+ unsigned int svr;
+ int ret = 0;
+
+ np = pdev->dev.of_node;
+
+ /* Initialize guts */
+ guts = kzalloc(sizeof(*guts), GFP_KERNEL);
+ if (!guts)
+ return -ENOMEM;
+
+ guts->little_endian = of_property_read_bool(np, "little-endian");
+
+ guts->regs = of_iomap(np, 0);
+ if (!guts->regs) {
+ ret = -ENOMEM;
+ goto out_free;
+ }
+
+ /* Register soc device */
+ soc_dev_attr = kzalloc(sizeof(*soc_dev_attr), GFP_KERNEL);
+ if (!soc_dev_attr) {
+ ret = -ENOMEM;
+ goto out_unmap;
+ }
+
+ machine = of_flat_dt_get_machine_name();
+ if (machine)
+ soc_dev_attr->machine = kasprintf(GFP_KERNEL, "%s", machine);
+
+ soc_dev_attr->family = kasprintf(GFP_KERNEL, "QorIQ");
+
+ svr = fsl_guts_get_svr();
+ fsl_soc = fsl_soc_device_match(svr, qoriq_soc);
+ if (fsl_soc) {
+ soc_dev_attr->soc_id = kasprintf(GFP_KERNEL, "%s",
+ fsl_soc->soc_id);
+ soc_dev_attr->revision = kasprintf(GFP_KERNEL, "%s",
+ fsl_soc->revision);
+ } else {
+ soc_dev_attr->soc_id = kasprintf(GFP_KERNEL, "0x%08x", svr);
+ soc_dev_attr->revision = kasprintf(GFP_KERNEL, "%d.%d",
+ SVR_MAJ(svr), SVR_MIN(svr));
+ }
+
+ soc_dev = soc_device_register(soc_dev_attr);
+ if (IS_ERR(soc_dev)) {
+ ret = -ENODEV;
+ goto out;
+ } else {
+ pr_info("Detected: %s\n", soc_dev_attr->machine);
+ pr_info("Detected SoC family: %s\n", soc_dev_attr->family);
+ pr_info("Detected SoC ID: %s, revision: %s\n",
+ soc_dev_attr->soc_id, soc_dev_attr->revision);
+ }
+ return 0;
+out:
+ kfree(soc_dev_attr->machine);
+ kfree(soc_dev_attr->family);
+ kfree(soc_dev_attr->soc_id);
+ kfree(soc_dev_attr->revision);
+ kfree(soc_dev_attr);
+out_unmap:
+ iounmap(guts->regs);
+out_free:
+ kfree(guts);
+ return ret;
+}
+
+static int fsl_guts_remove(struct platform_device *dev)
+{
+ kfree(soc_dev_attr->machine);
+ kfree(soc_dev_attr->family);
+ kfree(soc_dev_attr->soc_id);
+ kfree(soc_dev_attr->revision);
+ kfree(soc_dev_attr);
+ soc_device_unregister(soc_dev);
+ iounmap(guts->regs);
+ kfree(guts);
+ return 0;
+}
+
+/*
+ * Table for matching compatible strings, for device tree
+ * guts node, for Freescale QorIQ SOCs.
+ */
+static const struct of_device_id fsl_guts_of_match[] = {
+ { .compatible = "fsl,qoriq-device-config-1.0", },
+ { .compatible = "fsl,qoriq-device-config-2.0", },
+ { .compatible = "fsl,p1010-guts", },
+ { .compatible = "fsl,p1020-guts", },
+ { .compatible = "fsl,p1021-guts", },
+ { .compatible = "fsl,p1022-guts", },
+ { .compatible = "fsl,p1023-guts", },
+ { .compatible = "fsl,p2020-guts", },
+ { .compatible = "fsl,bsc9131-guts", },
+ { .compatible = "fsl,bsc9132-guts", },
+ { .compatible = "fsl,mpc8536-guts", },
+ { .compatible = "fsl,mpc8544-guts", },
+ { .compatible = "fsl,mpc8548-guts", },
+ { .compatible = "fsl,mpc8568-guts", },
+ { .compatible = "fsl,mpc8569-guts", },
+ { .compatible = "fsl,mpc8572-guts", },
+ { .compatible = "fsl,ls1021a-dcfg", },
+ { .compatible = "fsl,ls1043a-dcfg", },
+ { .compatible = "fsl,ls2080a-dcfg", },
+ {}
+};
+
+static struct platform_driver fsl_guts_driver = {
+ .driver = {
+ .name = "fsl-guts",
+ .of_match_table = fsl_guts_of_match,
+ },
+ .probe = fsl_guts_probe,
+ .remove = fsl_guts_remove,
+};
+
+module_platform_driver(fsl_guts_driver);
diff --git a/include/linux/fsl/guts.h b/include/linux/fsl/guts.h
index 649e917..c5e24cf 100644
--- a/include/linux/fsl/guts.h
+++ b/include/linux/fsl/guts.h
@@ -29,83 +29,114 @@
* #ifdefs.
*/
struct ccsr_guts {
- __be32 porpllsr; /* 0x.0000 - POR PLL Ratio Status Register */
- __be32 porbmsr; /* 0x.0004 - POR Boot Mode Status Register */
- __be32 porimpscr; /* 0x.0008 - POR I/O Impedance Status and Control Register */
- __be32 pordevsr; /* 0x.000c - POR I/O Device Status Register */
- __be32 pordbgmsr; /* 0x.0010 - POR Debug Mode Status Register */
- __be32 pordevsr2; /* 0x.0014 - POR device status register 2 */
+ u32 porpllsr; /* 0x.0000 - POR PLL Ratio Status Register */
+ u32 porbmsr; /* 0x.0004 - POR Boot Mode Status Register */
+ u32 porimpscr; /* 0x.0008 - POR I/O Impedance Status and
+ * Control Register
+ */
+ u32 pordevsr; /* 0x.000c - POR I/O Device Status Register */
+ u32 pordbgmsr; /* 0x.0010 - POR Debug Mode Status Register */
+ u32 pordevsr2; /* 0x.0014 - POR device status register 2 */
u8 res018[0x20 - 0x18];
- __be32 porcir; /* 0x.0020 - POR Configuration Information Register */
+ u32 porcir; /* 0x.0020 - POR Configuration Information
+ * Register
+ */
u8 res024[0x30 - 0x24];
- __be32 gpiocr; /* 0x.0030 - GPIO Control Register */
+ u32 gpiocr; /* 0x.0030 - GPIO Control Register */
u8 res034[0x40 - 0x34];
- __be32 gpoutdr; /* 0x.0040 - General-Purpose Output Data Register */
+ u32 gpoutdr; /* 0x.0040 - General-Purpose Output Data
+ * Register
+ */
u8 res044[0x50 - 0x44];
- __be32 gpindr; /* 0x.0050 - General-Purpose Input Data Register */
+ u32 gpindr; /* 0x.0050 - General-Purpose Input Data
+ * Register
+ */
u8 res054[0x60 - 0x54];
- __be32 pmuxcr; /* 0x.0060 - Alternate Function Signal Multiplex Control */
- __be32 pmuxcr2; /* 0x.0064 - Alternate function signal multiplex control 2 */
- __be32 dmuxcr; /* 0x.0068 - DMA Mux Control Register */
+ u32 pmuxcr; /* 0x.0060 - Alternate Function Signal
+ * Multiplex Control
+ */
+ u32 pmuxcr2; /* 0x.0064 - Alternate function signal
+ * multiplex control 2
+ */
+ u32 dmuxcr; /* 0x.0068 - DMA Mux Control Register */
u8 res06c[0x70 - 0x6c];
- __be32 devdisr; /* 0x.0070 - Device Disable Control */
+ u32 devdisr; /* 0x.0070 - Device Disable Control */
#define CCSR_GUTS_DEVDISR_TB1 0x00001000
#define CCSR_GUTS_DEVDISR_TB0 0x00004000
- __be32 devdisr2; /* 0x.0074 - Device Disable Control 2 */
+ u32 devdisr2; /* 0x.0074 - Device Disable Control 2 */
u8 res078[0x7c - 0x78];
- __be32 pmjcr; /* 0x.007c - 4 Power Management Jog Control Register */
- __be32 powmgtcsr; /* 0x.0080 - Power Management Status and Control Register */
- __be32 pmrccr; /* 0x.0084 - Power Management Reset Counter Configuration Register */
- __be32 pmpdccr; /* 0x.0088 - Power Management Power Down Counter Configuration Register */
- __be32 pmcdr; /* 0x.008c - 4Power management clock disable register */
- __be32 mcpsumr; /* 0x.0090 - Machine Check Summary Register */
- __be32 rstrscr; /* 0x.0094 - Reset Request Status and Control Register */
- __be32 ectrstcr; /* 0x.0098 - Exception reset control register */
- __be32 autorstsr; /* 0x.009c - Automatic reset status register */
- __be32 pvr; /* 0x.00a0 - Processor Version Register */
- __be32 svr; /* 0x.00a4 - System Version Register */
+ u32 pmjcr; /* 0x.007c - 4 Power Management Jog Control
+ * Register
+ */
+ u32 powmgtcsr; /* 0x.0080 - Power Management Status and
+ * Control Register
+ */
+ u32 pmrccr; /* 0x.0084 - Power Management Reset Counter
+ * Configuration Register
+ */
+ u32 pmpdccr; /* 0x.0088 - Power Management Power Down Counter
+ * Configuration Register
+ */
+ u32 pmcdr; /* 0x.008c - 4Power management clock disable
+ * register
+ */
+ u32 mcpsumr; /* 0x.0090 - Machine Check Summary Register */
+ u32 rstrscr; /* 0x.0094 - Reset Request Status and
+ * Control Register
+ */
+ u32 ectrstcr; /* 0x.0098 - Exception reset control register */
+ u32 autorstsr; /* 0x.009c - Automatic reset status register */
+ u32 pvr; /* 0x.00a0 - Processor Version Register */
+ u32 svr; /* 0x.00a4 - System Version Register */
u8 res0a8[0xb0 - 0xa8];
- __be32 rstcr; /* 0x.00b0 - Reset Control Register */
+ u32 rstcr; /* 0x.00b0 - Reset Control Register */
u8 res0b4[0xc0 - 0xb4];
- __be32 iovselsr; /* 0x.00c0 - I/O voltage select status register
+ u32 iovselsr; /* 0x.00c0 - I/O voltage select status register
Called 'elbcvselcr' on 86xx SOCs */
u8 res0c4[0x100 - 0xc4];
- __be32 rcwsr[16]; /* 0x.0100 - Reset Control Word Status registers
+ u32 rcwsr[16]; /* 0x.0100 - Reset Control Word Status registers
There are 16 registers */
u8 res140[0x224 - 0x140];
- __be32 iodelay1; /* 0x.0224 - IO delay control register 1 */
- __be32 iodelay2; /* 0x.0228 - IO delay control register 2 */
+ u32 iodelay1; /* 0x.0224 - IO delay control register 1 */
+ u32 iodelay2; /* 0x.0228 - IO delay control register 2 */
u8 res22c[0x604 - 0x22c];
- __be32 pamubypenr; /* 0x.604 - PAMU bypass enable register */
+ u32 pamubypenr; /* 0x.604 - PAMU bypass enable register */
u8 res608[0x800 - 0x608];
- __be32 clkdvdr; /* 0x.0800 - Clock Divide Register */
+ u32 clkdvdr; /* 0x.0800 - Clock Divide Register */
u8 res804[0x900 - 0x804];
- __be32 ircr; /* 0x.0900 - Infrared Control Register */
+ u32 ircr; /* 0x.0900 - Infrared Control Register */
u8 res904[0x908 - 0x904];
- __be32 dmacr; /* 0x.0908 - DMA Control Register */
+ u32 dmacr; /* 0x.0908 - DMA Control Register */
u8 res90c[0x914 - 0x90c];
- __be32 elbccr; /* 0x.0914 - eLBC Control Register */
+ u32 elbccr; /* 0x.0914 - eLBC Control Register */
u8 res918[0xb20 - 0x918];
- __be32 ddr1clkdr; /* 0x.0b20 - DDR1 Clock Disable Register */
- __be32 ddr2clkdr; /* 0x.0b24 - DDR2 Clock Disable Register */
- __be32 ddrclkdr; /* 0x.0b28 - DDR Clock Disable Register */
+ u32 ddr1clkdr; /* 0x.0b20 - DDR1 Clock Disable Register */
+ u32 ddr2clkdr; /* 0x.0b24 - DDR2 Clock Disable Register */
+ u32 ddrclkdr; /* 0x.0b28 - DDR Clock Disable Register */
u8 resb2c[0xe00 - 0xb2c];
- __be32 clkocr; /* 0x.0e00 - Clock Out Select Register */
+ u32 clkocr; /* 0x.0e00 - Clock Out Select Register */
u8 rese04[0xe10 - 0xe04];
- __be32 ddrdllcr; /* 0x.0e10 - DDR DLL Control Register */
+ u32 ddrdllcr; /* 0x.0e10 - DDR DLL Control Register */
u8 rese14[0xe20 - 0xe14];
- __be32 lbcdllcr; /* 0x.0e20 - LBC DLL Control Register */
- __be32 cpfor; /* 0x.0e24 - L2 charge pump fuse override register */
+ u32 lbcdllcr; /* 0x.0e20 - LBC DLL Control Register */
+ u32 cpfor; /* 0x.0e24 - L2 charge pump fuse override
+ * register
+ */
u8 rese28[0xf04 - 0xe28];
- __be32 srds1cr0; /* 0x.0f04 - SerDes1 Control Register 0 */
- __be32 srds1cr1; /* 0x.0f08 - SerDes1 Control Register 0 */
+ u32 srds1cr0; /* 0x.0f04 - SerDes1 Control Register 0 */
+ u32 srds1cr1; /* 0x.0f08 - SerDes1 Control Register 0 */
u8 resf0c[0xf2c - 0xf0c];
- __be32 itcr; /* 0x.0f2c - Internal transaction control register */
+ u32 itcr; /* 0x.0f2c - Internal transaction control
+ * register
+ */
u8 resf30[0xf40 - 0xf30];
- __be32 srds2cr0; /* 0x.0f40 - SerDes2 Control Register 0 */
- __be32 srds2cr1; /* 0x.0f44 - SerDes2 Control Register 0 */
+ u32 srds2cr0; /* 0x.0f40 - SerDes2 Control Register 0 */
+ u32 srds2cr1; /* 0x.0f44 - SerDes2 Control Register 0 */
} __attribute__ ((packed));
+#ifdef CONFIG_FSL_GUTS
+unsigned int fsl_guts_get_svr(void);
+#endif
/* Alternate function signal multiplex control */
#define MPC85xx_PMUXCR_QE(x) (0x8000 >> (x))
--
2.1.0.27.g96db324
^ permalink raw reply related
* [v11, 4/8] powerpc/fsl: move mpc85xx.h to include/linux/fsl
From: Yangbo Lu @ 2016-09-06 8:28 UTC (permalink / raw)
To: linux-mmc-u79uwXL29TY76Z2rM5mHXA,
ulf.hansson-QSEj5FYQhm4dnm+yROfE0A, Scott Wood, Arnd Bergmann
Cc: Mark Rutland, devicetree-u79uwXL29TY76Z2rM5mHXA, Russell King,
Yangbo Lu, Bhupesh Sharma, netdev-u79uwXL29TY76Z2rM5mHXA,
Santosh Shilimkar, linux-kernel-u79uwXL29TY76Z2rM5mHXA,
Jochen Friedrich, xiaobo.xie-3arQi8VN3Tc,
iommu-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA, Rob Herring,
linux-i2c-u79uwXL29TY76Z2rM5mHXA, Claudiu Manoil, Kumar Gala,
leoyang.li-3arQi8VN3Tc, linuxppc-dev-uLR06cmDAlY/bJ5BZ2RsiQ,
linux-clk-u79uwXL29TY76Z2rM5mHXA,
linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Qiang Zhao
In-Reply-To: <1473150503-9550-1-git-send-email-yangbo.lu-3arQi8VN3Tc@public.gmane.org>
Move mpc85xx.h to include/linux/fsl and rename it to svr.h as a common
header file. This SVR numberspace is used on some ARM chips as well as
PPC, and even to check for a PPC SVR multi-arch drivers would otherwise
need to ifdef the header inclusion and all references to the SVR symbols.
Signed-off-by: Yangbo Lu <yangbo.lu-3arQi8VN3Tc@public.gmane.org>
Acked-by: Wolfram Sang <wsa-z923LK4zBo2bacvFa/9K2g@public.gmane.org>
Acked-by: Stephen Boyd <sboyd-sgV2jX0FEOL9JmXXK+q4OQ@public.gmane.org>
Acked-by: Joerg Roedel <jroedel-l3A5Bk7waGM@public.gmane.org>
[scottwood: update description]
Signed-off-by: Scott Wood <oss-fOR+EgIDQEHk1uMJSBkQmQ@public.gmane.org>
---
Changes for v2:
- None
Changes for v3:
- None
Changes for v4:
- None
Changes for v5:
- Changed to Move mpc85xx.h to include/linux/fsl/
- Adjusted '#include <linux/fsl/svr.h>' position in file
Changes for v6:
- None
Changes for v7:
- Added 'Acked-by: Wolfram Sang' for I2C part
- Also applied to arch/powerpc/kernel/cpu_setup_fsl_booke.S
Changes for v8:
- Added 'Acked-by: Stephen Boyd' for clk part
- Added 'Acked-by: Scott Wood'
- Added 'Acked-by: Joerg Roedel' for iommu part
Changes for v9:
- None
Changes for v10:
- None
Changes for v11:
- Updated description by Scott
---
arch/powerpc/kernel/cpu_setup_fsl_booke.S | 2 +-
arch/powerpc/sysdev/fsl_pci.c | 2 +-
drivers/clk/clk-qoriq.c | 3 +--
drivers/i2c/busses/i2c-mpc.c | 2 +-
drivers/iommu/fsl_pamu.c | 3 +--
drivers/net/ethernet/freescale/gianfar.c | 2 +-
arch/powerpc/include/asm/mpc85xx.h => include/linux/fsl/svr.h | 4 ++--
7 files changed, 8 insertions(+), 10 deletions(-)
rename arch/powerpc/include/asm/mpc85xx.h => include/linux/fsl/svr.h (97%)
diff --git a/arch/powerpc/kernel/cpu_setup_fsl_booke.S b/arch/powerpc/kernel/cpu_setup_fsl_booke.S
index 462aed9..2b0284e 100644
--- a/arch/powerpc/kernel/cpu_setup_fsl_booke.S
+++ b/arch/powerpc/kernel/cpu_setup_fsl_booke.S
@@ -13,13 +13,13 @@
*
*/
+#include <linux/fsl/svr.h>
#include <asm/page.h>
#include <asm/processor.h>
#include <asm/cputable.h>
#include <asm/ppc_asm.h>
#include <asm/mmu-book3e.h>
#include <asm/asm-offsets.h>
-#include <asm/mpc85xx.h>
_GLOBAL(__e500_icache_setup)
mfspr r0, SPRN_L1CSR1
diff --git a/arch/powerpc/sysdev/fsl_pci.c b/arch/powerpc/sysdev/fsl_pci.c
index 0ef9df4..0fd1895 100644
--- a/arch/powerpc/sysdev/fsl_pci.c
+++ b/arch/powerpc/sysdev/fsl_pci.c
@@ -22,6 +22,7 @@
#include <linux/delay.h>
#include <linux/string.h>
#include <linux/fsl/edac.h>
+#include <linux/fsl/svr.h>
#include <linux/init.h>
#include <linux/interrupt.h>
#include <linux/memblock.h>
@@ -37,7 +38,6 @@
#include <asm/pci-bridge.h>
#include <asm/ppc-pci.h>
#include <asm/machdep.h>
-#include <asm/mpc85xx.h>
#include <asm/disassemble.h>
#include <asm/ppc-opcode.h>
#include <sysdev/fsl_soc.h>
diff --git a/drivers/clk/clk-qoriq.c b/drivers/clk/clk-qoriq.c
index 58566a17..4b6c438 100644
--- a/drivers/clk/clk-qoriq.c
+++ b/drivers/clk/clk-qoriq.c
@@ -13,6 +13,7 @@
#include <linux/clk.h>
#include <linux/clk-provider.h>
#include <linux/fsl/guts.h>
+#include <linux/fsl/svr.h>
#include <linux/io.h>
#include <linux/kernel.h>
#include <linux/module.h>
@@ -1149,8 +1150,6 @@ bad_args:
}
#ifdef CONFIG_PPC
-#include <asm/mpc85xx.h>
-
static const u32 a4510_svrs[] __initconst = {
(SVR_P2040 << 8) | 0x10, /* P2040 1.0 */
(SVR_P2040 << 8) | 0x11, /* P2040 1.1 */
diff --git a/drivers/i2c/busses/i2c-mpc.c b/drivers/i2c/busses/i2c-mpc.c
index 48ecffe..600704c 100644
--- a/drivers/i2c/busses/i2c-mpc.c
+++ b/drivers/i2c/busses/i2c-mpc.c
@@ -27,9 +27,9 @@
#include <linux/i2c.h>
#include <linux/interrupt.h>
#include <linux/delay.h>
+#include <linux/fsl/svr.h>
#include <asm/mpc52xx.h>
-#include <asm/mpc85xx.h>
#include <sysdev/fsl_soc.h>
#define DRV_NAME "mpc-i2c"
diff --git a/drivers/iommu/fsl_pamu.c b/drivers/iommu/fsl_pamu.c
index a34355f..af8fb27 100644
--- a/drivers/iommu/fsl_pamu.c
+++ b/drivers/iommu/fsl_pamu.c
@@ -21,11 +21,10 @@
#include "fsl_pamu.h"
#include <linux/fsl/guts.h>
+#include <linux/fsl/svr.h>
#include <linux/interrupt.h>
#include <linux/genalloc.h>
-#include <asm/mpc85xx.h>
-
/* define indexes for each operation mapping scenario */
#define OMI_QMAN 0x00
#define OMI_FMAN 0x01
diff --git a/drivers/net/ethernet/freescale/gianfar.c b/drivers/net/ethernet/freescale/gianfar.c
index d20935d..b8dac84 100644
--- a/drivers/net/ethernet/freescale/gianfar.c
+++ b/drivers/net/ethernet/freescale/gianfar.c
@@ -86,11 +86,11 @@
#include <linux/udp.h>
#include <linux/in.h>
#include <linux/net_tstamp.h>
+#include <linux/fsl/svr.h>
#include <asm/io.h>
#ifdef CONFIG_PPC
#include <asm/reg.h>
-#include <asm/mpc85xx.h>
#endif
#include <asm/irq.h>
#include <asm/uaccess.h>
diff --git a/arch/powerpc/include/asm/mpc85xx.h b/include/linux/fsl/svr.h
similarity index 97%
rename from arch/powerpc/include/asm/mpc85xx.h
rename to include/linux/fsl/svr.h
index 213f3a8..8d13836 100644
--- a/arch/powerpc/include/asm/mpc85xx.h
+++ b/include/linux/fsl/svr.h
@@ -9,8 +9,8 @@
* (at your option) any later version.
*/
-#ifndef __ASM_PPC_MPC85XX_H
-#define __ASM_PPC_MPC85XX_H
+#ifndef FSL_SVR_H
+#define FSL_SVR_H
#define SVR_REV(svr) ((svr) & 0xFF) /* SOC design resision */
#define SVR_MAJ(svr) (((svr) >> 4) & 0xF) /* Major revision field*/
--
2.1.0.27.g96db324
^ permalink raw reply related
* [v11, 3/8] dt: bindings: move guts devicetree doc out of powerpc directory
From: Yangbo Lu @ 2016-09-06 8:28 UTC (permalink / raw)
To: linux-mmc-u79uwXL29TY76Z2rM5mHXA,
ulf.hansson-QSEj5FYQhm4dnm+yROfE0A, Scott Wood, Arnd Bergmann
Cc: Mark Rutland, devicetree-u79uwXL29TY76Z2rM5mHXA, Russell King,
Yangbo Lu, Bhupesh Sharma, netdev-u79uwXL29TY76Z2rM5mHXA,
Santosh Shilimkar, linux-kernel-u79uwXL29TY76Z2rM5mHXA,
Jochen Friedrich, xiaobo.xie-3arQi8VN3Tc,
iommu-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA, Rob Herring,
linux-i2c-u79uwXL29TY76Z2rM5mHXA, Claudiu Manoil, Kumar Gala,
leoyang.li-3arQi8VN3Tc, linuxppc-dev-uLR06cmDAlY/bJ5BZ2RsiQ,
linux-clk-u79uwXL29TY76Z2rM5mHXA,
linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Qiang Zhao
In-Reply-To: <1473150503-9550-1-git-send-email-yangbo.lu-3arQi8VN3Tc@public.gmane.org>
Move guts devicetree doc to Documentation/devicetree/bindings/soc/fsl/
since it's used by not only PowerPC but also ARM. And add a specification
for 'little-endian' property.
Signed-off-by: Yangbo Lu <yangbo.lu-3arQi8VN3Tc@public.gmane.org>
Acked-by: Rob Herring <robh-DgEjT+Ai2ygdnm+yROfE0A@public.gmane.org>
Acked-by: Scott Wood <oss-fOR+EgIDQEHk1uMJSBkQmQ@public.gmane.org>
---
Changes for v4:
- Added this patch
Changes for v5:
- Modified the description for little-endian property
Changes for v6:
- None
Changes for v7:
- None
Changes for v8:
- Added 'Acked-by: Scott Wood'
- Added 'Acked-by: Rob Herring'
Changes for v9:
- None
Changes for v10:
- None
Changes for v11:
- None
---
Documentation/devicetree/bindings/{powerpc => soc}/fsl/guts.txt | 3 +++
1 file changed, 3 insertions(+)
rename Documentation/devicetree/bindings/{powerpc => soc}/fsl/guts.txt (91%)
diff --git a/Documentation/devicetree/bindings/powerpc/fsl/guts.txt b/Documentation/devicetree/bindings/soc/fsl/guts.txt
similarity index 91%
rename from Documentation/devicetree/bindings/powerpc/fsl/guts.txt
rename to Documentation/devicetree/bindings/soc/fsl/guts.txt
index b71b203..07adca9 100644
--- a/Documentation/devicetree/bindings/powerpc/fsl/guts.txt
+++ b/Documentation/devicetree/bindings/soc/fsl/guts.txt
@@ -25,6 +25,9 @@ Recommended properties:
- fsl,liodn-bits : Indicates the number of defined bits in the LIODN
registers, for those SOCs that have a PAMU device.
+ - little-endian : Indicates that the global utilities block is little
+ endian. The default is big endian.
+
Examples:
global-utilities@e0000 { /* global utilities block */
compatible = "fsl,mpc8548-guts";
--
2.1.0.27.g96db324
^ permalink raw reply related
* [v11, 2/8] ARM64: dts: ls2080a: add device configuration node
From: Yangbo Lu @ 2016-09-06 8:28 UTC (permalink / raw)
To: linux-mmc-u79uwXL29TY76Z2rM5mHXA,
ulf.hansson-QSEj5FYQhm4dnm+yROfE0A, Scott Wood, Arnd Bergmann
Cc: Mark Rutland, devicetree-u79uwXL29TY76Z2rM5mHXA, Russell King,
Yangbo Lu, Bhupesh Sharma, netdev-u79uwXL29TY76Z2rM5mHXA,
Santosh Shilimkar, linux-kernel-u79uwXL29TY76Z2rM5mHXA,
Jochen Friedrich, xiaobo.xie-3arQi8VN3Tc,
iommu-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA, Rob Herring,
linux-i2c-u79uwXL29TY76Z2rM5mHXA, Claudiu Manoil, Kumar Gala,
leoyang.li-3arQi8VN3Tc, linuxppc-dev-uLR06cmDAlY/bJ5BZ2RsiQ,
linux-clk-u79uwXL29TY76Z2rM5mHXA,
linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Qiang Zhao
In-Reply-To: <1473150503-9550-1-git-send-email-yangbo.lu-3arQi8VN3Tc@public.gmane.org>
Add the dts node for device configuration unit that provides
general purpose configuration and status for the device.
Signed-off-by: Yangbo Lu <yangbo.lu-3arQi8VN3Tc@public.gmane.org>
Acked-by: Scott Wood <oss-fOR+EgIDQEHk1uMJSBkQmQ@public.gmane.org>
---
Changes for v5:
- Added this patch
Changes for v6:
- None
Changes for v7:
- None
Changes for v8:
- Added 'Acked-by: Scott Wood'
Changes for v9:
- None
Changes for v10:
- None
Changes for v11:
- None
---
arch/arm64/boot/dts/freescale/fsl-ls2080a.dtsi | 6 ++++++
1 file changed, 6 insertions(+)
diff --git a/arch/arm64/boot/dts/freescale/fsl-ls2080a.dtsi b/arch/arm64/boot/dts/freescale/fsl-ls2080a.dtsi
index 21023a3..39f7743 100644
--- a/arch/arm64/boot/dts/freescale/fsl-ls2080a.dtsi
+++ b/arch/arm64/boot/dts/freescale/fsl-ls2080a.dtsi
@@ -215,6 +215,12 @@
clocks = <&sysclk>;
};
+ dcfg: dcfg@1e00000 {
+ compatible = "fsl,ls2080a-dcfg", "syscon";
+ reg = <0x0 0x1e00000 0x0 0x10000>;
+ little-endian;
+ };
+
serial0: serial@21c0500 {
compatible = "fsl,ns16550", "ns16550a";
reg = <0x0 0x21c0500 0x0 0x100>;
--
2.1.0.27.g96db324
^ permalink raw reply related
* [v11, 1/8] dt: bindings: update Freescale DCFG compatible
From: Yangbo Lu @ 2016-09-06 8:28 UTC (permalink / raw)
To: linux-mmc-u79uwXL29TY76Z2rM5mHXA,
ulf.hansson-QSEj5FYQhm4dnm+yROfE0A, Scott Wood, Arnd Bergmann
Cc: Mark Rutland, devicetree-u79uwXL29TY76Z2rM5mHXA, Russell King,
Yangbo Lu, Bhupesh Sharma, netdev-u79uwXL29TY76Z2rM5mHXA,
Santosh Shilimkar, linux-kernel-u79uwXL29TY76Z2rM5mHXA,
Jochen Friedrich, xiaobo.xie-3arQi8VN3Tc,
iommu-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA, Rob Herring,
linux-i2c-u79uwXL29TY76Z2rM5mHXA, Claudiu Manoil, Kumar Gala,
leoyang.li-3arQi8VN3Tc, linuxppc-dev-uLR06cmDAlY/bJ5BZ2RsiQ,
linux-clk-u79uwXL29TY76Z2rM5mHXA,
linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Qiang Zhao
In-Reply-To: <1473150503-9550-1-git-send-email-yangbo.lu-3arQi8VN3Tc@public.gmane.org>
Update Freescale DCFG compatible with 'fsl,<chip>-dcfg' instead
of 'fsl,ls1021a-dcfg' to include more chips such as ls1021a,
ls1043a, and ls2080a.
Signed-off-by: Yangbo Lu <yangbo.lu-3arQi8VN3Tc@public.gmane.org>
Acked-by: Rob Herring <robh-DgEjT+Ai2ygdnm+yROfE0A@public.gmane.org>
Signed-off-by: Scott Wood <oss-fOR+EgIDQEHk1uMJSBkQmQ@public.gmane.org>
---
Changes for v8:
- Added this patch
Changes for v9:
- Added a list for the possible compatibles
Changes for v10:
- None
Changes for v11:
- Added 'Acked-by: Rob Herring'
- Updated commit message by Scott
---
Documentation/devicetree/bindings/arm/fsl.txt | 6 +++++-
1 file changed, 5 insertions(+), 1 deletion(-)
diff --git a/Documentation/devicetree/bindings/arm/fsl.txt b/Documentation/devicetree/bindings/arm/fsl.txt
index dbbc095..713c1ae 100644
--- a/Documentation/devicetree/bindings/arm/fsl.txt
+++ b/Documentation/devicetree/bindings/arm/fsl.txt
@@ -119,7 +119,11 @@ Freescale DCFG
configuration and status for the device. Such as setting the secondary
core start address and release the secondary core from holdoff and startup.
Required properties:
- - compatible: should be "fsl,ls1021a-dcfg"
+ - compatible: should be "fsl,<chip>-dcfg"
+ Possible compatibles:
+ "fsl,ls1021a-dcfg"
+ "fsl,ls1043a-dcfg"
+ "fsl,ls2080a-dcfg"
- reg : should contain base address and length of DCFG memory-mapped registers
Example:
--
2.1.0.27.g96db324
^ permalink raw reply related
* [v11, 0/8] Fix eSDHC host version register bug
From: Yangbo Lu @ 2016-09-06 8:28 UTC (permalink / raw)
To: linux-mmc-u79uwXL29TY76Z2rM5mHXA,
ulf.hansson-QSEj5FYQhm4dnm+yROfE0A, Scott Wood, Arnd Bergmann
Cc: Mark Rutland, devicetree-u79uwXL29TY76Z2rM5mHXA, Russell King,
Yangbo Lu, Bhupesh Sharma, netdev-u79uwXL29TY76Z2rM5mHXA,
Santosh Shilimkar, linux-kernel-u79uwXL29TY76Z2rM5mHXA,
Jochen Friedrich, xiaobo.xie-3arQi8VN3Tc,
iommu-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA, Rob Herring,
linux-i2c-u79uwXL29TY76Z2rM5mHXA, Claudiu Manoil, Kumar Gala,
leoyang.li-3arQi8VN3Tc, linuxppc-dev-uLR06cmDAlY/bJ5BZ2RsiQ,
linux-clk-u79uwXL29TY76Z2rM5mHXA,
linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r, Qiang Zhao
This patchset is used to fix a host version register bug in the T4240-R1.0-R2.0
eSDHC controller. To match the SoC version and revision, 10 previous version
patchsets had tried many methods but all of them were rejected by reviewers.
Such as
- dts compatible method
- syscon method
- ifdef PPC method
- GUTS driver getting SVR method
Anrd suggested a soc_device_match method in v10, and this is the only available
method left now. This v11 patchset introduces the soc_device_match interface in
soc driver.
The first six patches are to add the GUTS driver. This is used to register a
soc device which contain soc version and revision information.
The following two patches introduce the soc_device_match method in soc driver
and apply it on esdhc driver to fix this bug.
Yangbo Lu (8):
dt: bindings: update Freescale DCFG compatible
ARM64: dts: ls2080a: add device configuration node
dt: bindings: move guts devicetree doc out of powerpc directory
powerpc/fsl: move mpc85xx.h to include/linux/fsl
soc: fsl: add GUTS driver for QorIQ platforms
MAINTAINERS: add entry for Freescale SoC drivers
base: soc: introduce soc_device_match() interface
mmc: sdhci-of-esdhc: fix host version for T4240-R1.0-R2.0
Documentation/devicetree/bindings/arm/fsl.txt | 6 +-
.../bindings/{powerpc => soc}/fsl/guts.txt | 3 +
MAINTAINERS | 11 +-
arch/arm64/boot/dts/freescale/fsl-ls2080a.dtsi | 6 +
arch/powerpc/kernel/cpu_setup_fsl_booke.S | 2 +-
arch/powerpc/sysdev/fsl_pci.c | 2 +-
drivers/base/Kconfig | 1 +
drivers/base/soc.c | 61 +++
drivers/clk/clk-qoriq.c | 3 +-
drivers/i2c/busses/i2c-mpc.c | 2 +-
drivers/iommu/fsl_pamu.c | 3 +-
drivers/mmc/host/Kconfig | 1 +
drivers/mmc/host/sdhci-of-esdhc.c | 20 +
drivers/net/ethernet/freescale/gianfar.c | 2 +-
drivers/soc/Kconfig | 2 +-
drivers/soc/fsl/Kconfig | 20 +
drivers/soc/fsl/Makefile | 1 +
drivers/soc/fsl/guts.c | 483 +++++++++++++++++++++
include/linux/fsl/guts.h | 127 ++++--
.../asm/mpc85xx.h => include/linux/fsl/svr.h | 4 +-
include/linux/sys_soc.h | 3 +
21 files changed, 702 insertions(+), 61 deletions(-)
rename Documentation/devicetree/bindings/{powerpc => soc}/fsl/guts.txt (91%)
create mode 100644 drivers/soc/fsl/Kconfig
create mode 100644 drivers/soc/fsl/guts.c
rename arch/powerpc/include/asm/mpc85xx.h => include/linux/fsl/svr.h (97%)
--
2.1.0.27.g96db324
^ permalink raw reply
* [PATCH 3/3] i2c: expose adapter probe and remove probed functions
From: David Lechner @ 2016-09-05 20:40 UTC (permalink / raw)
To: Wolfram Sang; +Cc: David Lechner, linux-i2c, linux-kernel
In-Reply-To: <1473108014-30787-1-git-send-email-david@lechnology.com>
Publicly expose functions for detecting devices and removing detected
devices.
Currently an i2c adapter only probes/detects new devices when the adapter
is added or when a new i2c driver is added. This adds a new function,
i2c_adapter_probe(), that allows detecting sensors at any time.
Furthermore, the function i2c_adapter_remove_probed() is added to remove
the devices added by i2c_adapter_probe() at any time.
The intended use of these functions is for LEGO MINDSTORMS sensors. These
are hot-plugable I2C devices. When a sensor is connected, i2c_adapter_probe()
is called to automatically configure the sensor. When the sensor is
disconnected, i2c_adapter_remove_probed() is called to remove the
automatically configured device.
Signed-off-by: David Lechner <david@lechnology.com>
---
drivers/i2c/i2c-core.c | 45 ++++++++++++++++++++++++++++++++++++++-------
include/linux/i2c.h | 3 +++
2 files changed, 41 insertions(+), 7 deletions(-)
diff --git a/drivers/i2c/i2c-core.c b/drivers/i2c/i2c-core.c
index 28436d9..2781a88 100644
--- a/drivers/i2c/i2c-core.c
+++ b/drivers/i2c/i2c-core.c
@@ -1691,6 +1691,23 @@ static int __process_new_adapter(struct device_driver *d, void *data)
return i2c_do_add_adapter(to_i2c_driver(d), data);
}
+/**
+ * i2c_adapter_probe - probe adapter for clients
+ * @adap: The i2c adapter.
+ *
+ * This calls the detect function of each driver that matches the class of the
+ * adapter. This function is called when an adapter is added, so there is no
+ * need to call this manually, unless you have hot-plugable i2c devices that
+ * are connected after the adapter is created.
+ */
+void i2c_adapter_probe(struct i2c_adapter *adap)
+{
+ mutex_lock(&core_lock);
+ bus_for_each_drv(&i2c_bus_type, NULL, adap, __process_new_adapter);
+ mutex_unlock(&core_lock);
+}
+EXPORT_SYMBOL(i2c_adapter_probe);
+
static int i2c_register_adapter(struct i2c_adapter *adap)
{
int res = -EINVAL;
@@ -1759,9 +1776,7 @@ static int i2c_register_adapter(struct i2c_adapter *adap)
i2c_scan_static_board_info(adap);
/* Notify drivers */
- mutex_lock(&core_lock);
- bus_for_each_drv(&i2c_bus_type, NULL, adap, __process_new_adapter);
- mutex_unlock(&core_lock);
+ i2c_adapter_probe(adap);
return 0;
@@ -1904,6 +1919,25 @@ static int __process_removed_adapter(struct device_driver *d, void *data)
}
/**
+ * i2c_adapter_remove_probed - Remove clients that were automatically detected.
+ * @adap: The i2c adapter.
+ *
+ * This removes all i2c clients from this adapter that were added via driver
+ * detect() functions. This function is called when an adapter is removed, so
+ * there is no need to call this manually, unless you have hot-plugable i2c
+ * devices that are disconnected before the adapter is destroyed.
+ *
+ * Any clients that were added manually (e.g. via sysfs) are not removed.
+ */
+void i2c_adapter_remove_probed(struct i2c_adapter *adap)
+{
+ mutex_lock(&core_lock);
+ bus_for_each_drv(&i2c_bus_type, NULL, adap, __process_removed_adapter);
+ mutex_unlock(&core_lock);
+}
+EXPORT_SYMBOL(i2c_adapter_remove_probed);
+
+/**
* i2c_del_adapter - unregister I2C adapter
* @adap: the adapter being unregistered
* Context: can sleep
@@ -1927,10 +1961,7 @@ void i2c_del_adapter(struct i2c_adapter *adap)
acpi_i2c_remove_space_handler(adap);
/* Tell drivers about this removal */
- mutex_lock(&core_lock);
- bus_for_each_drv(&i2c_bus_type, NULL, adap,
- __process_removed_adapter);
- mutex_unlock(&core_lock);
+ i2c_adapter_remove_probed(adap);
/* Remove devices instantiated from sysfs */
mutex_lock_nested(&adap->userspace_clients_lock,
diff --git a/include/linux/i2c.h b/include/linux/i2c.h
index 3eab858..0016623 100644
--- a/include/linux/i2c.h
+++ b/include/linux/i2c.h
@@ -657,6 +657,9 @@ extern int i2c_add_adapter(struct i2c_adapter *);
extern void i2c_del_adapter(struct i2c_adapter *);
extern int i2c_add_numbered_adapter(struct i2c_adapter *);
+extern void i2c_adapter_probe(struct i2c_adapter *adap);
+extern void i2c_adapter_remove_probed(struct i2c_adapter *adap);
+
extern int i2c_register_driver(struct module *, struct i2c_driver *);
extern void i2c_del_driver(struct i2c_driver *);
--
2.7.4
^ permalink raw reply related
* [PATCH 2/3] i2c: Add special case for detecting LEGO devices
From: David Lechner @ 2016-09-05 20:40 UTC (permalink / raw)
To: Wolfram Sang; +Cc: David Lechner, linux-i2c, linux-kernel
In-Reply-To: <1473108014-30787-1-git-send-email-david@lechnology.com>
LEGO chose to ignore the I2C specification and has created devices with
I2C addresses of 0x01 and 0x02. i2c_check_7bit_addr_validity_strict()
disallows these addresses, so we need a special case to skip this for
LEGO sensors.
Furthermore, LEGO devices do not respond to i2c_default_probe(), so we
skip this as a special case as well.
Signed-off-by: David Lechner <david@lechnology.com>
---
drivers/i2c/i2c-core.c | 17 ++++++++++-------
1 file changed, 10 insertions(+), 7 deletions(-)
diff --git a/drivers/i2c/i2c-core.c b/drivers/i2c/i2c-core.c
index da3a02e..28436d9 100644
--- a/drivers/i2c/i2c-core.c
+++ b/drivers/i2c/i2c-core.c
@@ -2591,12 +2591,14 @@ static int i2c_detect_address(struct i2c_client *temp_client,
int addr = temp_client->addr;
int err;
- /* Make sure the address is valid */
- err = i2c_check_7bit_addr_validity_strict(addr);
- if (err) {
- dev_warn(&adapter->dev, "Invalid probe address 0x%02x\n",
- addr);
- return err;
+ /* Make sure the address is valid - LEGO devices break the rules */
+ if (!(driver->class & I2C_CLASS_LEGO)) {
+ err = i2c_check_7bit_addr_validity_strict(addr);
+ if (err) {
+ dev_warn(&adapter->dev, "Invalid probe address 0x%02x\n",
+ addr);
+ return err;
+ }
}
/* Skip if already in use (7 bit, no need to encode flags) */
@@ -2604,7 +2606,8 @@ static int i2c_detect_address(struct i2c_client *temp_client,
return 0;
/* Make sure there is something at this address */
- if (!i2c_default_probe(adapter, addr))
+ if (!(driver->class & I2C_CLASS_LEGO) &&
+ !i2c_default_probe(adapter, addr))
return 0;
/* Finally call the custom detection function */
--
2.7.4
^ permalink raw reply related
* [PATCH 1/3] i2c: Add class for LEGO MINDSTORMS sensors
From: David Lechner @ 2016-09-05 20:40 UTC (permalink / raw)
To: Wolfram Sang; +Cc: David Lechner, linux-i2c, linux-kernel
In-Reply-To: <1473108014-30787-1-git-send-email-david@lechnology.com>
LEGO MINDSTORMS (robotics system from LEGO) has a number of sensors
that use I2C communications. These sensors have a well-know register
layout, so they are easily detected.
This class is being added so that future drivers for these sensors can
be automatically detected.
Signed-off-by: David Lechner <david@lechnology.com>
---
include/linux/i2c.h | 1 +
1 file changed, 1 insertion(+)
diff --git a/include/linux/i2c.h b/include/linux/i2c.h
index fffdc27..3eab858 100644
--- a/include/linux/i2c.h
+++ b/include/linux/i2c.h
@@ -638,6 +638,7 @@ i2c_unlock_adapter(struct i2c_adapter *adapter)
#define I2C_CLASS_DDC (1<<3) /* DDC bus on graphics adapters */
#define I2C_CLASS_SPD (1<<7) /* Memory modules */
#define I2C_CLASS_DEPRECATED (1<<8) /* Warn users that adapter will stop using classes */
+#define I2C_CLASS_LEGO (1<<9) /* LEGO MINDSTORMS sensors */
/* Internal numbers to terminate lists */
#define I2C_CLIENT_END 0xfffeU
--
2.7.4
^ permalink raw reply related
* [PATCH 0/3] LEGO MINDSTORMS I2C support
From: David Lechner @ 2016-09-05 20:40 UTC (permalink / raw)
To: Wolfram Sang; +Cc: David Lechner, linux-i2c, linux-kernel
I'm working on getting LEGO MINDSTORMS[1] support in the Linux kernel.
They have a system of modular sensors that are hot-plugable, some of which use
I2C communications. Unfortunately, these don't necessary follow standard I2C
conventions, but they do have a well-defined register layout, so they are
easy to detect.
This set of patches addresses the hot-plugability of the sensors.
[1]: http://mindstorms.lego.com
David Lechner (3):
i2c: Add class for LEGO MINDSTORMS sensors
i2c: Add special case for detecting LEGO devices
i2c: expose adapter probe and remove probed functions
drivers/i2c/i2c-core.c | 62 ++++++++++++++++++++++++++++++++++++++------------
include/linux/i2c.h | 4 ++++
2 files changed, 52 insertions(+), 14 deletions(-)
--
2.7.4
^ permalink raw reply
* Re: [patch 2/2] i2c: mux: mellanox: add driver
From: Peter Rosin @ 2016-09-02 12:16 UTC (permalink / raw)
To: vadimp, wsa; +Cc: linux-i2c, linux-kernel, jiri, Michael Shych
In-Reply-To: <1472492176-195844-1-git-send-email-vadimp@mellanox.com>
On 2016-08-29 19:36, vadimp@mellanox.com wrote:
> From: Vadim Pasternak <vadimp@mellanox.com>
>
> This driver allows I2C routing controlled through CPLD select registers on
> wide range of Mellanox systems (CPLD Lattice device).
> MUX selection is provided by digital and analog HW. Analog part is not
> under SW control.
> Digital part is under CPLD control (channel selection/de-selection).
>
> Connectivity schema.
> i2c-mlxcpld Digital Analog
> driver
> *--------* * -> mux1 (virt bus2) -> mux ->|
> | I2CLPC | i2c physical * -> mux2 (virt bus3) -> mux ->|
> | bridge | bus 1 *---------* |
> | logic |---------------------> * mux reg * |
> | in CPLD| *---------* |
> *--------* i2c-mux-mlxpcld ^ * -> muxn (virt busn) -> mux ->|
> | driver | |
> | *---------------* | Devices
> | * CPLD (LPC bus)* select |
> | * registers for *--------*
> | * mux selection * deselect
> | *---------------*
> | |
> <--------> <----------->
> i2c cntrl Board cntrl reg
> reg space space (mux select,
> | IO, LED, WD, info)
> | | *-----* *-----*
> *------------- LPC bus --------------| PCH |---| CPU |
> *-----* *-----*
>
> i2c-mux-mlxpcld does not necessary required i2c-mlxcpld. It can be use
s/necessary required/necessarily require a/
> along with another bus driver, and still control i2c routing through CPLD
> mux selection, in case the system is equipped with CPLD capable of mux
> selection control.
>
> The Kconfig currently controlling compilation of this code is:
> drivers/i2c/muxes/Kconfig:config I2C_MUX_MLXCPLD
>
> Signed-off-by: Michael Shych <michaelsh@mellanox.com>
> Signed-off-by: Vadim Pasternak <vadimp@mellanox.com>
> Reviewed-by: Jiri Pirko <jiri@mellanox.com>
> ---
> MAINTAINERS | 8 +
> drivers/i2c/muxes/Kconfig | 11 ++
> drivers/i2c/muxes/Makefile | 1 +
> drivers/i2c/muxes/i2c-mux-mlxcpld.c | 326 ++++++++++++++++++++++++++++++++++++
> include/linux/i2c/mlxcpld.h | 57 +++++++
> 5 files changed, 403 insertions(+)
> create mode 100644 drivers/i2c/muxes/i2c-mux-mlxcpld.c
> create mode 100644 include/linux/i2c/mlxcpld.h
It is customary to mark updated patches with v2, v3 etc in the subject
and to include a short changelog right here in this space (or perhaps
in a cover letter if it is a patch series). Please do so going
forward.
>
> diff --git a/MAINTAINERS b/MAINTAINERS
> index 8b3f8d7..a994455 100644
> --- a/MAINTAINERS
> +++ b/MAINTAINERS
> @@ -7664,6 +7664,14 @@ W: http://www.mellanox.com
> F: drivers/i2c/busses/i2c-mlxcpld.c
> F: Documentation/i2c/busses/i2c-mlxcpld
>
> +MELLANOX MLXCPLD I2C MUX DRIVER
> +M: Vadim Pasternak <vadimp@mellanox.com>
> +M: Michael Shych <michaelsh@mellanox.com>
> +L: linux-kernel@vger.kernel.org
Isn't the linux-i2c list a narrower and therefore better fit?
> +S: Supported
> +W: http://www.mellanox.com
> +F: drivers/i2c/muxes/i2c-mux-mlxcpld.c
> +
> SOFT-ROCE DRIVER (rxe)
> M: Moni Shoua <monis@mellanox.com>
> L: linux-rdma@vger.kernel.org
> diff --git a/drivers/i2c/muxes/Kconfig b/drivers/i2c/muxes/Kconfig
> index e280c8e..b7ab144 100644
> --- a/drivers/i2c/muxes/Kconfig
> +++ b/drivers/i2c/muxes/Kconfig
> @@ -81,4 +81,15 @@ config I2C_DEMUX_PINCTRL
> demultiplexer that uses the pinctrl subsystem. This is useful if you
> want to change the I2C master at run-time depending on features.
>
> +config I2C_MUX_MLXCPLD
> + tristate "Mellanox CPLD based I2C multiplexer"
> + help
> + If you say yes to this option, support will be included for a
> + CPLD based I2C multiplexer. This driver provides access to
> + I2C busses connected through a MUX, which is controlled
> + by a CPLD registers.
> +
> + This driver can also be built as a module. If so, the module
> + will be called i2c-mux-mlxcpld.
> +
> endmenu
> diff --git a/drivers/i2c/muxes/Makefile b/drivers/i2c/muxes/Makefile
> index 7c267c2..e5c990e 100644
> --- a/drivers/i2c/muxes/Makefile
> +++ b/drivers/i2c/muxes/Makefile
> @@ -10,5 +10,6 @@ obj-$(CONFIG_I2C_MUX_PCA9541) += i2c-mux-pca9541.o
> obj-$(CONFIG_I2C_MUX_PCA954x) += i2c-mux-pca954x.o
> obj-$(CONFIG_I2C_MUX_PINCTRL) += i2c-mux-pinctrl.o
> obj-$(CONFIG_I2C_MUX_REG) += i2c-mux-reg.o
> +obj-$(CONFIG_I2C_MUX_MLXCPLD) += i2c-mux-mlxcpld.o
>
> ccflags-$(CONFIG_I2C_DEBUG_BUS) := -DDEBUG
> diff --git a/drivers/i2c/muxes/i2c-mux-mlxcpld.c b/drivers/i2c/muxes/i2c-mux-mlxcpld.c
> new file mode 100644
> index 0000000..9624613
> --- /dev/null
> +++ b/drivers/i2c/muxes/i2c-mux-mlxcpld.c
> @@ -0,0 +1,326 @@
> +/*
> + * drivers/i2c/muxes/i2c-mux-mlxcpld.c
> + * Copyright (c) 2016 Mellanox Technologies. All rights reserved.
> + * Copyright (c) 2016 Michael Shych <michaels@mellanox.com>
> + *
> + * Redistribution and use in source and binary forms, with or without
> + * modification, are permitted provided that the following conditions are met:
> + *
> + * 1. Redistributions of source code must retain the above copyright
> + * notice, this list of conditions and the following disclaimer.
> + * 2. Redistributions in binary form must reproduce the above copyright
> + * notice, this list of conditions and the following disclaimer in the
> + * documentation and/or other materials provided with the distribution.
> + * 3. Neither the names of the copyright holders nor the names of its
> + * contributors may be used to endorse or promote products derived from
> + * this software without specific prior written permission.
> + *
> + * Alternatively, this software may be distributed under the terms of the
> + * GNU General Public License ("GPL") version 2 as published by the Free
> + * Software Foundation.
> + *
> + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
> + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
> + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
> + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
> + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
> + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
> + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
> + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
> + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
> + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
> + * POSSIBILITY OF SUCH DAMAGE.
> + */
> +
> +#include <linux/module.h>
> +#include <linux/version.h>
> +#include <linux/init.h>
> +#include <linux/slab.h>
> +#include <linux/device.h>
> +#include <linux/i2c.h>
> +#include <linux/i2c-mux.h>
> +#include <linux/io.h>
> +#include <linux/platform_device.h>
> +#include <linux/i2c/mlxcpld.h>
Please sort the includes.
> +
> +#define CPLD_MUX_MAX_NCHANS 8
> +#define CPLD_MUX_EXT_MAX_NCHANS 24
> +
> +/*
> + * mlxcpld_mux types - kind of mux supported by driver:
> + * @mlxcpld_mux_tor - LPC access; 8 channels.
> + * @mlxcpld_mux_mgmt - LPC access; 8 channels.
> + * @mlxcpld_mux_mgmt_ext - LPC access; 24 channels.
> + * @mlxcpld_mux_module - I2C access; 8 channels/legs.
> + */
> +enum mlxcpld_mux_type {
> + mlxcpld_mux_tor,
> + mlxcpld_mux_mgmt,
> + mlxcpld_mux_mgmt_ext,
> + mlxcpld_mux_module,
> +};
> +
> +/* mlxcpld_mux_type - underlying physical bus, to which device is connected:
> + * @lpc_access - LPC connected CPLD device
> + * @i2c_access - I2C connected CPLD device
> + */
> +enum mlxcpld_mux_access_type {
> + lpc_access,
> + i2c_access,
> +};
> +
> +/* mlxcpld_mux - mux control structure:
> + * @type - mux type
> + * @last_chan - last register value
> + * @client - I2C device client
> + */
> +struct mlxcpld_mux {
> + enum mlxcpld_mux_type type;
> + u8 last_chan;
> + struct i2c_client *client;
> +};
> +
> +/* mlxcpld_mux_desc - mux descriptor structure:
> + * @nchans - number of channels
> + * @muxtype - physical mux type (LPC or I2C)
> + */
> +struct mlxcpld_mux_desc {
> + u8 nchans;
> + enum mlxcpld_mux_access_type muxtype;
> +};
> +
> +/* MUX logic description.
> + * This logic can be applied for LPC attached CPLD and fro I2C attached CPLD.
> + * Driver can support different mux control logic, according to CPLD
> + * implementation.
> + *
> + * Connectivity schema.
> + *
> + * i2c-mlxcpld Digital Analog
> + * driver
> + * *--------* * -> mux1 (virt bus2) -> mux -> |
> + * | I2CLPC | i2c physical * -> mux2 (virt bus3) -> mux -> |
> + * | bridge | bus 1 *---------* |
> + * | logic |---------------------> * mux reg * |
> + * | in CPLD| *---------* |
> + * *--------* i2c-mux-mlxpcld ^ * -> muxn (virt busn) -> mux -> |
> + * | driver | |
> + * | *---------------* | Devices
> + * | * CPLD (LPC bus)* select |
> + * | * registers for *--------*
> + * | * mux selection * deselect
> + * | *---------------*
> + * | |
> + * <--------> <----------->
> + * i2c cntrl Board cntrl reg
> + * reg space space (mux select,
> + * | IO, LED, WD, info)
> + * | | *-----* *-----*
> + * *------------- LPC bus --------------| PCH |---| CPU |
> + * *-----* *-----*
> + *
> + */
> +static const struct mlxcpld_mux_desc muxes[] = {
> + [mlxcpld_mux_tor] = {
> + .nchans = CPLD_MUX_MAX_NCHANS,
> + .muxtype = lpc_access,
> + },
> + [mlxcpld_mux_mgmt] = {
> + .nchans = CPLD_MUX_MAX_NCHANS,
> + .muxtype = lpc_access,
> + },
> + [mlxcpld_mux_mgmt_ext] = {
> + .nchans = CPLD_MUX_EXT_MAX_NCHANS,
> + .muxtype = lpc_access,
> + },
> + [mlxcpld_mux_module] = {
> + .nchans = CPLD_MUX_MAX_NCHANS,
> + .muxtype = i2c_access,
> + },
> +};
> +
> +static const struct i2c_device_id mlxcpld_mux_id[] = {
> + { "mlxcpld_mux_tor", mlxcpld_mux_tor },
> + { "mlxcpld_mux_mgmt", mlxcpld_mux_mgmt },
> + { "mlxcpld_mux_mgmt_ext", mlxcpld_mux_mgmt_ext },
> + { "mlxcpld_mux_module", mlxcpld_mux_module },
> + { }
> +};
> +MODULE_DEVICE_TABLE(i2c, mlxcpld_mux_id);
> +
> +/* Write to mux register. Don't use i2c_transfer() and
> + * i2c_smbus_xfer() for this as they will try to lock adapter a second time
> + */
> +static int mlxcpld_mux_reg_write(struct i2c_adapter *adap,
> + struct i2c_client *client, u8 val,
> + enum mlxcpld_mux_access_type muxtype)
> +{
> + struct mlxcpld_mux_platform_data *pdata =
> + dev_get_platdata(&client->dev);
This looks weird (several instances). Use shorter names, assign after the
declaration or just ignore the line length "rule".
> + int ret = -ENODEV;
> +
> + switch (muxtype) {
> + case lpc_access:
> + outb(val, pdata->addr); /* addr = CPLD base + offset */
> + ret = 1;
> + break;
> +
> + case i2c_access:
> + if (adap->algo->master_xfer) {
> + struct i2c_msg msg;
> + u8 msgbuf[] = {pdata->sel_reg_addr, val};
> +
> + msg.addr = pdata->addr;
> + msg.flags = 0;
> + msg.len = 2;
> + msg.buf = msgbuf;
> + return __i2c_transfer(adap, &msg, 1);
> + }
> + dev_err(&client->dev, "SMBus isn't supported on this adapter\n");
> + break;
> +
> + default:
> + dev_err(&client->dev, "Incorrect muxtype %d\n", muxtype);
> + }
> +
> + return ret;
> +}
> +
> +static int mlxcpld_mux_select_chan(struct i2c_mux_core *muxc, u32 chan)
> +{
> + struct mlxcpld_mux *data = i2c_mux_priv(muxc);
> + struct i2c_client *client = data->client;
> + struct mlxcpld_mux_platform_data *pdata =
> + dev_get_platdata(&client->dev);
> + const struct mlxcpld_mux_desc *mux = &muxes[data->type];
> + u8 regval;
> + int err = 0;
> +
> + switch (data->type) {
> + case mlxcpld_mux_tor:
> + regval = pdata->first_channel + chan;
> + break;
> +
> + case mlxcpld_mux_mgmt:
> + case mlxcpld_mux_mgmt_ext:
> + case mlxcpld_mux_module:
> + regval = chan + 1;
> + break;
> +
> + default:
> + return -ENXIO;
> + }
> +
> + /* Only select the channel if its different from the last channel */
> + if (data->last_chan != regval) {
> + err = mlxcpld_mux_reg_write(muxc->parent, client, regval,
> + mux->muxtype);
> + data->last_chan = regval;
As I said for v2, if the reg write fails, you ignore the error when setting
last_chan. That means the reg write is not retried next time around and the
i2c traffic may end up on the wrong segment. I suggest that you set
last_chan to some "illegal" value on error (zero looks like a good candidate
if you look at deselect), so that the reg write is always done on a select
following an error.
> + }
> +
> + return err;
> +}
> +
> +static int mlxcpld_mux_deselect(struct i2c_mux_core *muxc, u32 chan)
> +{
> + struct mlxcpld_mux *data = i2c_mux_priv(muxc);
> + struct i2c_client *client = data->client;
> + const struct mlxcpld_mux_desc *mux = &muxes[data->type];
> +
> + /* Deselect active channel */
> + data->last_chan = 0;
> +
> + return mlxcpld_mux_reg_write(muxc->parent, client, data->last_chan,
> + mux->muxtype);
> +}
> +
> +/* I2C init/probing/exit functions */
> +static int mlxcpld_mux_probe(struct i2c_client *client,
> + const struct i2c_device_id *id)
> +{
> + struct i2c_adapter *adap = to_i2c_adapter(client->dev.parent);
> + struct mlxcpld_mux_platform_data *pdata =
> + dev_get_platdata(&client->dev);
> + struct i2c_mux_core *muxc;
> + int num, force;
> + u8 nchans;
> + struct mlxcpld_mux *data;
> + int err;
> +
> + if (!i2c_check_functionality(adap, I2C_FUNC_SMBUS_BYTE))
> + return -ENODEV;
> +
> + switch (id->driver_data) {
> + case mlxcpld_mux_tor:
> + case mlxcpld_mux_mgmt:
> + case mlxcpld_mux_mgmt_ext:
> + case mlxcpld_mux_module:
> + nchans = muxes[id->driver_data].nchans;
> + break;
> + default:
> + return -EINVAL;
> + }
> +
> + muxc = i2c_mux_alloc(adap, &client->dev, nchans, sizeof(*data), 0,
> + mlxcpld_mux_select_chan, mlxcpld_mux_deselect);
> + if (!muxc)
> + return -ENOMEM;
> +
> + data = i2c_mux_priv(muxc);
> + i2c_set_clientdata(client, muxc);
> + data->client = client;
> + data->type = id->driver_data;
> + data->last_chan = 0; /* force the first selection */
> +
> + /* Only in mlxcpld_mux_tor first_channel can be different.
> + * In other mlxcpld_mux types channel numbering begin from 1
> + * Now create an adapter for each channel
> + */
> + for (num = 0; num < muxes[data->type].nchans; num++) {
> + force = 0; /* dynamic adap number */
> + if (pdata) {
Here, you check if you have pdata, but in other places you assume
pdata is there. Maybe the probe should error out if there is no pdata?
> + if (num < pdata->num_adaps)
> + force = pdata->adap_ids[num];
> + else
> + /* discard unconfigured channels */
> + break;
> + }
> +
> + err = i2c_mux_add_adapter(muxc, force, num, 0);
> + if (err) {
> + dev_err(&client->dev, "failed to register multiplexed adapter %d as bus %d\n",
> + num, force);
> + goto virt_reg_failed;
> + }
> + }
> +
> + return 0;
> +
> +virt_reg_failed:
> + i2c_mux_del_adapters(muxc);
> + return err;
> +}
> +
> +static int mlxcpld_mux_remove(struct i2c_client *client)
> +{
> + struct i2c_mux_core *muxc = i2c_get_clientdata(client);
> +
> + i2c_mux_del_adapters(muxc);
> + return 0;
> +}
> +
> +static struct i2c_driver mlxcpld_mux_driver = {
> + .driver = {
> + .name = "mlxcpld-mux",
> + },
> + .probe = mlxcpld_mux_probe,
> + .remove = mlxcpld_mux_remove,
> + .id_table = mlxcpld_mux_id,
> +};
> +
> +module_i2c_driver(mlxcpld_mux_driver);
> +
> +MODULE_AUTHOR("Michael Shych (michaels@mellanox.com)");
> +MODULE_DESCRIPTION("Mellanox I2C-CPLD-MUX driver");
> +MODULE_LICENSE("GPL v2");
> +MODULE_ALIAS("platform:i2c-mux-mlxcpld");
> diff --git a/include/linux/i2c/mlxcpld.h b/include/linux/i2c/mlxcpld.h
> new file mode 100644
> index 0000000..ceb31da
> --- /dev/null
> +++ b/include/linux/i2c/mlxcpld.h
> @@ -0,0 +1,57 @@
> +/*
> + * mlxcpld.h - Mellanox I2C multiplexer support in CPLD
> + *
> + * Copyright (c) 2016 Mellanox Technologies. All rights reserved.
> + * Copyright (c) 2016 Michael Shych <michaels@mellanox.com>
> + *
> + * Redistribution and use in source and binary forms, with or without
> + * modification, are permitted provided that the following conditions are met:
> + *
> + * 1. Redistributions of source code must retain the above copyright
> + * notice, this list of conditions and the following disclaimer.
> + * 2. Redistributions in binary form must reproduce the above copyright
> + * notice, this list of conditions and the following disclaimer in the
> + * documentation and/or other materials provided with the distribution.
> + * 3. Neither the names of the copyright holders nor the names of its
> + * contributors may be used to endorse or promote products derived from
> + * this software without specific prior written permission.
> + *
> + * Alternatively, this software may be distributed under the terms of the
> + * GNU General Public License ("GPL") version 2 as published by the Free
> + * Software Foundation.
> + *
> + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
> + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
> + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
> + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
> + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
> + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
> + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
> + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
> + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
> + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
> + * POSSIBILITY OF SUCH DAMAGE.
> + */
> +
> +#ifndef _LINUX_I2C_MLXCPLD_H
> +#define _LINUX_I2C_MLXCPLD_H
> +
> +/* Platform data for the CPLD I2C multiplexers */
> +
> +/* mlxcpld_mux_platform_data - per mux data, used with i2c_register_board_info
> + * @adap_ids - adapter array
This description is a bit misleading, it's an adapter *id* array. And there
is a special value (0) for dynamic numbering.
> + * @num_adaps - number of adapters
> + * @sel_reg_addr - mux select register offset in CPLD space
> + * @first_channel - first channel to start virtual busses vector
> + * @addr - address of mux device - set to mux select register offset on LPC
> + * connected CPLDs or to I2C address on I2C conncted CPLDs
> + */
> +struct mlxcpld_mux_platform_data {
> + int *adap_ids;
> + int num_adaps;
> + int sel_reg_addr;
> + int first_channel;
> + int addr;
> +};
> +
> +#endif /* _LINUX_I2C_MLXCPLD_H */
>
^ permalink raw reply
* Re: [tpmdd-devel] [PATCH] Documentation: tpm: Adds the TPM device tree node documentation
From: Rob Herring @ 2016-09-02 17:57 UTC (permalink / raw)
To: Jason Gunthorpe
Cc: Nayna Jain, Mark Rutland, devicetree@vger.kernel.org, Pawel Moll,
Ian Campbell, wsa@the-dreams.de, tpmdd-devel, gcwilson,
linux-i2c@vger.kernel.org, Kumar Gala
In-Reply-To: <20160902170613.GA5024@obsidianresearch.com>
On Fri, Sep 2, 2016 at 12:06 PM, Jason Gunthorpe
<jgunthorpe@obsidianresearch.com> wrote:
> On Fri, Sep 02, 2016 at 09:51:21AM -0500, Rob Herring wrote:
>> > +- linux,sml-base : base address of the Event Log. It is a physical address.
>> > + sml stands for shared memory log.
>>
>> How is it a physical address on an i2c device? Why 2 cells (which needs
>> to be documented also)?
>
> To be clear, as I understand it, this mechanism is a hand off from the
> boot firmware to Linux.
>
> The boot firmware talks i2c to the device, does some stuff, writes it
> to memory and then linux reads that stuff. I agree it seems crazy to
> include a random physical address like that.
I'd put that in reserved-memory then if designing this from scratch...
Must not be completely random as somehow the kernel doesn't use that memory.
> The linux,sml-* names appear to have been used by IBM for a long time
> on their enterprise PPC platforms (see drivers/char/tpm/tpm_of.c), so
> I've expected we have to keep them?
Yes. I wasn't aware of that.
> I asked Nayna to document this stuff IBM is doing so the rest of us
> in TPM land can have a hope of maintaining it...
>
> Jason
> --
> To unsubscribe from this list: send the line "unsubscribe devicetree" 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] Documentation: tpm: Adds the TPM device tree node documentation
From: Jason Gunthorpe @ 2016-09-02 17:06 UTC (permalink / raw)
To: Rob Herring
Cc: mark.rutland-5wv7dgnIgG8, devicetree-u79uwXL29TY76Z2rM5mHXA,
ijc+devicetree-KcIKpvwj1kUDXYZnReoRVg, pawel.moll-5wv7dgnIgG8,
wsa-z923LK4zBo2bacvFa/9K2g,
tpmdd-devel-5NWGOfrQmneRv+LV9MX5uipxlwaOVQ5f,
gcwilson-r/Jw6+rmf7HQT0dZR+AlfA, linux-i2c-u79uwXL29TY76Z2rM5mHXA,
galak-sgV2jX0FEOL9JmXXK+q4OQ
In-Reply-To: <20160902145121.GA9636@rob-hp-laptop>
On Fri, Sep 02, 2016 at 09:51:21AM -0500, Rob Herring wrote:
> > +- linux,sml-base : base address of the Event Log. It is a physical address.
> > + sml stands for shared memory log.
>
> How is it a physical address on an i2c device? Why 2 cells (which needs
> to be documented also)?
To be clear, as I understand it, this mechanism is a hand off from the
boot firmware to Linux.
The boot firmware talks i2c to the device, does some stuff, writes it
to memory and then linux reads that stuff. I agree it seems crazy to
include a random physical address like that.
The linux,sml-* names appear to have been used by IBM for a long time
on their enterprise PPC platforms (see drivers/char/tpm/tpm_of.c), so
I've expected we have to keep them?
I asked Nayna to document this stuff IBM is doing so the rest of us
in TPM land can have a hope of maintaining it...
Jason
------------------------------------------------------------------------------
^ permalink raw reply
* i2c: imx: add slave support. v2 status
From: Baxter, Jim @ 2016-09-02 17:01 UTC (permalink / raw)
To: linux-i2c, syrchin
Cc: dbaranov, Wolfram Sang, Peter Rosin, linux-kernel@vger.kernel.org,
jiwang, Zapolskiy, Vladimir
Hi Maxim,
On 2016-03-04 11:06:10 in the thread "Re: [PATCH] i2c: imx: add slave support. v2"
referenced here: https://patchwork.ozlabs.org/patch/573353/ you said:
> Hi Wolfram,
> I'm now working on creating new driver version. I think I'll be able to
> sent it soon.
Do you still plan to release a driver update for an i2c imx driver slave support?
Best regards,
Jim Baxter
^ permalink raw reply
* Re: [tpmdd-devel] [PATCH] Documentation: tpm: Adds the TPM device tree node documentation
From: Jarkko Sakkinen @ 2016-09-02 16:00 UTC (permalink / raw)
To: Rob Herring
Cc: Nayna Jain, tpmdd-devel, devicetree, mark.rutland, pawel.moll,
ijc+devicetree, wsa, gcwilson, linux-i2c, galak
In-Reply-To: <20160902145238.GB9636@rob-hp-laptop>
On Fri, Sep 02, 2016 at 09:52:38AM -0500, Rob Herring wrote:
> On Tue, Aug 30, 2016 at 09:36:31AM +0300, Jarkko Sakkinen wrote:
> > On Tue, Aug 30, 2016 at 12:44:37AM -0400, Nayna Jain wrote:
> > > This is documenting device tree binding for
> > > I2C based TPM, similar concept which being used
> > > for virtual TPM on POWER7 and POWER8 systems running PowerVM.
> > >
> > > Signed-off-by: Nayna Jain <nayna@linux.vnet.ibm.com>
> > > ---
> > > Documentation/devicetree/bindings/i2c/i2c-tpm.txt | 29 +++++++++++++++++++++++
> > > 1 file changed, 29 insertions(+)
> > > create mode 100644 Documentation/devicetree/bindings/i2c/i2c-tpm.txt
> > >
> > > diff --git a/Documentation/devicetree/bindings/i2c/i2c-tpm.txt b/Documentation/devicetree/bindings/i2c/i2c-tpm.txt
> > > new file mode 100644
> > > index 0000000..8fdee14
> > > --- /dev/null
> > > +++ b/Documentation/devicetree/bindings/i2c/i2c-tpm.txt
> > > @@ -0,0 +1,29 @@
> > > +Device Tree Bindings for I2C based Trusted Platform Module(TPM)
> > > +---------------------------------------------------------------
> > > +
> > > +This node describes a TPM device connected to Processor on i2c bus.
> > > +
> > > +Required properties:
> > > +
> > > +- compatible : 'manufacturer,model'
> > > +- label : represents device type
> > > +- linux,sml-base : base address of the Event Log. It is a physical address.
> > > + sml stands for shared memory log.
> > > +- linux,sml-size : size of the memory allocated for the Event Log.
> > > +
> > > +Optional properties:
> > > +
> > > +- status: indicates whether the device is enabled or disabled. "okay" for
> > > + enabled and "disabled" for disabled.
> > > +
> > > +Example
> > > +-------
> > > +
> > > +tpm@57 {
> > > + reg = <0x57>;
> > > + label = "tpm";
> > > + compatible = "nuvoton,npct650", "nuvoton,npct601";
> > > + linux,sml-base = <0x7f 0xfd450000>;
> > > + linux,sml-size = <0x10000>;
> > > + status = "okay";
> > > +};
> >
> > I would rather name the fields event-log-base and event-log-size. They
> > would be much more readable and obvious names.
> >
> > Also, enabled should be "enabled", not "okay".
>
> No, okay is correct. But as I mentioned, don't document it here.
We'll stick to sml-base and sml-size because the existing code binds
already to those names.
/Jakrko
^ permalink raw reply
* Re: [PATCH] Documentation: tpm: Adds the TPM device tree node documentation
From: Rob Herring @ 2016-09-02 14:52 UTC (permalink / raw)
To: Jarkko Sakkinen
Cc: mark.rutland-5wv7dgnIgG8, devicetree-u79uwXL29TY76Z2rM5mHXA,
pawel.moll-5wv7dgnIgG8, ijc+devicetree-KcIKpvwj1kUDXYZnReoRVg,
wsa-z923LK4zBo2bacvFa/9K2g,
tpmdd-devel-5NWGOfrQmneRv+LV9MX5uipxlwaOVQ5f,
gcwilson-r/Jw6+rmf7HQT0dZR+AlfA, linux-i2c-u79uwXL29TY76Z2rM5mHXA,
galak-sgV2jX0FEOL9JmXXK+q4OQ
In-Reply-To: <20160830063631.GA5336-ral2JQCrhuEAvxtiuMwx3w@public.gmane.org>
On Tue, Aug 30, 2016 at 09:36:31AM +0300, Jarkko Sakkinen wrote:
> On Tue, Aug 30, 2016 at 12:44:37AM -0400, Nayna Jain wrote:
> > This is documenting device tree binding for
> > I2C based TPM, similar concept which being used
> > for virtual TPM on POWER7 and POWER8 systems running PowerVM.
> >
> > Signed-off-by: Nayna Jain <nayna-23VcF4HTsmIX0ybBhKVfKdBPR1lH4CV8@public.gmane.org>
> > ---
> > Documentation/devicetree/bindings/i2c/i2c-tpm.txt | 29 +++++++++++++++++++++++
> > 1 file changed, 29 insertions(+)
> > create mode 100644 Documentation/devicetree/bindings/i2c/i2c-tpm.txt
> >
> > diff --git a/Documentation/devicetree/bindings/i2c/i2c-tpm.txt b/Documentation/devicetree/bindings/i2c/i2c-tpm.txt
> > new file mode 100644
> > index 0000000..8fdee14
> > --- /dev/null
> > +++ b/Documentation/devicetree/bindings/i2c/i2c-tpm.txt
> > @@ -0,0 +1,29 @@
> > +Device Tree Bindings for I2C based Trusted Platform Module(TPM)
> > +---------------------------------------------------------------
> > +
> > +This node describes a TPM device connected to Processor on i2c bus.
> > +
> > +Required properties:
> > +
> > +- compatible : 'manufacturer,model'
> > +- label : represents device type
> > +- linux,sml-base : base address of the Event Log. It is a physical address.
> > + sml stands for shared memory log.
> > +- linux,sml-size : size of the memory allocated for the Event Log.
> > +
> > +Optional properties:
> > +
> > +- status: indicates whether the device is enabled or disabled. "okay" for
> > + enabled and "disabled" for disabled.
> > +
> > +Example
> > +-------
> > +
> > +tpm@57 {
> > + reg = <0x57>;
> > + label = "tpm";
> > + compatible = "nuvoton,npct650", "nuvoton,npct601";
> > + linux,sml-base = <0x7f 0xfd450000>;
> > + linux,sml-size = <0x10000>;
> > + status = "okay";
> > +};
>
> I would rather name the fields event-log-base and event-log-size. They
> would be much more readable and obvious names.
>
> Also, enabled should be "enabled", not "okay".
No, okay is correct. But as I mentioned, don't document it here.
Rob
------------------------------------------------------------------------------
^ permalink raw reply
* Re: [PATCH] Documentation: tpm: Adds the TPM device tree node documentation
From: Rob Herring @ 2016-09-02 14:51 UTC (permalink / raw)
To: Nayna Jain
Cc: tpmdd-devel, devicetree, wsa, pawel.moll, mark.rutland,
ijc+devicetree, galak, linux-i2c, hellerda, ltcgcw, gcwilson
In-Reply-To: <1472532277-21933-1-git-send-email-nayna@linux.vnet.ibm.com>
On Tue, Aug 30, 2016 at 12:44:37AM -0400, Nayna Jain wrote:
> This is documenting device tree binding for
> I2C based TPM, similar concept which being used
> for virtual TPM on POWER7 and POWER8 systems running PowerVM.
>
> Signed-off-by: Nayna Jain <nayna@linux.vnet.ibm.com>
> ---
> Documentation/devicetree/bindings/i2c/i2c-tpm.txt | 29 +++++++++++++++++++++++
> 1 file changed, 29 insertions(+)
> create mode 100644 Documentation/devicetree/bindings/i2c/i2c-tpm.txt
>
> diff --git a/Documentation/devicetree/bindings/i2c/i2c-tpm.txt b/Documentation/devicetree/bindings/i2c/i2c-tpm.txt
> new file mode 100644
> index 0000000..8fdee14
> --- /dev/null
> +++ b/Documentation/devicetree/bindings/i2c/i2c-tpm.txt
> @@ -0,0 +1,29 @@
> +Device Tree Bindings for I2C based Trusted Platform Module(TPM)
> +---------------------------------------------------------------
> +
> +This node describes a TPM device connected to Processor on i2c bus.
> +
> +Required properties:
> +
> +- compatible : 'manufacturer,model'
Needs specific compatible strings like your example has.
> +- label : represents device type
Why do you need this? label is human readable things like connectors on
boards.
> +- linux,sml-base : base address of the Event Log. It is a physical address.
> + sml stands for shared memory log.
How is it a physical address on an i2c device? Why 2 cells (which needs
to be documented also)?
Just 'log' would be more descriptive than sml.
> +- linux,sml-size : size of the memory allocated for the Event Log.
> +
> +Optional properties:
> +
> +- status: indicates whether the device is enabled or disabled. "okay" for
> + enabled and "disabled" for disabled.
status is always valid, so you don't need to document it.
^ permalink raw reply
* Re: [PATCH] i2c-eg20t: fix race between i2c init and interrupt enable
From: Yadi @ 2016-09-02 10:05 UTC (permalink / raw)
To: jdelvare, wsa; +Cc: linux-i2c
In-Reply-To: <1472439415-4024-1-git-send-email-yadi.hu@windriver.com>
Hi,guys
it may more make sense to add a check point on interrupt handler in case
field 'pch_base_address' has been assigned a effective value when an
interrupt arrives.
So something like:
diff --git a/drivers/i2c/busses/i2c-eg20t.c b/drivers/i2c/busses/i2c-eg20t.c
index 137125b..4ac8a49 100644
--- a/drivers/i2c/busses/i2c-eg20t.c
+++ b/drivers/i2c/busses/i2c-eg20t.c
@@ -152,6 +152,7 @@ struct i2c_algo_pch_data {
int pch_buff_mode_en;
u32 pch_event_flag;
bool pch_i2c_xfer_in_progress;
+ bool initflag;
};
/**
@@ -635,6 +636,8 @@ static irqreturn_t pch_i2c_handler(int irq, void *pData)
u32 mode;
for (i = 0, flag = 0; i < adap_info->ch_num; i++) {
+ if (!adap_info->pch_data[i].initflag)
+ continue;
p = adap_info->pch_data[i].pch_base_address;
mode = ioread32(p + PCH_I2CMOD);
mode &= BUFFER_MODE | EEPROM_SR_MODE;
@@ -783,6 +786,7 @@ static int pch_i2c_probe(struct pci_dev *pdev,
for (i = 0; i < adap_info->ch_num; i++) {
pch_adap = &adap_info->pch_data[i].pch_adapter;
adap_info->pch_i2c_suspended = false;
+ adap_info->pch_data[i].initflag = false;
adap_info->pch_data[i].p_adapter_info = adap_info;
@@ -806,6 +810,7 @@ static int pch_i2c_probe(struct pci_dev *pdev,
pch_pci_err(pdev, "i2c_add_adapter[ch:%d]
FAILED\n", i);
goto err_add_adapter;
}
+ adap_info->pch_data[i].initflag = ture;
}
Compared with last one, which one is better?
Yadi
On 2016年08月29日 10:56, Yadi Hu wrote:
> From: "Yadi.hu" <yadi.hu@windriver.com>
>
> the driver executes request_irq() function before the base address
> of i2c registers is remapped in kernel space. If i2c controller
> shares an interrupt line with other devices,it is possible that
> an interrupt arrives immediately after request_irq() is called.
> Since the interrupt handler pch_i2c_handler() is active, it will
> read its own register to determine if this interrupt was from
> its own device.
> At this moment, base address of i2c registers is not remapped
> in kernel space yet,so the INT handler access a unknown address
> and a error occurs.
>
> Bad IO access at port 0x18 (return inl(port))
> Call Trace:
> [<c102c733>] warn_slowpath_common+0x73/0xa0
> [<c13109f5>] ? bad_io_access+0x45/0x50
> [<c13109f5>] ? bad_io_access+0x45/0x50
> [<c102c804>] warn_slowpath_fmt+0x34/0x40
> [<c13109f5>] bad_io_access+0x45/0x50
> [<c1310b62>] ioread32+0x22/0x40
> [<c14c60db>] pch_i2c_handler+0x3b/0x120
> [<c1092f34>] handle_irq_event_percpu+0x64/0x330
> [<c109323b>] handle_irq_event+0x3b/0x60
> [<c1095b50>] ? unmask_irq+0x30/0x30
> [<c1095ba0>] handle_fasteoi_irq+0x50/0xe0
> <IRQ> [<c16e7e78>] ? do_IRQ+0x48/0xc0
> [<c16e7f6f>] ? smp_apic_timer_interrupt+0x7f/0x17a
> [<c16e7da9>] ? common_interrupt+0x29/0x30
> [<c1008ebb>] ? mwait_idle+0x8b/0x2c0
> [<c1009e8e>] ? cpu_idle+0x9e/0xc0
> [<c16be408>] ? rest_init+0x6c/0x74
> [<c19f770a>] ? start_kernel+0x311/0x318
> [<c19f7231>] ? repair_env_string+0x51/0x51
> [<c19f7078>] ? i386_start_kernel+0x78/0x7d
> ---[ end trace eb3a1028f468a140 ]---
> i2c_eg20t 0000:05:0c.2: pch_i2c_handler :I2C-3 mode(0) is not supported
>
> Signed-off-by: Yadi.hu <yadi.hu@windriver.com>
> ---
> drivers/i2c/busses/i2c-eg20t.c | 18 +++++++++---------
> 1 file changed, 9 insertions(+), 9 deletions(-)
>
> diff --git a/drivers/i2c/busses/i2c-eg20t.c b/drivers/i2c/busses/i2c-eg20t.c
> index 137125b..48483a5 100644
> --- a/drivers/i2c/busses/i2c-eg20t.c
> +++ b/drivers/i2c/busses/i2c-eg20t.c
> @@ -773,13 +773,6 @@ static int pch_i2c_probe(struct pci_dev *pdev,
> /* Set the number of I2C channel instance */
> adap_info->ch_num = id->driver_data;
>
> - ret = request_irq(pdev->irq, pch_i2c_handler, IRQF_SHARED,
> - KBUILD_MODNAME, adap_info);
> - if (ret) {
> - pch_pci_err(pdev, "request_irq FAILED\n");
> - goto err_request_irq;
> - }
> -
> for (i = 0; i < adap_info->ch_num; i++) {
> pch_adap = &adap_info->pch_data[i].pch_adapter;
> adap_info->pch_i2c_suspended = false;
> @@ -808,16 +801,23 @@ static int pch_i2c_probe(struct pci_dev *pdev,
> }
> }
>
> + ret = request_irq(pdev->irq, pch_i2c_handler, IRQF_SHARED,
> + KBUILD_MODNAME, adap_info);
> + if (ret) {
> + pch_pci_err(pdev, "request_irq FAILED\n");
> + goto err_request_irq;
> + }
> +
> pci_set_drvdata(pdev, adap_info);
> pch_pci_dbg(pdev, "returns %d.\n", ret);
> return 0;
>
> +err_request_irq:
> + pci_iounmap(pdev, base_addr);
> err_add_adapter:
> for (j = 0; j < i; j++)
> i2c_del_adapter(&adap_info->pch_data[j].pch_adapter);
> free_irq(pdev->irq, adap_info);
> -err_request_irq:
> - pci_iounmap(pdev, base_addr);
> err_pci_iomap:
> pci_release_regions(pdev);
> err_pci_req:
^ permalink raw reply related
page: next (older) | prev (newer) | latest
- recent:[subjects (threaded)|topics (new)|topics (active)]
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox