RE: [PATCH 1/2] platform/chrome: cros_ec_typec: Skip port partner check in configure_mux()

2021-02-05 Thread Mani, Rajmohan
Hi Prashant,

> -Original Message-
> From: Prashant Malani 
> Sent: Friday, February 05, 2021 12:07 PM
> To: Mani, Rajmohan 
> Cc: Benson Leung ; Enric Balletbo i Serra
> ; Guenter Roeck ;
> Linux Kernel Mailing List ; Heikki Krogerus
> 
> Subject: Re: [PATCH 1/2] platform/chrome: cros_ec_typec: Skip port partner
> check in configure_mux()
> 
> Hi Raj,
> 
> On Fri, Feb 5, 2021 at 11:52 AM Rajmohan Mani
>  wrote:
> >
> > For certain needs like updating the USB4 retimer firmware when no
> > device are connected, the Type-C ports require mux configuration, to
> > be able to communicate with the retimer. So removed the above check to
> > allow for mux configuration of Type-C ports, to enable retimer
> > communication.
> >
> > Signed-off-by: Rajmohan Mani 
> Reviewed-by: Prashant Malani 
> 

Thanks for the review of the patch series.

> > ---
> >  drivers/platform/chrome/cros_ec_typec.c | 3 ---
> >  1 file changed, 3 deletions(-)
> >
> > diff --git a/drivers/platform/chrome/cros_ec_typec.c
> > b/drivers/platform/chrome/cros_ec_typec.c
> > index e724a5eaef1c..3d8ff3f8a514 100644
> > --- a/drivers/platform/chrome/cros_ec_typec.c
> > +++ b/drivers/platform/chrome/cros_ec_typec.c
> > @@ -536,9 +536,6 @@ static int cros_typec_configure_mux(struct
> cros_typec_data *typec, int port_num,
> > enum typec_orientation orientation;
> > int ret;
> >
> > -   if (!port->partner)
> > -   return 0;
> > -
> > if (mux_flags & USB_PD_MUX_POLARITY_INVERTED)
> > orientation = TYPEC_ORIENTATION_REVERSE;
> > else
> > --
> > 2.30.0
> >


RE: [PATCH 0/2] Add support for Type-C mux events without port partners

2021-02-05 Thread Mani, Rajmohan
Hi Benson,

> Subject: Re: [PATCH 0/2] Add support for Type-C mux events without port
> partners
> 
> Hi Rajmohan,
> 
> On Fri, 5 Feb 2021 11:51:11 -0800, Rajmohan Mani wrote:
> > There are cases, where support for Type-C mux events is needed, that
> > does not have port partners.
> > Enabling communication to a retimer connected to an USB4 port, when no
> > devices are attached, is a case that requires support for handling
> > Type-C mux events without port partners.
> >
> > The following patches[1] are needed on top of the mainline kernel to
> > be able to verify these patches.
> >
> > [...]
> 
> Applied, thanks!
> 

Thanks for the quick review / follow up.

...


[PATCH 1/2] platform/chrome: cros_ec_typec: Skip port partner check in configure_mux()

2021-02-05 Thread Rajmohan Mani
For certain needs like updating the USB4 retimer firmware when no
device are connected, the Type-C ports require mux configuration,
to be able to communicate with the retimer. So removed the above
check to allow for mux configuration of Type-C ports, to enable
retimer communication.

Signed-off-by: Rajmohan Mani 
---
 drivers/platform/chrome/cros_ec_typec.c | 3 ---
 1 file changed, 3 deletions(-)

diff --git a/drivers/platform/chrome/cros_ec_typec.c 
b/drivers/platform/chrome/cros_ec_typec.c
index e724a5eaef1c..3d8ff3f8a514 100644
--- a/drivers/platform/chrome/cros_ec_typec.c
+++ b/drivers/platform/chrome/cros_ec_typec.c
@@ -536,9 +536,6 @@ static int cros_typec_configure_mux(struct cros_typec_data 
*typec, int port_num,
enum typec_orientation orientation;
int ret;
 
-   if (!port->partner)
-   return 0;
-
if (mux_flags & USB_PD_MUX_POLARITY_INVERTED)
orientation = TYPEC_ORIENTATION_REVERSE;
else
-- 
2.30.0



[PATCH 2/2] platform/chrome: cros_ec_types: Support disconnect events without partners

2021-02-05 Thread Rajmohan Mani
There are certain scenarios, where a disconnect event might
occur on a Type-C port with no port partners. This is required
to enable communication to Burnside Bridge USB4 retimers.

Signed-off-by: Rajmohan Mani 
---
 drivers/platform/chrome/cros_ec_typec.c | 26 ++---
 1 file changed, 19 insertions(+), 7 deletions(-)

diff --git a/drivers/platform/chrome/cros_ec_typec.c 
b/drivers/platform/chrome/cros_ec_typec.c
index 3d8ff3f8a514..d89fe51b74b1 100644
--- a/drivers/platform/chrome/cros_ec_typec.c
+++ b/drivers/platform/chrome/cros_ec_typec.c
@@ -203,20 +203,26 @@ static void cros_typec_unregister_altmodes(struct 
cros_typec_data *typec, int po
}
 }
 
-static void cros_typec_remove_partner(struct cros_typec_data *typec,
-int port_num)
+static int cros_typec_usb_disconnect_state(struct cros_typec_port *port)
 {
-   struct cros_typec_port *port = typec->ports[port_num];
-
-   cros_typec_unregister_altmodes(typec, port_num, true);
-
port->state.alt = NULL;
port->state.mode = TYPEC_STATE_USB;
port->state.data = NULL;
 
usb_role_switch_set_role(port->role_sw, USB_ROLE_NONE);
typec_switch_set(port->ori_sw, TYPEC_ORIENTATION_NONE);
-   typec_mux_set(port->mux, >state);
+
+   return typec_mux_set(port->mux, >state);
+}
+
+static void cros_typec_remove_partner(struct cros_typec_data *typec,
+ int port_num)
+{
+   struct cros_typec_port *port = typec->ports[port_num];
+
+   cros_typec_unregister_altmodes(typec, port_num, true);
+
+   cros_typec_usb_disconnect_state(port);
 
typec_unregister_partner(port->partner);
port->partner = NULL;
@@ -536,6 +542,11 @@ static int cros_typec_configure_mux(struct cros_typec_data 
*typec, int port_num,
enum typec_orientation orientation;
int ret;
 
+   if (mux_flags == USB_PD_MUX_NONE) {
+   ret = cros_typec_usb_disconnect_state(port);
+   goto mux_ack;
+   }
+
if (mux_flags & USB_PD_MUX_POLARITY_INVERTED)
orientation = TYPEC_ORIENTATION_REVERSE;
else
@@ -569,6 +580,7 @@ static int cros_typec_configure_mux(struct cros_typec_data 
*typec, int port_num,
mux_flags);
}
 
+mux_ack:
if (!typec->needs_mux_ack)
return ret;
 
-- 
2.30.0



[PATCH 0/2] Add support for Type-C mux events without port partners

2021-02-05 Thread Rajmohan Mani
There are cases, where support for Type-C mux events is needed, that
does not have port partners.
Enabling communication to a retimer connected to an USB4 port, when
no devices are attached, is a case that requires support for handling
Type-C mux events without port partners.

The following patches[1] are needed on top of the mainline kernel to be
able to verify these patches.

commit 8553a979fcd0 ("platform/chrome: cros_ec_typec: Send mux
  configuration acknowledgment to EC")
commit ba8ce515454e ("platform/chrome: cros_ec_typec: Parameterize
  cros_typec_cmds_supported()")
commit 156309096542 ("platform/chrome: cros_ec_typec: Register plug
  altmodes")
commit f4edab68e101 ("platform/chrome: cros_ec_typec: Register SOP'
  cable plug")
commit 599229763911 ("platform/chrome: cros_ec_typec: Set partner
  num_altmodes")
commit 72d6e32bd85b ("platform/chrome: cros_ec_typec: Store cable plug
  type")
commit 8b46a212ad11 ("platform/chrome: cros_ec_typec: Register cable")
commit c097f229b71e ("platform/chrome: cros_ec_typec: Rename discovery
  struct")
commit 8fab2755191f ("platform/chrome: cros_ec_typec: Factor out PD
  identity parsing")
commit a906f45d1480 ("platform/chrome: cros_ec_typec: Make disc_done
  flag partner-only")

[1]: https://git.kernel.org/pub/scm/linux/kernel/git/chrome-platform/
linux.git/log/?h=cros-ec-typec-for-5.12

Rajmohan Mani (2):
  platform/chrome: cros_ec_typec: Skip port partner check in
configure_mux()
  platform/chrome: cros_ec_types: Support disconnect events without
partners

 drivers/platform/chrome/cros_ec_typec.c | 27 -
 1 file changed, 18 insertions(+), 9 deletions(-)

-- 
2.30.0



RE: [PATCH v2 1/3] platform/x86: Add Intel Input Output Manager (IOM) driver

2020-08-31 Thread Mani, Rajmohan
Hi Greg,

> Subject: Re: [PATCH v2 1/3] platform/x86: Add Intel Input Output Manager
> (IOM) driver
> 
> On Fri, Aug 28, 2020 at 03:20:22PM +, Mani, Rajmohan wrote:
> > Hi Greg,
> >
> > > Subject: Re: [PATCH v2 1/3] platform/x86: Add Intel Input Output
> > > Manager
> > > (IOM) driver
> > >
> > > Hi Greg,
> > >
> > > On Fri, Aug 28, 2020 at 09:43:59AM +0200, Greg Kroah-Hartman wrote:
> > > > I still find this crazy that a whole separate driver is created
> > > > just to read a single 32bit value.
> > > >
> > > > Why not put this logic in the driver that wants to read that value?
> > > > That would be much simpler, smaller, and more obvious.
> > >
> > > That would mean that we start maintaining something like DMI quirk
> > > table in those drivers. Unfortunately the IOM device is not available on
> every platform.
> > > Also, even on platforms that do have it, there is no guarantee that
> > > the device is always going to be mapped to the same address.
> > >
> > > Nevertheless, I was originally hoping that we could hide the
> > > handling of IOM somehow in ACPI without the need for an actual
> > > device object, but it now turns out that the other features of the
> > > IOM chip have created interest. At least our i915 guys probable have
> > > some use for it (I don't know exactly what they are planning to use it 
> > > for).
> > >
> > > So the fact that we may later need the device for something else, on
> > > top of the clumsiness and most importantly risks involved with using
> > > ACPI to take care of extra tasks (ASL tends to have bugs - bugs that
> > > may never ever get fixed), I think the IOM device object, and the
> > > driver that binds to it, do have a valid reason for existing.
> > >
> >
> > Intel PMC USB mux device is part of the PCH, while IOM is part of the SoC.
> 
> I have no idea what a "PCH" is, what "IOM" is, and how any of this relates to 
> a
> "SoC" :)
> 

I was just meaning to say IOM (Intel Output Manager) is a separate device, that
is not part of PCH (Platform Controller Hub) like PMC (Power Management 
Controller).

For the sake of completeness

PCH - Platform Controller Hub (usually that handles I/Os in Intel core 
platforms)
IOM - Input Output Manager (IOM) is part of the Tiger Lake SoC that handles 
Type-C
topology, configuration and PM functions of various Type-C devices connected
on the platform

> Don't impose arbritrary hardware "splits" to kernel code when the kernel has
> no such "partitioning" please.
> 

Ack.

> > This was another reason we had to have a separate ACPI device.
> 
> That sounds like a firmware issue you can solve in UEFI.
> 

Ack

> I think this is the most TLA-laden email I have ever written, and I used to 
> work
> at IBM :)

I thought it was only Intel where TLAs are abundantly used.

Thanks for the reviews and the direction on this topic.

> 
> greg k-h


RE: [PATCH v2 1/3] platform/x86: Add Intel Input Output Manager (IOM) driver

2020-08-28 Thread Mani, Rajmohan
> Subject: Re: [PATCH v2 1/3] platform/x86: Add Intel Input Output Manager
> (IOM) driver
> 
> On Fri, Aug 28, 2020 at 12:03:35PM +0200, Greg Kroah-Hartman wrote:
> > Handle the situation today, if, in the future, someone else
> > needs/wants this, _then_ work on splitting it out into separate
> > pieces.  Don't create additional complexity today, for no benefit
> > today.  It's already caused numerous review comments/complaints the way
> this is designed...
> 
> OK. We'll handle this in the mux driver for now.
> 

Ack. Will work with Heikki on this.

> 
> thanks,
> 
> --
> heikki


RE: [PATCH v2 1/3] platform/x86: Add Intel Input Output Manager (IOM) driver

2020-08-28 Thread Mani, Rajmohan
Hi Greg,

> Subject: Re: [PATCH v2 1/3] platform/x86: Add Intel Input Output Manager
> (IOM) driver
> 
> Hi Greg,
> 
> On Fri, Aug 28, 2020 at 09:43:59AM +0200, Greg Kroah-Hartman wrote:
> > I still find this crazy that a whole separate driver is created just
> > to read a single 32bit value.
> >
> > Why not put this logic in the driver that wants to read that value?
> > That would be much simpler, smaller, and more obvious.
> 
> That would mean that we start maintaining something like DMI quirk table in
> those drivers. Unfortunately the IOM device is not available on every 
> platform.
> Also, even on platforms that do have it, there is no guarantee that the 
> device is
> always going to be mapped to the same address.
> 
> Nevertheless, I was originally hoping that we could hide the handling of IOM
> somehow in ACPI without the need for an actual device object, but it now
> turns out that the other features of the IOM chip have created interest. At
> least our i915 guys probable have some use for it (I don't know exactly what
> they are planning to use it for).
> 
> So the fact that we may later need the device for something else, on top of 
> the
> clumsiness and most importantly risks involved with using ACPI to take care of
> extra tasks (ASL tends to have bugs - bugs that may never ever get fixed), I
> think the IOM device object, and the driver that binds to it, do have a valid
> reason for existing.
> 

Intel PMC USB mux device is part of the PCH, while IOM is part of the SoC.
This was another reason we had to have a separate ACPI device.

> 
> thanks,
> 
> --
> heikki


RE: [PATCH v2 1/3] platform/x86: Add Intel Input Output Manager (IOM) driver

2020-08-24 Thread Mani, Rajmohan
Hi Prashant,

...

> > > > +
> > > > +   reg = iom->regbar + IOM_PORT_STATUS_OFFSET + IOM_REG_LEN *
> > > port;
> > > > +
> > > > +   *status = ioread32(reg);
> > >
> > > Perhaps just inline reg within the parentheses?
> >
> > Kept this way to increase readability. Let me know if you feel
> > strongly towards inline reg.
> 
> I'd rather this be inlined, you save a couple lines from the variable 
> declaration,
> and IMO we're not gaining much in terms of readability by declaring this
> separately.
> 

Ack
(at least to me, it was more readable)

...

> >
> > > > +
> > > > +   return 0;
> > > > +}
> > > > +EXPORT_SYMBOL_GPL(intel_iom_port_status);
> > > > +
> > > > +static int intel_iom_probe(struct platform_device *pdev) {
> > > > +   void __iomem *addr;
> > > > +
> > > > +   /* only one IOM device is supported */
> > >
> > > Minor nit: s/only/Only
> >
> > And then I may need to end the comment with a period.
> > Let me know if you feel strongly.
> Yes, let's capitalize and add the period. Let's try to use the right 
> punctuation
> where possible.
> 

Ack
Will take care of this as part of v3.


RE: [PATCH v2 1/3] platform/x86: Add Intel Input Output Manager (IOM) driver

2020-08-24 Thread Mani, Rajmohan
Hi Prashant,

Thanks for the quick review.

> Subject: Re: [PATCH v2 1/3] platform/x86: Add Intel Input Output Manager
> (IOM) driver
> 
> Hi Rajmohan,
> 
> On Fri, Aug 21, 2020 at 09:05:06PM -0700, Rajmohan Mani wrote:
> > Input Output Manager (IOM) is part of the Tiger Lake SoC that
> > configures the Type-C Sub System (TCSS). IOM is a micro controller
> > that handles Type-C topology, configuration and PM functions of
> > various Type-C devices connected on the platform.
> >
> > This driver helps read relevant information such as Type-C port status
> > (whether a device is connected to a Type-C port or not) and the
> > activity type on the Type-C ports (such as USB, Display Port,
> > Thunderbolt), for consumption by other drivers.
> >
> > Currently intel_iom_port_status() API is exported by this driver, that
> > has information about the Type-C port status and port activity type.
> >
> > Signed-off-by: Rajmohan Mani 
> > ---
> 
> Perhaps include a version log of changes since v1?

Yes. It's there in the cover letter (patch v2 0/3).

> > diff --git a/drivers/platform/x86/intel_iom.c
> > b/drivers/platform/x86/intel_iom.c
> > new file mode 100644
> > index ..cda7716410c6
> > --- /dev/null
> > +++ b/drivers/platform/x86/intel_iom.c
> > +int intel_iom_port_status(u8 port, u32 *status) {
> > +   void __iomem *reg;
> > +
> > +   if (!iom || !iom->dev || !iom->regbar)
> 
> Do we need to check for !iom->dev and !iom->regbar?

It's a good practice to have sanity checks on pointer members dereferenced.

So I can lose the check on iom->dev, but prefer to keep the check on regbar.
Let me know if you feel strongly about losing the check for regbar as well.

> Is there a valid situation
> where iom != NULL but iom->dev and/or iom->regbar == NULL?
> Sounds like it shouldn't, but I may be missing something.
> 

I think I am being conservative here.

> > +   return -ENODEV;
> > +
> > +   if (!status || (port > IOM_MAX_PORTS - 1))
> 
> I think parentheses around "port > IOM_MAX_PORT - 1" aren't required.

Ack

> > +   return -EINVAL;
> > +
> > +   reg = iom->regbar + IOM_PORT_STATUS_OFFSET + IOM_REG_LEN *
> port;
> > +
> > +   *status = ioread32(reg);
> 
> Perhaps just inline reg within the parentheses?

Kept this way to increase readability. Let me know if you feel strongly towards
inline reg.

> > +
> > +   return 0;
> > +}
> > +EXPORT_SYMBOL_GPL(intel_iom_port_status);
> > +
> > +static int intel_iom_probe(struct platform_device *pdev) {
> > +   void __iomem *addr;
> > +
> > +   /* only one IOM device is supported */
> 
> Minor nit: s/only/Only

And then I may need to end the comment with a period.
Let me know if you feel strongly.

> > +   if (iom)
> > +   return -EBUSY;
> > +
> > +   iom = devm_kzalloc(>dev, sizeof(*iom), GFP_KERNEL);
> > +   if (!iom)
> > +   return -ENOMEM;
> > +
> > +   addr = devm_platform_ioremap_resource(pdev, 0);
> > +   if (IS_ERR(addr))
> > +   return PTR_ERR(addr);
> > +
> > +   iom->regbar = addr;
> > +   iom->dev = >dev;
> > +
> > +   return 0;
> > +}
> > +
> > +static const struct acpi_device_id intel_iom_acpi_ids[] = {
> > +   { "INTC1072" },
> > +   {}
> > +};
> > +MODULE_DEVICE_TABLE(acpi, intel_iom_acpi_ids);
> > +
> > +static struct platform_driver intel_iom_driver = {
> > +   .probe = intel_iom_probe,
> 
> nit: I generally see ".probe" listed below ".driver".

Ack

> > +   .driver = {
> > +   .name = "intel_iom",
> > +   .acpi_match_table = intel_iom_acpi_ids,
> > +   },
> > +};
> > +
> > +module_platform_driver_probe(intel_iom_driver, intel_iom_probe);
> > +
> > +MODULE_AUTHOR("Rajmohan Mani ");
> > +MODULE_DESCRIPTION("Intel IOM driver"); MODULE_LICENSE("GPL v2");
> > diff --git a/include/linux/platform_data/x86/intel_iom.h
> > b/include/linux/platform_data/x86/intel_iom.h
> > new file mode 100644
> > index ..e4c9a305e7a9
> > --- /dev/null
> > +++ b/include/linux/platform_data/x86/intel_iom.h
> > @@ -0,0 +1,49 @@
> > +/* SPDX-License-Identifier: GPL-2.0 */
> > +
> > +#ifndef _PLATFORM_DATA_X86_INTEL_IOM_H_ #define
> > +_PLATFORM_DATA_X86_INTEL_IOM_H_
> > +
> > +
> > +#define IOM_MAX_PORTS  4
> > +/* Register length in bytes */
> > +#define IOM_REG_LEN4
> 
> Do these two #define's need to be in the header, instead of directly in
> intel_iom.c ?
> 

Ack. These 2 can be moved to .c file.

> > +
> > +#ifdef CONFIG_ACPI
> > +
> > +int intel_iom_port_status(u8 port, u32 *status);
> > +
> > +#else
> > +
> > +int intel_iom_port_status(struct intel_iom *iom, u8 port, u32
> > +*status)
> 
> Should the function signature be the same as the #ifdef case?
> 

Thanks for catching this. I missed it.


[PATCH v2 1/3] platform/x86: Add Intel Input Output Manager (IOM) driver

2020-08-21 Thread Rajmohan Mani
Input Output Manager (IOM) is part of the Tiger Lake SoC that
configures the Type-C Sub System (TCSS). IOM is a micro controller
that handles Type-C topology, configuration and PM functions of
various Type-C devices connected on the platform.

This driver helps read relevant information such as Type-C port
status (whether a device is connected to a Type-C port or not) and
the activity type on the Type-C ports (such as USB, Display Port,
Thunderbolt), for consumption by other drivers.

Currently intel_iom_port_status() API is exported by this driver,
that has information about the Type-C port status and port activity
type.

Signed-off-by: Rajmohan Mani 
---
 drivers/platform/x86/Kconfig| 16 
 drivers/platform/x86/Makefile   |  1 +
 drivers/platform/x86/intel_iom.c| 95 +
 include/linux/platform_data/x86/intel_iom.h | 49 +++
 4 files changed, 161 insertions(+)
 create mode 100644 drivers/platform/x86/intel_iom.c
 create mode 100644 include/linux/platform_data/x86/intel_iom.h

diff --git a/drivers/platform/x86/Kconfig b/drivers/platform/x86/Kconfig
index 40219bba6801..f09b4b525ea5 100644
--- a/drivers/platform/x86/Kconfig
+++ b/drivers/platform/x86/Kconfig
@@ -837,6 +837,22 @@ config INTEL_INT0002_VGPIO
  To compile this driver as a module, choose M here: the module will
  be called intel_int0002_vgpio.
 
+config INTEL_IOM
+   tristate "Intel Input Output Manager (IOM) driver"
+   depends on ACPI && PCI
+   help
+ This driver helps read relevant information such as Type-C port
+ status (whether a device is connected to a Type-C port or not)
+ and the activity type on the Type-C ports (such as USB, Display
+ Port, Thunderbolt), for consumption by other drivers.
+
+ Currently intel_iom_port_status() API is exported by this driver,
+ that has information about the Type-C port status and port activity
+ type.
+
+ To compile this driver as a module, choose M here: the module will
+ be called intel_iom.
+
 config INTEL_MENLOW
tristate "Thermal Management driver for Intel menlow platform"
depends on ACPI_THERMAL
diff --git a/drivers/platform/x86/Makefile b/drivers/platform/x86/Makefile
index 5f823f7eff45..b44f706074c3 100644
--- a/drivers/platform/x86/Makefile
+++ b/drivers/platform/x86/Makefile
@@ -77,6 +77,7 @@ intel_cht_int33fe-objs:= 
intel_cht_int33fe_common.o \
   intel_cht_int33fe_microb.o
 obj-$(CONFIG_INTEL_HID_EVENT)  += intel-hid.o
 obj-$(CONFIG_INTEL_INT0002_VGPIO)  += intel_int0002_vgpio.o
+obj-$(CONFIG_INTEL_IOM)+= intel_iom.o
 obj-$(CONFIG_INTEL_MENLOW) += intel_menlow.o
 obj-$(CONFIG_INTEL_OAKTRAIL)   += intel_oaktrail.o
 obj-$(CONFIG_INTEL_VBTN)   += intel-vbtn.o
diff --git a/drivers/platform/x86/intel_iom.c b/drivers/platform/x86/intel_iom.c
new file mode 100644
index ..cda7716410c6
--- /dev/null
+++ b/drivers/platform/x86/intel_iom.c
@@ -0,0 +1,95 @@
+// SPDX-License-Identifier: GPL-2.0
+/*
+ * Intel Core SoC Input Output Manager (IOM) driver.
+ *
+ * This driver provides access to the Input Output Manager (IOM) (that
+ * is part of Tiger Lake SoC) registers that can be used to know about
+ * Type-C Sub System related information (such as Type-C port status,
+ * activity type on Type-C ports).
+ *
+ * Copyright (C) 2020, Intel Corporation
+ * Author: Rajmohan Mani 
+ */
+
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+
+#define IOM_PORT_STATUS_OFFSET 0x560
+
+struct intel_iom {
+   struct device *dev;
+   void __iomem *regbar;
+};
+
+static struct intel_iom *iom;
+
+/**
+ * intel_iom_port_status() - Get status bits for the Type-C port
+ * @port: Type-C port number
+ * @status: pointer to receive the status bits
+ *
+ * Returns 0 on success, error otherwise.
+ */
+int intel_iom_port_status(u8 port, u32 *status)
+{
+   void __iomem *reg;
+
+   if (!iom || !iom->dev || !iom->regbar)
+   return -ENODEV;
+
+   if (!status || (port > IOM_MAX_PORTS - 1))
+   return -EINVAL;
+
+   reg = iom->regbar + IOM_PORT_STATUS_OFFSET + IOM_REG_LEN * port;
+
+   *status = ioread32(reg);
+
+   return 0;
+}
+EXPORT_SYMBOL_GPL(intel_iom_port_status);
+
+static int intel_iom_probe(struct platform_device *pdev)
+{
+   void __iomem *addr;
+
+   /* only one IOM device is supported */
+   if (iom)
+   return -EBUSY;
+
+   iom = devm_kzalloc(>dev, sizeof(*iom), GFP_KERNEL);
+   if (!iom)
+   return -ENOMEM;
+
+   addr = devm_platform_ioremap_resource(pdev, 0);
+   if (IS_ERR(addr))
+   return PTR_ERR(addr);
+
+   iom->regbar = addr;
+   iom->dev = >dev;
+
+   return 0;
+}
+
+s

[PATCH v2 3/3] usb: typec: intel_pmc_mux: Support for device role (UFP)

2020-08-21 Thread Rajmohan Mani
From: Heikki Krogerus 

This adds support for device data role, and data role
swapping. The driver no longer relies on the cached role, as
it may not be valid (for example after bootup). Instead, the
role is always checked by readding the port status from IOM.

Note. After this, the orientation is always only cached, so
the driver does not support scenario where the role is set
before orientation. It means the typec drivers must always
set the orientation first before role.

Signed-off-by: Heikki Krogerus 
Signed-off-by: Rajmohan Mani 
---
 drivers/usb/typec/mux/intel_pmc_mux.c | 67 ++-
 1 file changed, 34 insertions(+), 33 deletions(-)

diff --git a/drivers/usb/typec/mux/intel_pmc_mux.c 
b/drivers/usb/typec/mux/intel_pmc_mux.c
index c758d6113c41..d4ee7132227b 100644
--- a/drivers/usb/typec/mux/intel_pmc_mux.c
+++ b/drivers/usb/typec/mux/intel_pmc_mux.c
@@ -191,9 +191,6 @@ pmc_usb_mux_dp(struct pmc_usb_port *port, struct 
typec_mux_state *state)
return pmc_usb_mux_dp_hpd(port, state->data);
}
 
-   if (data->status & DP_STATUS_IRQ_HPD)
-   return pmc_usb_mux_dp_hpd(port, state->data);
-
req.usage = PMC_USB_ALT_MODE;
req.usage |= port->usb3_port << PMC_USB_MSG_USB3_PORT_SHIFT;
req.mode_type = PMC_USB_MODE_TYPE_DP << PMC_USB_MODE_TYPE_SHIFT;
@@ -312,39 +309,52 @@ static int pmc_usb_mux_safe_state(struct pmc_usb_port 
*port)
return pmc_usb_command(port, , sizeof(msg));
 }
 
-static int pmc_usb_connect(struct pmc_usb_port *port)
+static int pmc_usb_disconnect(struct pmc_usb_port *port)
 {
+   struct typec_displayport_data data = { };
u8 msg[2];
 
-   if (port->iom_status & IOM_PORT_STATUS_CONNECTED)
+   if (!(port->iom_status & IOM_PORT_STATUS_CONNECTED))
return 0;
 
-   msg[0] = PMC_USB_CONNECT;
+   /* Clear DisplayPort HPD if it's still asserted. */
+   if (IOM_PORT_HPD_ASSERTED(port->iom_status))
+   pmc_usb_mux_dp_hpd(port, );
+
+   msg[0] = PMC_USB_DISCONNECT;
msg[0] |= port->usb3_port << PMC_USB_MSG_USB3_PORT_SHIFT;
 
msg[1] = port->usb2_port << PMC_USB_MSG_USB2_PORT_SHIFT;
-   msg[1] |= hsl_orientation(port) << PMC_USB_MSG_ORI_HSL_SHIFT;
-   msg[1] |= sbu_orientation(port) << PMC_USB_MSG_ORI_AUX_SHIFT;
 
return pmc_usb_command(port, msg, sizeof(msg));
 }
 
-static int pmc_usb_disconnect(struct pmc_usb_port *port)
+static int pmc_usb_connect(struct pmc_usb_port *port, enum usb_role role)
 {
-   struct typec_displayport_data data = { };
+   u8 ufp = role == USB_ROLE_DEVICE ? 1 : 0;
u8 msg[2];
+   int ret;
 
-   if (!(port->iom_status & IOM_PORT_STATUS_CONNECTED))
-   return 0;
+   if (port->orientation == TYPEC_ORIENTATION_NONE)
+   return -EINVAL;
 
-   /* Clear DisplayPort HPD if it's still asserted. */
-   if (IOM_PORT_HPD_ASSERTED(port->iom_status))
-   pmc_usb_mux_dp_hpd(port, );
+   if (port->iom_status & IOM_PORT_STATUS_CONNECTED) {
+   if (port->role == role || port->role == USB_ROLE_NONE)
+   return 0;
 
-   msg[0] = PMC_USB_DISCONNECT;
+   /* Role swap */
+   ret = pmc_usb_disconnect(port);
+   if (ret)
+   return ret;
+   }
+
+   msg[0] = PMC_USB_CONNECT;
msg[0] |= port->usb3_port << PMC_USB_MSG_USB3_PORT_SHIFT;
 
msg[1] = port->usb2_port << PMC_USB_MSG_USB2_PORT_SHIFT;
+   msg[1] |= ufp << PMC_USB_MSG_UFP_SHIFT;
+   msg[1] |= hsl_orientation(port) << PMC_USB_MSG_ORI_HSL_SHIFT;
+   msg[1] |= sbu_orientation(port) << PMC_USB_MSG_ORI_AUX_SHIFT;
 
return pmc_usb_command(port, msg, sizeof(msg));
 }
@@ -365,7 +375,7 @@ pmc_usb_mux_set(struct typec_mux *mux, struct 
typec_mux_state *state)
if (state->mode == TYPEC_STATE_SAFE)
return pmc_usb_mux_safe_state(port);
if (state->mode == TYPEC_STATE_USB)
-   return pmc_usb_connect(port);
+   return pmc_usb_connect(port, port->role);
 
if (state->alt) {
switch (state->alt->svid) {
@@ -380,7 +390,7 @@ pmc_usb_mux_set(struct typec_mux *mux, struct 
typec_mux_state *state)
/* REVISIT: Try with usb3_port set to 0? */
break;
case TYPEC_MODE_USB3:
-   return pmc_usb_connect(port);
+   return pmc_usb_connect(port, port->role);
case TYPEC_MODE_USB4:
return pmc_usb_mux_usb4(port, state);
}
@@ -401,13 +411,6 @@ static int pmc_usb_set_orientation(struct typec_switch *sw,
 
port->orientation = orientation;
 
-   if (port->role) {
-   if (orie

[PATCH v2 0/3] Add Intel Input Output Manager driver

2020-08-21 Thread Rajmohan Mani
Hi,

This patch series add support for Intel Input Output Manager (IOM)
driver, which is leveraged by the Intel PMC USB mux control driver.

changes from v1:
- Included device role (UFP) support patch from Heikki to this series.
- Addressed Greg's comments on v1 with below changes
- Used per-instance variable for struct intel_iom
- Removed struct device *dev inside probe function
- Removed dev_set_drvdata() inside probe function
- Added NULL pointer check on struct intel_iom * as well as members
  dev and regbar, inside intel_iom_port_status(), to protect against
  calls to this API before driver gets probed.
- Limit support to only one IOM device
- Removed intel_iom_get()/intel_iom_put() calls, as the dependency through
  Kconfig is enough to prevent the IOM driver from unloading, when used
  by callers.

Heikki Krogerus (2):
  usb: typec: intel_pmc_mux: Check the port status before connect
  usb: typec: intel_pmc_mux: Support for device role (UFP)

Rajmohan Mani (1):
  platform/x86: Add Intel Input Output Manager (IOM) driver

 drivers/platform/x86/Kconfig|  16 +++
 drivers/platform/x86/Makefile   |   1 +
 drivers/platform/x86/intel_iom.c|  95 +++
 drivers/usb/typec/mux/Kconfig   |   1 +
 drivers/usb/typec/mux/intel_pmc_mux.c   | 124 ++--
 include/linux/platform_data/x86/intel_iom.h |  49 
 6 files changed, 251 insertions(+), 35 deletions(-)
 create mode 100644 drivers/platform/x86/intel_iom.c
 create mode 100644 include/linux/platform_data/x86/intel_iom.h

-- 
2.20.1



[PATCH v2 2/3] usb: typec: intel_pmc_mux: Check the port status before connect

2020-08-21 Thread Rajmohan Mani
From: Heikki Krogerus 

The PMC microcontroller that we use for configuration, does
not supply any status information back. For port status we
need to talk to another controller on the board called IOM
(I/O manager).

By checking the port status before configuring the muxes, we
can make sure that we do not reconfigure the port after
bootup when the system firmware (for example BIOS) has
already configured it.

Using the status information also to check if DisplayPort
HPD is still asserted when the cable plug is disconnected,
and clearing it if it is.

Signed-off-by: Heikki Krogerus 
Signed-off-by: Rajmohan Mani 
---
 drivers/usb/typec/mux/Kconfig |  1 +
 drivers/usb/typec/mux/intel_pmc_mux.c | 75 +++
 2 files changed, 65 insertions(+), 11 deletions(-)

diff --git a/drivers/usb/typec/mux/Kconfig b/drivers/usb/typec/mux/Kconfig
index a4dbd11f8ee2..46f5512de63d 100644
--- a/drivers/usb/typec/mux/Kconfig
+++ b/drivers/usb/typec/mux/Kconfig
@@ -12,6 +12,7 @@ config TYPEC_MUX_PI3USB30532
 config TYPEC_MUX_INTEL_PMC
tristate "Intel PMC mux control"
depends on INTEL_SCU_IPC
+   depends on INTEL_IOM
select USB_ROLE_SWITCH
help
  Driver for USB muxes controlled by Intel PMC FW. Intel PMC FW can
diff --git a/drivers/usb/typec/mux/intel_pmc_mux.c 
b/drivers/usb/typec/mux/intel_pmc_mux.c
index e4021e13af40..c758d6113c41 100644
--- a/drivers/usb/typec/mux/intel_pmc_mux.c
+++ b/drivers/usb/typec/mux/intel_pmc_mux.c
@@ -9,6 +9,7 @@
 #include 
 #include 
 #include 
+#include 
 #include 
 #include 
 #include 
@@ -83,10 +84,22 @@ enum {
 #define PMC_USB_DP_HPD_LVL BIT(4)
 #define PMC_USB_DP_HPD_IRQ BIT(5)
 
+/* IOM Port Status */
+#define IOM_PORT_ACTIVITY_IS(_status_, _type_) \
+   _status_) & IOM_PORT_STATUS_ACTIVITY_TYPE_MASK) >>  \
+ IOM_PORT_STATUS_ACTIVITY_TYPE_SHIFT) ==   \
+(IOM_PORT_STATUS_ACTIVITY_TYPE_##_type_))
+
+#define IOM_PORT_HPD_ASSERTED(_status_)
\
+   _status_) & IOM_PORT_STATUS_DHPD_HPD_STATUS_MASK) >>\
+ IOM_PORT_STATUS_DHPD_HPD_STATUS_SHIFT) &  \
+IOM_PORT_STATUS_DHPD_HPD_STATUS_ASSERT)
+
 struct pmc_usb;
 
 struct pmc_usb_port {
int num;
+   u32 iom_status;
struct pmc_usb *pmc;
struct typec_mux *typec_mux;
struct typec_switch *typec_sw;
@@ -145,18 +158,17 @@ static int pmc_usb_command(struct pmc_usb_port *port, u8 
*msg, u32 len)
 }
 
 static int
-pmc_usb_mux_dp_hpd(struct pmc_usb_port *port, struct typec_mux_state *state)
+pmc_usb_mux_dp_hpd(struct pmc_usb_port *port, struct typec_displayport_data 
*dp)
 {
-   struct typec_displayport_data *data = state->data;
u8 msg[2] = { };
 
msg[0] = PMC_USB_DP_HPD;
msg[0] |= port->usb3_port << PMC_USB_MSG_USB3_PORT_SHIFT;
 
-   if (data->status & DP_STATUS_IRQ_HPD)
+   if (dp->status & DP_STATUS_IRQ_HPD)
msg[1] = PMC_USB_DP_HPD_IRQ;
 
-   if (data->status & DP_STATUS_HPD_STATE)
+   if (dp->status & DP_STATUS_HPD_STATE)
msg[1] |= PMC_USB_DP_HPD_LVL;
 
return pmc_usb_command(port, msg, sizeof(msg));
@@ -169,8 +181,18 @@ pmc_usb_mux_dp(struct pmc_usb_port *port, struct 
typec_mux_state *state)
struct altmode_req req = { };
int ret;
 
+   if (IOM_PORT_ACTIVITY_IS(port->iom_status, DP) ||
+   IOM_PORT_ACTIVITY_IS(port->iom_status, DP_MFD)) {
+   if (IOM_PORT_HPD_ASSERTED(port->iom_status) &&
+   (!(data->status & DP_STATUS_IRQ_HPD) &&
+   data->status & DP_STATUS_HPD_STATE))
+   return 0;
+
+   return pmc_usb_mux_dp_hpd(port, state->data);
+   }
+
if (data->status & DP_STATUS_IRQ_HPD)
-   return pmc_usb_mux_dp_hpd(port, state);
+   return pmc_usb_mux_dp_hpd(port, state->data);
 
req.usage = PMC_USB_ALT_MODE;
req.usage |= port->usb3_port << PMC_USB_MSG_USB3_PORT_SHIFT;
@@ -192,8 +214,8 @@ pmc_usb_mux_dp(struct pmc_usb_port *port, struct 
typec_mux_state *state)
if (ret)
return ret;
 
-   if (data->status & DP_STATUS_HPD_STATE)
-   return pmc_usb_mux_dp_hpd(port, state);
+   if (data->status & (DP_STATUS_IRQ_HPD | DP_STATUS_HPD_STATE))
+   return pmc_usb_mux_dp_hpd(port, state->data);
 
return 0;
 }
@@ -205,6 +227,10 @@ pmc_usb_mux_tbt(struct pmc_usb_port *port, struct 
typec_mux_state *state)
u8 cable_speed = TBT_CABLE_SPEED(data->cable_mode);
struct altmode_req req = { };
 
+   if (IOM_PORT_ACTIVITY_IS(port->iom_status, TBT) ||
+   IOM_PORT_ACTIVITY_IS(port->iom_status, ALT_MODE_TBT_U

RE: [PATCH 1/2] platform/x86: Add Intel Input Output Manager (IOM) driver

2020-07-23 Thread Mani, Rajmohan
Hi Greg,

> Subject: Re: [PATCH 1/2] platform/x86: Add Intel Input Output Manager (IOM)
> driver

...

> > > > +struct intel_iom {
> > > > +   struct device *dev;
> > > > +   void __iomem *regbar;
> > > > +};
> > > > +
> > > > +static struct intel_iom iom_dev;
> > >
> > > Why just one?  Why is this static?
> > >
> >
> > There is just one IOM device in the system.
> 
> For today, yes, no need to force yourself to have to change this in the 
> future.
> Just use a normal per-instance variable instead please, if you really need it.
> 

Ack

> > > > +
> > > > +   /* Prevent this driver from being unloaded while in use */
> > > > +   if (!try_module_get(dev->driver->owner)) {
> > >
> > > Why are you poking around in a random device's driver's owner?
> > >
> > > That's not ok.  And probably totally racy.
> > >
> > > Handle module reference counts properly, not like this.
> > >
> >
> > Ack. Will use THIS_MODULE here.
> 
> No, that is not the answer, and is always wrong to use :(
> 

This should not matter anymore, as I find reference counting may not be needed.

> > > And why does it even matter that you incremented the module
> > > reference count?  What is that "protecting" you from?
> > >
> >
> > To prevent this driver from being unloaded, while it is being used.
> 
> Why does that matter?  Shouldn't normal reference counting and
> dependancies be all that you need?
> 

I find just dependencies are enough to prevent the driver from being unloaded.

With Intel PMC USB mux control driver, not using 
intel_iom_get()/intel_iom_put(),
just invoking intel_iom_port_status() is enough for rmmod to report failure
(citing the use by intel_pmc_mux) in unloading the IOM driver.

> > > > +   put_device(iom_dev.dev);
> > > > +   return ERR_PTR(-EBUSY);
> > > > +   }
> > > > +
> > > > +   return _dev;
> > > > +}
> > > > +EXPORT_SYMBOL_GPL(intel_iom_get);
> > >
> > > Who calls this function?
> > >
> >
> > Intel PMC USB mux control driver, in this case.
> > The callers are expected to call intel_iom_get() before using the
> > intel_iom_port_status(), after which intel_iom_put() can be called to
> > release the IOM device instance.
> 
> Why not just have a single call if all this driver does is support one thing. 
>  The
> reference counting shouldn't be needed at all, right?
> 

Ack. That looks to be the case, based on my findings.

> > > > +/**
> > > > + * intel_iom_put() - Put IOM device instance
> > > > + * @iom: IOM device instance
> > > > + *
> > > > + * This function releases the IOM device instance created using
> > > > + * intel_iom_get() and allows the driver to be unloaded.
> > > > + *
> > > > + * Call intel_iom_put() to release the instance.
> > > > + */
> > > > +void intel_iom_put(struct intel_iom *iom) {
> > > > +   if (!iom)
> > > > +   return;
> > > > +
> > > > +   module_put(iom->dev->driver->owner);
> > >
> > > And if the device doesn't have a driver?  boom :(
> > >
> > > Don't do this.
> > >
> >
> > Ack. Will use THIS_MODULE here.
> 
> Again, no, that will be even more incorrect.
> 

This shouldn't be relevant anymore.

> > > > +   put_device(iom->dev);
> > > > +}
> > > > +EXPORT_SYMBOL_GPL(intel_iom_put);
> > > > +
> > > > +/**
> > > > + * intel_iom_port_status() - Get status bits for the Type-C port
> > > > + * @iom: IOM device instance
> > > > + * @port: Type-C port number
> > > > + * @status: pointer to receive the status bits
> > > > + *
> > > > + * Returns 0 on success, error otherwise.
> > > > + */
> > > > +int intel_iom_port_status(struct intel_iom *iom, u8 port, u32
> > > > +*status) {
> > > > +   void __iomem *reg;
> > > > +
> > > > +   if (!iom)
> > > > +   return -ENODEV;
> > > > +
> > > > +   if (!status || (port > IOM_MAX_PORTS - 1))
> > > > +   return -EINVAL;
> > > > +
> > > > +   reg = iom->regbar + IOM_PORT_STATUS_OFFSET + IOM_REG_LEN *
> > > port;
> > > > +
> > > > +   *status = ioread32(reg);
> > > > +
> > > > +   return 0;
> > > > +}
> > > > +EXPORT_SYMBOL_GPL(intel_iom_port_status);
> > >
> > > So the whole driver is here just to read, directly from memory, a
> > > single
> > > 32 bit value?
> >
> > Yes.
> 
> Ok, then this whole driver could be about 90% smaller and more obvious.
> Don't add the reference counting, the static variables and all the other stuff
> just to get a 32bit number.
> 

Ack


RE: [PATCH 2/2] usb: typec: intel_pmc_mux: Check the port status before connect

2020-07-17 Thread Mani, Rajmohan
Hi Greg,

> -Original Message-
> From: Greg Kroah-Hartman 
> Sent: Thursday, July 16, 2020 12:05 AM
> To: Mani, Rajmohan 
> Cc: Darren Hart ; Andy Shevchenko
> ; Mika Westerberg
> ; Dmitry Torokhov
> ; Lee Jones ; Ayman
> Bagabas ; Masahiro Yamada
> ; Joseph, Jithu ; Blaž
> Hrastnik ; Srinivas Pandruvada
> ; linux-kernel@vger.kernel.org;
> platform-driver-...@vger.kernel.org; Heikki Krogerus
> ; linux-...@vger.kernel.org;
> pmal...@chromium.org; ble...@chromium.org
> Subject: Re: [PATCH 2/2] usb: typec: intel_pmc_mux: Check the port status
> before connect
> 
> On Wed, Jul 15, 2020 at 05:33:10PM -0700, Rajmohan Mani wrote:
> > From: Heikki Krogerus 
> >
> > The PMC microcontroller that we use for configuration, does not supply
> > any status information back. For port status we need to talk to
> > another controller on the board called IOM (I/O manager).
> >
> > By checking the port status before configuring the muxes, we can make
> > sure that we do not reconfigure the port after bootup when the system
> > firmware (for example BIOS) has already configured it.
> >
> > Using the status information also to check if DisplayPort HPD is still
> > asserted when the cable plug is disconnected, and clearing it if it
> > is.
> >
> > Signed-off-by: Heikki Krogerus 
> 
> You can't just forward on patches from others without also adding your
> signed-off-by to them, right?
> 

Sorry I missed this.

> Please fix up this series and try again.
> 

Ack. Will fix this with v2.

> thanks,
> 
> greg k-h


RE: [PATCH 1/2] platform/x86: Add Intel Input Output Manager (IOM) driver

2020-07-17 Thread Mani, Rajmohan
Hi Greg,

Thanks for the reviews.

> -Original Message-
> From: Greg Kroah-Hartman 
> Sent: Thursday, July 16, 2020 12:10 AM
> To: Mani, Rajmohan 
> Cc: Darren Hart ; Andy Shevchenko
> ; Mika Westerberg
> ; Dmitry Torokhov
> ; Lee Jones ; Ayman
> Bagabas ; Masahiro Yamada
> ; Joseph, Jithu ; Blaž
> Hrastnik ; Srinivas Pandruvada
> ; linux-kernel@vger.kernel.org;
> platform-driver-...@vger.kernel.org; Heikki Krogerus
> ; linux-...@vger.kernel.org;
> pmal...@chromium.org; ble...@chromium.org
> Subject: Re: [PATCH 1/2] platform/x86: Add Intel Input Output Manager (IOM)
> driver
> 
> On Wed, Jul 15, 2020 at 05:33:09PM -0700, Rajmohan Mani wrote:
> > Input Output Manager (IOM) is part of the Tiger Lake SoC that
> > configures the Type-C Sub System (TCSS). IOM is a micro controller
> > that handles Type-C topology, configuration and PM functions of
> > various Type-C devices connected on the platform.
> >
> > This driver helps read relevant information such as Type-C port status
> > (whether a device is connected to a Type-C port or not) and the
> > activity type on the Type-C ports (such as USB, Display Port,
> > Thunderbolt), for consumption by other drivers.
> >
> > Currently intel_iom_port_status() API is exported by this driver, that
> > has information about the Type-C port status and port activity type.
> >
> > Signed-off-by: Rajmohan Mani 
> > ---
> >  drivers/platform/x86/Kconfig|  16 +++
> >  drivers/platform/x86/Makefile   |   1 +
> >  drivers/platform/x86/intel_iom.c| 133 
> >  include/linux/platform_data/x86/intel_iom.h |  62 +
> 
> Why do you need a .h file for a single .c file that no one else shares this 
> data?
> Just put it all in the .c file please.
> 

The APIs exported by this driver, are used by the caller (Intel PMC USB mux
control driver), hence the need for header file.

> >  4 files changed, 212 insertions(+)
> >  create mode 100644 drivers/platform/x86/intel_iom.c  create mode
> > 100644 include/linux/platform_data/x86/intel_iom.h
> >
> > diff --git a/drivers/platform/x86/Kconfig
> > b/drivers/platform/x86/Kconfig index 0581a54cf562..271feddb20ef 100644
> > --- a/drivers/platform/x86/Kconfig
> > +++ b/drivers/platform/x86/Kconfig
> > @@ -816,6 +816,22 @@ config INTEL_INT0002_VGPIO
> >   To compile this driver as a module, choose M here: the module will
> >   be called intel_int0002_vgpio.
> >
> > +config INTEL_IOM
> > +   tristate "Intel Input Output Manager (IOM) driver"
> > +   depends on ACPI && PCI
> > +   help
> > + This driver helps read relevant information such as Type-C port
> > + status (whether a device is connected to a Type-C port or not)
> > + and the activity type on the Type-C ports (such as USB, Display
> > + Port, Thunderbolt), for consumption by other drivers.
> > +
> > + Currently intel_iom_port_status() API is exported by this driver,
> > + that has information about the Type-C port status and port activity
> > + type.
> > +
> > + To compile this driver as a module, choose M here: the module will
> > + be called intel_iom.
> > +
> >  config INTEL_MENLOW
> > tristate "Thermal Management driver for Intel menlow platform"
> > depends on ACPI_THERMAL
> > diff --git a/drivers/platform/x86/Makefile
> > b/drivers/platform/x86/Makefile index 2b85852a1a87..d71e4620a7c6
> > 100644
> > --- a/drivers/platform/x86/Makefile
> > +++ b/drivers/platform/x86/Makefile
> > @@ -76,6 +76,7 @@ intel_cht_int33fe-objs:=
> intel_cht_int33fe_common.o \
> >intel_cht_int33fe_microb.o
> >  obj-$(CONFIG_INTEL_HID_EVENT)  += intel-hid.o
> >  obj-$(CONFIG_INTEL_INT0002_VGPIO)  += intel_int0002_vgpio.o
> > +obj-$(CONFIG_INTEL_IOM)+= intel_iom.o
> >  obj-$(CONFIG_INTEL_MENLOW) += intel_menlow.o
> >  obj-$(CONFIG_INTEL_OAKTRAIL)   += intel_oaktrail.o
> >  obj-$(CONFIG_INTEL_VBTN)   += intel-vbtn.o
> > diff --git a/drivers/platform/x86/intel_iom.c
> > b/drivers/platform/x86/intel_iom.c
> > new file mode 100644
> > index ..ece0fe720b2d
> > --- /dev/null
> > +++ b/drivers/platform/x86/intel_iom.c
> > @@ -0,0 +1,133 @@
> > +// SPDX-License-Identifier: GPL-2.0
> > +/*
> > + * Intel Core SoC Input Output Manager (IOM) driver.
> > + *
> > + * This driver provides access to the Input Output Manager (IOM)
&

[PATCH 0/2] Add Intel Input Output Manager driver

2020-07-15 Thread Rajmohan Mani
Hi,

This patch series add support for Intel Input Output Manager (IOM)
driver, which is leveraged by the Intel PMC USB mux control driver.

This patch series has a dependency on the following 4 patches, that
are in Greg's usb-next branch.
https://git.kernel.org/pub/scm/linux/kernel/git/gregkh/usb.git/tree/?h=usb-next

ffe82945d8eb usb: typec: intel_pmc_mux: Add support for USB4
cab9219d2af4 usb: typec: intel_pmc_mux: Definitions for response status bits
1a1be50b5ebd usb: typec: Add data structure for Enter_USB message
6701911bb1c1 usb: typec: Combine the definitions for Accessory and USB modes

Heikki Krogerus (1):
  usb: typec: intel_pmc_mux: Check the port status before connect

Rajmohan Mani (1):
  platform/x86: Add Intel Input Output Manager (IOM) driver

 drivers/platform/x86/Kconfig|  16 +++
 drivers/platform/x86/Makefile   |   1 +
 drivers/platform/x86/intel_iom.c| 133 
 drivers/usb/typec/mux/Kconfig   |   1 +
 drivers/usb/typec/mux/intel_pmc_mux.c   |  73 +--
 include/linux/platform_data/x86/intel_iom.h |  62 +
 6 files changed, 276 insertions(+), 10 deletions(-)
 create mode 100644 drivers/platform/x86/intel_iom.c
 create mode 100644 include/linux/platform_data/x86/intel_iom.h

-- 
2.20.1



[PATCH 1/2] platform/x86: Add Intel Input Output Manager (IOM) driver

2020-07-15 Thread Rajmohan Mani
Input Output Manager (IOM) is part of the Tiger Lake SoC that
configures the Type-C Sub System (TCSS). IOM is a micro controller
that handles Type-C topology, configuration and PM functions of
various Type-C devices connected on the platform.

This driver helps read relevant information such as Type-C port
status (whether a device is connected to a Type-C port or not) and
the activity type on the Type-C ports (such as USB, Display Port,
Thunderbolt), for consumption by other drivers.

Currently intel_iom_port_status() API is exported by this driver,
that has information about the Type-C port status and port activity
type.

Signed-off-by: Rajmohan Mani 
---
 drivers/platform/x86/Kconfig|  16 +++
 drivers/platform/x86/Makefile   |   1 +
 drivers/platform/x86/intel_iom.c| 133 
 include/linux/platform_data/x86/intel_iom.h |  62 +
 4 files changed, 212 insertions(+)
 create mode 100644 drivers/platform/x86/intel_iom.c
 create mode 100644 include/linux/platform_data/x86/intel_iom.h

diff --git a/drivers/platform/x86/Kconfig b/drivers/platform/x86/Kconfig
index 0581a54cf562..271feddb20ef 100644
--- a/drivers/platform/x86/Kconfig
+++ b/drivers/platform/x86/Kconfig
@@ -816,6 +816,22 @@ config INTEL_INT0002_VGPIO
  To compile this driver as a module, choose M here: the module will
  be called intel_int0002_vgpio.
 
+config INTEL_IOM
+   tristate "Intel Input Output Manager (IOM) driver"
+   depends on ACPI && PCI
+   help
+ This driver helps read relevant information such as Type-C port
+ status (whether a device is connected to a Type-C port or not)
+ and the activity type on the Type-C ports (such as USB, Display
+ Port, Thunderbolt), for consumption by other drivers.
+
+ Currently intel_iom_port_status() API is exported by this driver,
+ that has information about the Type-C port status and port activity
+ type.
+
+ To compile this driver as a module, choose M here: the module will
+ be called intel_iom.
+
 config INTEL_MENLOW
tristate "Thermal Management driver for Intel menlow platform"
depends on ACPI_THERMAL
diff --git a/drivers/platform/x86/Makefile b/drivers/platform/x86/Makefile
index 2b85852a1a87..d71e4620a7c6 100644
--- a/drivers/platform/x86/Makefile
+++ b/drivers/platform/x86/Makefile
@@ -76,6 +76,7 @@ intel_cht_int33fe-objs:= 
intel_cht_int33fe_common.o \
   intel_cht_int33fe_microb.o
 obj-$(CONFIG_INTEL_HID_EVENT)  += intel-hid.o
 obj-$(CONFIG_INTEL_INT0002_VGPIO)  += intel_int0002_vgpio.o
+obj-$(CONFIG_INTEL_IOM)+= intel_iom.o
 obj-$(CONFIG_INTEL_MENLOW) += intel_menlow.o
 obj-$(CONFIG_INTEL_OAKTRAIL)   += intel_oaktrail.o
 obj-$(CONFIG_INTEL_VBTN)   += intel-vbtn.o
diff --git a/drivers/platform/x86/intel_iom.c b/drivers/platform/x86/intel_iom.c
new file mode 100644
index ..ece0fe720b2d
--- /dev/null
+++ b/drivers/platform/x86/intel_iom.c
@@ -0,0 +1,133 @@
+// SPDX-License-Identifier: GPL-2.0
+/*
+ * Intel Core SoC Input Output Manager (IOM) driver.
+ *
+ * This driver provides access to the Input Output Manager (IOM) (that
+ * is part of Tiger Lake SoC) registers that can be used to know about
+ * Type-C Sub System related information (such as Type-C port status,
+ * activity type on Type-C ports).
+ *
+ * Copyright (C) 2020, Intel Corporation
+ * Author: Rajmohan Mani 
+ */
+
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+
+#define IOM_PORT_STATUS_OFFSET 0x560
+
+struct intel_iom {
+   struct device *dev;
+   void __iomem *regbar;
+};
+
+static struct intel_iom iom_dev;
+
+/**
+ * intel_iom_get() - Get IOM device instance
+ *
+ * This function returns the IOM device instance. This also ensures that
+ * this driver cannot be unloaded while the caller has the instance.
+ *
+ * Call intel_iom_put() to release the instance.
+ *
+ * Returns IOM device instance on success or error pointer otherwise.
+ */
+struct intel_iom *intel_iom_get(void)
+{
+   struct device *dev = get_device(iom_dev.dev);
+
+   /* Prevent this driver from being unloaded while in use */
+   if (!try_module_get(dev->driver->owner)) {
+   put_device(iom_dev.dev);
+   return ERR_PTR(-EBUSY);
+   }
+
+   return _dev;
+}
+EXPORT_SYMBOL_GPL(intel_iom_get);
+
+/**
+ * intel_iom_put() - Put IOM device instance
+ * @iom: IOM device instance
+ *
+ * This function releases the IOM device instance created using
+ * intel_iom_get() and allows the driver to be unloaded.
+ *
+ * Call intel_iom_put() to release the instance.
+ */
+void intel_iom_put(struct intel_iom *iom)
+{
+   if (!iom)
+   return;
+
+   module_put(iom->dev->driver->owner);
+   put_device(iom

[PATCH 2/2] usb: typec: intel_pmc_mux: Check the port status before connect

2020-07-15 Thread Rajmohan Mani
From: Heikki Krogerus 

The PMC microcontroller that we use for configuration, does
not supply any status information back. For port status we
need to talk to another controller on the board called IOM
(I/O manager).

By checking the port status before configuring the muxes, we
can make sure that we do not reconfigure the port after
bootup when the system firmware (for example BIOS) has
already configured it.

Using the status information also to check if DisplayPort
HPD is still asserted when the cable plug is disconnected,
and clearing it if it is.

Signed-off-by: Heikki Krogerus 
---
 drivers/usb/typec/mux/Kconfig |  1 +
 drivers/usb/typec/mux/intel_pmc_mux.c | 73 +++
 2 files changed, 64 insertions(+), 10 deletions(-)

diff --git a/drivers/usb/typec/mux/Kconfig b/drivers/usb/typec/mux/Kconfig
index a4dbd11f8ee2..46f5512de63d 100644
--- a/drivers/usb/typec/mux/Kconfig
+++ b/drivers/usb/typec/mux/Kconfig
@@ -12,6 +12,7 @@ config TYPEC_MUX_PI3USB30532
 config TYPEC_MUX_INTEL_PMC
tristate "Intel PMC mux control"
depends on INTEL_SCU_IPC
+   depends on INTEL_IOM
select USB_ROLE_SWITCH
help
  Driver for USB muxes controlled by Intel PMC FW. Intel PMC FW can
diff --git a/drivers/usb/typec/mux/intel_pmc_mux.c 
b/drivers/usb/typec/mux/intel_pmc_mux.c
index 2aba07c7b221..84101fb99934 100644
--- a/drivers/usb/typec/mux/intel_pmc_mux.c
+++ b/drivers/usb/typec/mux/intel_pmc_mux.c
@@ -9,6 +9,7 @@
 #include 
 #include 
 #include 
+#include 
 #include 
 #include 
 #include 
@@ -83,10 +84,17 @@ enum {
 #define PMC_USB_DP_HPD_LVL BIT(4)
 #define PMC_USB_DP_HPD_IRQ BIT(5)
 
+/* IOM Port Status */
+#define IOM_PORT_ACTIVITY_IS(_status_, _type_) \
+   _status_) & IOM_PORT_STATUS_ACTIVITY_TYPE_MASK) >>  \
+ IOM_PORT_STATUS_ACTIVITY_TYPE_SHIFT) ==   \
+(IOM_PORT_STATUS_ACTIVITY_TYPE_##_type_))
+
 struct pmc_usb;
 
 struct pmc_usb_port {
int num;
+   u32 iom_status;
struct pmc_usb *pmc;
struct typec_mux *typec_mux;
struct typec_switch *typec_sw;
@@ -105,6 +113,7 @@ struct pmc_usb_port {
 struct pmc_usb {
u8 num_ports;
struct device *dev;
+   struct intel_iom *iom;
struct intel_scu_ipc_dev *ipc;
struct pmc_usb_port *port;
 };
@@ -145,18 +154,17 @@ static int pmc_usb_command(struct pmc_usb_port *port, u8 
*msg, u32 len)
 }
 
 static int
-pmc_usb_mux_dp_hpd(struct pmc_usb_port *port, struct typec_mux_state *state)
+pmc_usb_mux_dp_hpd(struct pmc_usb_port *port, struct typec_displayport_data 
*dp)
 {
-   struct typec_displayport_data *data = state->data;
u8 msg[2] = { };
 
msg[0] = PMC_USB_DP_HPD;
msg[0] |= port->usb3_port << PMC_USB_MSG_USB3_PORT_SHIFT;
 
-   if (data->status & DP_STATUS_IRQ_HPD)
+   if (dp->status & DP_STATUS_IRQ_HPD)
msg[1] = PMC_USB_DP_HPD_IRQ;
 
-   if (data->status & DP_STATUS_HPD_STATE)
+   if (dp->status & DP_STATUS_HPD_STATE)
msg[1] |= PMC_USB_DP_HPD_LVL;
 
return pmc_usb_command(port, msg, sizeof(msg));
@@ -169,8 +177,12 @@ pmc_usb_mux_dp(struct pmc_usb_port *port, struct 
typec_mux_state *state)
struct altmode_req req = { };
int ret;
 
+   if (IOM_PORT_ACTIVITY_IS(port->iom_status, DP) ||
+   IOM_PORT_ACTIVITY_IS(port->iom_status, DP_MFD))
+   return 0;
+
if (data->status & DP_STATUS_IRQ_HPD)
-   return pmc_usb_mux_dp_hpd(port, state);
+   return pmc_usb_mux_dp_hpd(port, state->data);
 
req.usage = PMC_USB_ALT_MODE;
req.usage |= port->usb3_port << PMC_USB_MSG_USB3_PORT_SHIFT;
@@ -193,7 +205,7 @@ pmc_usb_mux_dp(struct pmc_usb_port *port, struct 
typec_mux_state *state)
return ret;
 
if (data->status & DP_STATUS_HPD_STATE)
-   return pmc_usb_mux_dp_hpd(port, state);
+   return pmc_usb_mux_dp_hpd(port, state->data);
 
return 0;
 }
@@ -205,6 +217,10 @@ pmc_usb_mux_tbt(struct pmc_usb_port *port, struct 
typec_mux_state *state)
u8 cable_speed = TBT_CABLE_SPEED(data->cable_mode);
struct altmode_req req = { };
 
+   if (IOM_PORT_ACTIVITY_IS(port->iom_status, TBT) ||
+   IOM_PORT_ACTIVITY_IS(port->iom_status, ALT_MODE_TBT_USB))
+   return 0;
+
req.usage = PMC_USB_ALT_MODE;
req.usage |= port->usb3_port << PMC_USB_MSG_USB3_PORT_SHIFT;
req.mode_type = PMC_USB_MODE_TYPE_TBT << PMC_USB_MODE_TYPE_SHIFT;
@@ -239,6 +255,10 @@ pmc_usb_mux_usb4(struct pmc_usb_port *port, struct 
typec_mux_state *state)
struct altmode_req req = { };
u8 cable_speed;
 
+   if (IOM_PORT_ACTIVITY_IS(port->iom_status, TBT) ||
+   IOM_PORT_ACTIVITY_IS(port->iom_status, ALT_MODE_TBT_USB))
+   return 0;
+
req.usage = PMC_USB_ALT_MODE;
req.usage |= 

[PATCH 14/14] bus: mhi: core: Handle syserr during power_up

2020-05-21 Thread mani
From: Jeffrey Hugo 

The MHI device may be in the syserr state when we attempt to init it in
power_up().  Since we have no local state, the handling is simple -
reset the device and wait for it to transition out of the reset state.

Signed-off-by: Jeffrey Hugo 
Reviewed-by: Hemant Kumar 
Reviewed-by: Manivannan Sadhasivam 
Signed-off-by: Manivannan Sadhasivam 
---
 drivers/bus/mhi/core/pm.c | 27 +++
 1 file changed, 27 insertions(+)

diff --git a/drivers/bus/mhi/core/pm.c b/drivers/bus/mhi/core/pm.c
index e6236a3ca39d..1bd61a64d7bb 100644
--- a/drivers/bus/mhi/core/pm.c
+++ b/drivers/bus/mhi/core/pm.c
@@ -763,6 +763,7 @@ static void mhi_deassert_dev_wake(struct mhi_controller 
*mhi_cntrl,
 
 int mhi_async_power_up(struct mhi_controller *mhi_cntrl)
 {
+   enum mhi_state state;
enum mhi_ee_type current_ee;
enum dev_st_transition next_state;
struct device *dev = _cntrl->mhi_dev->dev;
@@ -832,6 +833,32 @@ int mhi_async_power_up(struct mhi_controller *mhi_cntrl)
goto error_bhi_offset;
}
 
+   state = mhi_get_mhi_state(mhi_cntrl);
+   if (state == MHI_STATE_SYS_ERR) {
+   mhi_set_mhi_state(mhi_cntrl, MHI_STATE_RESET);
+   ret = wait_event_timeout(mhi_cntrl->state_event,
+   MHI_PM_IN_FATAL_STATE(mhi_cntrl->pm_state) ||
+   mhi_read_reg_field(mhi_cntrl,
+  mhi_cntrl->regs,
+  MHICTRL,
+  MHICTRL_RESET_MASK,
+  MHICTRL_RESET_SHIFT,
+  ) ||
+   !val,
+   msecs_to_jiffies(mhi_cntrl->timeout_ms));
+   if (ret) {
+   ret = -EIO;
+   dev_info(dev, "Failed to reset MHI due to syserr 
state\n");
+   goto error_bhi_offset;
+   }
+
+   /*
+* device cleares INTVEC as part of RESET processing,
+* re-program it
+*/
+   mhi_write_reg(mhi_cntrl, mhi_cntrl->bhi, BHI_INTVEC, 0);
+   }
+
/* Transition to next state */
next_state = MHI_IN_PBL(current_ee) ?
DEV_ST_TRANSITION_PBL : DEV_ST_TRANSITION_READY;
-- 
2.26.GIT



[PATCH 13/14] bus: mhi: core: Handle write lock properly in mhi_pm_m0_transition

2020-05-21 Thread mani
From: Hemant Kumar 

Take write lock only to protect db_mode member of mhi channel.
This allows rest of the mhi channels to just take read lock which
fine grains the locking. It prevents channel readers to starve if
they try to enter critical section after a writer.

Signed-off-by: Hemant Kumar 
Reviewed-by: Manivannan Sadhasivam 
Signed-off-by: Manivannan Sadhasivam 
---
 drivers/bus/mhi/core/pm.c | 10 +++---
 1 file changed, 7 insertions(+), 3 deletions(-)

diff --git a/drivers/bus/mhi/core/pm.c b/drivers/bus/mhi/core/pm.c
index a5d9973059c8..e6236a3ca39d 100644
--- a/drivers/bus/mhi/core/pm.c
+++ b/drivers/bus/mhi/core/pm.c
@@ -288,14 +288,18 @@ int mhi_pm_m0_transition(struct mhi_controller *mhi_cntrl)
for (i = 0; i < mhi_cntrl->max_chan; i++, mhi_chan++) {
struct mhi_ring *tre_ring = _chan->tre_ring;
 
-   write_lock_irq(_chan->lock);
-   if (mhi_chan->db_cfg.reset_req)
+   if (mhi_chan->db_cfg.reset_req) {
+   write_lock_irq(_chan->lock);
mhi_chan->db_cfg.db_mode = true;
+   write_unlock_irq(_chan->lock);
+   }
+
+   read_lock_irq(_chan->lock);
 
/* Only ring DB if ring is not empty */
if (tre_ring->base && tre_ring->wp  != tre_ring->rp)
mhi_ring_chan_db(mhi_cntrl, mhi_chan);
-   write_unlock_irq(_chan->lock);
+   read_unlock_irq(_chan->lock);
}
 
mhi_cntrl->wake_put(mhi_cntrl, false);
-- 
2.26.GIT



[PATCH 12/14] bus: mhi: core: Do not process SYS_ERROR if RDDM is supported

2020-05-21 Thread mani
From: Hemant Kumar 

Devices that support RDDM do not require processing SYS_ERROR as it is
deemed redundant. Avoid SYS_ERROR processing if RDDM is supported by
the device.

Signed-off-by: Hemant Kumar 
Reviewed-by: Jeffrey Hugo 
Reviewed-by: Manivannan Sadhasivam 
Signed-off-by: Manivannan Sadhasivam 
---
 drivers/bus/mhi/core/main.c | 11 ---
 1 file changed, 8 insertions(+), 3 deletions(-)

diff --git a/drivers/bus/mhi/core/main.c b/drivers/bus/mhi/core/main.c
index 7429189840b0..eef145180a55 100644
--- a/drivers/bus/mhi/core/main.c
+++ b/drivers/bus/mhi/core/main.c
@@ -396,9 +396,9 @@ irqreturn_t mhi_intvec_threaded_handler(int irq_number, 
void *priv)
}
write_unlock_irq(_cntrl->pm_lock);
 
-   /* If device in RDDM don't bother processing SYS error */
-   if (mhi_cntrl->ee == MHI_EE_RDDM) {
-   if (mhi_cntrl->ee != ee) {
+/* If device supports RDDM don't bother processing SYS error */
+   if (mhi_cntrl->rddm_image) {
+   if (mhi_cntrl->ee == MHI_EE_RDDM && mhi_cntrl->ee != ee) {
mhi_cntrl->status_cb(mhi_cntrl, MHI_CB_EE_RDDM);
wake_up_all(_cntrl->state_event);
}
@@ -734,6 +734,11 @@ int mhi_process_ctrl_ev_ring(struct mhi_controller 
*mhi_cntrl,
{
enum mhi_pm_state new_state;
 
+   /* skip SYS_ERROR handling if RDDM supported */
+   if (mhi_cntrl->ee == MHI_EE_RDDM ||
+   mhi_cntrl->rddm_image)
+   break;
+
dev_dbg(dev, "System error detected\n");
write_lock_irq(_cntrl->pm_lock);
new_state = mhi_tryset_pm_state(mhi_cntrl,
-- 
2.26.GIT



[PATCH 08/14] bus: mhi: core: Ensure non-zero session or sequence ID values are used

2020-05-21 Thread mani
From: Bhaumik Bhatt 

While writing any sequence or session identifiers, it is possible that
the host could write a zero value, whereas only non-zero values should
be supported writes to those registers. Ensure that the host does not
write a non-zero value for them and also log them in debug messages. A
macro is introduced to simplify this check and the existing checks are
also converted to use this macro.

Signed-off-by: Bhaumik Bhatt 
Reviewed-by: Jeffrey Hugo 
Reviewed-by: Manivannan Sadhasivam 
Signed-off-by: Manivannan Sadhasivam 
---
 drivers/bus/mhi/core/boot.c | 15 +++
 drivers/bus/mhi/core/internal.h |  1 +
 2 files changed, 8 insertions(+), 8 deletions(-)

diff --git a/drivers/bus/mhi/core/boot.c b/drivers/bus/mhi/core/boot.c
index 80e4d7609aaa..0b38014d040e 100644
--- a/drivers/bus/mhi/core/boot.c
+++ b/drivers/bus/mhi/core/boot.c
@@ -43,10 +43,7 @@ void mhi_rddm_prepare(struct mhi_controller *mhi_cntrl,
  lower_32_bits(mhi_buf->dma_addr));
 
mhi_write_reg(mhi_cntrl, base, BHIE_RXVECSIZE_OFFS, mhi_buf->len);
-   sequence_id = prandom_u32() & BHIE_RXVECSTATUS_SEQNUM_BMSK;
-
-   if (unlikely(!sequence_id))
-   sequence_id = 1;
+   sequence_id = MHI_RANDOM_U32_NONZERO(BHIE_RXVECSTATUS_SEQNUM_BMSK);
 
mhi_write_reg_field(mhi_cntrl, base, BHIE_RXVECDB_OFFS,
BHIE_RXVECDB_SEQNUM_BMSK, BHIE_RXVECDB_SEQNUM_SHFT,
@@ -189,7 +186,9 @@ static int mhi_fw_load_amss(struct mhi_controller 
*mhi_cntrl,
return -EIO;
}
 
-   dev_dbg(dev, "Starting AMSS download via BHIe\n");
+   sequence_id = MHI_RANDOM_U32_NONZERO(BHIE_TXVECSTATUS_SEQNUM_BMSK);
+   dev_dbg(dev, "Starting AMSS download via BHIe. Sequence ID:%u\n",
+   sequence_id);
mhi_write_reg(mhi_cntrl, base, BHIE_TXVECADDR_HIGH_OFFS,
  upper_32_bits(mhi_buf->dma_addr));
 
@@ -198,7 +197,6 @@ static int mhi_fw_load_amss(struct mhi_controller 
*mhi_cntrl,
 
mhi_write_reg(mhi_cntrl, base, BHIE_TXVECSIZE_OFFS, mhi_buf->len);
 
-   sequence_id = prandom_u32() & BHIE_TXVECSTATUS_SEQNUM_BMSK;
mhi_write_reg_field(mhi_cntrl, base, BHIE_TXVECDB_OFFS,
BHIE_TXVECDB_SEQNUM_BMSK, BHIE_TXVECDB_SEQNUM_SHFT,
sequence_id);
@@ -246,14 +244,15 @@ static int mhi_fw_load_sbl(struct mhi_controller 
*mhi_cntrl,
goto invalid_pm_state;
}
 
-   dev_dbg(dev, "Starting SBL download via BHI\n");
+   session_id = MHI_RANDOM_U32_NONZERO(BHI_TXDB_SEQNUM_BMSK);
+   dev_dbg(dev, "Starting SBL download via BHI. Session ID:%u\n",
+   session_id);
mhi_write_reg(mhi_cntrl, base, BHI_STATUS, 0);
mhi_write_reg(mhi_cntrl, base, BHI_IMGADDR_HIGH,
  upper_32_bits(dma_addr));
mhi_write_reg(mhi_cntrl, base, BHI_IMGADDR_LOW,
  lower_32_bits(dma_addr));
mhi_write_reg(mhi_cntrl, base, BHI_IMGSIZE, size);
-   session_id = prandom_u32() & BHI_TXDB_SEQNUM_BMSK;
mhi_write_reg(mhi_cntrl, base, BHI_IMGTXDB, session_id);
read_unlock_bh(pm_lock);
 
diff --git a/drivers/bus/mhi/core/internal.h b/drivers/bus/mhi/core/internal.h
index 0965ca3c9632..80b32c20149c 100644
--- a/drivers/bus/mhi/core/internal.h
+++ b/drivers/bus/mhi/core/internal.h
@@ -452,6 +452,7 @@ enum mhi_pm_state {
 #define PRIMARY_CMD_RING   0
 #define MHI_DEV_WAKE_DB127
 #define MHI_MAX_MTU0x
+#define MHI_RANDOM_U32_NONZERO(bmsk)   (prandom_u32_max(bmsk) + 1)
 
 enum mhi_er_type {
MHI_ER_TYPE_INVALID = 0x0,
-- 
2.26.GIT



[PATCH 07/14] bus: mhi: core: Improve debug logs for loading firmware

2020-05-21 Thread mani
From: Bhaumik Bhatt 

Add log messages to track boot flow errors and timeouts in SBL or AMSS
firmware loading to aid in debug.

Signed-off-by: Bhaumik Bhatt 
Reviewed-by: Jeffrey Hugo 
Reviewed-by: Manivannan Sadhasivam 
Signed-off-by: Manivannan Sadhasivam 
---
 drivers/bus/mhi/core/boot.c | 21 ++---
 1 file changed, 18 insertions(+), 3 deletions(-)

diff --git a/drivers/bus/mhi/core/boot.c b/drivers/bus/mhi/core/boot.c
index cf6dc5a2361c..80e4d7609aaa 100644
--- a/drivers/bus/mhi/core/boot.c
+++ b/drivers/bus/mhi/core/boot.c
@@ -121,7 +121,8 @@ static int __mhi_download_rddm_in_panic(struct 
mhi_controller *mhi_cntrl)
ee = mhi_get_exec_env(mhi_cntrl);
}
 
-   dev_dbg(dev, "Waiting for image download completion, current EE: %s\n",
+   dev_dbg(dev,
+   "Waiting for RDDM image download via BHIe, current EE:%s\n",
TO_MHI_EXEC_STR(ee));
 
while (retry--) {
@@ -152,11 +153,14 @@ static int __mhi_download_rddm_in_panic(struct 
mhi_controller *mhi_cntrl)
 int mhi_download_rddm_img(struct mhi_controller *mhi_cntrl, bool in_panic)
 {
void __iomem *base = mhi_cntrl->bhie;
+   struct device *dev = _cntrl->mhi_dev->dev;
u32 rx_status;
 
if (in_panic)
return __mhi_download_rddm_in_panic(mhi_cntrl);
 
+   dev_dbg(dev, "Waiting for RDDM image download via BHIe\n");
+
/* Wait for the image download to complete */
wait_event_timeout(mhi_cntrl->state_event,
   mhi_read_reg_field(mhi_cntrl, base,
@@ -174,6 +178,7 @@ static int mhi_fw_load_amss(struct mhi_controller 
*mhi_cntrl,
const struct mhi_buf *mhi_buf)
 {
void __iomem *base = mhi_cntrl->bhie;
+   struct device *dev = _cntrl->mhi_dev->dev;
rwlock_t *pm_lock = _cntrl->pm_lock;
u32 tx_status, sequence_id;
int ret;
@@ -184,6 +189,7 @@ static int mhi_fw_load_amss(struct mhi_controller 
*mhi_cntrl,
return -EIO;
}
 
+   dev_dbg(dev, "Starting AMSS download via BHIe\n");
mhi_write_reg(mhi_cntrl, base, BHIE_TXVECADDR_HIGH_OFFS,
  upper_32_bits(mhi_buf->dma_addr));
 
@@ -435,7 +441,12 @@ void mhi_fw_load_handler(struct mhi_controller *mhi_cntrl)
release_firmware(firmware);
 
/* Error or in EDL mode, we're done */
-   if (ret || mhi_cntrl->ee == MHI_EE_EDL)
+   if (ret) {
+   dev_err(dev, "MHI did not load SBL, ret:%d\n", ret);
+   return;
+   }
+
+   if (mhi_cntrl->ee == MHI_EE_EDL)
return;
 
write_lock_irq(_cntrl->pm_lock);
@@ -463,8 +474,10 @@ void mhi_fw_load_handler(struct mhi_controller *mhi_cntrl)
if (!mhi_cntrl->fbc_download)
return;
 
-   if (ret)
+   if (ret) {
+   dev_err(dev, "MHI did not enter READY state\n");
goto error_read;
+   }
 
/* Wait for the SBL event */
ret = wait_event_timeout(mhi_cntrl->state_event,
@@ -482,6 +495,8 @@ void mhi_fw_load_handler(struct mhi_controller *mhi_cntrl)
ret = mhi_fw_load_amss(mhi_cntrl,
   /* Vector table is the last entry */
   _info->mhi_buf[image_info->entries - 1]);
+   if (ret)
+   dev_err(dev, "MHI did not load AMSS, ret:%d\n", ret);
 
release_firmware(firmware);
 
-- 
2.26.GIT



[PATCH 04/14] bus: mhi: core: Read transfer length from an event properly

2020-05-21 Thread mani
From: Hemant Kumar 

When MHI Driver receives an EOT event, it reads xfer_len from the
event in the last TRE. The value is under control of the MHI device
and never validated by Host MHI driver. The value should never be
larger than the real size of the buffer but a malicious device can
set the value 0x as maximum. This causes driver to memory
overflow (both read or write). Fix this issue by reading minimum of
transfer length from event and the buffer length provided.

Signed-off-by: Hemant Kumar 
Signed-off-by: Bhaumik Bhatt 
Reviewed-by: Jeffrey Hugo 
Reviewed-by: Manivannan Sadhasivam 
Signed-off-by: Manivannan Sadhasivam 
---
 drivers/bus/mhi/core/main.c | 9 +++--
 1 file changed, 7 insertions(+), 2 deletions(-)

diff --git a/drivers/bus/mhi/core/main.c b/drivers/bus/mhi/core/main.c
index 64022865cb75..a394691d9383 100644
--- a/drivers/bus/mhi/core/main.c
+++ b/drivers/bus/mhi/core/main.c
@@ -513,7 +513,10 @@ static int parse_xfer_event(struct mhi_controller 
*mhi_cntrl,
mhi_cntrl->unmap_single(mhi_cntrl, buf_info);
 
result.buf_addr = buf_info->cb_buf;
-   result.bytes_xferd = xfer_len;
+
+   /* truncate to buf len if xfer_len is larger */
+   result.bytes_xferd =
+   min_t(u16, xfer_len, buf_info->len);
mhi_del_ring_element(mhi_cntrl, buf_ring);
mhi_del_ring_element(mhi_cntrl, tre_ring);
local_rp = tre_ring->rp;
@@ -597,7 +600,9 @@ static int parse_rsc_event(struct mhi_controller *mhi_cntrl,
 
result.transaction_status = (ev_code == MHI_EV_CC_OVERFLOW) ?
-EOVERFLOW : 0;
-   result.bytes_xferd = xfer_len;
+
+   /* truncate to buf len if xfer_len is larger */
+   result.bytes_xferd = min_t(u16, xfer_len, buf_info->len);
result.buf_addr = buf_info->cb_buf;
result.dir = mhi_chan->dir;
 
-- 
2.26.GIT



[PATCH 10/14] bus: mhi: core: Handle disable transitions in state worker

2020-05-21 Thread mani
From: Hemant Kumar 

Mission mode transition is handled by state worker thread but
power off is not. There is a possibility while mission mode
transition is in progress which calls MHI client driver probe,
power off is issued by MHI controller. This results into client
driver probe and remove running in parallel and causes use after
free situation. By queuing disable transition work when mission
mode is in progress prevents the race condition.

Signed-off-by: Hemant Kumar 
Reviewed-by: Jeffrey Hugo 
Reviewed-by: Manivannan Sadhasivam 
Signed-off-by: Manivannan Sadhasivam 
---
 drivers/bus/mhi/core/init.c |  1 +
 drivers/bus/mhi/core/internal.h |  1 +
 drivers/bus/mhi/core/pm.c   | 11 ++-
 3 files changed, 12 insertions(+), 1 deletion(-)

diff --git a/drivers/bus/mhi/core/init.c b/drivers/bus/mhi/core/init.c
index 3a853c5d2103..12207cc438aa 100644
--- a/drivers/bus/mhi/core/init.c
+++ b/drivers/bus/mhi/core/init.c
@@ -35,6 +35,7 @@ const char * const dev_state_tran_str[DEV_ST_TRANSITION_MAX] 
= {
[DEV_ST_TRANSITION_SBL] = "SBL",
[DEV_ST_TRANSITION_MISSION_MODE] = "MISSION_MODE",
[DEV_ST_TRANSITION_SYS_ERR] = "SYS_ERR",
+   [DEV_ST_TRANSITION_DISABLE] = "DISABLE",
 };
 
 const char * const mhi_state_str[MHI_STATE_MAX] = {
diff --git a/drivers/bus/mhi/core/internal.h b/drivers/bus/mhi/core/internal.h
index f01283b8a451..b1f640b75a94 100644
--- a/drivers/bus/mhi/core/internal.h
+++ b/drivers/bus/mhi/core/internal.h
@@ -387,6 +387,7 @@ enum dev_st_transition {
DEV_ST_TRANSITION_SBL,
DEV_ST_TRANSITION_MISSION_MODE,
DEV_ST_TRANSITION_SYS_ERR,
+   DEV_ST_TRANSITION_DISABLE,
DEV_ST_TRANSITION_MAX,
 };
 
diff --git a/drivers/bus/mhi/core/pm.c b/drivers/bus/mhi/core/pm.c
index 743b3207c390..a5d9973059c8 100644
--- a/drivers/bus/mhi/core/pm.c
+++ b/drivers/bus/mhi/core/pm.c
@@ -657,6 +657,10 @@ void mhi_pm_st_worker(struct work_struct *work)
mhi_pm_disable_transition
(mhi_cntrl, MHI_PM_SYS_ERR_PROCESS);
break;
+   case DEV_ST_TRANSITION_DISABLE:
+   mhi_pm_disable_transition
+   (mhi_cntrl, MHI_PM_SHUTDOWN_PROCESS);
+   break;
default:
break;
}
@@ -868,7 +872,12 @@ void mhi_power_down(struct mhi_controller *mhi_cntrl, bool 
graceful)
to_mhi_pm_state_str(MHI_PM_LD_ERR_FATAL_DETECT),
to_mhi_pm_state_str(mhi_cntrl->pm_state));
}
-   mhi_pm_disable_transition(mhi_cntrl, MHI_PM_SHUTDOWN_PROCESS);
+
+   mhi_queue_state_transition(mhi_cntrl, DEV_ST_TRANSITION_DISABLE);
+
+   /* Wait for shutdown to complete */
+   flush_work(_cntrl->st_worker);
+
mhi_deinit_free_irq(mhi_cntrl);
 
if (!mhi_cntrl->pre_init) {
-- 
2.26.GIT



[PATCH 06/14] bus: mhi: core: Return appropriate error codes for AMSS load failure

2020-05-21 Thread mani
From: Bhaumik Bhatt 

When loading AMSS firmware using BHIe protocol, return -ETIMEDOUT if no
response is received within the timeout or return -EIO in case of a
protocol returned failure or an MHI error state.

Signed-off-by: Bhaumik Bhatt 
Reviewed-by: Jeffrey Hugo 
Reviewed-by: Manivannan Sadhasivam 
Signed-off-by: Manivannan Sadhasivam 
---
 drivers/bus/mhi/core/boot.c | 23 ---
 1 file changed, 12 insertions(+), 11 deletions(-)

diff --git a/drivers/bus/mhi/core/boot.c b/drivers/bus/mhi/core/boot.c
index 17c636b4bc6e..cf6dc5a2361c 100644
--- a/drivers/bus/mhi/core/boot.c
+++ b/drivers/bus/mhi/core/boot.c
@@ -176,6 +176,7 @@ static int mhi_fw_load_amss(struct mhi_controller 
*mhi_cntrl,
void __iomem *base = mhi_cntrl->bhie;
rwlock_t *pm_lock = _cntrl->pm_lock;
u32 tx_status, sequence_id;
+   int ret;
 
read_lock_bh(pm_lock);
if (!MHI_REG_ACCESS_VALID(mhi_cntrl->pm_state)) {
@@ -198,19 +199,19 @@ static int mhi_fw_load_amss(struct mhi_controller 
*mhi_cntrl,
read_unlock_bh(pm_lock);
 
/* Wait for the image download to complete */
-   wait_event_timeout(mhi_cntrl->state_event,
-  MHI_PM_IN_ERROR_STATE(mhi_cntrl->pm_state) ||
-  mhi_read_reg_field(mhi_cntrl, base,
- BHIE_TXVECSTATUS_OFFS,
- BHIE_TXVECSTATUS_STATUS_BMSK,
- BHIE_TXVECSTATUS_STATUS_SHFT,
- _status) || tx_status,
-  msecs_to_jiffies(mhi_cntrl->timeout_ms));
-
-   if (MHI_PM_IN_ERROR_STATE(mhi_cntrl->pm_state))
+   ret = wait_event_timeout(mhi_cntrl->state_event,
+MHI_PM_IN_ERROR_STATE(mhi_cntrl->pm_state) ||
+mhi_read_reg_field(mhi_cntrl, base,
+  BHIE_TXVECSTATUS_OFFS,
+  BHIE_TXVECSTATUS_STATUS_BMSK,
+  BHIE_TXVECSTATUS_STATUS_SHFT,
+  _status) || tx_status,
+msecs_to_jiffies(mhi_cntrl->timeout_ms));
+   if (MHI_PM_IN_ERROR_STATE(mhi_cntrl->pm_state) ||
+   tx_status != BHIE_TXVECSTATUS_STATUS_XFER_COMPL)
return -EIO;
 
-   return (tx_status == BHIE_TXVECSTATUS_STATUS_XFER_COMPL) ? 0 : -EIO;
+   return (!ret) ? -ETIMEDOUT : 0;
 }
 
 static int mhi_fw_load_sbl(struct mhi_controller *mhi_cntrl,
-- 
2.26.GIT



[PATCH 09/14] bus: mhi: core: Remove the system error worker thread

2020-05-21 Thread mani
From: Hemant Kumar 

Remove the system error worker thread and instead have the
execution environment worker handle that transition to serialize
processing and avoid any possible race conditions during
shutdown.

Signed-off-by: Hemant Kumar 
Reviewed-by: Jeffrey Hugo 
Reviewed-by: Manivannan Sadhasivam 
Signed-off-by: Manivannan Sadhasivam 
---
 drivers/bus/mhi/core/init.c |  2 +-
 drivers/bus/mhi/core/internal.h |  3 ++-
 drivers/bus/mhi/core/main.c |  6 +++---
 drivers/bus/mhi/core/pm.c   | 32 ++--
 include/linux/mhi.h |  2 --
 5 files changed, 20 insertions(+), 25 deletions(-)

diff --git a/drivers/bus/mhi/core/init.c b/drivers/bus/mhi/core/init.c
index 6882206ad80e..3a853c5d2103 100644
--- a/drivers/bus/mhi/core/init.c
+++ b/drivers/bus/mhi/core/init.c
@@ -34,6 +34,7 @@ const char * const dev_state_tran_str[DEV_ST_TRANSITION_MAX] 
= {
[DEV_ST_TRANSITION_READY] = "READY",
[DEV_ST_TRANSITION_SBL] = "SBL",
[DEV_ST_TRANSITION_MISSION_MODE] = "MISSION_MODE",
+   [DEV_ST_TRANSITION_SYS_ERR] = "SYS_ERR",
 };
 
 const char * const mhi_state_str[MHI_STATE_MAX] = {
@@ -834,7 +835,6 @@ int mhi_register_controller(struct mhi_controller 
*mhi_cntrl,
spin_lock_init(_cntrl->transition_lock);
spin_lock_init(_cntrl->wlock);
INIT_WORK(_cntrl->st_worker, mhi_pm_st_worker);
-   INIT_WORK(_cntrl->syserr_worker, mhi_pm_sys_err_worker);
init_waitqueue_head(_cntrl->state_event);
 
mhi_cmd = mhi_cntrl->mhi_cmd;
diff --git a/drivers/bus/mhi/core/internal.h b/drivers/bus/mhi/core/internal.h
index 80b32c20149c..f01283b8a451 100644
--- a/drivers/bus/mhi/core/internal.h
+++ b/drivers/bus/mhi/core/internal.h
@@ -386,6 +386,7 @@ enum dev_st_transition {
DEV_ST_TRANSITION_READY,
DEV_ST_TRANSITION_SBL,
DEV_ST_TRANSITION_MISSION_MODE,
+   DEV_ST_TRANSITION_SYS_ERR,
DEV_ST_TRANSITION_MAX,
 };
 
@@ -587,7 +588,7 @@ enum mhi_ee_type mhi_get_exec_env(struct mhi_controller 
*mhi_cntrl);
 int mhi_queue_state_transition(struct mhi_controller *mhi_cntrl,
   enum dev_st_transition state);
 void mhi_pm_st_worker(struct work_struct *work);
-void mhi_pm_sys_err_worker(struct work_struct *work);
+void mhi_pm_sys_err_handler(struct mhi_controller *mhi_cntrl);
 void mhi_fw_load_worker(struct work_struct *work);
 int mhi_ready_state_transition(struct mhi_controller *mhi_cntrl);
 void mhi_ctrl_ev_task(unsigned long data);
diff --git a/drivers/bus/mhi/core/main.c b/drivers/bus/mhi/core/main.c
index a394691d9383..e5f6500e89fd 100644
--- a/drivers/bus/mhi/core/main.c
+++ b/drivers/bus/mhi/core/main.c
@@ -405,7 +405,7 @@ irqreturn_t mhi_intvec_threaded_handler(int irq_number, 
void *dev)
if (MHI_IN_PBL(ee))
mhi_cntrl->status_cb(mhi_cntrl, MHI_CB_FATAL_ERROR);
else
-   schedule_work(_cntrl->syserr_worker);
+   mhi_pm_sys_err_handler(mhi_cntrl);
}
 
 exit_intvec:
@@ -733,7 +733,7 @@ int mhi_process_ctrl_ev_ring(struct mhi_controller 
*mhi_cntrl,
MHI_PM_SYS_ERR_DETECT);
write_unlock_irq(_cntrl->pm_lock);
if (new_state == MHI_PM_SYS_ERR_DETECT)
-   
schedule_work(_cntrl->syserr_worker);
+   mhi_pm_sys_err_handler(mhi_cntrl);
break;
}
default:
@@ -919,7 +919,7 @@ void mhi_ctrl_ev_task(unsigned long data)
}
write_unlock_irq(_cntrl->pm_lock);
if (pm_state == MHI_PM_SYS_ERR_DETECT)
-   schedule_work(_cntrl->syserr_worker);
+   mhi_pm_sys_err_handler(mhi_cntrl);
}
 }
 
diff --git a/drivers/bus/mhi/core/pm.c b/drivers/bus/mhi/core/pm.c
index 6d56441013af..743b3207c390 100644
--- a/drivers/bus/mhi/core/pm.c
+++ b/drivers/bus/mhi/core/pm.c
@@ -449,19 +449,8 @@ static void mhi_pm_disable_transition(struct 
mhi_controller *mhi_cntrl,
to_mhi_pm_state_str(transition_state));
 
/* We must notify MHI control driver so it can clean up first */
-   if (transition_state == MHI_PM_SYS_ERR_PROCESS) {
-   /*
-* If controller supports RDDM, we do not process
-* SYS error state, instead we will jump directly
-* to RDDM state
-*/
-   if (mhi_cntrl->rddm_image) {
-   dev_dbg(dev,
-"Controller supports RDDM, so skip SYS_ERR\n");
-   return;
-   }
+   if (transition_state == MHI_PM_SYS_ERR_PROCESS)
mhi_cntrl->status_cb(mhi_cntrl, MHI_CB_SYS_ERROR);
-   }
 
mutex_lock(_cntrl->pm_mutex);

[PATCH 05/14] bus: mhi: core: Handle firmware load using state worker

2020-05-21 Thread mani
From: Bhaumik Bhatt 

Upon power up, driver queues firmware worker thread if the execution
environment is PBL. Firmware worker is blocked with a timeout until
state worker gets a chance to run and unblock firmware worker. An
endpoint power up failure can be seen if state worker gets a chance to
run after firmware worker has timed out. Remove this dependency and
handle firmware load directly using state worker thread.

Signed-off-by: Bhaumik Bhatt 
Reviewed-by: Jeffrey Hugo 
Reviewed-by: Manivannan Sadhasivam 
Signed-off-by: Manivannan Sadhasivam 
---
 drivers/bus/mhi/core/boot.c | 18 +++---
 drivers/bus/mhi/core/init.c |  1 -
 drivers/bus/mhi/core/internal.h |  1 +
 drivers/bus/mhi/core/pm.c   |  6 +-
 include/linux/mhi.h |  2 --
 5 files changed, 5 insertions(+), 23 deletions(-)

diff --git a/drivers/bus/mhi/core/boot.c b/drivers/bus/mhi/core/boot.c
index ebad5eb48e5a..17c636b4bc6e 100644
--- a/drivers/bus/mhi/core/boot.c
+++ b/drivers/bus/mhi/core/boot.c
@@ -377,30 +377,18 @@ static void mhi_firmware_copy(struct mhi_controller 
*mhi_cntrl,
}
 }
 
-void mhi_fw_load_worker(struct work_struct *work)
+void mhi_fw_load_handler(struct mhi_controller *mhi_cntrl)
 {
-   struct mhi_controller *mhi_cntrl;
const struct firmware *firmware = NULL;
struct image_info *image_info;
-   struct device *dev;
+   struct device *dev = _cntrl->mhi_dev->dev;
const char *fw_name;
void *buf;
dma_addr_t dma_addr;
size_t size;
int ret;
 
-   mhi_cntrl = container_of(work, struct mhi_controller, fw_worker);
-   dev = _cntrl->mhi_dev->dev;
-
-   dev_dbg(dev, "Waiting for device to enter PBL from: %s\n",
-   TO_MHI_EXEC_STR(mhi_cntrl->ee));
-
-   ret = wait_event_timeout(mhi_cntrl->state_event,
-MHI_IN_PBL(mhi_cntrl->ee) ||
-MHI_PM_IN_ERROR_STATE(mhi_cntrl->pm_state),
-msecs_to_jiffies(mhi_cntrl->timeout_ms));
-
-   if (!ret || MHI_PM_IN_ERROR_STATE(mhi_cntrl->pm_state)) {
+   if (MHI_PM_IN_ERROR_STATE(mhi_cntrl->pm_state)) {
dev_err(dev, "Device MHI is not in valid state\n");
return;
}
diff --git a/drivers/bus/mhi/core/init.c b/drivers/bus/mhi/core/init.c
index 1a93d24efffc..6882206ad80e 100644
--- a/drivers/bus/mhi/core/init.c
+++ b/drivers/bus/mhi/core/init.c
@@ -835,7 +835,6 @@ int mhi_register_controller(struct mhi_controller 
*mhi_cntrl,
spin_lock_init(_cntrl->wlock);
INIT_WORK(_cntrl->st_worker, mhi_pm_st_worker);
INIT_WORK(_cntrl->syserr_worker, mhi_pm_sys_err_worker);
-   INIT_WORK(_cntrl->fw_worker, mhi_fw_load_worker);
init_waitqueue_head(_cntrl->state_event);
 
mhi_cmd = mhi_cntrl->mhi_cmd;
diff --git a/drivers/bus/mhi/core/internal.h b/drivers/bus/mhi/core/internal.h
index 40c47f918ca3..0965ca3c9632 100644
--- a/drivers/bus/mhi/core/internal.h
+++ b/drivers/bus/mhi/core/internal.h
@@ -627,6 +627,7 @@ int mhi_init_irq_setup(struct mhi_controller *mhi_cntrl);
 void mhi_deinit_free_irq(struct mhi_controller *mhi_cntrl);
 void mhi_rddm_prepare(struct mhi_controller *mhi_cntrl,
  struct image_info *img_info);
+void mhi_fw_load_handler(struct mhi_controller *mhi_cntrl);
 int mhi_prepare_channel(struct mhi_controller *mhi_cntrl,
struct mhi_chan *mhi_chan);
 int mhi_init_chan_ctxt(struct mhi_controller *mhi_cntrl,
diff --git a/drivers/bus/mhi/core/pm.c b/drivers/bus/mhi/core/pm.c
index dc83d65f7784..6d56441013af 100644
--- a/drivers/bus/mhi/core/pm.c
+++ b/drivers/bus/mhi/core/pm.c
@@ -528,7 +528,6 @@ static void mhi_pm_disable_transition(struct mhi_controller 
*mhi_cntrl,
dev_dbg(dev, "Waiting for all pending threads to complete\n");
wake_up_all(_cntrl->state_event);
flush_work(_cntrl->st_worker);
-   flush_work(_cntrl->fw_worker);
 
dev_dbg(dev, "Reset all active channels and remove MHI devices\n");
device_for_each_child(mhi_cntrl->cntrl_dev, NULL, mhi_destroy_device);
@@ -643,7 +642,7 @@ void mhi_pm_st_worker(struct work_struct *work)
mhi_cntrl->ee = mhi_get_exec_env(mhi_cntrl);
write_unlock_irq(_cntrl->pm_lock);
if (MHI_IN_PBL(mhi_cntrl->ee))
-   wake_up_all(_cntrl->state_event);
+   mhi_fw_load_handler(mhi_cntrl);
break;
case DEV_ST_TRANSITION_SBL:
write_lock_irq(_cntrl->pm_lock);
@@ -833,9 +832,6 @@ int mhi_async_power_up(struct mhi_controller *mhi_cntrl)
next_state = MHI_IN_PBL(current_ee) ?
DEV_ST_TRANSITION_PBL : DEV_ST_TRANSITION_READY;
 
-   if (next_state == DEV_ST_TRANSITION_PBL)
-   schedule_work(_cntrl->fw_worker);
-
mhi_queue_state_transition(mhi_cntrl, 

[PATCH 11/14] bus: mhi: core: Skip handling BHI irq if MHI reg access is not allowed

2020-05-21 Thread mani
From: Hemant Kumar 

Driver continues handling of BHI interrupt even if MHI register access
is not allowed. By doing so it calls the status call back and performs
early notification for the MHI client. This is not needed when MHI
register access is not allowed. Hence skip the handling in this case and
return. Also add debug log to print device state, local EE and device EE
when reg access is valid.

Signed-off-by: Hemant Kumar 
Reviewed-by: Jeffrey Hugo 
Reviewed-by: Manivannan Sadhasivam 
Signed-off-by: Manivannan Sadhasivam 
---
 drivers/bus/mhi/core/main.c | 21 ++---
 1 file changed, 14 insertions(+), 7 deletions(-)

diff --git a/drivers/bus/mhi/core/main.c b/drivers/bus/mhi/core/main.c
index e5f6500e89fd..7429189840b0 100644
--- a/drivers/bus/mhi/core/main.c
+++ b/drivers/bus/mhi/core/main.c
@@ -368,22 +368,29 @@ irqreturn_t mhi_irq_handler(int irq_number, void *dev)
return IRQ_HANDLED;
 }
 
-irqreturn_t mhi_intvec_threaded_handler(int irq_number, void *dev)
+irqreturn_t mhi_intvec_threaded_handler(int irq_number, void *priv)
 {
-   struct mhi_controller *mhi_cntrl = dev;
+   struct mhi_controller *mhi_cntrl = priv;
+   struct device *dev = _cntrl->mhi_dev->dev;
enum mhi_state state = MHI_STATE_MAX;
enum mhi_pm_state pm_state = 0;
enum mhi_ee_type ee = 0;
 
write_lock_irq(_cntrl->pm_lock);
-   if (MHI_REG_ACCESS_VALID(mhi_cntrl->pm_state)) {
-   state = mhi_get_mhi_state(mhi_cntrl);
-   ee = mhi_cntrl->ee;
-   mhi_cntrl->ee = mhi_get_exec_env(mhi_cntrl);
+   if (!MHI_REG_ACCESS_VALID(mhi_cntrl->pm_state)) {
+   write_unlock_irq(_cntrl->pm_lock);
+   goto exit_intvec;
}
 
+   state = mhi_get_mhi_state(mhi_cntrl);
+   ee = mhi_cntrl->ee;
+   mhi_cntrl->ee = mhi_get_exec_env(mhi_cntrl);
+   dev_dbg(dev, "local ee:%s device ee:%s dev_state:%s\n",
+   TO_MHI_EXEC_STR(mhi_cntrl->ee), TO_MHI_EXEC_STR(ee),
+   TO_MHI_STATE_STR(state));
+
if (state == MHI_STATE_SYS_ERR) {
-   dev_dbg(_cntrl->mhi_dev->dev, "System error detected\n");
+   dev_dbg(dev, "System error detected\n");
pm_state = mhi_tryset_pm_state(mhi_cntrl,
   MHI_PM_SYS_ERR_DETECT);
}
-- 
2.26.GIT



[PATCH 03/14] bus: mhi: core: Add range check for channel id received in event ring

2020-05-21 Thread mani
From: Hemant Kumar 

MHI data completion handler function reads channel id from event
ring element. Value is under the control of MHI devices and can be
any value between 0 and 255. In order to prevent out of bound access
add a bound check against the max channel supported by controller
and skip processing of that event ring element.

Signed-off-by: Hemant Kumar 
Signed-off-by: Bhaumik Bhatt 
Reviewed-by: Jeffrey Hugo 
Reviewed-by: Manivannan Sadhasivam 
Signed-off-by: Manivannan Sadhasivam 
---
 drivers/bus/mhi/core/main.c | 40 +++--
 1 file changed, 29 insertions(+), 11 deletions(-)

diff --git a/drivers/bus/mhi/core/main.c b/drivers/bus/mhi/core/main.c
index beac8d33d1cb..64022865cb75 100644
--- a/drivers/bus/mhi/core/main.c
+++ b/drivers/bus/mhi/core/main.c
@@ -774,9 +774,18 @@ int mhi_process_ctrl_ev_ring(struct mhi_controller 
*mhi_cntrl,
}
case MHI_PKT_TYPE_TX_EVENT:
chan = MHI_TRE_GET_EV_CHID(local_rp);
-   mhi_chan = _cntrl->mhi_chan[chan];
-   parse_xfer_event(mhi_cntrl, local_rp, mhi_chan);
-   event_quota--;
+
+   WARN_ON(chan >= mhi_cntrl->max_chan);
+
+   /*
+* Only process the event ring elements whose channel
+* ID is within the maximum supported range.
+*/
+   if (chan < mhi_cntrl->max_chan) {
+   mhi_chan = _cntrl->mhi_chan[chan];
+   parse_xfer_event(mhi_cntrl, local_rp, mhi_chan);
+   event_quota--;
+   }
break;
default:
dev_err(dev, "Unhandled event type: %d\n", type);
@@ -819,14 +828,23 @@ int mhi_process_data_event_ring(struct mhi_controller 
*mhi_cntrl,
enum mhi_pkt_type type = MHI_TRE_GET_EV_TYPE(local_rp);
 
chan = MHI_TRE_GET_EV_CHID(local_rp);
-   mhi_chan = _cntrl->mhi_chan[chan];
-
-   if (likely(type == MHI_PKT_TYPE_TX_EVENT)) {
-   parse_xfer_event(mhi_cntrl, local_rp, mhi_chan);
-   event_quota--;
-   } else if (type == MHI_PKT_TYPE_RSC_TX_EVENT) {
-   parse_rsc_event(mhi_cntrl, local_rp, mhi_chan);
-   event_quota--;
+
+   WARN_ON(chan >= mhi_cntrl->max_chan);
+
+   /*
+* Only process the event ring elements whose channel
+* ID is within the maximum supported range.
+*/
+   if (chan < mhi_cntrl->max_chan) {
+   mhi_chan = _cntrl->mhi_chan[chan];
+
+   if (likely(type == MHI_PKT_TYPE_TX_EVENT)) {
+   parse_xfer_event(mhi_cntrl, local_rp, mhi_chan);
+   event_quota--;
+   } else if (type == MHI_PKT_TYPE_RSC_TX_EVENT) {
+   parse_rsc_event(mhi_cntrl, local_rp, mhi_chan);
+   event_quota--;
+   }
}
 
mhi_recycle_ev_ring_element(mhi_cntrl, ev_ring);
-- 
2.26.GIT



[PATCH 01/14] bus: mhi: core: Refactor mhi queue APIs

2020-05-21 Thread mani
From: Hemant Kumar 

Move all the common code to generate TRE from mhi_queue_buf,
mhi_queue_dma and mhi_queue_skb to mhi_gen_tre. This helps
to centralize the TRE generation code which makes any future
bug fixing easier to manage in these APIs.

Suggested-by: Jeffrey Hugo 
Signed-off-by: Hemant Kumar 
Signed-off-by: Bhaumik Bhatt 
Reviewed-by: Jeffrey Hugo 
Reviewed-by: Manivannan Sadhasivam 
Signed-off-by: Manivannan Sadhasivam 
---
 drivers/bus/mhi/core/internal.h |   3 +-
 drivers/bus/mhi/core/main.c | 107 ++--
 2 files changed, 47 insertions(+), 63 deletions(-)

diff --git a/drivers/bus/mhi/core/internal.h b/drivers/bus/mhi/core/internal.h
index 095d95bc0e37..40c47f918ca3 100644
--- a/drivers/bus/mhi/core/internal.h
+++ b/drivers/bus/mhi/core/internal.h
@@ -670,8 +670,7 @@ irqreturn_t mhi_intvec_threaded_handler(int irq_number, 
void *dev);
 irqreturn_t mhi_intvec_handler(int irq_number, void *dev);
 
 int mhi_gen_tre(struct mhi_controller *mhi_cntrl, struct mhi_chan *mhi_chan,
-   void *buf, void *cb, size_t buf_len, enum mhi_flags flags);
-
+   struct mhi_buf_info *info, enum mhi_flags flags);
 int mhi_map_single_no_bb(struct mhi_controller *mhi_cntrl,
 struct mhi_buf_info *buf_info);
 int mhi_map_single_use_bb(struct mhi_controller *mhi_cntrl,
diff --git a/drivers/bus/mhi/core/main.c b/drivers/bus/mhi/core/main.c
index 0ac064327e35..beac8d33d1cb 100644
--- a/drivers/bus/mhi/core/main.c
+++ b/drivers/bus/mhi/core/main.c
@@ -918,9 +918,7 @@ int mhi_queue_skb(struct mhi_device *mhi_dev, enum 
dma_data_direction dir,
struct mhi_chan *mhi_chan = (dir == DMA_TO_DEVICE) ? mhi_dev->ul_chan :
 mhi_dev->dl_chan;
struct mhi_ring *tre_ring = _chan->tre_ring;
-   struct mhi_ring *buf_ring = _chan->buf_ring;
-   struct mhi_buf_info *buf_info;
-   struct mhi_tre *mhi_tre;
+   struct mhi_buf_info buf_info = { };
int ret;
 
/* If MHI host pre-allocates buffers then client drivers cannot queue */
@@ -945,27 +943,15 @@ int mhi_queue_skb(struct mhi_device *mhi_dev, enum 
dma_data_direction dir,
/* Toggle wake to exit out of M2 */
mhi_cntrl->wake_toggle(mhi_cntrl);
 
-   /* Generate the TRE */
-   buf_info = buf_ring->wp;
-
-   buf_info->v_addr = skb->data;
-   buf_info->cb_buf = skb;
-   buf_info->wp = tre_ring->wp;
-   buf_info->dir = mhi_chan->dir;
-   buf_info->len = len;
-   ret = mhi_cntrl->map_single(mhi_cntrl, buf_info);
-   if (ret)
-   goto map_error;
-
-   mhi_tre = tre_ring->wp;
-
-   mhi_tre->ptr = MHI_TRE_DATA_PTR(buf_info->p_addr);
-   mhi_tre->dword[0] = MHI_TRE_DATA_DWORD0(buf_info->len);
-   mhi_tre->dword[1] = MHI_TRE_DATA_DWORD1(1, 1, 0, 0);
+   buf_info.v_addr = skb->data;
+   buf_info.cb_buf = skb;
+   buf_info.len = len;
 
-   /* increment WP */
-   mhi_add_ring_element(mhi_cntrl, tre_ring);
-   mhi_add_ring_element(mhi_cntrl, buf_ring);
+   ret = mhi_gen_tre(mhi_cntrl, mhi_chan, _info, mflags);
+   if (unlikely(ret)) {
+   read_unlock_bh(_cntrl->pm_lock);
+   return ret;
+   }
 
if (mhi_chan->dir == DMA_TO_DEVICE)
atomic_inc(_cntrl->pending_pkts);
@@ -979,11 +965,6 @@ int mhi_queue_skb(struct mhi_device *mhi_dev, enum 
dma_data_direction dir,
read_unlock_bh(_cntrl->pm_lock);
 
return 0;
-
-map_error:
-   read_unlock_bh(_cntrl->pm_lock);
-
-   return ret;
 }
 EXPORT_SYMBOL_GPL(mhi_queue_skb);
 
@@ -995,9 +976,8 @@ int mhi_queue_dma(struct mhi_device *mhi_dev, enum 
dma_data_direction dir,
 mhi_dev->dl_chan;
struct device *dev = _cntrl->mhi_dev->dev;
struct mhi_ring *tre_ring = _chan->tre_ring;
-   struct mhi_ring *buf_ring = _chan->buf_ring;
-   struct mhi_buf_info *buf_info;
-   struct mhi_tre *mhi_tre;
+   struct mhi_buf_info buf_info = { };
+   int ret;
 
/* If MHI host pre-allocates buffers then client drivers cannot queue */
if (mhi_chan->pre_alloc)
@@ -1024,25 +1004,16 @@ int mhi_queue_dma(struct mhi_device *mhi_dev, enum 
dma_data_direction dir,
/* Toggle wake to exit out of M2 */
mhi_cntrl->wake_toggle(mhi_cntrl);
 
-   /* Generate the TRE */
-   buf_info = buf_ring->wp;
-   WARN_ON(buf_info->used);
-   buf_info->p_addr = mhi_buf->dma_addr;
-   buf_info->pre_mapped = true;
-   buf_info->cb_buf = mhi_buf;
-   buf_info->wp = tre_ring->wp;
-   buf_info->dir = mhi_chan->dir;
-   buf_info->len = len;
-
-   mhi_tre = tre_ring->wp;
-
-   mhi_tre->ptr = MHI_TRE_DATA_PTR(buf_info->p_addr);
-   mhi_tre->dword[0] = MHI_TRE_DATA_DWORD0(buf_info->len);
-   mhi_tre->dword[1] = MHI_TRE_DATA_DWORD1(1, 1, 0, 0);
+   buf_info.p_addr = mhi_buf->dma_addr;
+   

[PATCH 02/14] bus: mhi: core: Cache intmod from mhi event to mhi channel

2020-05-21 Thread mani
From: Hemant Kumar 

Driver is using zero initialized intmod value from mhi channel when
configuring TRE for bei field. This prevents interrupt moderation to
take effect in case it is supported by an event ring. Fix this by
copying intmod value from associated event ring to mhi channel upon
registering mhi controller.

Signed-off-by: Hemant Kumar 
Signed-off-by: Bhaumik Bhatt 
Reviewed-by: Jeffrey Hugo 
Reviewed-by: Manivannan Sadhasivam 
Signed-off-by: Manivannan Sadhasivam 
---
 drivers/bus/mhi/core/init.c | 4 
 1 file changed, 4 insertions(+)

diff --git a/drivers/bus/mhi/core/init.c b/drivers/bus/mhi/core/init.c
index eb2ab058a01d..1a93d24efffc 100644
--- a/drivers/bus/mhi/core/init.c
+++ b/drivers/bus/mhi/core/init.c
@@ -863,6 +863,10 @@ int mhi_register_controller(struct mhi_controller 
*mhi_cntrl,
mutex_init(_chan->mutex);
init_completion(_chan->completion);
rwlock_init(_chan->lock);
+
+   /* used in setting bei field of TRE */
+   mhi_event = _cntrl->mhi_event[mhi_chan->er_index];
+   mhi_chan->intmod = mhi_event->intmod;
}
 
if (mhi_cntrl->bounce_buf) {
-- 
2.26.GIT



[PATCH 00/14] MHI patches for v5.8

2020-05-21 Thread mani
From: Manivannan Sadhasivam 

Hi Greg,

Here is the set of MHI patches for v5.8. Most of the patches are cleanup and
refactoring ones. All of them are reviewed by myself and Jeff and also
verified on x86 and ARM64 architectures for functionality.

Here is the short summary:
-

- The firmware download was handled by a worker thread which gets scheduled
when the device powers up. But this thread waits until the device gets into
PBL state (notified using PM state worker). Sometimes, there might be delay for
the device to enter PBL state and due to that the firmware worker thread will
timeout. So in order to handle this situation effectively, the firmware load
is now directly called by PM state worker instead of scheduling the thread.

- Return proper error codes incase of error while loading the AMSS firmware
through BHIE protocol

- The MHI register space of the device accepts only non-zero values for the
sequence identifier. But there is a possibility that the host might write zero
(due to the use of prandom_u32() API). Hence, a macro is introduced which
provides non-zero sequence identifiers and used them in all places.

- Moved all common TRE generation code to mhi_gen_tre() function

- The MHI host reads channel ID from the event ring element of the client
device. This ID can be of any value between 0 to 255 but the host may not
support all those IDs. So reject the event ring elements whose channel IDs
are not within the limits of the controller.

- Limit the transfer length read from the client device. This value should
be within the size of the MHI host buffer but there are chances this can
be larger.

- Remove the system worker thread for processing the SYS_ERR condition and
instead call the function directly from EE worker. This is done to avoid
any possible race while MHI shutting down.

- Handle MHI power off in the state worker thread as like MISSION_MODE. This
helps in preventing a possible race condition where a power off is issued by
the controller while processing mission mode.

- Skip the handling of BHI interrupt when the register access is not allowed
due to the device in wrong PM state.

- The write_lock of 'mhi_chan->lock' should only protect 'db_mode'. Hence, use
it properly in places where it is protecting other unwanted regions.

- Reset the client device if it is in SYS_ERR state during power up.

-

Please consider merging!

Thanks,
Mani

Bhaumik Bhatt (4):
  bus: mhi: core: Handle firmware load using state worker
  bus: mhi: core: Return appropriate error codes for AMSS load failure
  bus: mhi: core: Improve debug logs for loading firmware
  bus: mhi: core: Ensure non-zero session or sequence ID values are used

Hemant Kumar (9):
  bus: mhi: core: Refactor mhi queue APIs
  bus: mhi: core: Cache intmod from mhi event to mhi channel
  bus: mhi: core: Add range check for channel id received in event ring
  bus: mhi: core: Read transfer length from an event properly
  bus: mhi: core: Remove the system error worker thread
  bus: mhi: core: Handle disable transitions in state worker
  bus: mhi: core: Skip handling BHI irq if MHI reg access is not allowed
  bus: mhi: core: Do not process SYS_ERROR if RDDM is supported
  bus: mhi: core: Handle write lock properly in mhi_pm_m0_transition

Jeffrey Hugo (1):
  bus: mhi: core: Handle syserr during power_up

 drivers/bus/mhi/core/boot.c |  75 ++--
 drivers/bus/mhi/core/init.c |   8 +-
 drivers/bus/mhi/core/internal.h |   9 +-
 drivers/bus/mhi/core/main.c | 194 ++--
 drivers/bus/mhi/core/pm.c   |  86 +-
 include/linux/mhi.h |   4 -
 6 files changed, 217 insertions(+), 159 deletions(-)

-- 
2.26.GIT



[PATCH v2 5/6] dt-bindings: arm: stm32: Document IoT Box compatible

2020-05-03 Thread mani
From: Manivannan Sadhasivam 

Document devicetree compatible of Shiratech IoT Box.

Signed-off-by: Manivannan Sadhasivam 
---
 Documentation/devicetree/bindings/arm/stm32/stm32.yaml | 1 +
 1 file changed, 1 insertion(+)

diff --git a/Documentation/devicetree/bindings/arm/stm32/stm32.yaml 
b/Documentation/devicetree/bindings/arm/stm32/stm32.yaml
index 3849f1d0e03e..790e6dd48e34 100644
--- a/Documentation/devicetree/bindings/arm/stm32/stm32.yaml
+++ b/Documentation/devicetree/bindings/arm/stm32/stm32.yaml
@@ -39,6 +39,7 @@ properties:
   - enum:
   - arrow,stm32mp157a-avenger96 # Avenger96
   - lxa,stm32mp157c-mc1
+  - shiratech,stm32mp157a-iot-box # IoT Box
   - shiratech,stm32mp157a-stinger96 # Stinger96
   - st,stm32mp157c-ed1
   - st,stm32mp157a-dk1
-- 
2.17.1



[PATCH v2 3/6] dt-bindings: arm: stm32: Document Stinger96 compatible

2020-05-03 Thread mani
From: Manivannan Sadhasivam 

Document devicetree compatible of Shiratech Stinger96 board.

Signed-off-by: Manivannan Sadhasivam 
---
 Documentation/devicetree/bindings/arm/stm32/stm32.yaml | 1 +
 1 file changed, 1 insertion(+)

diff --git a/Documentation/devicetree/bindings/arm/stm32/stm32.yaml 
b/Documentation/devicetree/bindings/arm/stm32/stm32.yaml
index 71ea3f04ab9c..3849f1d0e03e 100644
--- a/Documentation/devicetree/bindings/arm/stm32/stm32.yaml
+++ b/Documentation/devicetree/bindings/arm/stm32/stm32.yaml
@@ -39,6 +39,7 @@ properties:
   - enum:
   - arrow,stm32mp157a-avenger96 # Avenger96
   - lxa,stm32mp157c-mc1
+  - shiratech,stm32mp157a-stinger96 # Stinger96
   - st,stm32mp157c-ed1
   - st,stm32mp157a-dk1
   - st,stm32mp157c-dk2
-- 
2.17.1



[PATCH v2 2/6] ARM: dts: stm32: Add missing pinctrl entries for STM32MP15

2020-05-03 Thread mani
From: Manivannan Sadhasivam 

These pinctrl definitions will be used by Stinger96/IoTBox boards
from Shiratech.

Signed-off-by: Manivannan Sadhasivam 
---
 arch/arm/boot/dts/stm32mp15-pinctrl.dtsi | 64 
 1 file changed, 64 insertions(+)

diff --git a/arch/arm/boot/dts/stm32mp15-pinctrl.dtsi 
b/arch/arm/boot/dts/stm32mp15-pinctrl.dtsi
index aeddcaadb829..858c83038e5a 100644
--- a/arch/arm/boot/dts/stm32mp15-pinctrl.dtsi
+++ b/arch/arm/boot/dts/stm32mp15-pinctrl.dtsi
@@ -1519,6 +1519,30 @@
};
};
 
+   usart2_pins_b: usart2-1 {
+   pins1 {
+   pinmux = , /* USART2_TX */
+; /* USART2_RTS */
+   bias-disable;
+   drive-push-pull;
+   slew-rate = <0>;
+   };
+   pins2 {
+   pinmux = , /* USART2_RX */
+; /* 
USART2_CTS_NSS */
+   bias-disable;
+   };
+   };
+
+   usart2_sleep_pins_b: usart2-sleep-1 {
+   pins {
+   pinmux = , /* USART2_TX */
+, /* USART2_RTS 
*/
+, /* USART2_RX */
+; /* 
USART2_CTS_NSS */
+   };
+   };
+
usart3_pins_a: usart3-0 {
pins1 {
pinmux = ; /* USART3_TX */
@@ -1558,6 +1582,19 @@
};
};
 
+   uart4_pins_c: uart4-2 {
+   pins1 {
+   pinmux = ; /* UART4_TX */
+   bias-disable;
+   drive-push-pull;
+   slew-rate = <0>;
+   };
+   pins2 {
+   pinmux = ; /* UART4_RX */
+   bias-disable;
+   };
+   };
+
uart7_pins_a: uart7-0 {
pins1 {
pinmux = ; /* UART4_TX */
@@ -1573,6 +1610,19 @@
};
};
 
+   uart7_pins_b: uart7-1 {
+   pins1 {
+   pinmux = ; /* UART7_TX */
+   bias-disable;
+   drive-push-pull;
+   slew-rate = <0>;
+   };
+   pins2 {
+   pinmux = ; /* UART7_RX */
+   bias-disable;
+   };
+   };
+
uart8_pins_a: uart8-0 {
pins1 {
pinmux = ; /* UART8_TX */
@@ -1647,4 +1697,18 @@
bias-disable;
};
};
+
+   spi4_pins_a: spi4-0 {
+   pins {
+   pinmux = , /* SPI4_SCK */
+;  /* SPI4_MOSI */
+   bias-disable;
+   drive-push-pull;
+   slew-rate = <1>;
+   };
+   pins2 {
+   pinmux = ; /* SPI4_MISO */
+   bias-disable;
+   };
+   };
 };
-- 
2.17.1



[PATCH v2 0/6] Add Stinger96 and IoT Box board support

2020-05-03 Thread mani
From: Manivannan Sadhasivam 

Hello,

This series adds Stinger96 and IoT Box board support. These boards are
based on STM32MP157A SoC, designed and manufactured by Shiratech solutions.

The Stinger96 is a base board (96Boards IoT Extended edition) while IoT Box
adds one mezzanine on top of it and sold as a gateway device.

This series depends on below patchsets already submitted and gone through
reviews:

[PATCH v3 0/3] Add Reset and Wakeup support for CCS811
[PATCH v3 0/2] Add CTS/RTS gpio support to STM32 UART

More information about these boards can be found in below links:

https://www.shiratech-solutions.com/products/stinger96/
https://www.shiratech-solutions.com/products/iot-box/

Thanks,
Mani

Changes in v2:

* Used "stm32" prefix for all DT commits
* Dropped custom sdmmc2 pinctrl node since existing node itself has pullup
  enabled and works fine.

Manivannan Sadhasivam (6):
  dt-bindings: Add vendor prefix for Shiratech Solutions
  ARM: dts: stm32: Add missing pinctrl entries for STM32MP15
  dt-bindings: arm: stm32: Document Stinger96 compatible
  ARM: dts: stm32: Add Stinger96 board support
  dt-bindings: arm: stm32: Document IoT Box compatible
  ARM: dts: stm32: Add IoT Box board support

 .../devicetree/bindings/arm/stm32/stm32.yaml  |   2 +
 .../devicetree/bindings/vendor-prefixes.yaml  |   2 +
 arch/arm/boot/dts/Makefile|   2 +
 arch/arm/boot/dts/stm32mp15-pinctrl.dtsi  |  64 
 arch/arm/boot/dts/stm32mp157a-iot-box.dts |  68 
 arch/arm/boot/dts/stm32mp157a-stinger96.dts   |  12 +
 arch/arm/boot/dts/stm32mp157a-stinger96.dtsi  | 342 ++
 7 files changed, 492 insertions(+)
 create mode 100644 arch/arm/boot/dts/stm32mp157a-iot-box.dts
 create mode 100644 arch/arm/boot/dts/stm32mp157a-stinger96.dts
 create mode 100644 arch/arm/boot/dts/stm32mp157a-stinger96.dtsi

-- 
2.17.1



[PATCH v2 6/6] ARM: dts: stm32: Add IoT Box board support

2020-05-03 Thread mani
From: Manivannan Sadhasivam 

IoT Box is an IoT gateway device based on Stinger96 board powered by
STM32MP1 SoC, designed and manufactured by Shiratech Solutions. This
device makes use of Stinger96 board by having it as a base board with
one additional mezzanine on top.

Following are the features exposed by this device in addition to the
Stinger96 board:

* WiFi/BT
* CCS811 VOC sensor
* 2x Digital microphones IM69D130
* 12x WS2812B LEDs

Following peripherals are tested and known to work:

* WiFi/BT
* CCS811

More information about this device can be found in Shiratech website:
https://www.shiratech-solutions.com/products/iot-box/

Signed-off-by: Manivannan Sadhasivam 
---
 arch/arm/boot/dts/Makefile|  1 +
 arch/arm/boot/dts/stm32mp157a-iot-box.dts | 68 +++
 2 files changed, 69 insertions(+)
 create mode 100644 arch/arm/boot/dts/stm32mp157a-iot-box.dts

diff --git a/arch/arm/boot/dts/Makefile b/arch/arm/boot/dts/Makefile
index 966b81dfffd6..455ec6eb6303 100644
--- a/arch/arm/boot/dts/Makefile
+++ b/arch/arm/boot/dts/Makefile
@@ -1030,6 +1030,7 @@ dtb-$(CONFIG_ARCH_STM32) += \
stm32h743i-disco.dtb \
stm32mp157a-avenger96.dtb \
stm32mp157a-dk1.dtb \
+   stm32mp157a-iot-box.dtb \
stm32mp157a-stinger96.dtb \
stm32mp157c-dhcom-pdk2.dtb \
stm32mp157c-dk2.dtb \
diff --git a/arch/arm/boot/dts/stm32mp157a-iot-box.dts 
b/arch/arm/boot/dts/stm32mp157a-iot-box.dts
new file mode 100644
index ..70f394b4d3c0
--- /dev/null
+++ b/arch/arm/boot/dts/stm32mp157a-iot-box.dts
@@ -0,0 +1,68 @@
+// SPDX-License-Identifier: (GPL-2.0+ OR MIT)
+/*
+ * Copyright (C) 2020 Manivannan Sadhasivam
+ */
+
+/dts-v1/;
+#include "stm32mp157a-stinger96.dtsi"
+
+/ {
+   model = "Shiratech STM32MP157A IoT Box";
+   compatible = "shiratech,stm32mp157a-iot-box", "st,stm32mp157";
+
+   wlan_pwr: regulator-wlan {
+   compatible = "regulator-fixed";
+
+   regulator-name = "wl-reg";
+   regulator-min-microvolt = <330>;
+   regulator-max-microvolt = <330>;
+
+   gpios = < 3 GPIO_ACTIVE_HIGH>;
+   enable-active-high;
+   };
+};
+
+ {
+   ccs811@5b {
+   compatible = "ams,ccs811";
+   reg = <0x5b>;
+   wakeup-gpios = < 12 GPIO_ACTIVE_LOW>;
+   reset-gpios = < 11 GPIO_ACTIVE_LOW>;
+   };
+};
+
+/* WiFi */
+ {
+   pinctrl-names = "default", "opendrain", "sleep";
+   pinctrl-0 = <_b4_pins_a>;
+   pinctrl-1 = <_b4_od_pins_b>;
+   pinctrl-2 = <_b4_sleep_pins_a>;
+   broken-cd;
+   non-removable;
+   st,neg-edge;
+   bus-width = <1>;
+   vmmc-supply = <_pwr>;
+   status = "okay";
+
+   #address-cells = <1>;
+   #size-cells = <0>;
+   brcmf: bcrmf@1 {
+   reg = <1>;
+   compatible = "brcm,bcm4329-fmac";
+   };
+};
+
+/* Bluetooth */
+ {
+   /* Note: HW flow control is broken, hence using custom CTS/RTS gpios */
+   /delete-property/st,hw-flow-ctrl;
+   cts-gpios = < 15 GPIO_ACTIVE_LOW>;
+   rts-gpios = < 0 GPIO_ACTIVE_LOW>;
+   status = "okay";
+
+   bluetooth {
+   shutdown-gpios = < 2 GPIO_ACTIVE_HIGH>;
+   compatible = "brcm,bcm43438-bt";
+   max-speed = <115200>;
+   };
+};
-- 
2.17.1



[PATCH v2 1/6] dt-bindings: Add vendor prefix for Shiratech Solutions

2020-05-03 Thread mani
From: Manivannan Sadhasivam 

This commit adds devicetree vendor prefix for Shiratech solutions,
a SOM/embedded board manufacturing company.

https://www.shiratech-solutions.com/

Signed-off-by: Manivannan Sadhasivam 
---
 Documentation/devicetree/bindings/vendor-prefixes.yaml | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/Documentation/devicetree/bindings/vendor-prefixes.yaml 
b/Documentation/devicetree/bindings/vendor-prefixes.yaml
index e3f1b06d12ae..48ad8f954f33 100644
--- a/Documentation/devicetree/bindings/vendor-prefixes.yaml
+++ b/Documentation/devicetree/bindings/vendor-prefixes.yaml
@@ -902,6 +902,8 @@ patternProperties:
 description: Sharp Corporation
   "^shimafuji,.*":
 description: Shimafuji Electric, Inc.
+  "^shiratech,.*":
+description: Shiratech Solutions
   "^si-en,.*":
 description: Si-En Technology Ltd.
   "^si-linux,.*":
-- 
2.17.1



[PATCH v2 4/6] ARM: dts: stm32: Add Stinger96 board support

2020-05-03 Thread mani
From: Manivannan Sadhasivam 

Stinger96 is a 96Boards IoT Extended edition board designed and
manufactured by Shiratech solutions based on STM32MP1 SoC. Following
are the features of this board:

* 256MB DDR
* 125MB NAND Flash
* Onboard BG96 modem
* 1x uSD
* 2x USB (1 available as external connector and another connected to BG96)
* 1x SPI
* 1x PCM
* 2x UART (apart from serial console)
* 2x I2C (apart from one connected to PMIC)

Following peripherals are tested and known to work:

* BG96 modem
* 1x I2C (LS-I2C0)
* 1x SPI
* 1x UART (LS-UART0)
* USB (Only Gadget mode)
* uSD

More information about this board can be found in Shiratech website:
https://www.shiratech-solutions.com/products/stinger96/

Signed-off-by: Manivannan Sadhasivam 
---
 arch/arm/boot/dts/Makefile   |   1 +
 arch/arm/boot/dts/stm32mp157a-stinger96.dts  |  12 +
 arch/arm/boot/dts/stm32mp157a-stinger96.dtsi | 342 +++
 3 files changed, 355 insertions(+)
 create mode 100644 arch/arm/boot/dts/stm32mp157a-stinger96.dts
 create mode 100644 arch/arm/boot/dts/stm32mp157a-stinger96.dtsi

diff --git a/arch/arm/boot/dts/Makefile b/arch/arm/boot/dts/Makefile
index f43467b02bcd..966b81dfffd6 100644
--- a/arch/arm/boot/dts/Makefile
+++ b/arch/arm/boot/dts/Makefile
@@ -1030,6 +1030,7 @@ dtb-$(CONFIG_ARCH_STM32) += \
stm32h743i-disco.dtb \
stm32mp157a-avenger96.dtb \
stm32mp157a-dk1.dtb \
+   stm32mp157a-stinger96.dtb \
stm32mp157c-dhcom-pdk2.dtb \
stm32mp157c-dk2.dtb \
stm32mp157c-ed1.dtb \
diff --git a/arch/arm/boot/dts/stm32mp157a-stinger96.dts 
b/arch/arm/boot/dts/stm32mp157a-stinger96.dts
new file mode 100644
index ..249a53877512
--- /dev/null
+++ b/arch/arm/boot/dts/stm32mp157a-stinger96.dts
@@ -0,0 +1,12 @@
+// SPDX-License-Identifier: (GPL-2.0+ OR MIT)
+/*
+ * Copyright (C) 2020 Manivannan Sadhasivam
+ */
+
+/dts-v1/;
+#include "stm32mp157a-stinger96.dtsi"
+
+/ {
+   model = "Shiratech STM32MP157A Stinger96 board";
+   compatible = "shiratech,stm32mp157a-stinger96", "st,stm32mp157";
+};
diff --git a/arch/arm/boot/dts/stm32mp157a-stinger96.dtsi 
b/arch/arm/boot/dts/stm32mp157a-stinger96.dtsi
new file mode 100644
index ..58275bcf9e26
--- /dev/null
+++ b/arch/arm/boot/dts/stm32mp157a-stinger96.dtsi
@@ -0,0 +1,342 @@
+// SPDX-License-Identifier: (GPL-2.0+ OR MIT)
+/*
+ * Copyright (C) 2020 Manivannan Sadhasivam
+ */
+
+/dts-v1/;
+
+#include "stm32mp157.dtsi"
+#include "stm32mp15-pinctrl.dtsi"
+#include "stm32mp15xxac-pinctrl.dtsi"
+#include 
+#include 
+
+/ {
+   aliases {
+   mmc0 = 
+   serial0 = 
+   serial1 = 
+   serial2 = 
+   spi0 = 
+   };
+
+   chosen {
+   stdout-path = "serial1:115200n8";
+   };
+
+   memory@c000 {
+   device_type = "memory";
+   reg = <0xc000 0x1000>;
+   };
+
+   led {
+   compatible = "gpio-leds";
+
+   led1 {
+   label = "green:user1";
+   gpios = < 13 GPIO_ACTIVE_HIGH>;
+   linux,default-trigger = "heartbeat";
+   default-state = "off";
+   };
+
+   led2 {
+   label = "green:user2";
+   gpios = < 3 GPIO_ACTIVE_HIGH>;
+   linux,default-trigger = "mmc0";
+   default-state = "off";
+   };
+
+   led3 {
+   label = "green:user3";
+   gpios = < 2 GPIO_ACTIVE_HIGH>;
+   linux,default-trigger = "mmc1";
+   default-state = "off";
+   };
+
+   led4 {
+   label = "green:user4";
+   gpios = < 12 GPIO_ACTIVE_HIGH>;
+   linux,default-trigger = "none";
+   default-state = "off";
+   panic-indicator;
+   };
+   };
+
+   sd_switch: regulator-sd_switch {
+   compatible = "regulator-gpio";
+   regulator-name = "sd_switch";
+   regulator-min-microvolt = <180>;
+   regulator-max-microvolt = <290>;
+   regulator-type = "voltage";
+   regulator-always-on;
+
+   gpios = < 8 GPIO_ACTIVE_HIGH>;
+   gpios-states = <0>;
+   states = <180 0x1>,
+<290 0x0>;
+   };
+};
+
+/* Only headless mode is supported */
+ {
+   status = "disabled";
+};
+
+/* LS-I2C0 */
+ {
+   pinctrl-names = "default";
+   pinctrl-0 = <_pins_a>;
+   i2c-scl-rising-time-ns = <1000>;
+   i2c-scl-falling-time-ns = <300>;
+   status = "okay";
+   /delete-property/dmas;
+   /delete-property/dma-names;
+};
+
+ {
+   pinctrl-names = "default";
+   pinctrl-0 = <_pins_a>;
+   

[PATCH v3 1/2] usb: serial: Add MaxLinear/Exar USB to Serial driver

2020-04-30 Thread mani
From: Manivannan Sadhasivam 

Add support for MaxLinear/Exar USB to Serial converters. This driver
only supports XR21V141X series but it can be extended to other series
from Exar as well in future.

This driver is inspired from the initial one submitted by Patong Yang:

https://patchwork.kernel.org/patch/10543261/

While the initial driver was a custom tty USB driver exposing whole
new serial interface ttyXRUSBn, this version is completely based on USB
serial core thus exposing the interfaces as ttyUSBn. This will avoid
the overhead of exposing a new USB serial interface which the userspace
tools are unaware of.

Signed-off-by: Manivannan Sadhasivam 
---
 drivers/usb/serial/Kconfig |   9 +
 drivers/usb/serial/Makefile|   1 +
 drivers/usb/serial/xr_serial.c | 624 +
 3 files changed, 634 insertions(+)
 create mode 100644 drivers/usb/serial/xr_serial.c

diff --git a/drivers/usb/serial/Kconfig b/drivers/usb/serial/Kconfig
index 25d7e0c36d38..8f6ad9f94735 100644
--- a/drivers/usb/serial/Kconfig
+++ b/drivers/usb/serial/Kconfig
@@ -644,6 +644,15 @@ config USB_SERIAL_UPD78F0730
  To compile this driver as a module, choose M here: the
  module will be called upd78f0730.
 
+config USB_SERIAL_XR
+   tristate "USB MaxLinear/Exar USB to Serial driver"
+   help
+ Say Y here if you want to use MaxLinear/Exar USB to Serial converter
+ devices.
+
+ To compile this driver as a module, choose M here: the
+ module will be called xr_serial.
+
 config USB_SERIAL_DEBUG
tristate "USB Debugging Device"
help
diff --git a/drivers/usb/serial/Makefile b/drivers/usb/serial/Makefile
index 2d491e434f11..4f69c2a3aff3 100644
--- a/drivers/usb/serial/Makefile
+++ b/drivers/usb/serial/Makefile
@@ -62,4 +62,5 @@ obj-$(CONFIG_USB_SERIAL_VISOR)+= 
visor.o
 obj-$(CONFIG_USB_SERIAL_WISHBONE)  += wishbone-serial.o
 obj-$(CONFIG_USB_SERIAL_WHITEHEAT) += whiteheat.o
 obj-$(CONFIG_USB_SERIAL_XIRCOM)+= keyspan_pda.o
+obj-$(CONFIG_USB_SERIAL_XR)+= xr_serial.o
 obj-$(CONFIG_USB_SERIAL_XSENS_MT)  += xsens_mt.o
diff --git a/drivers/usb/serial/xr_serial.c b/drivers/usb/serial/xr_serial.c
new file mode 100644
index ..fdb9ddf8bd95
--- /dev/null
+++ b/drivers/usb/serial/xr_serial.c
@@ -0,0 +1,624 @@
+// SPDX-License-Identifier: GPL-2.0+
+/*
+ * MaxLinear/Exar USB to Serial driver
+ *
+ * Based on initial driver written by Patong Yang 
+ *
+ * Copyright (c) 2020 Manivannan Sadhasivam 
+ */
+
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+
+struct xr_uart_regs {
+   u8 enable;
+   u8 format;
+   u8 flow_ctrl;
+   u8 xon_char;
+   u8 xoff_char;
+   u8 loopback;
+   u8 tx_break;
+   u8 rs485_delay;
+   u8 gpio_mode;
+   u8 gpio_dir;
+   u8 gpio_int_mask;
+   u8 gpio_set;
+   u8 gpio_clr;
+   u8 gpio_status;
+};
+
+struct xr_port_private {
+   const struct xr_uart_regs *regs;
+};
+
+struct xr_txrx_clk_mask {
+   u16 tx;
+   u16 rx0;
+   u16 rx1;
+};
+
+#define XR21V141X_ID   0x1410
+#define XR_INT_OSC_HZ  4800
+
+/* USB Requests */
+#define XR_SET_XR21V141X   0
+#define XR_GET_XR21V141X   1
+
+#define XR21V141X_CLOCK_DIVISOR_0  0x4
+#define XR21V141X_CLOCK_DIVISOR_1  0x5
+#define XR21V141X_CLOCK_DIVISOR_2  0x6
+#define XR21V141X_TX_CLOCK_MASK_0  0x7
+#define XR21V141X_TX_CLOCK_MASK_1  0x8
+#define XR21V141X_RX_CLOCK_MASK_0  0x9
+#define XR21V141X_RX_CLOCK_MASK_1  0xa
+
+/* XR21V141X register blocks */
+#define XR21V141X_UART_REG_BLOCK   0
+#define XR21V141X_URM_REG_BLOCK4
+#define XR21V141X_UART_CUSTOM_BLOCK0x66
+
+/* XR21V141X UART Manager Registers */
+#define XR21V141X_URM_FIFO_ENABLE_REG  0x10
+#define XR21V141X_URM_ENABLE_TX_FIFO   0x1
+#define XR21V141X_URM_ENABLE_RX_FIFO   0x2
+
+#define XR21V141X_URM_RX_FIFO_RESET0x18
+#define XR21V141X_URM_TX_FIFO_RESET0x1c
+
+#define UART_ENABLE_TX 0x1
+#define UART_ENABLE_RX 0x2
+
+#define UART_MODE_RI   BIT(0)
+#define UART_MODE_CD   BIT(1)
+#define UART_MODE_DSR  BIT(2)
+#define UART_MODE_DTR  BIT(3)
+#define UART_MODE_CTS  BIT(4)
+#define UART_MODE_RTS  BIT(5)
+
+#define UART_BREAK_ON  0xff
+#define UART_BREAK_OFF 0
+
+#define UART_DATA_MASK GENMASK(3, 0)
+#define UART_DATA_70x7
+#define UART_DATA_80x8
+
+#define UART_PARITY_MASK   GENMASK(6, 4)
+#define UART_PARITY_SHIFT  0x4
+#define UART_PARITY_NONE   0x0
+#define UART_PARITY_ODD0x1
+#define UART_PARITY_EVEN   0x2
+#define UART_PARITY_MARK  

[PATCH v3 0/2] Add support for MaxLinear/Exar USB to serial converters

2020-04-30 Thread mani
From: Manivannan Sadhasivam 

Hello,

This series adds support for MaxLinear/Exar USB to serial converters.
This driver only supports XR21V141X series but it can easily be extended
to other series in future.

This driver is inspired from the initial one submitted by Patong Yang:

https://patchwork.kernel.org/patch/10543261/

While the initial driver was a custom tty USB driver exposing whole
new serial interface ttyXRUSBn, this version is completely based on USB
serial core thus exposing the interfaces as ttyUSBn. This will avoid
the overhead of exposing a new USB serial interface which the userspace
tools are unaware of.

This series has been tested with Hikey970 board hosting XR21V141X chip.

Thanks,
Mani

Changes in v3:

* Dropped the check for PID and also the reg_width property.

Changes in v2:

* Dropped the code related to handling variable register size. It's all u8 now.
* Dropped the header file and moved the contents to driver itself.
* Added Linus's reviewed-by tag for gpiochip patch.
* Added PID to gpiochip label
* Dropped gpiochip for interface 0

Manivannan Sadhasivam (2):
  usb: serial: Add MaxLinear/Exar USB to Serial driver
  usb: serial: xr_serial: Add gpiochip support

 drivers/usb/serial/Kconfig |   9 +
 drivers/usb/serial/Makefile|   1 +
 drivers/usb/serial/xr_serial.c | 821 +
 3 files changed, 831 insertions(+)
 create mode 100644 drivers/usb/serial/xr_serial.c

-- 
2.17.1



[PATCH v3 2/2] usb: serial: xr_serial: Add gpiochip support

2020-04-30 Thread mani
From: Manivannan Sadhasivam 

Add gpiochip support for Maxlinear/Exar USB to serial converter
for controlling the available gpios.

Cc: Linus Walleij 
Cc: linux-g...@vger.kernel.org
Reviewed-by: Linus Walleij 
Signed-off-by: Manivannan Sadhasivam 
---
 drivers/usb/serial/xr_serial.c | 199 -
 1 file changed, 198 insertions(+), 1 deletion(-)

diff --git a/drivers/usb/serial/xr_serial.c b/drivers/usb/serial/xr_serial.c
index fdb9ddf8bd95..255a30540b52 100644
--- a/drivers/usb/serial/xr_serial.c
+++ b/drivers/usb/serial/xr_serial.c
@@ -7,6 +7,7 @@
  * Copyright (c) 2020 Manivannan Sadhasivam 
  */
 
+#include 
 #include 
 #include 
 #include 
@@ -32,6 +33,11 @@ struct xr_uart_regs {
 };
 
 struct xr_port_private {
+#ifdef CONFIG_GPIOLIB
+   struct gpio_chip gc;
+   bool gpio_registered;
+   u8 gpio_altfunc;
+#endif
const struct xr_uart_regs *regs;
 };
 
@@ -562,6 +568,196 @@ static void xr_break_ctl(struct tty_struct *tty, int 
break_state)
   state);
 }
 
+#ifdef CONFIG_GPIOLIB
+
+static int xr_gpio_request(struct gpio_chip *gc, unsigned int offset)
+{
+   struct usb_serial_port *port = gpiochip_get_data(gc);
+   struct xr_port_private *port_priv = usb_get_serial_port_data(port);
+
+   /* Check if the requested GPIO is occupied */
+   if (port_priv->gpio_altfunc & BIT(offset))
+   return -ENODEV;
+
+   return 0;
+}
+
+static int xr_gpio_get(struct gpio_chip *gc, unsigned int gpio)
+{
+   struct usb_serial_port *port = gpiochip_get_data(gc);
+   struct xr_port_private *port_priv = usb_get_serial_port_data(port);
+   int ret;
+   u8 gpio_status;
+
+   ret = xr_get_reg(port, XR21V141X_UART_REG_BLOCK,
+port_priv->regs->gpio_status, _status);
+   if (ret)
+   return ret;
+
+   return !!(gpio_status & BIT(gpio));
+}
+
+static void xr_gpio_set(struct gpio_chip *gc, unsigned int gpio, int val)
+{
+   struct usb_serial_port *port = gpiochip_get_data(gc);
+   struct xr_port_private *port_priv = usb_get_serial_port_data(port);
+
+   if (val)
+   xr_set_reg(port, XR21V141X_UART_REG_BLOCK,
+  port_priv->regs->gpio_set, BIT(gpio));
+   else
+   xr_set_reg(port, XR21V141X_UART_REG_BLOCK,
+  port_priv->regs->gpio_clr, BIT(gpio));
+}
+
+static int xr_gpio_direction_get(struct gpio_chip *gc, unsigned int gpio)
+{
+   struct usb_serial_port *port = gpiochip_get_data(gc);
+   struct xr_port_private *port_priv = usb_get_serial_port_data(port);
+   int ret;
+   u8 gpio_dir;
+
+   ret = xr_get_reg(port, XR21V141X_UART_REG_BLOCK,
+port_priv->regs->gpio_dir, _dir);
+   if (ret)
+   return ret;
+
+   /* Logic 0 = input and Logic 1 = output */
+   return !(gpio_dir & BIT(gpio));
+}
+
+static int xr_gpio_direction_input(struct gpio_chip *gc, unsigned int gpio)
+{
+   struct usb_serial_port *port = gpiochip_get_data(gc);
+   struct xr_port_private *port_priv = usb_get_serial_port_data(port);
+   int ret;
+   u8 gpio_dir;
+
+   ret = xr_get_reg(port, XR21V141X_UART_REG_BLOCK,
+port_priv->regs->gpio_dir, _dir);
+   if (ret)
+   return ret;
+
+   gpio_dir &= ~BIT(gpio);
+
+   return xr_set_reg(port, XR21V141X_UART_REG_BLOCK,
+ port_priv->regs->gpio_dir, gpio_dir);
+}
+
+static int xr_gpio_direction_output(struct gpio_chip *gc, unsigned int gpio,
+   int val)
+{
+   struct usb_serial_port *port = gpiochip_get_data(gc);
+   struct xr_port_private *port_priv = usb_get_serial_port_data(port);
+   int ret;
+   u8 gpio_dir;
+
+   ret = xr_get_reg(port, XR21V141X_UART_REG_BLOCK,
+port_priv->regs->gpio_dir, _dir);
+   if (ret)
+   return ret;
+
+   gpio_dir |= BIT(gpio);
+
+   ret = xr_set_reg(port, XR21V141X_UART_REG_BLOCK,
+port_priv->regs->gpio_dir, gpio_dir);
+   if (ret)
+   return ret;
+
+   xr_gpio_set(gc, gpio, val);
+
+   return 0;
+}
+
+static int xr21v141x_gpio_init(struct usb_serial_port *port)
+{
+   struct xr_port_private *port_priv = usb_get_serial_port_data(port);
+   int ret;
+   u8 gpio_mode;
+
+   port_priv->gc.ngpio = 6;
+
+   ret = xr_get_reg(port, XR21V141X_UART_REG_BLOCK,
+port_priv->regs->gpio_mode, _mode);
+   if (ret)
+   return ret;
+
+   /* Mark all pins which are not in GPIO mode */
+   if (gpio_mode & UART_MODE_RTS_CTS)
+   port_priv->gpio_altfunc |= (BIT(4) | BIT(5));
+   else if (gpio_mode & UART_MODE_DTR_DSR)
+   port_priv->gpio_altfunc |= (BIT(2) | BIT(3));
+   else if (gpio_mode & UART_MODE_RS485)
+   port_priv->gpio_altfunc |= BIT(5);
+   else if 

[PATCH v2 0/2] Add support for MaxLinear/Exar USB to serial converters

2020-04-29 Thread mani
From: Manivannan Sadhasivam 

Hello,

This series adds support for MaxLinear/Exar USB to serial converters.
This driver only supports XR21V141X series but provision has been made
to support other series in future.

This driver is inspired from the initial one submitted by Patong Yang:

https://patchwork.kernel.org/patch/10543261/

While the initial driver was a custom tty USB driver exposing whole
new serial interface ttyXRUSBn, this version is completely based on USB
serial core thus exposing the interfaces as ttyUSBn. This will avoid
the overhead of exposing a new USB serial interface which the userspace
tools are unaware of.

This series has been tested with Hikey970 board hosting XR21V141X chip.

Thanks,
Mani

Changes in v2:

* Dropped the code related to handling variable register size. It's all u8 now.
* Dropped the header file and moved the contents to driver itself.
* Added Linus's reviewed-by tag for gpiochip patch.
* Added PID to gpiochip label
* Dropped gpiochip for interface 0

Manivannan Sadhasivam (2):
  usb: serial: Add MaxLinear/Exar USB to Serial driver
  usb: serial: xr_serial: Add gpiochip support

 drivers/usb/serial/Kconfig |   9 +
 drivers/usb/serial/Makefile|   1 +
 drivers/usb/serial/xr_serial.c | 833 +
 3 files changed, 843 insertions(+)
 create mode 100644 drivers/usb/serial/xr_serial.c

-- 
2.17.1



[PATCH v2 2/2] usb: serial: xr_serial: Add gpiochip support

2020-04-29 Thread mani
From: Manivannan Sadhasivam 

Add gpiochip support for Maxlinear/Exar USB to serial converter
for controlling the available gpios.

Cc: Linus Walleij 
Cc: linux-g...@vger.kernel.org
Reviewed-by: Linus Walleij 
Signed-off-by: Manivannan Sadhasivam 
---
 drivers/usb/serial/xr_serial.c | 197 -
 1 file changed, 196 insertions(+), 1 deletion(-)

diff --git a/drivers/usb/serial/xr_serial.c b/drivers/usb/serial/xr_serial.c
index d607906e46ad..fa99e6bfffa2 100644
--- a/drivers/usb/serial/xr_serial.c
+++ b/drivers/usb/serial/xr_serial.c
@@ -7,6 +7,7 @@
  * Copyright (c) 2020 Manivannan Sadhasivam 
  */
 
+#include 
 #include 
 #include 
 #include 
@@ -32,6 +33,11 @@ struct xr_uart_regs {
 };
 
 struct xr_port_private {
+#ifdef CONFIG_GPIOLIB
+   struct gpio_chip gc;
+   bool gpio_registered;
+   u8 gpio_altfunc;
+#endif
const struct xr_uart_regs *regs;
u16 idProduct;
u8 reg_width;
@@ -570,6 +576,194 @@ static void xr_break_ctl(struct tty_struct *tty, int 
break_state)
   state);
 }
 
+#ifdef CONFIG_GPIOLIB
+
+static int xr_gpio_request(struct gpio_chip *gc, unsigned int offset)
+{
+   struct usb_serial_port *port = gpiochip_get_data(gc);
+   struct xr_port_private *port_priv = usb_get_serial_port_data(port);
+
+   /* Check if the requested GPIO is occupied */
+   if (port_priv->gpio_altfunc & BIT(offset))
+   return -ENODEV;
+
+   return 0;
+}
+
+static int xr_gpio_get(struct gpio_chip *gc, unsigned int gpio)
+{
+   struct usb_serial_port *port = gpiochip_get_data(gc);
+   struct xr_port_private *port_priv = usb_get_serial_port_data(port);
+   int ret;
+   u8 gpio_status;
+
+   ret = xr_get_reg(port, XR21V141X_UART_REG_BLOCK,
+port_priv->regs->gpio_status, _status);
+   if (ret)
+   return ret;
+
+   return !!(gpio_status & BIT(gpio));
+}
+
+static void xr_gpio_set(struct gpio_chip *gc, unsigned int gpio, int val)
+{
+   struct usb_serial_port *port = gpiochip_get_data(gc);
+   struct xr_port_private *port_priv = usb_get_serial_port_data(port);
+
+   if (val)
+   xr_set_reg(port, XR21V141X_UART_REG_BLOCK,
+  port_priv->regs->gpio_set, BIT(gpio));
+   else
+   xr_set_reg(port, XR21V141X_UART_REG_BLOCK,
+  port_priv->regs->gpio_clr, BIT(gpio));
+}
+
+static int xr_gpio_direction_get(struct gpio_chip *gc, unsigned int gpio)
+{
+   struct usb_serial_port *port = gpiochip_get_data(gc);
+   struct xr_port_private *port_priv = usb_get_serial_port_data(port);
+   int ret;
+   u8 gpio_dir;
+
+   ret = xr_get_reg(port, XR21V141X_UART_REG_BLOCK,
+port_priv->regs->gpio_dir, _dir);
+   if (ret)
+   return ret;
+
+   /* Logic 0 = input and Logic 1 = output */
+   return !(gpio_dir & BIT(gpio));
+}
+
+static int xr_gpio_direction_input(struct gpio_chip *gc, unsigned int gpio)
+{
+   struct usb_serial_port *port = gpiochip_get_data(gc);
+   struct xr_port_private *port_priv = usb_get_serial_port_data(port);
+   int ret;
+   u8 gpio_dir;
+
+   ret = xr_get_reg(port, XR21V141X_UART_REG_BLOCK,
+port_priv->regs->gpio_dir, _dir);
+   if (ret)
+   return ret;
+
+   gpio_dir &= ~BIT(gpio);
+
+   return xr_set_reg(port, XR21V141X_UART_REG_BLOCK,
+ port_priv->regs->gpio_dir, gpio_dir);
+}
+
+static int xr_gpio_direction_output(struct gpio_chip *gc, unsigned int gpio,
+   int val)
+{
+   struct usb_serial_port *port = gpiochip_get_data(gc);
+   struct xr_port_private *port_priv = usb_get_serial_port_data(port);
+   int ret;
+   u8 gpio_dir;
+
+   ret = xr_get_reg(port, XR21V141X_UART_REG_BLOCK,
+port_priv->regs->gpio_dir, _dir);
+   if (ret)
+   return ret;
+
+   gpio_dir |= BIT(gpio);
+
+   ret = xr_set_reg(port, XR21V141X_UART_REG_BLOCK,
+port_priv->regs->gpio_dir, gpio_dir);
+   if (ret)
+   return ret;
+
+   xr_gpio_set(gc, gpio, val);
+
+   return 0;
+}
+
+static int xr21v141x_gpio_init(struct usb_serial_port *port)
+{
+   struct xr_port_private *port_priv = usb_get_serial_port_data(port);
+   int ret;
+   u8 gpio_mode;
+
+   port_priv->gc.ngpio = 6;
+
+   ret = xr_get_reg(port, XR21V141X_UART_REG_BLOCK,
+port_priv->regs->gpio_mode, _mode);
+   if (ret)
+   return ret;
+
+   /* Mark all pins which are not in GPIO mode */
+   if (gpio_mode & UART_MODE_RTS_CTS)
+   port_priv->gpio_altfunc |= (BIT(4) | BIT(5));
+   else if (gpio_mode & UART_MODE_DTR_DSR)
+   port_priv->gpio_altfunc |= (BIT(2) | BIT(3));
+   else if (gpio_mode & UART_MODE_RS485)
+   

[PATCH v2 1/2] usb: serial: Add MaxLinear/Exar USB to Serial driver

2020-04-29 Thread mani
From: Manivannan Sadhasivam 

Add support for MaxLinear/Exar USB to Serial converters. This driver
only supports XR21V141X series but provision has been made to support
other series in future.

This driver is inspired from the initial one submitted by Patong Yang:

https://patchwork.kernel.org/patch/10543261/

While the initial driver was a custom tty USB driver exposing whole
new serial interface ttyXRUSBn, this version is completely based on USB
serial core thus exposing the interfaces as ttyUSBn. This will avoid
the overhead of exposing a new USB serial interface which the userspace
tools are unaware of.

Signed-off-by: Manivannan Sadhasivam 
---
 drivers/usb/serial/Kconfig |   9 +
 drivers/usb/serial/Makefile|   1 +
 drivers/usb/serial/xr_serial.c | 638 +
 3 files changed, 648 insertions(+)
 create mode 100644 drivers/usb/serial/xr_serial.c

diff --git a/drivers/usb/serial/Kconfig b/drivers/usb/serial/Kconfig
index 25d7e0c36d38..8f6ad9f94735 100644
--- a/drivers/usb/serial/Kconfig
+++ b/drivers/usb/serial/Kconfig
@@ -644,6 +644,15 @@ config USB_SERIAL_UPD78F0730
  To compile this driver as a module, choose M here: the
  module will be called upd78f0730.
 
+config USB_SERIAL_XR
+   tristate "USB MaxLinear/Exar USB to Serial driver"
+   help
+ Say Y here if you want to use MaxLinear/Exar USB to Serial converter
+ devices.
+
+ To compile this driver as a module, choose M here: the
+ module will be called xr_serial.
+
 config USB_SERIAL_DEBUG
tristate "USB Debugging Device"
help
diff --git a/drivers/usb/serial/Makefile b/drivers/usb/serial/Makefile
index 2d491e434f11..4f69c2a3aff3 100644
--- a/drivers/usb/serial/Makefile
+++ b/drivers/usb/serial/Makefile
@@ -62,4 +62,5 @@ obj-$(CONFIG_USB_SERIAL_VISOR)+= 
visor.o
 obj-$(CONFIG_USB_SERIAL_WISHBONE)  += wishbone-serial.o
 obj-$(CONFIG_USB_SERIAL_WHITEHEAT) += whiteheat.o
 obj-$(CONFIG_USB_SERIAL_XIRCOM)+= keyspan_pda.o
+obj-$(CONFIG_USB_SERIAL_XR)+= xr_serial.o
 obj-$(CONFIG_USB_SERIAL_XSENS_MT)  += xsens_mt.o
diff --git a/drivers/usb/serial/xr_serial.c b/drivers/usb/serial/xr_serial.c
new file mode 100644
index ..d607906e46ad
--- /dev/null
+++ b/drivers/usb/serial/xr_serial.c
@@ -0,0 +1,638 @@
+// SPDX-License-Identifier: GPL-2.0+
+/*
+ * MaxLinear/Exar USB to Serial driver
+ *
+ * Based on initial driver written by Patong Yang 
+ *
+ * Copyright (c) 2020 Manivannan Sadhasivam 
+ */
+
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+
+struct xr_uart_regs {
+   u8 enable;
+   u8 format;
+   u8 flow_ctrl;
+   u8 xon_char;
+   u8 xoff_char;
+   u8 loopback;
+   u8 tx_break;
+   u8 rs485_delay;
+   u8 gpio_mode;
+   u8 gpio_dir;
+   u8 gpio_int_mask;
+   u8 gpio_set;
+   u8 gpio_clr;
+   u8 gpio_status;
+};
+
+struct xr_port_private {
+   const struct xr_uart_regs *regs;
+   u16 idProduct;
+   u8 reg_width;
+};
+
+struct xr_txrx_clk_mask {
+   u16 tx;
+   u16 rx0;
+   u16 rx1;
+};
+
+#define XR21V141X_ID   0x1410
+#define XR_INT_OSC_HZ  4800
+
+/* USB Requests */
+#define XR_SET_XR21V141X   0
+#define XR_GET_XR21V141X   1
+
+#define XR21V141X_CLOCK_DIVISOR_0  0x4
+#define XR21V141X_CLOCK_DIVISOR_1  0x5
+#define XR21V141X_CLOCK_DIVISOR_2  0x6
+#define XR21V141X_TX_CLOCK_MASK_0  0x7
+#define XR21V141X_TX_CLOCK_MASK_1  0x8
+#define XR21V141X_RX_CLOCK_MASK_0  0x9
+#define XR21V141X_RX_CLOCK_MASK_1  0xa
+
+/* XR21V141X register blocks */
+#define XR21V141X_UART_REG_BLOCK   0
+#define XR21V141X_URM_REG_BLOCK4
+#define XR21V141X_UART_CUSTOM_BLOCK0x66
+
+/* XR21V141X UART Manager Registers */
+#define XR21V141X_URM_FIFO_ENABLE_REG  0x10
+#define XR21V141X_URM_ENABLE_TX_FIFO   0x1
+#define XR21V141X_URM_ENABLE_RX_FIFO   0x2
+
+#define XR21V141X_URM_RX_FIFO_RESET0x18
+#define XR21V141X_URM_TX_FIFO_RESET0x1c
+
+#define UART_ENABLE_TX 0x1
+#define UART_ENABLE_RX 0x2
+
+#define UART_MODE_RI   BIT(0)
+#define UART_MODE_CD   BIT(1)
+#define UART_MODE_DSR  BIT(2)
+#define UART_MODE_DTR  BIT(3)
+#define UART_MODE_CTS  BIT(4)
+#define UART_MODE_RTS  BIT(5)
+
+#define UART_BREAK_ON  0xff
+#define UART_BREAK_OFF 0
+
+#define UART_DATA_MASK GENMASK(3, 0)
+#define UART_DATA_70x7
+#define UART_DATA_80x8
+
+#define UART_PARITY_MASK   GENMASK(6, 4)
+#define UART_PARITY_SHIFT  0x4
+#define UART_PARITY_NONE   0x0
+#define UART_PARITY_ODD0x1
+#define UART_PARITY_EVEN  

[PATCH 2/2] usb: serial: xr_serial: Add gpiochip support

2020-04-28 Thread mani
From: Manivannan Sadhasivam 

Add gpiochip support for Maxlinear/Exar USB to serial converter
for controlling the available gpios.

Cc: Linus Walleij 
Cc: linux-g...@vger.kernel.org
Signed-off-by: Manivannan Sadhasivam 
---
 drivers/usb/serial/xr_serial.c | 186 -
 drivers/usb/serial/xr_serial.h |   7 ++
 2 files changed, 192 insertions(+), 1 deletion(-)

diff --git a/drivers/usb/serial/xr_serial.c b/drivers/usb/serial/xr_serial.c
index ea4a0b167d3f..d86fd40839f8 100644
--- a/drivers/usb/serial/xr_serial.c
+++ b/drivers/usb/serial/xr_serial.c
@@ -476,6 +476,189 @@ static void xr_break_ctl(struct tty_struct *tty, int 
break_state)
   state);
 }
 
+#ifdef CONFIG_GPIOLIB
+
+static int xr_gpio_request(struct gpio_chip *gc, unsigned int offset)
+{
+   struct usb_serial_port *port = gpiochip_get_data(gc);
+   struct xr_port_private *port_priv = usb_get_serial_port_data(port);
+
+   /* Check if the requested GPIO is occupied */
+   if (port_priv->gpio_altfunc & BIT(offset))
+   return -ENODEV;
+
+   return 0;
+}
+
+static int xr_gpio_get(struct gpio_chip *gc, unsigned int gpio)
+{
+   struct usb_serial_port *port = gpiochip_get_data(gc);
+   struct xr_port_private *port_priv = usb_get_serial_port_data(port);
+   int ret;
+   u16 gpio_status;
+
+   ret = xr_get_reg(port, XR21V141X_UART_REG_BLOCK,
+port_priv->regs->gpio_status, _status);
+   if (ret)
+   return ret;
+
+   return !!(gpio_status & BIT(gpio));
+}
+
+static void xr_gpio_set(struct gpio_chip *gc, unsigned int gpio, int val)
+{
+   struct usb_serial_port *port = gpiochip_get_data(gc);
+   struct xr_port_private *port_priv = usb_get_serial_port_data(port);
+
+   if (val)
+   xr_set_reg(port, XR21V141X_UART_REG_BLOCK,
+  port_priv->regs->gpio_set, BIT(gpio));
+   else
+   xr_set_reg(port, XR21V141X_UART_REG_BLOCK,
+  port_priv->regs->gpio_clr, BIT(gpio));
+}
+
+static int xr_gpio_direction_get(struct gpio_chip *gc, unsigned int gpio)
+{
+   struct usb_serial_port *port = gpiochip_get_data(gc);
+   struct xr_port_private *port_priv = usb_get_serial_port_data(port);
+   int ret;
+   u16 gpio_dir;
+
+   ret = xr_get_reg(port, XR21V141X_UART_REG_BLOCK,
+port_priv->regs->gpio_dir, _dir);
+   if (ret)
+   return ret;
+
+   /* Logic 0 = input and Logic 1 = output */
+   return !(gpio_dir & BIT(gpio));
+}
+
+static int xr_gpio_direction_input(struct gpio_chip *gc, unsigned int gpio)
+{
+   struct usb_serial_port *port = gpiochip_get_data(gc);
+   struct xr_port_private *port_priv = usb_get_serial_port_data(port);
+   int ret;
+   u16 gpio_dir;
+
+   ret = xr_get_reg(port, XR21V141X_UART_REG_BLOCK,
+port_priv->regs->gpio_dir, _dir);
+   if (ret)
+   return ret;
+
+   gpio_dir &= ~BIT(gpio);
+
+   return xr_set_reg(port, XR21V141X_UART_REG_BLOCK,
+ port_priv->regs->gpio_dir, gpio_dir);
+}
+
+static int xr_gpio_direction_output(struct gpio_chip *gc, unsigned int gpio,
+   int val)
+{
+   struct usb_serial_port *port = gpiochip_get_data(gc);
+   struct xr_port_private *port_priv = usb_get_serial_port_data(port);
+   int ret;
+   u16 gpio_dir;
+
+   ret = xr_get_reg(port, XR21V141X_UART_REG_BLOCK,
+port_priv->regs->gpio_dir, _dir);
+   if (ret)
+   return ret;
+
+   gpio_dir |= BIT(gpio);
+
+   ret = xr_set_reg(port, XR21V141X_UART_REG_BLOCK,
+port_priv->regs->gpio_dir, gpio_dir);
+   if (ret)
+   return ret;
+
+   xr_gpio_set(gc, gpio, val);
+
+   return 0;
+}
+
+static int xr21v141x_gpio_init(struct usb_serial_port *port)
+{
+   struct xr_port_private *port_priv = usb_get_serial_port_data(port);
+   int ret;
+   u16 gpio_mode;
+
+   port_priv->gc.ngpio = 6;
+
+   ret = xr_get_reg(port, XR21V141X_UART_REG_BLOCK,
+port_priv->regs->gpio_mode, _mode);
+   if (ret)
+   return ret;
+
+   /* Mark all pins which are not in GPIO mode */
+   if (gpio_mode & UART_MODE_RTS_CTS)
+   port_priv->gpio_altfunc |= (BIT(4) | BIT(5));
+   else if (gpio_mode & UART_MODE_DTR_DSR)
+   port_priv->gpio_altfunc |= (BIT(2) | BIT(3));
+   else if (gpio_mode & UART_MODE_RS485)
+   port_priv->gpio_altfunc |= BIT(5);
+   else if (gpio_mode & UART_MODE_RS485_ADDR)
+   port_priv->gpio_altfunc |= BIT(5);
+   else
+   port_priv->gpio_altfunc = 0; /* All GPIOs are available */
+
+   return ret;
+}
+
+static int xr_gpio_init(struct usb_serial_port *port)
+{
+   struct xr_port_private *port_priv = 

[PATCH 0/2] Add support for MaxLinear/Exar USB to serial converters

2020-04-28 Thread mani
From: Manivannan Sadhasivam 

Hello,

This series adds support for MaxLinear/Exar USB to serial converters.
This driver only supports XR21V141X series but provision has been made
to support other series in future.

This driver is inspired from the initial one submitted by Patong Yang:

https://patchwork.kernel.org/patch/10543261/

While the initial driver was a custom tty USB driver exposing whole
new serial interface ttyXRUSBn, this version is completely based on USB
serial core thus exposing the interfaces as ttyUSBn. This will avoid
the overhead of exposing a new USB serial interface which the userspace
tools are unaware of.

This series has been tested on Hikey970 board hosting XR21V141X chip.

Thanks,
Mani

Manivannan Sadhasivam (2):
  usb: serial: Add MaxLinear/Exar USB to Serial driver
  usb: serial: xr_serial: Add gpiochip support

 drivers/usb/serial/Kconfig |   9 +
 drivers/usb/serial/Makefile|   1 +
 drivers/usb/serial/xr_serial.c | 728 +
 drivers/usb/serial/xr_serial.h | 110 +
 4 files changed, 848 insertions(+)
 create mode 100644 drivers/usb/serial/xr_serial.c
 create mode 100644 drivers/usb/serial/xr_serial.h

-- 
2.17.1



[PATCH 1/2] usb: serial: Add MaxLinear/Exar USB to Serial driver

2020-04-28 Thread mani
From: Manivannan Sadhasivam 

Add support for MaxLinear/Exar USB to Serial converters. This driver
only supports XR21V141X series but provision has been made to support
other series in future.

This driver is inspired from the initial one submitted by Patong Yang:

https://patchwork.kernel.org/patch/10543261/

While the initial driver was a custom tty USB driver exposing whole
new serial interface ttyXRUSBn, this version is completely based on USB
serial core thus exposing the interfaces as ttyUSBn. This will avoid
the overhead of exposing a new USB serial interface which the userspace
tools are unaware of.

Signed-off-by: Manivannan Sadhasivam 
---
 drivers/usb/serial/Kconfig |   9 +
 drivers/usb/serial/Makefile|   1 +
 drivers/usb/serial/xr_serial.c | 544 +
 drivers/usb/serial/xr_serial.h | 103 +++
 4 files changed, 657 insertions(+)
 create mode 100644 drivers/usb/serial/xr_serial.c
 create mode 100644 drivers/usb/serial/xr_serial.h

diff --git a/drivers/usb/serial/Kconfig b/drivers/usb/serial/Kconfig
index 25d7e0c36d38..8f6ad9f94735 100644
--- a/drivers/usb/serial/Kconfig
+++ b/drivers/usb/serial/Kconfig
@@ -644,6 +644,15 @@ config USB_SERIAL_UPD78F0730
  To compile this driver as a module, choose M here: the
  module will be called upd78f0730.
 
+config USB_SERIAL_XR
+   tristate "USB MaxLinear/Exar USB to Serial driver"
+   help
+ Say Y here if you want to use MaxLinear/Exar USB to Serial converter
+ devices.
+
+ To compile this driver as a module, choose M here: the
+ module will be called xr_serial.
+
 config USB_SERIAL_DEBUG
tristate "USB Debugging Device"
help
diff --git a/drivers/usb/serial/Makefile b/drivers/usb/serial/Makefile
index 2d491e434f11..4f69c2a3aff3 100644
--- a/drivers/usb/serial/Makefile
+++ b/drivers/usb/serial/Makefile
@@ -62,4 +62,5 @@ obj-$(CONFIG_USB_SERIAL_VISOR)+= 
visor.o
 obj-$(CONFIG_USB_SERIAL_WISHBONE)  += wishbone-serial.o
 obj-$(CONFIG_USB_SERIAL_WHITEHEAT) += whiteheat.o
 obj-$(CONFIG_USB_SERIAL_XIRCOM)+= keyspan_pda.o
+obj-$(CONFIG_USB_SERIAL_XR)+= xr_serial.o
 obj-$(CONFIG_USB_SERIAL_XSENS_MT)  += xsens_mt.o
diff --git a/drivers/usb/serial/xr_serial.c b/drivers/usb/serial/xr_serial.c
new file mode 100644
index ..ea4a0b167d3f
--- /dev/null
+++ b/drivers/usb/serial/xr_serial.c
@@ -0,0 +1,544 @@
+// SPDX-License-Identifier: GPL-2.0+
+/*
+ * MaxLinear/Exar USB to Serial driver
+ *
+ * Based on initial driver written by Patong Yang 
+ *
+ * Copyright (c) 2020 Manivannan Sadhasivam 
+ */
+
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+
+#include "xr_serial.h"
+
+static const struct xr_uart_regs xr21v141x_regs = {
+   .enable = 0x03,
+   .format = 0x0b,
+   .flow_ctrl = 0x0c,
+   .xon_char = 0x10,
+   .xoff_char = 0x11,
+   .loopback = 0x12,
+   .tx_break = 0x14,
+   .rs485_delay = 0x15,
+   .gpio_mode = 0x1a,
+   .gpio_dir = 0x1b,
+   .gpio_int_mask = 0x1c,
+   .gpio_set = 0x1d,
+   .gpio_clr = 0x1e,
+   .gpio_status = 0x1f,
+};
+
+static int xr_set_reg(struct usb_serial_port *port, u8 block, u16 reg,
+ u16 val)
+{
+   struct usb_serial *serial = port->serial;
+   struct xr_port_private *port_priv = usb_get_serial_port_data(port);
+   int ret = -EINVAL;
+
+   if (port_priv->idProduct == XR21V141X_ID) {
+   /* XR21V141X uses custom command for writing UART registers */
+   ret = usb_control_msg(serial->dev,
+ usb_sndctrlpipe(serial->dev, 0),
+ XR_SET_XR21V141X,
+ USB_DIR_OUT | USB_TYPE_VENDOR, val,
+ reg | (block << 8), NULL, 0,
+ USB_CTRL_SET_TIMEOUT);
+   }
+
+   if (ret < 0)
+   dev_err(>dev, "Failed to set reg 0x%x status: %d\n",
+   reg, ret);
+
+   return ret;
+}
+
+static int xr_get_reg(struct usb_serial_port *port, u8 block, u16 reg,
+ u16 *val)
+{
+   struct usb_serial *serial = port->serial;
+   struct xr_port_private *port_priv = usb_get_serial_port_data(port);
+   void *dmabuf;
+   int ret = -EINVAL;
+
+   dmabuf = kmalloc(sizeof(reg), GFP_KERNEL);
+   if (!dmabuf)
+   return -ENOMEM;
+
+   if (port_priv->idProduct == XR21V141X_ID) {
+   /* XR21V141X uses custom command for reading UART registers */
+   ret = usb_control_msg(serial->dev,
+ usb_rcvctrlpipe(serial->dev, 0),
+ XR_GET_XR21V141X,
+ USB_DIR_IN | USB_TYPE_VENDOR, 0,
+ reg | (block << 8), 

RE: [RFC PATCH 19/22] thunderbolt: Add support for Time Management Unit

2019-10-02 Thread Mani, Rajmohan
Hi Mika,

> -Original Message-
> From: Mika Westerberg [mailto:mika.westerb...@linux.intel.com]
> Sent: Tuesday, October 01, 2019 4:38 AM
> To: linux-...@vger.kernel.org
> Cc: Andreas Noever ; Jamet, Michael
> ; Mika Westerberg
> ; Yehezkel Bernat
> ; Mani, Rajmohan ;
> Nicholas Johnson ; Lukas
> Wunner ; Greg Kroah-Hartman
> ; Alan Stern ;
> mario.limoncie...@dell.com; Anthony Wong
> ; linux-kernel@vger.kernel.org
> Subject: [RFC PATCH 19/22] thunderbolt: Add support for Time Management
> Unit
> 
> From: Rajmohan Mani 
> 
> Time Management Unit (TMU) is included in each USB4 router. It is used to
> synchronize time across the USB4 fabric. By default when USB4 router is
> plugged to the domain, its TMU is turned off. This differs from Thunderbolt 
> (1,
> 2 and 3) devices whose TMU is by default configured to bi-directional HiFi
> mode. Since time synchronization is needed for proper Display Port tunneling
> this means we need to configure the TMU on
> USB4 compliant devices.
> 
> The USB4 spec allows some flexibility on how the TMU can be configured.
> This makes it possible to enable link power management states (CLx) in certain
> topologies, where for example DP tunneling is not used. TMU can also be re-
> configured dynamicaly depending on types of tunnels created over the USB4
> fabric.
> 
> In this patch we simply configure the TMU to be in bi-directional HiFi mode.
> This way we can tunnel any kind of traffic without need to perform complex
> steps to re-configure the domain dynamically. We can add more fine-grained
> TMU configuration later on when we start enabling CLx states.
> 
> Signed-off-by: Rajmohan Mani 
> Co-developed-by: Mika Westerberg 
> Signed-off-by: Mika Westerberg 
> ---
>  drivers/thunderbolt/Makefile  |   2 +-
>  drivers/thunderbolt/switch.c  |   4 +
>  drivers/thunderbolt/tb.c  |  29 +++
>  drivers/thunderbolt/tb.h  |  47 +
>  drivers/thunderbolt/tb_regs.h |  20 ++
>  drivers/thunderbolt/tmu.c | 380 ++
>  6 files changed, 481 insertions(+), 1 deletion(-)  create mode 100644
> drivers/thunderbolt/tmu.c
> 
> diff --git a/drivers/thunderbolt/Makefile b/drivers/thunderbolt/Makefile index
> c0b2fd73dfbd..2014bc840b06 100644
> --- a/drivers/thunderbolt/Makefile
> +++ b/drivers/thunderbolt/Makefile
> @@ -1,4 +1,4 @@
>  # SPDX-License-Identifier: GPL-2.0-only  obj-${CONFIG_THUNDERBOLT} :=
> thunderbolt.o  thunderbolt-objs := nhi.o nhi_ops.o ctl.o tb.o switch.o cap.o
> path.o tunnel.o eeprom.o -thunderbolt-objs += domain.o dma_port.o icm.o
> property.o xdomain.o lc.o usb4.o
> +thunderbolt-objs += domain.o dma_port.o icm.o property.o xdomain.o lc.o
> +tmu.o usb4.o
> diff --git a/drivers/thunderbolt/switch.c b/drivers/thunderbolt/switch.c index
> 2ccd1004920e..58e3f54ddbb9 100644
> --- a/drivers/thunderbolt/switch.c
> +++ b/drivers/thunderbolt/switch.c
> @@ -2278,6 +2278,10 @@ int tb_switch_add(struct tb_switch *sw)
>   ret = tb_switch_update_link_attributes(sw);
>   if (ret)
>   return ret;
> +
> + ret = tb_switch_tmu_init(sw);
> + if (ret)
> + return ret;
>   }
> 
>   ret = device_add(>dev);
> diff --git a/drivers/thunderbolt/tb.c b/drivers/thunderbolt/tb.c index
> 24e37e47dc48..f2868c125637 100644
> --- a/drivers/thunderbolt/tb.c
> +++ b/drivers/thunderbolt/tb.c
> @@ -161,6 +161,25 @@ static void tb_scan_xdomain(struct tb_port *port)
>   }
>  }
> 
> +static int tb_enable_tmu(struct tb_switch *sw) {
> + int ret;
> +
> + /* If it is already enabled in correct mode, don't touch it */
> + if (tb_switch_tmu_is_enabled(sw))
> + return 0;
> +
> + ret = tb_switch_tmu_disable(sw);
> + if (ret)
> + return ret;
> +
> + ret = tb_switch_tmu_post_time(sw);
> + if (ret)
> + return ret;
> +
> + return tb_switch_tmu_enable(sw);
> +}
> +
>  static void tb_scan_port(struct tb_port *port);
> 
>  /**
> @@ -263,6 +282,9 @@ static void tb_scan_port(struct tb_port *port)
>   if (tb_switch_lane_bonding_enable(sw))
>   tb_sw_warn(sw, "failed to enable lane bonding\n");
> 
> + if (tb_enable_tmu(sw))
> + tb_sw_warn(sw, "failed to enable TMU\n");
> +
>   tb_scan_switch(sw);
>  }
> 
> @@ -713,6 +735,7 @@ static void tb_handle_hotplug(struct work_struct
> *work)
>   tb_sw_set_unplugged(port->remote->sw);
>   tb_free_invalid_tunnels(tb);
>   tb_remove_dp_resources(port->remote->sw);
> +

RE: [PATCH] media: staging/intel-ipu3: Implement lock for stream on/off operations

2019-02-04 Thread Mani, Rajmohan
Hi Sakari,

[snip]

> > > > >  fail_stop_pipeline:
> > > > > @@ -543,6 +546,8 @@ static void ipu3_vb2_stop_streaming(struct
> > > > vb2_queue *vq)
> > > > >   dev_err(>pci_dev->dev,
> > > > >   "failed to stop subdev streaming\n");
> > > > >
> > > > > + mutex_lock(>streaming_lock);
> > > > > +
> > > > >   /* Was this the first node with streaming disabled? */
> > > > >   if (imgu->streaming && ipu3_all_nodes_streaming(imgu, node)) {
> > > > >   /* Yes, really stop streaming now */ @@ -552,6 +557,7 @@
> > > > static
> > > > > void ipu3_vb2_stop_streaming(struct vb2_queue *vq)
> > > > >   imgu->streaming = false;
> > > > >   }
> > > > >
> > > > > + mutex_unlock(>streaming_lock);
> > > > >   ipu3_return_all_buffers(imgu, node, VB2_BUF_STATE_ERROR);
> >
> > I'd also call ipu3_return_all_buffers() before releasing the lock: in
> > principle the user may have queued new buffers on the devices before
> > the driver marks the buffers as faulty.
> >

Ack
(Somehow I missed this comment.)

[snip]


RE: [PATCH] media: staging/intel-ipu3: Implement lock for stream on/off operations

2019-02-01 Thread Mani, Rajmohan
Hi Sakari,

> Subject: Re: [PATCH] media: staging/intel-ipu3: Implement lock for stream
> on/off operations
> 
> Hi Raj,
> 
> On Wed, Jan 30, 2019 at 05:17:15PM +, Mani, Rajmohan wrote:
> > Hi Sakari,
> >
> > > -Original Message-
> > > From: Sakari Ailus [mailto:sakari.ai...@linux.intel.com]
> > > Sent: Wednesday, January 30, 2019 12:59 AM
> > > To: Mani, Rajmohan 
> > > Cc: Mauro Carvalho Chehab ; Greg Kroah-Hartman
> > > ; linux-me...@vger.kernel.org;
> > > de...@driverdev.osuosl.org; linux-kernel@vger.kernel.org; Laurent
> > > Pinchart ; Jacopo Mondi
> > > ; Qiu, Tian Shu ; Cao,
> > > Bingbu ; z...@paasikivi.fi.intel.com; Zhi, Yong
> > > ; hverk...@xs4all.nl; tf...@chromium.org
> > > Subject: Re: [PATCH] media: staging/intel-ipu3: Implement lock for
> > > stream on/off operations
> > >
> > > Hi Rajmohan,
> > >
> > > On Tue, Jan 29, 2019 at 02:27:36PM -0800, Rajmohan Mani wrote:
> > > > Currently concurrent stream off operations on ImgU nodes are not
> > > > synchronized, leading to use-after-free bugs (as reported by KASAN).
> > > >
> > > > [  250.090724] BUG: KASAN: use-after-free in
> > > > ipu3_dmamap_free+0xc5/0x116 [ipu3_imgu] [  250.090726] Read of
> > > > size 8 at addr 888127b29bc0 by task yavta/18836 [  250.090731]
> > > > Hardware
> > > > name: HP Soraka/Soraka, BIOS Google_Soraka.10431.17.0 03/22/2018 [
> > > 250.090732] Call Trace:
> > > > [  250.090735]  dump_stack+0x6a/0xb1 [  250.090739]
> > > > print_address_description+0x8e/0x279
> > > > [  250.090743]  ? ipu3_dmamap_free+0xc5/0x116 [ipu3_imgu] [
> > > > 250.090746]  kasan_report+0x260/0x28a [  250.090750]
> > > > ipu3_dmamap_free+0xc5/0x116 [ipu3_imgu] [  250.090754]
> > > > ipu3_css_pool_cleanup+0x24/0x37 [ipu3_imgu] [  250.090759]
> > > > ipu3_css_pipeline_cleanup+0x61/0xb9 [ipu3_imgu] [  250.090763]
> > > > ipu3_css_stop_streaming+0x1f2/0x321 [ipu3_imgu] [  250.090768]
> > > > imgu_s_stream+0x94/0x443 [ipu3_imgu] [  250.090772]  ?
> > > > ipu3_vb2_buf_queue+0x280/0x280 [ipu3_imgu] [  250.090775]  ?
> > > > vb2_dma_sg_unmap_dmabuf+0x16/0x6f [videobuf2_dma_sg] [
> > > > 250.090778]
> > > ?
> > > > vb2_buffer_in_use+0x36/0x58 [videobuf2_common] [  250.090782]
> > > > ipu3_vb2_stop_streaming+0xf9/0x135 [ipu3_imgu]
> > > >
> > > > Implemented a lock to synchronize imgu stream on / off operations
> > > > and the modification of streaming flag (in struct imgu_device), to
> > > > prevent these issues.
> > > >
> > > > Reported-by: Laurent Pinchart 
> > > > Suggested-by: Laurent Pinchart 
> > > >
> > > > Signed-off-by: Rajmohan Mani 
> > > > ---
> > > >  drivers/staging/media/ipu3/ipu3-v4l2.c | 6 ++
> > > >  drivers/staging/media/ipu3/ipu3.c  | 3 +++
> > > >  drivers/staging/media/ipu3/ipu3.h  | 4 
> > > >  3 files changed, 13 insertions(+)
> > > >
> > > > diff --git a/drivers/staging/media/ipu3/ipu3-v4l2.c
> > > > b/drivers/staging/media/ipu3/ipu3-v4l2.c
> > > > index c7936032beb9..cf7e917cd0c8 100644
> > > > --- a/drivers/staging/media/ipu3/ipu3-v4l2.c
> > > > +++ b/drivers/staging/media/ipu3/ipu3-v4l2.c
> > > > @@ -507,12 +507,15 @@ static int ipu3_vb2_start_streaming(struct
> > > vb2_queue *vq, unsigned int count)
> > > > goto fail_stop_pipeline;
> > > > }
> > > >
> > > > +   mutex_lock(>streaming_lock);
> > > > +
> > >
> > > You appear to be using imgu_device.lock (while searching buffers to
> > > queue to the device) as well as imgu_video_device.lock (qbuf, dqbuf)
> > > to serialise access to imgu_video_device.buffers list.
> >
> > Ack
> >
> > > The two locks may be acquired at the same time but each by different
> > > processes. That needs to be addressed, but probably not in this
> > > patch.
> > >
> >
> > The node specific locks will be used by different processes and all of
> > these processes will be competing commonly (and successfully) for the
> imgu_device lock.
> > I will look into this more.
> >
> > > I wonder if it'd be more simple to use imgu->lock here instead of
> > > adding a new one.
> > >
> >
> > Extending img

RE: [PATCH] media: staging/intel-ipu3: Implement lock for stream on/off operations

2019-01-30 Thread Mani, Rajmohan
Hi Sakari,

> -Original Message-
> From: Sakari Ailus [mailto:sakari.ai...@linux.intel.com]
> Sent: Wednesday, January 30, 2019 12:59 AM
> To: Mani, Rajmohan 
> Cc: Mauro Carvalho Chehab ; Greg Kroah-Hartman
> ; linux-me...@vger.kernel.org;
> de...@driverdev.osuosl.org; linux-kernel@vger.kernel.org; Laurent Pinchart
> ; Jacopo Mondi ;
> Qiu, Tian Shu ; Cao, Bingbu
> ; z...@paasikivi.fi.intel.com; Zhi, Yong
> ; hverk...@xs4all.nl; tf...@chromium.org
> Subject: Re: [PATCH] media: staging/intel-ipu3: Implement lock for stream
> on/off operations
> 
> Hi Rajmohan,
> 
> On Tue, Jan 29, 2019 at 02:27:36PM -0800, Rajmohan Mani wrote:
> > Currently concurrent stream off operations on ImgU nodes are not
> > synchronized, leading to use-after-free bugs (as reported by KASAN).
> >
> > [  250.090724] BUG: KASAN: use-after-free in
> > ipu3_dmamap_free+0xc5/0x116 [ipu3_imgu] [  250.090726] Read of size 8
> > at addr 888127b29bc0 by task yavta/18836 [  250.090731] Hardware
> > name: HP Soraka/Soraka, BIOS Google_Soraka.10431.17.0 03/22/2018 [
> 250.090732] Call Trace:
> > [  250.090735]  dump_stack+0x6a/0xb1
> > [  250.090739]  print_address_description+0x8e/0x279
> > [  250.090743]  ? ipu3_dmamap_free+0xc5/0x116 [ipu3_imgu] [
> > 250.090746]  kasan_report+0x260/0x28a [  250.090750]
> > ipu3_dmamap_free+0xc5/0x116 [ipu3_imgu] [  250.090754]
> > ipu3_css_pool_cleanup+0x24/0x37 [ipu3_imgu] [  250.090759]
> > ipu3_css_pipeline_cleanup+0x61/0xb9 [ipu3_imgu] [  250.090763]
> > ipu3_css_stop_streaming+0x1f2/0x321 [ipu3_imgu] [  250.090768]
> > imgu_s_stream+0x94/0x443 [ipu3_imgu] [  250.090772]  ?
> > ipu3_vb2_buf_queue+0x280/0x280 [ipu3_imgu] [  250.090775]  ?
> > vb2_dma_sg_unmap_dmabuf+0x16/0x6f [videobuf2_dma_sg] [  250.090778]
> ?
> > vb2_buffer_in_use+0x36/0x58 [videobuf2_common] [  250.090782]
> > ipu3_vb2_stop_streaming+0xf9/0x135 [ipu3_imgu]
> >
> > Implemented a lock to synchronize imgu stream on / off operations and
> > the modification of streaming flag (in struct imgu_device), to prevent
> > these issues.
> >
> > Reported-by: Laurent Pinchart 
> > Suggested-by: Laurent Pinchart 
> >
> > Signed-off-by: Rajmohan Mani 
> > ---
> >  drivers/staging/media/ipu3/ipu3-v4l2.c | 6 ++
> >  drivers/staging/media/ipu3/ipu3.c  | 3 +++
> >  drivers/staging/media/ipu3/ipu3.h  | 4 
> >  3 files changed, 13 insertions(+)
> >
> > diff --git a/drivers/staging/media/ipu3/ipu3-v4l2.c
> > b/drivers/staging/media/ipu3/ipu3-v4l2.c
> > index c7936032beb9..cf7e917cd0c8 100644
> > --- a/drivers/staging/media/ipu3/ipu3-v4l2.c
> > +++ b/drivers/staging/media/ipu3/ipu3-v4l2.c
> > @@ -507,12 +507,15 @@ static int ipu3_vb2_start_streaming(struct
> vb2_queue *vq, unsigned int count)
> > goto fail_stop_pipeline;
> > }
> >
> > +   mutex_lock(>streaming_lock);
> > +
> 
> You appear to be using imgu_device.lock (while searching buffers to queue to
> the device) as well as imgu_video_device.lock (qbuf, dqbuf) to serialise 
> access
> to imgu_video_device.buffers list.

Ack

> The two locks may be acquired at the same
> time but each by different processes. That needs to be addressed, but
> probably not in this patch.
> 

The node specific locks will be used by different processes and all of these 
processes
will be competing commonly (and successfully) for the imgu_device lock.
I will look into this more.

> I wonder if it'd be more simple to use imgu->lock here instead of adding a new
> one.
> 

Extending imgu->lock here, does not work in this case, as imgu_queue_buffers()
will be stuck acquiring imgu->lock, which was already acquired by 
imgu_s_stream()
through ipu3_vb2_start_streaming().

> > /* Start streaming of the whole pipeline now */
> > dev_dbg(dev, "IMGU streaming is ready to start");
> > r = imgu_s_stream(imgu, true);
> > if (!r)
> > imgu->streaming = true;
> >
> > +   mutex_unlock(>streaming_lock);
> > return 0;
> >
> >  fail_stop_pipeline:
> > @@ -543,6 +546,8 @@ static void ipu3_vb2_stop_streaming(struct
> vb2_queue *vq)
> > dev_err(>pci_dev->dev,
> > "failed to stop subdev streaming\n");
> >
> > +   mutex_lock(>streaming_lock);
> > +
> > /* Was this the first node with streaming disabled? */
> > if (imgu->streaming && ipu3_all_nodes_streaming(imgu, node)) {
> > /* Yes, really stop streaming now */ @@ -552,6 +557,7 @@
> static
> > void ipu3_vb

[PATCH] media: staging/intel-ipu3: Implement lock for stream on/off operations

2019-01-29 Thread Rajmohan Mani
Currently concurrent stream off operations on ImgU nodes are not
synchronized, leading to use-after-free bugs (as reported by KASAN).

[  250.090724] BUG: KASAN: use-after-free in ipu3_dmamap_free+0xc5/0x116 
[ipu3_imgu]
[  250.090726] Read of size 8 at addr 888127b29bc0 by task yavta/18836
[  250.090731] Hardware name: HP Soraka/Soraka, BIOS Google_Soraka.10431.17.0 
03/22/2018
[  250.090732] Call Trace:
[  250.090735]  dump_stack+0x6a/0xb1
[  250.090739]  print_address_description+0x8e/0x279
[  250.090743]  ? ipu3_dmamap_free+0xc5/0x116 [ipu3_imgu]
[  250.090746]  kasan_report+0x260/0x28a
[  250.090750]  ipu3_dmamap_free+0xc5/0x116 [ipu3_imgu]
[  250.090754]  ipu3_css_pool_cleanup+0x24/0x37 [ipu3_imgu]
[  250.090759]  ipu3_css_pipeline_cleanup+0x61/0xb9 [ipu3_imgu]
[  250.090763]  ipu3_css_stop_streaming+0x1f2/0x321 [ipu3_imgu]
[  250.090768]  imgu_s_stream+0x94/0x443 [ipu3_imgu]
[  250.090772]  ? ipu3_vb2_buf_queue+0x280/0x280 [ipu3_imgu]
[  250.090775]  ? vb2_dma_sg_unmap_dmabuf+0x16/0x6f [videobuf2_dma_sg]
[  250.090778]  ? vb2_buffer_in_use+0x36/0x58 [videobuf2_common]
[  250.090782]  ipu3_vb2_stop_streaming+0xf9/0x135 [ipu3_imgu]

Implemented a lock to synchronize imgu stream on / off operations and
the modification of streaming flag (in struct imgu_device), to prevent
these issues.

Reported-by: Laurent Pinchart 
Suggested-by: Laurent Pinchart 

Signed-off-by: Rajmohan Mani 
---
 drivers/staging/media/ipu3/ipu3-v4l2.c | 6 ++
 drivers/staging/media/ipu3/ipu3.c  | 3 +++
 drivers/staging/media/ipu3/ipu3.h  | 4 
 3 files changed, 13 insertions(+)

diff --git a/drivers/staging/media/ipu3/ipu3-v4l2.c 
b/drivers/staging/media/ipu3/ipu3-v4l2.c
index c7936032beb9..cf7e917cd0c8 100644
--- a/drivers/staging/media/ipu3/ipu3-v4l2.c
+++ b/drivers/staging/media/ipu3/ipu3-v4l2.c
@@ -507,12 +507,15 @@ static int ipu3_vb2_start_streaming(struct vb2_queue *vq, 
unsigned int count)
goto fail_stop_pipeline;
}
 
+   mutex_lock(>streaming_lock);
+
/* Start streaming of the whole pipeline now */
dev_dbg(dev, "IMGU streaming is ready to start");
r = imgu_s_stream(imgu, true);
if (!r)
imgu->streaming = true;
 
+   mutex_unlock(>streaming_lock);
return 0;
 
 fail_stop_pipeline:
@@ -543,6 +546,8 @@ static void ipu3_vb2_stop_streaming(struct vb2_queue *vq)
dev_err(>pci_dev->dev,
"failed to stop subdev streaming\n");
 
+   mutex_lock(>streaming_lock);
+
/* Was this the first node with streaming disabled? */
if (imgu->streaming && ipu3_all_nodes_streaming(imgu, node)) {
/* Yes, really stop streaming now */
@@ -552,6 +557,7 @@ static void ipu3_vb2_stop_streaming(struct vb2_queue *vq)
imgu->streaming = false;
}
 
+   mutex_unlock(>streaming_lock);
ipu3_return_all_buffers(imgu, node, VB2_BUF_STATE_ERROR);
media_pipeline_stop(>vdev.entity);
 }
diff --git a/drivers/staging/media/ipu3/ipu3.c 
b/drivers/staging/media/ipu3/ipu3.c
index d521b3afb8b1..2daee51cd845 100644
--- a/drivers/staging/media/ipu3/ipu3.c
+++ b/drivers/staging/media/ipu3/ipu3.c
@@ -635,6 +635,7 @@ static int imgu_pci_probe(struct pci_dev *pci_dev,
return r;
 
mutex_init(>lock);
+   mutex_init(>streaming_lock);
atomic_set(>qbuf_barrier, 0);
init_waitqueue_head(>buf_drain_wq);
 
@@ -699,6 +700,7 @@ static int imgu_pci_probe(struct pci_dev *pci_dev,
ipu3_css_set_powerdown(_dev->dev, imgu->base);
 out_mutex_destroy:
mutex_destroy(>lock);
+   mutex_destroy(>streaming_lock);
 
return r;
 }
@@ -716,6 +718,7 @@ static void imgu_pci_remove(struct pci_dev *pci_dev)
ipu3_dmamap_exit(imgu);
ipu3_mmu_exit(imgu->mmu);
mutex_destroy(>lock);
+   mutex_destroy(>streaming_lock);
 }
 
 static int __maybe_unused imgu_suspend(struct device *dev)
diff --git a/drivers/staging/media/ipu3/ipu3.h 
b/drivers/staging/media/ipu3/ipu3.h
index 04fc99f47ebb..f732315f0701 100644
--- a/drivers/staging/media/ipu3/ipu3.h
+++ b/drivers/staging/media/ipu3/ipu3.h
@@ -146,6 +146,10 @@ struct imgu_device {
 * vid_buf.list and css->queue
 */
struct mutex lock;
+
+   /* Lock to protect writes to streaming flag in this struct */
+   struct mutex streaming_lock;
+
/* Forbit streaming and buffer queuing during system suspend. */
atomic_t qbuf_barrier;
/* Indicate if system suspend take place while imgu is streaming. */
-- 
2.19.1



RE: [PATCH v2 0/2] Add a property in at24.c

2018-06-26 Thread Mani, Rajmohan
Hi Bartosz,

> -Original Message-
> From: Yeh, Andy
> Sent: Tuesday, June 26, 2018 9:21 AM
> To: Andy Shevchenko ; Bartosz
> Golaszewski 
> Cc: Chiang, AlanX ; linux-i2c  i...@vger.kernel.org>; Sakari Ailus ; Mani,
> Rajmohan ; Andy Shevchenko
> ; Rob Herring ; Mark
> Rutland ; Arnd Bergmann ; Greg
> Kroah-Hartman ; Linux Kernel Mailing List
> 
> Subject: RE: [PATCH v2 0/2] Add a property in at24.c
> 
> > -Original Message-
> > From: Andy Shevchenko [mailto:andriy.shevche...@linux.intel.com]
> > Sent: Tuesday, June 26, 2018 11:48 PM
> > To: Bartosz Golaszewski 
> > Cc: Chiang, AlanX ; linux-i2c  > i...@vger.kernel.org>; Yeh, Andy ; Sakari Ailus
> > ; Mani, Rajmohan
> > ; Andy Shevchenko
> > ; Rob Herring ; Mark
> > Rutland ; Arnd Bergmann ; Greg
> > Kroah-Hartman ; Linux Kernel Mailing List
> > 
> > Subject: Re: [PATCH v2 0/2] Add a property in at24.c
> >
> > On Tue, 2018-06-26 at 15:30 +0200, Bartosz Golaszewski wrote:
> > > 2018-06-26 15:23 GMT+02:00 Andy Shevchenko
> >  > > tel.com>:
> > > > On Tue, 2018-06-26 at 14:36 +0200, Bartosz Golaszewski wrote:
> > > > > 2018-06-26 14:14 GMT+02:00 Andy Shevchenko
> > > > > :
> > > > > > On Tue, 2018-06-26 at 09:41 +0200, Bartosz Golaszewski wrote:
> > > > > > > What is your use case exactly? Do you have an EEPROM model
> > > > > > > that's not yet supported explicitly in the driver? Why would
> > > > > > > you need this option?
> > > > > >
> > > > > > The current at24 driver has no address width support,  thus,
> > > > > > reusing same
> > > > > > (allocated) IDs (non-DT case) is hard.
> > > >
> > > > ^
> > > >
> > > > > Every supported compatible has the width already specified in
> > > > > its corresponding chip data.
> > > >
> > > >
> > > > Please, read again carefully what I wrote before.
> > > >
> > >
> > > Ok makes sense in that case. Could you just point me towards an
> > > example model which has the address width different than the default
> > > for its type?
> >
> > AFAIK, it's a companion device inside the camera voice coil IC, i.e.
> > DONGWOON DW9714.
> >
> 
> Nope, actually it is DW9807 instead, which is used on a Samsung Chromebook.

M24C64S is one example, where reusing same id (non-DT case) is not possible,
since this model uses 16 bits as address width, as the driver supports only
8 bits address width as default.

Thanks
Raj


RE: [PATCH v2 0/2] Add a property in at24.c

2018-06-26 Thread Mani, Rajmohan
Hi Bartosz,

> -Original Message-
> From: Yeh, Andy
> Sent: Tuesday, June 26, 2018 9:21 AM
> To: Andy Shevchenko ; Bartosz
> Golaszewski 
> Cc: Chiang, AlanX ; linux-i2c  i...@vger.kernel.org>; Sakari Ailus ; Mani,
> Rajmohan ; Andy Shevchenko
> ; Rob Herring ; Mark
> Rutland ; Arnd Bergmann ; Greg
> Kroah-Hartman ; Linux Kernel Mailing List
> 
> Subject: RE: [PATCH v2 0/2] Add a property in at24.c
> 
> > -Original Message-
> > From: Andy Shevchenko [mailto:andriy.shevche...@linux.intel.com]
> > Sent: Tuesday, June 26, 2018 11:48 PM
> > To: Bartosz Golaszewski 
> > Cc: Chiang, AlanX ; linux-i2c  > i...@vger.kernel.org>; Yeh, Andy ; Sakari Ailus
> > ; Mani, Rajmohan
> > ; Andy Shevchenko
> > ; Rob Herring ; Mark
> > Rutland ; Arnd Bergmann ; Greg
> > Kroah-Hartman ; Linux Kernel Mailing List
> > 
> > Subject: Re: [PATCH v2 0/2] Add a property in at24.c
> >
> > On Tue, 2018-06-26 at 15:30 +0200, Bartosz Golaszewski wrote:
> > > 2018-06-26 15:23 GMT+02:00 Andy Shevchenko
> >  > > tel.com>:
> > > > On Tue, 2018-06-26 at 14:36 +0200, Bartosz Golaszewski wrote:
> > > > > 2018-06-26 14:14 GMT+02:00 Andy Shevchenko
> > > > > :
> > > > > > On Tue, 2018-06-26 at 09:41 +0200, Bartosz Golaszewski wrote:
> > > > > > > What is your use case exactly? Do you have an EEPROM model
> > > > > > > that's not yet supported explicitly in the driver? Why would
> > > > > > > you need this option?
> > > > > >
> > > > > > The current at24 driver has no address width support,  thus,
> > > > > > reusing same
> > > > > > (allocated) IDs (non-DT case) is hard.
> > > >
> > > > ^
> > > >
> > > > > Every supported compatible has the width already specified in
> > > > > its corresponding chip data.
> > > >
> > > >
> > > > Please, read again carefully what I wrote before.
> > > >
> > >
> > > Ok makes sense in that case. Could you just point me towards an
> > > example model which has the address width different than the default
> > > for its type?
> >
> > AFAIK, it's a companion device inside the camera voice coil IC, i.e.
> > DONGWOON DW9714.
> >
> 
> Nope, actually it is DW9807 instead, which is used on a Samsung Chromebook.

M24C64S is one example, where reusing same id (non-DT case) is not possible,
since this model uses 16 bits as address width, as the driver supports only
8 bits address width as default.

Thanks
Raj


[PATCH] media: dw9714: Update to SPDX license identifier

2018-02-20 Thread Rajmohan Mani
Remove the GPL v2 license boilerplate and update with the SPDX license
identifier.

Signed-off-by: Rajmohan Mani <rajmohan.m...@intel.com>
---
 drivers/media/i2c/dw9714.c | 14 ++
 1 file changed, 2 insertions(+), 12 deletions(-)

diff --git a/drivers/media/i2c/dw9714.c b/drivers/media/i2c/dw9714.c
index 8dbbf0f..91fae01 100644
--- a/drivers/media/i2c/dw9714.c
+++ b/drivers/media/i2c/dw9714.c
@@ -1,15 +1,5 @@
-/*
- * Copyright (c) 2015--2017 Intel Corporation.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License version
- * 2 as published by the Free Software Foundation.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- */
+// SPDX-License-Identifier: GPL-2.0
+// Copyright (c) 2015--2017 Intel Corporation.
 
 #include 
 #include 
-- 
1.9.1



[PATCH] media: dw9714: Update to SPDX license identifier

2018-02-20 Thread Rajmohan Mani
Remove the GPL v2 license boilerplate and update with the SPDX license
identifier.

Signed-off-by: Rajmohan Mani 
---
 drivers/media/i2c/dw9714.c | 14 ++
 1 file changed, 2 insertions(+), 12 deletions(-)

diff --git a/drivers/media/i2c/dw9714.c b/drivers/media/i2c/dw9714.c
index 8dbbf0f..91fae01 100644
--- a/drivers/media/i2c/dw9714.c
+++ b/drivers/media/i2c/dw9714.c
@@ -1,15 +1,5 @@
-/*
- * Copyright (c) 2015--2017 Intel Corporation.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License version
- * 2 as published by the Free Software Foundation.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- */
+// SPDX-License-Identifier: GPL-2.0
+// Copyright (c) 2015--2017 Intel Corporation.
 
 #include 
 #include 
-- 
1.9.1



[PATCH 0/3] Update TPS68470 PMIC drivers with SPDX tags

2018-02-20 Thread Rajmohan Mani
This patch series update the TPS68470 PMIC drivers with SPDX license
identifiers, while removing the GPL v2 boilerplate license text.

Rajmohan Mani (3):
  mfd: Update to SPDX license identifier
  gpio: Update to SPDX license identifier
  ACPI / PMIC: Update to SPDX license identifier

 drivers/acpi/pmic/tps68470_pmic.c | 10 +-
 drivers/gpio/gpio-tps68470.c  | 10 +-
 drivers/mfd/tps68470.c| 10 +-
 include/linux/mfd/tps68470.h  | 17 +++--
 4 files changed, 6 insertions(+), 41 deletions(-)

-- 
1.9.1



[PATCH 1/3] mfd: Update to SPDX license identifier

2018-02-20 Thread Rajmohan Mani
Remove the GPL v2 license boilerplate and update with
the SPDX license identifier.

Signed-off-by: Rajmohan Mani <rajmohan.m...@intel.com>
---
 drivers/mfd/tps68470.c   | 10 +-
 include/linux/mfd/tps68470.h | 17 +++--
 2 files changed, 4 insertions(+), 23 deletions(-)

diff --git a/drivers/mfd/tps68470.c b/drivers/mfd/tps68470.c
index 189efae..a5981a7 100644
--- a/drivers/mfd/tps68470.c
+++ b/drivers/mfd/tps68470.c
@@ -1,3 +1,4 @@
+// SPDX-License-Identifier: GPL-2.0
 /*
  * TPS68470 chip Parent driver
  *
@@ -8,15 +9,6 @@
  * Tianshu Qiu <tian.shu@intel.com>
  * Jian Xu Zheng <jian.xu.zh...@intel.com>
  * Yuning Pu <yuning...@intel.com>
- *
- * 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 version 2.
- *
- * This program is distributed "as is" WITHOUT ANY WARRANTY of any
- * kind, whether express or implied; without even the implied warranty
- * of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
  */
 
 #include 
diff --git a/include/linux/mfd/tps68470.h b/include/linux/mfd/tps68470.h
index 44f9d9f..ffe8112 100644
--- a/include/linux/mfd/tps68470.h
+++ b/include/linux/mfd/tps68470.h
@@ -1,17 +1,6 @@
-/*
- * Copyright (c) 2017 Intel Corporation
- *
- * Functions to access TPS68470 power management chip.
- *
- * 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 version 2.
- *
- * This program is distributed "as is" WITHOUT ANY WARRANTY of any
- * kind, whether express or implied; without even the implied warranty
- * of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- */
+/* SPDX-License-Identifier: GPL-2.0 */
+/* Copyright (C) 2017 Intel Corporation */
+/* Functions to access TPS68470 power management chip. */
 
 #ifndef __LINUX_MFD_TPS68470_H
 #define __LINUX_MFD_TPS68470_H
-- 
1.9.1



[PATCH 0/3] Update TPS68470 PMIC drivers with SPDX tags

2018-02-20 Thread Rajmohan Mani
This patch series update the TPS68470 PMIC drivers with SPDX license
identifiers, while removing the GPL v2 boilerplate license text.

Rajmohan Mani (3):
  mfd: Update to SPDX license identifier
  gpio: Update to SPDX license identifier
  ACPI / PMIC: Update to SPDX license identifier

 drivers/acpi/pmic/tps68470_pmic.c | 10 +-
 drivers/gpio/gpio-tps68470.c  | 10 +-
 drivers/mfd/tps68470.c| 10 +-
 include/linux/mfd/tps68470.h  | 17 +++--
 4 files changed, 6 insertions(+), 41 deletions(-)

-- 
1.9.1



[PATCH 1/3] mfd: Update to SPDX license identifier

2018-02-20 Thread Rajmohan Mani
Remove the GPL v2 license boilerplate and update with
the SPDX license identifier.

Signed-off-by: Rajmohan Mani 
---
 drivers/mfd/tps68470.c   | 10 +-
 include/linux/mfd/tps68470.h | 17 +++--
 2 files changed, 4 insertions(+), 23 deletions(-)

diff --git a/drivers/mfd/tps68470.c b/drivers/mfd/tps68470.c
index 189efae..a5981a7 100644
--- a/drivers/mfd/tps68470.c
+++ b/drivers/mfd/tps68470.c
@@ -1,3 +1,4 @@
+// SPDX-License-Identifier: GPL-2.0
 /*
  * TPS68470 chip Parent driver
  *
@@ -8,15 +9,6 @@
  * Tianshu Qiu 
  * Jian Xu Zheng 
  * Yuning Pu 
- *
- * 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 version 2.
- *
- * This program is distributed "as is" WITHOUT ANY WARRANTY of any
- * kind, whether express or implied; without even the implied warranty
- * of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
  */
 
 #include 
diff --git a/include/linux/mfd/tps68470.h b/include/linux/mfd/tps68470.h
index 44f9d9f..ffe8112 100644
--- a/include/linux/mfd/tps68470.h
+++ b/include/linux/mfd/tps68470.h
@@ -1,17 +1,6 @@
-/*
- * Copyright (c) 2017 Intel Corporation
- *
- * Functions to access TPS68470 power management chip.
- *
- * 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 version 2.
- *
- * This program is distributed "as is" WITHOUT ANY WARRANTY of any
- * kind, whether express or implied; without even the implied warranty
- * of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- */
+/* SPDX-License-Identifier: GPL-2.0 */
+/* Copyright (C) 2017 Intel Corporation */
+/* Functions to access TPS68470 power management chip. */
 
 #ifndef __LINUX_MFD_TPS68470_H
 #define __LINUX_MFD_TPS68470_H
-- 
1.9.1



[PATCH 2/3] gpio: Update to SPDX license identifier

2018-02-20 Thread Rajmohan Mani
Remove the GPL v2 license boilerplate and update with
the SPDX license identifier.

Signed-off-by: Rajmohan Mani <rajmohan.m...@intel.com>
---
 drivers/gpio/gpio-tps68470.c | 10 +-
 1 file changed, 1 insertion(+), 9 deletions(-)

diff --git a/drivers/gpio/gpio-tps68470.c b/drivers/gpio/gpio-tps68470.c
index fa2662f..aff6e50 100644
--- a/drivers/gpio/gpio-tps68470.c
+++ b/drivers/gpio/gpio-tps68470.c
@@ -1,3 +1,4 @@
+// SPDX-License-Identifier: GPL-2.0
 /*
  * GPIO driver for TPS68470 PMIC
  *
@@ -8,15 +9,6 @@
  * Tianshu Qiu <tian.shu@intel.com>
  * Jian Xu Zheng <jian.xu.zh...@intel.com>
  * Yuning Pu <yuning...@intel.com>
- *
- * 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 version 2.
- *
- * This program is distributed "as is" WITHOUT ANY WARRANTY of any
- * kind, whether express or implied; without even the implied warranty
- * of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
  */
 
 #include 
-- 
1.9.1



[PATCH 2/3] gpio: Update to SPDX license identifier

2018-02-20 Thread Rajmohan Mani
Remove the GPL v2 license boilerplate and update with
the SPDX license identifier.

Signed-off-by: Rajmohan Mani 
---
 drivers/gpio/gpio-tps68470.c | 10 +-
 1 file changed, 1 insertion(+), 9 deletions(-)

diff --git a/drivers/gpio/gpio-tps68470.c b/drivers/gpio/gpio-tps68470.c
index fa2662f..aff6e50 100644
--- a/drivers/gpio/gpio-tps68470.c
+++ b/drivers/gpio/gpio-tps68470.c
@@ -1,3 +1,4 @@
+// SPDX-License-Identifier: GPL-2.0
 /*
  * GPIO driver for TPS68470 PMIC
  *
@@ -8,15 +9,6 @@
  * Tianshu Qiu 
  * Jian Xu Zheng 
  * Yuning Pu 
- *
- * 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 version 2.
- *
- * This program is distributed "as is" WITHOUT ANY WARRANTY of any
- * kind, whether express or implied; without even the implied warranty
- * of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
  */
 
 #include 
-- 
1.9.1



[PATCH 3/3] ACPI / PMIC: Update to SPDX license identifier

2018-02-20 Thread Rajmohan Mani
Remove the GPL v2 license boilerplate and update with
the SPDX license identifier.

Signed-off-by: Rajmohan Mani <rajmohan.m...@intel.com>
---
 drivers/acpi/pmic/tps68470_pmic.c | 10 +-
 1 file changed, 1 insertion(+), 9 deletions(-)

diff --git a/drivers/acpi/pmic/tps68470_pmic.c 
b/drivers/acpi/pmic/tps68470_pmic.c
index 7f3c567..a083de5 100644
--- a/drivers/acpi/pmic/tps68470_pmic.c
+++ b/drivers/acpi/pmic/tps68470_pmic.c
@@ -1,3 +1,4 @@
+// SPDX-License-Identifier: GPL-2.0
 /*
  * TI TPS68470 PMIC operation region driver
  *
@@ -5,15 +6,6 @@
  *
  * Author: Rajmohan Mani <rajmohan.m...@intel.com>
  *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License version
- * 2 as published by the Free Software Foundation.
- *
- * This program is distributed "as is" WITHOUT ANY WARRANTY of any
- * kind, whether express or implied; without even the implied warranty
- * of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
  * Based on drivers/acpi/pmic/intel_pmic* drivers
  */
 
-- 
1.9.1



[PATCH 3/3] ACPI / PMIC: Update to SPDX license identifier

2018-02-20 Thread Rajmohan Mani
Remove the GPL v2 license boilerplate and update with
the SPDX license identifier.

Signed-off-by: Rajmohan Mani 
---
 drivers/acpi/pmic/tps68470_pmic.c | 10 +-
 1 file changed, 1 insertion(+), 9 deletions(-)

diff --git a/drivers/acpi/pmic/tps68470_pmic.c 
b/drivers/acpi/pmic/tps68470_pmic.c
index 7f3c567..a083de5 100644
--- a/drivers/acpi/pmic/tps68470_pmic.c
+++ b/drivers/acpi/pmic/tps68470_pmic.c
@@ -1,3 +1,4 @@
+// SPDX-License-Identifier: GPL-2.0
 /*
  * TI TPS68470 PMIC operation region driver
  *
@@ -5,15 +6,6 @@
  *
  * Author: Rajmohan Mani 
  *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License version
- * 2 as published by the Free Software Foundation.
- *
- * This program is distributed "as is" WITHOUT ANY WARRANTY of any
- * kind, whether express or implied; without even the implied warranty
- * of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
  * Based on drivers/acpi/pmic/intel_pmic* drivers
  */
 
-- 
1.9.1



RE: [PATCH v6 3/3] ACPI / PMIC: Add TI PMIC TPS68470 operation region driver

2017-11-14 Thread Mani, Rajmohan
Hi Rafael,

> -Original Message-
> From: Rafael J. Wysocki [mailto:r...@rjwysocki.net]
> Sent: Tuesday, October 03, 2017 4:44 AM
> To: Sakari Ailus <sakari.ai...@iki.fi>
> Cc: Mani, Rajmohan <rajmohan.m...@intel.com>; linux-
> ker...@vger.kernel.org; linux-g...@vger.kernel.org; linux-
> a...@vger.kernel.org; Lee Jones <lee.jo...@linaro.org>; Linus Walleij
> <linus.wall...@linaro.org>; Alexandre Courbot <gnu...@gmail.com>; Len
> Brown <l...@kernel.org>; Andy Shevchenko <andy.shevche...@gmail.com>
> Subject: Re: [PATCH v6 3/3] ACPI / PMIC: Add TI PMIC TPS68470 operation
> region driver
> 
> On Monday, October 2, 2017 6:54:03 PM CEST Sakari Ailus wrote:
> > Hi Rafael,
> >
> > On Mon, Aug 14, 2017 at 11:39:00PM +0300, Sakari Ailus wrote:
> > > On Fri, Jul 28, 2017 at 05:30:26PM -0700, Rajmohan Mani wrote:
> > > > The Kabylake platform coreboot (Chrome OS equivalent of
> > > > BIOS) has defined 4 operation regions for the TI TPS68470 PMIC.
> > > > These operation regions are to enable/disable voltage regulators,
> > > > configure voltage regulators, enable/disable clocks and to
> > > > configure clocks.
> > > >
> > > > This config adds ACPI operation region support for TI TPS68470 PMIC.
> > > > TPS68470 device is an advanced power management unit that powers a
> > > > Compact Camera Module (CCM), generates clocks for image sensors,
> > > > drives a dual LED for flash and incorporates two LED drivers for
> > > > general purpose indicators.
> > > > This driver enables ACPI operation region support to control
> > > > voltage regulators and clocks for the TPS68470 PMIC.
> > > >
> > > > Signed-off-by: Rajmohan Mani <rajmohan.m...@intel.com>
> > >
> > > Acked-by: Sakari Ailus <sakari.ai...@linux.intel.com>
> >
> > The other two patches from the set are in v4.14-rc1.
> 
> Thanks!
> 
> I'll queue it up for 4.15 then.
> 

Thanks. This patch has landed in mainline kernel couple of days ago.

Raj


RE: [PATCH v6 3/3] ACPI / PMIC: Add TI PMIC TPS68470 operation region driver

2017-11-14 Thread Mani, Rajmohan
Hi Rafael,

> -Original Message-
> From: Rafael J. Wysocki [mailto:r...@rjwysocki.net]
> Sent: Tuesday, October 03, 2017 4:44 AM
> To: Sakari Ailus 
> Cc: Mani, Rajmohan ; linux-
> ker...@vger.kernel.org; linux-g...@vger.kernel.org; linux-
> a...@vger.kernel.org; Lee Jones ; Linus Walleij
> ; Alexandre Courbot ; Len
> Brown ; Andy Shevchenko 
> Subject: Re: [PATCH v6 3/3] ACPI / PMIC: Add TI PMIC TPS68470 operation
> region driver
> 
> On Monday, October 2, 2017 6:54:03 PM CEST Sakari Ailus wrote:
> > Hi Rafael,
> >
> > On Mon, Aug 14, 2017 at 11:39:00PM +0300, Sakari Ailus wrote:
> > > On Fri, Jul 28, 2017 at 05:30:26PM -0700, Rajmohan Mani wrote:
> > > > The Kabylake platform coreboot (Chrome OS equivalent of
> > > > BIOS) has defined 4 operation regions for the TI TPS68470 PMIC.
> > > > These operation regions are to enable/disable voltage regulators,
> > > > configure voltage regulators, enable/disable clocks and to
> > > > configure clocks.
> > > >
> > > > This config adds ACPI operation region support for TI TPS68470 PMIC.
> > > > TPS68470 device is an advanced power management unit that powers a
> > > > Compact Camera Module (CCM), generates clocks for image sensors,
> > > > drives a dual LED for flash and incorporates two LED drivers for
> > > > general purpose indicators.
> > > > This driver enables ACPI operation region support to control
> > > > voltage regulators and clocks for the TPS68470 PMIC.
> > > >
> > > > Signed-off-by: Rajmohan Mani 
> > >
> > > Acked-by: Sakari Ailus 
> >
> > The other two patches from the set are in v4.14-rc1.
> 
> Thanks!
> 
> I'll queue it up for 4.15 then.
> 

Thanks. This patch has landed in mainline kernel couple of days ago.

Raj


RE: [PATCH v5 0/3] TPS68470 PMIC drivers

2017-09-25 Thread Mani, Rajmohan
Hi Rafael, Andy,

Just pinging to see if there are updates on ACPI / PMIC opregion patch...

Thanks
Raj

> -Original Message-
> From: Mani, Rajmohan
> Sent: Thursday, September 07, 2017 5:46 PM
> To: 'Rafael J. Wysocki' <raf...@kernel.org>
> Cc: 'Rafael J. Wysocki' <r...@rjwysocki.net>; 'Andy Shevchenko'
> <andy.shevche...@gmail.com>; 'linux-kernel@vger.kernel.org'  ker...@vger.kernel.org>; 'linux-g...@vger.kernel.org'  g...@vger.kernel.org>; 'linux-a...@vger.kernel.org'  a...@vger.kernel.org>; 'Lee Jones' <lee.jo...@linaro.org>; 'Linus Walleij'
> <linus.wall...@linaro.org>; 'Alexandre Courbot' <gnu...@gmail.com>; 'Len
> Brown' <l...@kernel.org>; 'sakari.ai...@linux.intel.com'
> <sakari.ai...@linux.intel.com>
> Subject: RE: [PATCH v5 0/3] TPS68470 PMIC drivers
> 
> Hi Rafael,
> 
> > Subject: RE: [PATCH v5 0/3] TPS68470 PMIC drivers
> >
> > Hi Rafael,
> >
> > > >> > >> > This is the patch series for TPS68470 PMIC that works as a
> > > >> > >> > camera
> > > PMIC.
> > > >> > >> >
> > > >> > >> > The patch series provide the following 3 drivers, to help
> > > >> > >> > configure the
> > > >> voltage regulators, clocks and GPIOs provided by the TPS68470
> > > >> PMIC, to be able to use the camera sensors connected to this PMIC.
> > > >> > >> >
> > > >> > >> > TPS68470 MFD driver:
> > > >> > >> > This is the multi function driver that initializes the
> > > >> > >> > TPS68470 PMIC and
> > > >> supports the GPIO and Op Region functions.
> > > >> > >> >
> > > >> > >> > TPS68470 GPIO driver:
> > > >> > >> > This is the PMIC GPIO driver that will be used by the OS
> > > >> > >> > GPIO layer,
> > > >> when the BIOS / firmware triggered GPIO access is done.
> > > >> > >> >
> > > >> > >> > TPS68470 Op Region driver:
> > > >> > >> > This is the driver that will be invoked, when the BIOS /
> > > >> > >> > firmware
> > > >> configures the voltage / clock for the sensors / vcm devices
> > > >> connected to the PMIC.
> > > >> > >> >
> > > >> > >>
> > > >> > >> All three patches are good to me (we did few rounds of
> > > >> > >> internal review before posting v4)
> > > >> > >>
> > > >> > >> Reviewed-by: Andy Shevchenko <andy.shevche...@gmail.com>
> > > >> > >
> > > >> > > OK, so how should they be routed?
> > > >> >
> > > >> > Good question. I don't know how last time PMIC drivers were
> > > >> > merged, here I think is just sane to route vi MFD with
> > > >> > immutable branch created.
> > > >>
> > > >> OK
> > > >>
> > > >> I will assume that the series will go in through MFD then.
> > > >>
> > > >
> > > > Now that the MFD and GPIO patches of v6 of this series have been
> > > > applied
> > > on respective trees, can you advise the next steps for the ACPI /
> > > PMIC Opregion driver?
> > >
> > > Well, it would have been better to route the whole series through one
> tree.
> > > Now it's better to wait until the two other trees get merged and
> > > then apply the opregion patch.
> > >
> >
> > Ack.
> > Let me get back once the other 2 trees are merged.
> >
> 
> Both MFD and GPIO patches of this series got merged upstream as of today.
> 
> Thanks
> Raj


RE: [PATCH v5 0/3] TPS68470 PMIC drivers

2017-09-25 Thread Mani, Rajmohan
Hi Rafael, Andy,

Just pinging to see if there are updates on ACPI / PMIC opregion patch...

Thanks
Raj

> -Original Message-
> From: Mani, Rajmohan
> Sent: Thursday, September 07, 2017 5:46 PM
> To: 'Rafael J. Wysocki' 
> Cc: 'Rafael J. Wysocki' ; 'Andy Shevchenko'
> ; 'linux-kernel@vger.kernel.org'  ker...@vger.kernel.org>; 'linux-g...@vger.kernel.org'  g...@vger.kernel.org>; 'linux-a...@vger.kernel.org'  a...@vger.kernel.org>; 'Lee Jones' ; 'Linus Walleij'
> ; 'Alexandre Courbot' ; 'Len
> Brown' ; 'sakari.ai...@linux.intel.com'
> 
> Subject: RE: [PATCH v5 0/3] TPS68470 PMIC drivers
> 
> Hi Rafael,
> 
> > Subject: RE: [PATCH v5 0/3] TPS68470 PMIC drivers
> >
> > Hi Rafael,
> >
> > > >> > >> > This is the patch series for TPS68470 PMIC that works as a
> > > >> > >> > camera
> > > PMIC.
> > > >> > >> >
> > > >> > >> > The patch series provide the following 3 drivers, to help
> > > >> > >> > configure the
> > > >> voltage regulators, clocks and GPIOs provided by the TPS68470
> > > >> PMIC, to be able to use the camera sensors connected to this PMIC.
> > > >> > >> >
> > > >> > >> > TPS68470 MFD driver:
> > > >> > >> > This is the multi function driver that initializes the
> > > >> > >> > TPS68470 PMIC and
> > > >> supports the GPIO and Op Region functions.
> > > >> > >> >
> > > >> > >> > TPS68470 GPIO driver:
> > > >> > >> > This is the PMIC GPIO driver that will be used by the OS
> > > >> > >> > GPIO layer,
> > > >> when the BIOS / firmware triggered GPIO access is done.
> > > >> > >> >
> > > >> > >> > TPS68470 Op Region driver:
> > > >> > >> > This is the driver that will be invoked, when the BIOS /
> > > >> > >> > firmware
> > > >> configures the voltage / clock for the sensors / vcm devices
> > > >> connected to the PMIC.
> > > >> > >> >
> > > >> > >>
> > > >> > >> All three patches are good to me (we did few rounds of
> > > >> > >> internal review before posting v4)
> > > >> > >>
> > > >> > >> Reviewed-by: Andy Shevchenko 
> > > >> > >
> > > >> > > OK, so how should they be routed?
> > > >> >
> > > >> > Good question. I don't know how last time PMIC drivers were
> > > >> > merged, here I think is just sane to route vi MFD with
> > > >> > immutable branch created.
> > > >>
> > > >> OK
> > > >>
> > > >> I will assume that the series will go in through MFD then.
> > > >>
> > > >
> > > > Now that the MFD and GPIO patches of v6 of this series have been
> > > > applied
> > > on respective trees, can you advise the next steps for the ACPI /
> > > PMIC Opregion driver?
> > >
> > > Well, it would have been better to route the whole series through one
> tree.
> > > Now it's better to wait until the two other trees get merged and
> > > then apply the opregion patch.
> > >
> >
> > Ack.
> > Let me get back once the other 2 trees are merged.
> >
> 
> Both MFD and GPIO patches of this series got merged upstream as of today.
> 
> Thanks
> Raj


RE: [PATCH v6 3/3] eeprom: at24: enable runtime pm support

2017-09-19 Thread Mani, Rajmohan
Adding Tomasz...

> -Original Message-
> From: Mohandass, Divagar
> Sent: Monday, September 04, 2017 3:29 AM
> To: robh...@kernel.org; mark.rutl...@arm.com; w...@the-dreams.de;
> sakari.ai...@iki.fi
> Cc: devicet...@vger.kernel.org; linux-...@vger.kernel.org; linux-
> ker...@vger.kernel.org; Mani, Rajmohan <rajmohan.m...@intel.com>;
> Mohandass, Divagar <divagar.mohand...@intel.com>
> Subject: [PATCH v6 3/3] eeprom: at24: enable runtime pm support
> 
> Currently the device is kept in D0, there is an opportunity to save power by
> enabling runtime pm.
> 
> Device can be daisy chained from PMIC and we can't rely on I2C core for auto
> resume/suspend. Driver will decide when to resume/suspend.
> 
> Signed-off-by: Divagar Mohandass <divagar.mohand...@intel.com>
> ---
>  drivers/misc/eeprom/at24.c | 38
> ++
>  1 file changed, 38 insertions(+)
> 
> diff --git a/drivers/misc/eeprom/at24.c b/drivers/misc/eeprom/at24.c index
> 2199c42..d718a7a 100644
> --- a/drivers/misc/eeprom/at24.c
> +++ b/drivers/misc/eeprom/at24.c
> @@ -24,6 +24,7 @@
>  #include 
>  #include 
>  #include 
> +#include 
> 
>  /*
>   * I2C EEPROMs from most vendors are inexpensive and mostly
> interchangeable.
> @@ -501,11 +502,21 @@ static ssize_t at24_eeprom_write_i2c(struct
> at24_data *at24, const char *buf,  static int at24_read(void *priv, unsigned 
> int
> off, void *val, size_t count)  {
>   struct at24_data *at24 = priv;
> + struct i2c_client *client;
>   char *buf = val;
> + int ret;
> 
>   if (unlikely(!count))
>   return count;
> 
> + client = at24_translate_offset(at24, );
> +
> + ret = pm_runtime_get_sync(>dev);
> + if (ret < 0) {
> + pm_runtime_put_noidle(>dev);
> + return ret;
> + }
> +
>   /*
>* Read data from chip, protecting against concurrent updates
>* from this host, but not from other I2C masters.
> @@ -518,6 +529,7 @@ static int at24_read(void *priv, unsigned int off, void
> *val, size_t count)
>   status = at24->read_func(at24, buf, off, count);
>   if (status < 0) {
>   mutex_unlock(>lock);
> + pm_runtime_put(>dev);
>   return status;
>   }
>   buf += status;
> @@ -527,17 +539,29 @@ static int at24_read(void *priv, unsigned int off, void
> *val, size_t count)
> 
>   mutex_unlock(>lock);
> 
> + pm_runtime_put(>dev);
> +
>   return 0;
>  }
> 
>  static int at24_write(void *priv, unsigned int off, void *val, size_t count) 
>  {
>   struct at24_data *at24 = priv;
> + struct i2c_client *client;
>   char *buf = val;
> + int ret;
> 
>   if (unlikely(!count))
>   return -EINVAL;
> 
> + client = at24_translate_offset(at24, );
> +
> + ret = pm_runtime_get_sync(>dev);
> + if (ret < 0) {
> + pm_runtime_put_noidle(>dev);
> + return ret;
> + }
> +
>   /*
>* Write data to chip, protecting against concurrent updates
>* from this host, but not from other I2C masters.
> @@ -550,6 +574,7 @@ static int at24_write(void *priv, unsigned int off, void
> *val, size_t count)
>   status = at24->write_func(at24, buf, off, count);
>   if (status < 0) {
>   mutex_unlock(>lock);
> + pm_runtime_put(>dev);
>   return status;
>   }
>   buf += status;
> @@ -559,6 +584,8 @@ static int at24_write(void *priv, unsigned int off, void
> *val, size_t count)
> 
>   mutex_unlock(>lock);
> 
> + pm_runtime_put(>dev);
> +
>   return 0;
>  }
> 
> @@ -743,11 +770,17 @@ static int at24_probe(struct i2c_client *client, const
> struct i2c_device_id *id)
> 
>   i2c_set_clientdata(client, at24);
> 
> + /* enable runtime pm */
> + pm_runtime_get_noresume(>dev);
> + pm_runtime_set_active(>dev);
> + pm_runtime_enable(>dev);
> +
>   /*
>* Perform a one-byte test read to verify that the
>* chip is functional.
>*/
>   err = at24_read(at24, 0, _byte, 1);
> + pm_runtime_put(>dev);
>   if (err) {
>   err = -ENODEV;
>   goto err_clients;
> @@ -795,6 +828,8 @@ static int at24_probe(struct i2c_client *client, const
> struct i2c_device_id *id)
>   if (at24->client[i])
>   i2c_unregister_device(at24->client[i]);
> 
> + pm_runtime_disable(>dev);
> +
>   return err;
>  }
> 
> @@ -810,6 +845,9 @@ static int at24_remove(struct i2c_client *client)
>   for (i = 1; i < at24->num_addresses; i++)
>   i2c_unregister_device(at24->client[i]);
> 
> + pm_runtime_disable(>dev);
> + pm_runtime_set_suspended(>dev);
> +
>   return 0;
>  }
> 
> --
> 1.9.1



RE: [PATCH v6 3/3] eeprom: at24: enable runtime pm support

2017-09-19 Thread Mani, Rajmohan
Adding Tomasz...

> -Original Message-
> From: Mohandass, Divagar
> Sent: Monday, September 04, 2017 3:29 AM
> To: robh...@kernel.org; mark.rutl...@arm.com; w...@the-dreams.de;
> sakari.ai...@iki.fi
> Cc: devicet...@vger.kernel.org; linux-...@vger.kernel.org; linux-
> ker...@vger.kernel.org; Mani, Rajmohan ;
> Mohandass, Divagar 
> Subject: [PATCH v6 3/3] eeprom: at24: enable runtime pm support
> 
> Currently the device is kept in D0, there is an opportunity to save power by
> enabling runtime pm.
> 
> Device can be daisy chained from PMIC and we can't rely on I2C core for auto
> resume/suspend. Driver will decide when to resume/suspend.
> 
> Signed-off-by: Divagar Mohandass 
> ---
>  drivers/misc/eeprom/at24.c | 38
> ++
>  1 file changed, 38 insertions(+)
> 
> diff --git a/drivers/misc/eeprom/at24.c b/drivers/misc/eeprom/at24.c index
> 2199c42..d718a7a 100644
> --- a/drivers/misc/eeprom/at24.c
> +++ b/drivers/misc/eeprom/at24.c
> @@ -24,6 +24,7 @@
>  #include 
>  #include 
>  #include 
> +#include 
> 
>  /*
>   * I2C EEPROMs from most vendors are inexpensive and mostly
> interchangeable.
> @@ -501,11 +502,21 @@ static ssize_t at24_eeprom_write_i2c(struct
> at24_data *at24, const char *buf,  static int at24_read(void *priv, unsigned 
> int
> off, void *val, size_t count)  {
>   struct at24_data *at24 = priv;
> + struct i2c_client *client;
>   char *buf = val;
> + int ret;
> 
>   if (unlikely(!count))
>   return count;
> 
> + client = at24_translate_offset(at24, );
> +
> + ret = pm_runtime_get_sync(>dev);
> + if (ret < 0) {
> + pm_runtime_put_noidle(>dev);
> + return ret;
> + }
> +
>   /*
>* Read data from chip, protecting against concurrent updates
>* from this host, but not from other I2C masters.
> @@ -518,6 +529,7 @@ static int at24_read(void *priv, unsigned int off, void
> *val, size_t count)
>   status = at24->read_func(at24, buf, off, count);
>   if (status < 0) {
>   mutex_unlock(>lock);
> + pm_runtime_put(>dev);
>   return status;
>   }
>   buf += status;
> @@ -527,17 +539,29 @@ static int at24_read(void *priv, unsigned int off, void
> *val, size_t count)
> 
>   mutex_unlock(>lock);
> 
> + pm_runtime_put(>dev);
> +
>   return 0;
>  }
> 
>  static int at24_write(void *priv, unsigned int off, void *val, size_t count) 
>  {
>   struct at24_data *at24 = priv;
> + struct i2c_client *client;
>   char *buf = val;
> + int ret;
> 
>   if (unlikely(!count))
>   return -EINVAL;
> 
> + client = at24_translate_offset(at24, );
> +
> + ret = pm_runtime_get_sync(>dev);
> + if (ret < 0) {
> + pm_runtime_put_noidle(>dev);
> + return ret;
> + }
> +
>   /*
>* Write data to chip, protecting against concurrent updates
>* from this host, but not from other I2C masters.
> @@ -550,6 +574,7 @@ static int at24_write(void *priv, unsigned int off, void
> *val, size_t count)
>   status = at24->write_func(at24, buf, off, count);
>   if (status < 0) {
>   mutex_unlock(>lock);
> + pm_runtime_put(>dev);
>   return status;
>   }
>   buf += status;
> @@ -559,6 +584,8 @@ static int at24_write(void *priv, unsigned int off, void
> *val, size_t count)
> 
>   mutex_unlock(>lock);
> 
> + pm_runtime_put(>dev);
> +
>   return 0;
>  }
> 
> @@ -743,11 +770,17 @@ static int at24_probe(struct i2c_client *client, const
> struct i2c_device_id *id)
> 
>   i2c_set_clientdata(client, at24);
> 
> + /* enable runtime pm */
> + pm_runtime_get_noresume(>dev);
> + pm_runtime_set_active(>dev);
> + pm_runtime_enable(>dev);
> +
>   /*
>* Perform a one-byte test read to verify that the
>* chip is functional.
>*/
>   err = at24_read(at24, 0, _byte, 1);
> + pm_runtime_put(>dev);
>   if (err) {
>   err = -ENODEV;
>   goto err_clients;
> @@ -795,6 +828,8 @@ static int at24_probe(struct i2c_client *client, const
> struct i2c_device_id *id)
>   if (at24->client[i])
>   i2c_unregister_device(at24->client[i]);
> 
> + pm_runtime_disable(>dev);
> +
>   return err;
>  }
> 
> @@ -810,6 +845,9 @@ static int at24_remove(struct i2c_client *client)
>   for (i = 1; i < at24->num_addresses; i++)
>   i2c_unregister_device(at24->client[i]);
> 
> + pm_runtime_disable(>dev);
> + pm_runtime_set_suspended(>dev);
> +
>   return 0;
>  }
> 
> --
> 1.9.1



RE: [PATCH v6 2/3] eeprom: at24: add support to fetch eeprom device property "size"

2017-09-19 Thread Mani, Rajmohan
Adding Tomasz...

> -Original Message-
> From: Mohandass, Divagar
> Sent: Monday, September 04, 2017 3:29 AM
> To: robh...@kernel.org; mark.rutl...@arm.com; w...@the-dreams.de;
> sakari.ai...@iki.fi
> Cc: devicet...@vger.kernel.org; linux-...@vger.kernel.org; linux-
> ker...@vger.kernel.org; Mani, Rajmohan <rajmohan.m...@intel.com>;
> Mohandass, Divagar <divagar.mohand...@intel.com>
> Subject: [PATCH v6 2/3] eeprom: at24: add support to fetch eeprom device
> property "size"
> 
> Obtain the size of the EEPROM chip from DT if the "size" property is specified
> for the device.
> 
> Signed-off-by: Divagar Mohandass <divagar.mohand...@intel.com>
> ---
>  drivers/misc/eeprom/at24.c | 4 
>  1 file changed, 4 insertions(+)
> 
> diff --git a/drivers/misc/eeprom/at24.c b/drivers/misc/eeprom/at24.c index
> 764ff5df..2199c42 100644
> --- a/drivers/misc/eeprom/at24.c
> +++ b/drivers/misc/eeprom/at24.c
> @@ -570,6 +570,10 @@ static void at24_get_pdata(struct device *dev, struct
> at24_platform_data *chip)
>   if (device_property_present(dev, "read-only"))
>   chip->flags |= AT24_FLAG_READONLY;
> 
> + err = device_property_read_u32(dev, "size", );
> + if (!err)
> + chip->byte_len = val;
> +
>   err = device_property_read_u32(dev, "pagesize", );
>   if (!err) {
>   chip->page_size = val;
> --
> 1.9.1



RE: [PATCH v6 2/3] eeprom: at24: add support to fetch eeprom device property "size"

2017-09-19 Thread Mani, Rajmohan
Adding Tomasz...

> -Original Message-
> From: Mohandass, Divagar
> Sent: Monday, September 04, 2017 3:29 AM
> To: robh...@kernel.org; mark.rutl...@arm.com; w...@the-dreams.de;
> sakari.ai...@iki.fi
> Cc: devicet...@vger.kernel.org; linux-...@vger.kernel.org; linux-
> ker...@vger.kernel.org; Mani, Rajmohan ;
> Mohandass, Divagar 
> Subject: [PATCH v6 2/3] eeprom: at24: add support to fetch eeprom device
> property "size"
> 
> Obtain the size of the EEPROM chip from DT if the "size" property is specified
> for the device.
> 
> Signed-off-by: Divagar Mohandass 
> ---
>  drivers/misc/eeprom/at24.c | 4 
>  1 file changed, 4 insertions(+)
> 
> diff --git a/drivers/misc/eeprom/at24.c b/drivers/misc/eeprom/at24.c index
> 764ff5df..2199c42 100644
> --- a/drivers/misc/eeprom/at24.c
> +++ b/drivers/misc/eeprom/at24.c
> @@ -570,6 +570,10 @@ static void at24_get_pdata(struct device *dev, struct
> at24_platform_data *chip)
>   if (device_property_present(dev, "read-only"))
>   chip->flags |= AT24_FLAG_READONLY;
> 
> + err = device_property_read_u32(dev, "size", );
> + if (!err)
> + chip->byte_len = val;
> +
>   err = device_property_read_u32(dev, "pagesize", );
>   if (!err) {
>   chip->page_size = val;
> --
> 1.9.1



RE: [PATCH v6 1/3] dt-bindings: add eeprom "size" property

2017-09-19 Thread Mani, Rajmohan
Adding Tomasz...

> -Original Message-
> From: Mohandass, Divagar
> Sent: Monday, September 04, 2017 3:29 AM
> To: robh...@kernel.org; mark.rutl...@arm.com; w...@the-dreams.de;
> sakari.ai...@iki.fi
> Cc: devicet...@vger.kernel.org; linux-...@vger.kernel.org; linux-
> ker...@vger.kernel.org; Mani, Rajmohan <rajmohan.m...@intel.com>;
> Mohandass, Divagar <divagar.mohand...@intel.com>
> Subject: [PATCH v6 1/3] dt-bindings: add eeprom "size" property
> 
> This adds eeprom "size" as optional property for i2c eeproms.
> The "size" property allows explicitly specifying the size of the EEPROM chip 
> in
> bytes.
> 
> Signed-off-by: Divagar Mohandass <divagar.mohand...@intel.com>
> Acked-by: Rob Herring <r...@kernel.org>
> ---
>  Documentation/devicetree/bindings/eeprom/eeprom.txt | 2 ++
>  1 file changed, 2 insertions(+)
> 
> diff --git a/Documentation/devicetree/bindings/eeprom/eeprom.txt
> b/Documentation/devicetree/bindings/eeprom/eeprom.txt
> index 5696eb5..1436569 100644
> --- a/Documentation/devicetree/bindings/eeprom/eeprom.txt
> +++ b/Documentation/devicetree/bindings/eeprom/eeprom.txt
> @@ -32,6 +32,8 @@ Optional properties:
> 
>- read-only: this parameterless property disables writes to the eeprom
> 
> +  - size: total eeprom size in bytes
> +
>  Example:
> 
>  eeprom@52 {
> --
> 1.9.1



RE: [PATCH v6 1/3] dt-bindings: add eeprom "size" property

2017-09-19 Thread Mani, Rajmohan
Adding Tomasz...

> -Original Message-
> From: Mohandass, Divagar
> Sent: Monday, September 04, 2017 3:29 AM
> To: robh...@kernel.org; mark.rutl...@arm.com; w...@the-dreams.de;
> sakari.ai...@iki.fi
> Cc: devicet...@vger.kernel.org; linux-...@vger.kernel.org; linux-
> ker...@vger.kernel.org; Mani, Rajmohan ;
> Mohandass, Divagar 
> Subject: [PATCH v6 1/3] dt-bindings: add eeprom "size" property
> 
> This adds eeprom "size" as optional property for i2c eeproms.
> The "size" property allows explicitly specifying the size of the EEPROM chip 
> in
> bytes.
> 
> Signed-off-by: Divagar Mohandass 
> Acked-by: Rob Herring 
> ---
>  Documentation/devicetree/bindings/eeprom/eeprom.txt | 2 ++
>  1 file changed, 2 insertions(+)
> 
> diff --git a/Documentation/devicetree/bindings/eeprom/eeprom.txt
> b/Documentation/devicetree/bindings/eeprom/eeprom.txt
> index 5696eb5..1436569 100644
> --- a/Documentation/devicetree/bindings/eeprom/eeprom.txt
> +++ b/Documentation/devicetree/bindings/eeprom/eeprom.txt
> @@ -32,6 +32,8 @@ Optional properties:
> 
>- read-only: this parameterless property disables writes to the eeprom
> 
> +  - size: total eeprom size in bytes
> +
>  Example:
> 
>  eeprom@52 {
> --
> 1.9.1



RE: [PATCH v6 0/3] enable eeprom "size" property and runtime pm

2017-09-19 Thread Mani, Rajmohan
Adding Tomasz...

> -Original Message-
> From: Sakari Ailus [mailto:sakari.ai...@iki.fi]
> Sent: Tuesday, September 05, 2017 6:48 AM
> To: Mohandass, Divagar <divagar.mohand...@intel.com>
> Cc: robh...@kernel.org; mark.rutl...@arm.com; w...@the-dreams.de;
> devicet...@vger.kernel.org; linux-...@vger.kernel.org; linux-
> ker...@vger.kernel.org; Mani, Rajmohan <rajmohan.m...@intel.com>
> Subject: Re: [PATCH v6 0/3] enable eeprom "size" property and runtime pm
> 
> Hi Divagar,
> 
> On Mon, Sep 04, 2017 at 03:58:45PM +0530, Divagar Mohandass wrote:
> > This series adds support for eeprom "size" property which will be read
> > by the driver for eeprom size. The existing ACPI has a different
> > default size which can be overridden with a DSD property value provided by
> the platform FW.
> >
> > This series also adds support for runtime PM. The eeprom driver
> > currently did not have support for runtime PM and the device was kept in D0
> throughout.
> >
> > [v1]
> > - Add support for eeprom "size" property.
> > - Add runtime PM support to the driver.
> >
> > [v2]
> > - Improved the patch subject.
> >
> > [v3]
> > - Addressed comments from Sakari Ailus.
> > - Improved patch description.
> > - Improved pm support patch.
> >
> > [v4]
> > - Improved runtime pm support.
> > - Addressed comments from Sakari Ailus.
> >
> > [v5]
> > - Addressed comments from Sakari Ailus.
> > - Improved error handling for PM support.
> >
> > [v6]
> > - Addressed comments from Sakari Ailus.
> >
> > Divagar Mohandass (3):
> >   dt-bindings: add eeprom "size" property
> >   eeprom: at24: add support to fetch eeprom device property "size"
> >   eeprom: at24: enable runtime pm support
> >
> >  .../devicetree/bindings/eeprom/eeprom.txt  |  2 ++
> >  drivers/misc/eeprom/at24.c | 42 
> > ++
> >  2 files changed, 44 insertions(+)
> 
> Thanks for the update!
> 
> For the set:
> 
> Reviewed-by: Sakari Ailus <sakari.ai...@linux.intel.com>
> 
> --
> Kind regards,
> 
> Sakari Ailus
> e-mail: sakari.ai...@iki.fi


RE: [PATCH v6 0/3] enable eeprom "size" property and runtime pm

2017-09-19 Thread Mani, Rajmohan
Adding Tomasz...

> -Original Message-
> From: Sakari Ailus [mailto:sakari.ai...@iki.fi]
> Sent: Tuesday, September 05, 2017 6:48 AM
> To: Mohandass, Divagar 
> Cc: robh...@kernel.org; mark.rutl...@arm.com; w...@the-dreams.de;
> devicet...@vger.kernel.org; linux-...@vger.kernel.org; linux-
> ker...@vger.kernel.org; Mani, Rajmohan 
> Subject: Re: [PATCH v6 0/3] enable eeprom "size" property and runtime pm
> 
> Hi Divagar,
> 
> On Mon, Sep 04, 2017 at 03:58:45PM +0530, Divagar Mohandass wrote:
> > This series adds support for eeprom "size" property which will be read
> > by the driver for eeprom size. The existing ACPI has a different
> > default size which can be overridden with a DSD property value provided by
> the platform FW.
> >
> > This series also adds support for runtime PM. The eeprom driver
> > currently did not have support for runtime PM and the device was kept in D0
> throughout.
> >
> > [v1]
> > - Add support for eeprom "size" property.
> > - Add runtime PM support to the driver.
> >
> > [v2]
> > - Improved the patch subject.
> >
> > [v3]
> > - Addressed comments from Sakari Ailus.
> > - Improved patch description.
> > - Improved pm support patch.
> >
> > [v4]
> > - Improved runtime pm support.
> > - Addressed comments from Sakari Ailus.
> >
> > [v5]
> > - Addressed comments from Sakari Ailus.
> > - Improved error handling for PM support.
> >
> > [v6]
> > - Addressed comments from Sakari Ailus.
> >
> > Divagar Mohandass (3):
> >   dt-bindings: add eeprom "size" property
> >   eeprom: at24: add support to fetch eeprom device property "size"
> >   eeprom: at24: enable runtime pm support
> >
> >  .../devicetree/bindings/eeprom/eeprom.txt  |  2 ++
> >  drivers/misc/eeprom/at24.c | 42 
> > ++
> >  2 files changed, 44 insertions(+)
> 
> Thanks for the update!
> 
> For the set:
> 
> Reviewed-by: Sakari Ailus 
> 
> --
> Kind regards,
> 
> Sakari Ailus
> e-mail: sakari.ai...@iki.fi


RE: [PATCH v5 0/3] TPS68470 PMIC drivers

2017-09-07 Thread Mani, Rajmohan
Hi Rafael,

> Subject: RE: [PATCH v5 0/3] TPS68470 PMIC drivers
> 
> Hi Rafael,
> 
> > >> > >> > This is the patch series for TPS68470 PMIC that works as a
> > >> > >> > camera
> > PMIC.
> > >> > >> >
> > >> > >> > The patch series provide the following 3 drivers, to help
> > >> > >> > configure the
> > >> voltage regulators, clocks and GPIOs provided by the TPS68470 PMIC,
> > >> to be able to use the camera sensors connected to this PMIC.
> > >> > >> >
> > >> > >> > TPS68470 MFD driver:
> > >> > >> > This is the multi function driver that initializes the
> > >> > >> > TPS68470 PMIC and
> > >> supports the GPIO and Op Region functions.
> > >> > >> >
> > >> > >> > TPS68470 GPIO driver:
> > >> > >> > This is the PMIC GPIO driver that will be used by the OS
> > >> > >> > GPIO layer,
> > >> when the BIOS / firmware triggered GPIO access is done.
> > >> > >> >
> > >> > >> > TPS68470 Op Region driver:
> > >> > >> > This is the driver that will be invoked, when the BIOS /
> > >> > >> > firmware
> > >> configures the voltage / clock for the sensors / vcm devices
> > >> connected to the PMIC.
> > >> > >> >
> > >> > >>
> > >> > >> All three patches are good to me (we did few rounds of
> > >> > >> internal review before posting v4)
> > >> > >>
> > >> > >> Reviewed-by: Andy Shevchenko 
> > >> > >
> > >> > > OK, so how should they be routed?
> > >> >
> > >> > Good question. I don't know how last time PMIC drivers were
> > >> > merged, here I think is just sane to route vi MFD with immutable
> > >> > branch created.
> > >>
> > >> OK
> > >>
> > >> I will assume that the series will go in through MFD then.
> > >>
> > >
> > > Now that the MFD and GPIO patches of v6 of this series have been
> > > applied
> > on respective trees, can you advise the next steps for the ACPI / PMIC
> > Opregion driver?
> >
> > Well, it would have been better to route the whole series through one tree.
> > Now it's better to wait until the two other trees get merged and then
> > apply the opregion patch.
> >
> 
> Ack.
> Let me get back once the other 2 trees are merged.
> 

Both MFD and GPIO patches of this series got merged upstream as of today.

Thanks
Raj


RE: [PATCH v5 0/3] TPS68470 PMIC drivers

2017-09-07 Thread Mani, Rajmohan
Hi Rafael,

> Subject: RE: [PATCH v5 0/3] TPS68470 PMIC drivers
> 
> Hi Rafael,
> 
> > >> > >> > This is the patch series for TPS68470 PMIC that works as a
> > >> > >> > camera
> > PMIC.
> > >> > >> >
> > >> > >> > The patch series provide the following 3 drivers, to help
> > >> > >> > configure the
> > >> voltage regulators, clocks and GPIOs provided by the TPS68470 PMIC,
> > >> to be able to use the camera sensors connected to this PMIC.
> > >> > >> >
> > >> > >> > TPS68470 MFD driver:
> > >> > >> > This is the multi function driver that initializes the
> > >> > >> > TPS68470 PMIC and
> > >> supports the GPIO and Op Region functions.
> > >> > >> >
> > >> > >> > TPS68470 GPIO driver:
> > >> > >> > This is the PMIC GPIO driver that will be used by the OS
> > >> > >> > GPIO layer,
> > >> when the BIOS / firmware triggered GPIO access is done.
> > >> > >> >
> > >> > >> > TPS68470 Op Region driver:
> > >> > >> > This is the driver that will be invoked, when the BIOS /
> > >> > >> > firmware
> > >> configures the voltage / clock for the sensors / vcm devices
> > >> connected to the PMIC.
> > >> > >> >
> > >> > >>
> > >> > >> All three patches are good to me (we did few rounds of
> > >> > >> internal review before posting v4)
> > >> > >>
> > >> > >> Reviewed-by: Andy Shevchenko 
> > >> > >
> > >> > > OK, so how should they be routed?
> > >> >
> > >> > Good question. I don't know how last time PMIC drivers were
> > >> > merged, here I think is just sane to route vi MFD with immutable
> > >> > branch created.
> > >>
> > >> OK
> > >>
> > >> I will assume that the series will go in through MFD then.
> > >>
> > >
> > > Now that the MFD and GPIO patches of v6 of this series have been
> > > applied
> > on respective trees, can you advise the next steps for the ACPI / PMIC
> > Opregion driver?
> >
> > Well, it would have been better to route the whole series through one tree.
> > Now it's better to wait until the two other trees get merged and then
> > apply the opregion patch.
> >
> 
> Ack.
> Let me get back once the other 2 trees are merged.
> 

Both MFD and GPIO patches of this series got merged upstream as of today.

Thanks
Raj


RE: [PATCH v5 0/3] TPS68470 PMIC drivers

2017-08-21 Thread Mani, Rajmohan
Hi Rafael,

> >> > >> > This is the patch series for TPS68470 PMIC that works as a camera
> PMIC.
> >> > >> >
> >> > >> > The patch series provide the following 3 drivers, to help
> >> > >> > configure the
> >> voltage regulators, clocks and GPIOs provided by the TPS68470 PMIC,
> >> to be able to use the camera sensors connected to this PMIC.
> >> > >> >
> >> > >> > TPS68470 MFD driver:
> >> > >> > This is the multi function driver that initializes the
> >> > >> > TPS68470 PMIC and
> >> supports the GPIO and Op Region functions.
> >> > >> >
> >> > >> > TPS68470 GPIO driver:
> >> > >> > This is the PMIC GPIO driver that will be used by the OS GPIO
> >> > >> > layer,
> >> when the BIOS / firmware triggered GPIO access is done.
> >> > >> >
> >> > >> > TPS68470 Op Region driver:
> >> > >> > This is the driver that will be invoked, when the BIOS /
> >> > >> > firmware
> >> configures the voltage / clock for the sensors / vcm devices
> >> connected to the PMIC.
> >> > >> >
> >> > >>
> >> > >> All three patches are good to me (we did few rounds of internal
> >> > >> review before posting v4)
> >> > >>
> >> > >> Reviewed-by: Andy Shevchenko 
> >> > >
> >> > > OK, so how should they be routed?
> >> >
> >> > Good question. I don't know how last time PMIC drivers were merged,
> >> > here I think is just sane to route vi MFD with immutable branch
> >> > created.
> >>
> >> OK
> >>
> >> I will assume that the series will go in through MFD then.
> >>
> >
> > Now that the MFD and GPIO patches of v6 of this series have been applied
> on respective trees, can you advise the next steps for the ACPI / PMIC 
> Opregion
> driver?
> 
> Well, it would have been better to route the whole series through one tree.
> Now it's better to wait until the two other trees get merged and then apply 
> the
> opregion patch.
> 

Ack.
Let me get back once the other 2 trees are merged.

Thanks
Raj


RE: [PATCH v5 0/3] TPS68470 PMIC drivers

2017-08-21 Thread Mani, Rajmohan
Hi Rafael,

> >> > >> > This is the patch series for TPS68470 PMIC that works as a camera
> PMIC.
> >> > >> >
> >> > >> > The patch series provide the following 3 drivers, to help
> >> > >> > configure the
> >> voltage regulators, clocks and GPIOs provided by the TPS68470 PMIC,
> >> to be able to use the camera sensors connected to this PMIC.
> >> > >> >
> >> > >> > TPS68470 MFD driver:
> >> > >> > This is the multi function driver that initializes the
> >> > >> > TPS68470 PMIC and
> >> supports the GPIO and Op Region functions.
> >> > >> >
> >> > >> > TPS68470 GPIO driver:
> >> > >> > This is the PMIC GPIO driver that will be used by the OS GPIO
> >> > >> > layer,
> >> when the BIOS / firmware triggered GPIO access is done.
> >> > >> >
> >> > >> > TPS68470 Op Region driver:
> >> > >> > This is the driver that will be invoked, when the BIOS /
> >> > >> > firmware
> >> configures the voltage / clock for the sensors / vcm devices
> >> connected to the PMIC.
> >> > >> >
> >> > >>
> >> > >> All three patches are good to me (we did few rounds of internal
> >> > >> review before posting v4)
> >> > >>
> >> > >> Reviewed-by: Andy Shevchenko 
> >> > >
> >> > > OK, so how should they be routed?
> >> >
> >> > Good question. I don't know how last time PMIC drivers were merged,
> >> > here I think is just sane to route vi MFD with immutable branch
> >> > created.
> >>
> >> OK
> >>
> >> I will assume that the series will go in through MFD then.
> >>
> >
> > Now that the MFD and GPIO patches of v6 of this series have been applied
> on respective trees, can you advise the next steps for the ACPI / PMIC 
> Opregion
> driver?
> 
> Well, it would have been better to route the whole series through one tree.
> Now it's better to wait until the two other trees get merged and then apply 
> the
> opregion patch.
> 

Ack.
Let me get back once the other 2 trees are merged.

Thanks
Raj


RE: [PATCH v5 0/3] TPS68470 PMIC drivers

2017-08-21 Thread Mani, Rajmohan
Hi Andy,

> > >> > This is the patch series for TPS68470 PMIC that works as a camera PMIC.
> > >> >
> > >> > The patch series provide the following 3 drivers, to help configure the
> voltage regulators, clocks and GPIOs provided by the TPS68470 PMIC, to be
> able to use the camera sensors connected to this PMIC.
> > >> >
> > >> > TPS68470 MFD driver:
> > >> > This is the multi function driver that initializes the TPS68470 PMIC 
> > >> > and
> supports the GPIO and Op Region functions.
> > >> >
> > >> > TPS68470 GPIO driver:
> > >> > This is the PMIC GPIO driver that will be used by the OS GPIO layer,
> when the BIOS / firmware triggered GPIO access is done.
> > >> >
> > >> > TPS68470 Op Region driver:
> > >> > This is the driver that will be invoked, when the BIOS / firmware
> configures the voltage / clock for the sensors / vcm devices connected to the
> PMIC.
> > >> >
> > >>
> > >> All three patches are good to me (we did few rounds of internal
> > >> review before posting v4)
> > >>
> > >> Reviewed-by: Andy Shevchenko 
> > >
> > > OK, so how should they be routed?
> >
> > Good question. I don't know how last time PMIC drivers were merged,
> > here I think is just sane to route vi MFD with immutable branch
> > created.
> 
> OK
> 
> I will assume that the series will go in through MFD then.
> 

Now that the MFD and GPIO patches of v6 of this series have been applied on 
respective trees, can you advise the next steps for the ACPI / PMIC Opregion 
driver?

Thanks
Raj


RE: [PATCH v5 0/3] TPS68470 PMIC drivers

2017-08-21 Thread Mani, Rajmohan
Hi Andy,

> > >> > This is the patch series for TPS68470 PMIC that works as a camera PMIC.
> > >> >
> > >> > The patch series provide the following 3 drivers, to help configure the
> voltage regulators, clocks and GPIOs provided by the TPS68470 PMIC, to be
> able to use the camera sensors connected to this PMIC.
> > >> >
> > >> > TPS68470 MFD driver:
> > >> > This is the multi function driver that initializes the TPS68470 PMIC 
> > >> > and
> supports the GPIO and Op Region functions.
> > >> >
> > >> > TPS68470 GPIO driver:
> > >> > This is the PMIC GPIO driver that will be used by the OS GPIO layer,
> when the BIOS / firmware triggered GPIO access is done.
> > >> >
> > >> > TPS68470 Op Region driver:
> > >> > This is the driver that will be invoked, when the BIOS / firmware
> configures the voltage / clock for the sensors / vcm devices connected to the
> PMIC.
> > >> >
> > >>
> > >> All three patches are good to me (we did few rounds of internal
> > >> review before posting v4)
> > >>
> > >> Reviewed-by: Andy Shevchenko 
> > >
> > > OK, so how should they be routed?
> >
> > Good question. I don't know how last time PMIC drivers were merged,
> > here I think is just sane to route vi MFD with immutable branch
> > created.
> 
> OK
> 
> I will assume that the series will go in through MFD then.
> 

Now that the MFD and GPIO patches of v6 of this series have been applied on 
respective trees, can you advise the next steps for the ACPI / PMIC Opregion 
driver?

Thanks
Raj


RE: [PATCH v6 2/3] gpio: Add support for TPS68470 GPIOs

2017-08-14 Thread Mani, Rajmohan
Hi Linus,

> -Original Message-
> From: Linus Walleij [mailto:linus.wall...@linaro.org]
> Sent: Monday, August 14, 2017 6:39 AM
> To: Mani, Rajmohan <rajmohan.m...@intel.com>
> Cc: linux-kernel@vger.kernel.org; linux-g...@vger.kernel.org; ACPI Devel
> Maling List <linux-a...@vger.kernel.org>; Lee Jones <lee.jo...@linaro.org>;
> Alexandre Courbot <gnu...@gmail.com>; Rafael J. Wysocki
> <r...@rjwysocki.net>; Len Brown <l...@kernel.org>;
> sakari.ai...@linux.intel.com; Andy Shevchenko
> <andy.shevche...@gmail.com>
> Subject: Re: [PATCH v6 2/3] gpio: Add support for TPS68470 GPIOs
> 
> On Sat, Jul 29, 2017 at 2:30 AM, Rajmohan Mani
> <rajmohan.m...@intel.com> wrote:
> 
> > This patch adds support for TPS68470 GPIOs.
> > There are 7 GPIOs and a few sensor related GPIOs.
> > These GPIOs can be requested and configured as appropriate.
> >
> > The GPIOs are also provided with descriptive names.
> > However, the typical use case is that the OS GPIO driver will interact
> > with TPS68470 GPIO driver to configure these GPIOs, as requested by
> > the platform firmware.
> >
> > Signed-off-by: Rajmohan Mani <rajmohan.m...@intel.com>
> > Reviewed-by: Linus Walleij <linus.wall...@linaro.org>
> 
> (...)
> 
> > +config GPIO_TPS68470
> > +   bool "TPS68470 GPIO"
> > +   depends on MFD_TPS68470
> 
> Guarded by this symbol, so:
> patch applied to the GPIO tree, thanks!
> 

Thanks for the reviews and update.
Raj


RE: [PATCH v6 2/3] gpio: Add support for TPS68470 GPIOs

2017-08-14 Thread Mani, Rajmohan
Hi Linus,

> -Original Message-
> From: Linus Walleij [mailto:linus.wall...@linaro.org]
> Sent: Monday, August 14, 2017 6:39 AM
> To: Mani, Rajmohan 
> Cc: linux-kernel@vger.kernel.org; linux-g...@vger.kernel.org; ACPI Devel
> Maling List ; Lee Jones ;
> Alexandre Courbot ; Rafael J. Wysocki
> ; Len Brown ;
> sakari.ai...@linux.intel.com; Andy Shevchenko
> 
> Subject: Re: [PATCH v6 2/3] gpio: Add support for TPS68470 GPIOs
> 
> On Sat, Jul 29, 2017 at 2:30 AM, Rajmohan Mani
>  wrote:
> 
> > This patch adds support for TPS68470 GPIOs.
> > There are 7 GPIOs and a few sensor related GPIOs.
> > These GPIOs can be requested and configured as appropriate.
> >
> > The GPIOs are also provided with descriptive names.
> > However, the typical use case is that the OS GPIO driver will interact
> > with TPS68470 GPIO driver to configure these GPIOs, as requested by
> > the platform firmware.
> >
> > Signed-off-by: Rajmohan Mani 
> > Reviewed-by: Linus Walleij 
> 
> (...)
> 
> > +config GPIO_TPS68470
> > +   bool "TPS68470 GPIO"
> > +   depends on MFD_TPS68470
> 
> Guarded by this symbol, so:
> patch applied to the GPIO tree, thanks!
> 

Thanks for the reviews and update.
Raj


RE: [PATCH v6 0/3] TPS68470 PMIC drivers

2017-08-09 Thread Mani, Rajmohan
Hi All,

Now that Lee has applied the MFD patch 
(https://git.kernel.org/pub/scm/linux/kernel/git/lee/mfd.git/commit/?h=for-mfd-next=6a58f36b0c49c8179804bead579f5ff6304f0245),
 can someone help clarify the next steps for the GPIO and ACPI / PMIC OpRegion 
patches of this series?

Both these patches depend on the MFD patch (MFD_TPS68470 config option) to 
compile.

Thanks
Raj

> -Original Message-
> From: Mani, Rajmohan
> Sent: Friday, July 28, 2017 5:30 PM
> To: linux-kernel@vger.kernel.org; linux-g...@vger.kernel.org; linux-
> a...@vger.kernel.org
> Cc: Lee Jones <lee.jo...@linaro.org>; Linus Walleij
> <linus.wall...@linaro.org>; Alexandre Courbot <gnu...@gmail.com>; Rafael
> J. Wysocki <r...@rjwysocki.net>; Len Brown <l...@kernel.org>;
> sakari.ai...@linux.intel.com; Andy Shevchenko
> <andy.shevche...@gmail.com>; Mani, Rajmohan
> <rajmohan.m...@intel.com>
> Subject: [PATCH v6 0/3] TPS68470 PMIC drivers
> 
> This is the patch series for TPS68470 PMIC that works as a camera PMIC.
> 
> The patch series provide the following 3 drivers, to help configure the 
> voltage
> regulators, clocks and GPIOs provided by the TPS68470 PMIC, to be able to
> use the camera sensors connected to this PMIC.
> 
> TPS68470 MFD driver:
> This is the multi function driver that initializes the TPS68470 PMIC and
> supports the GPIO and Op Region functions.
> 
> TPS68470 GPIO driver:
> This is the PMIC GPIO driver that will be used by the OS GPIO layer, when the
> BIOS / firmware triggered GPIO access is done.
> 
> TPS68470 Op Region driver:
> This is the driver that will be invoked, when the BIOS / firmware configures
> the voltage / clock for the sensors / vcm devices connected to the PMIC.
> 
> ---
> 
> Update on 2 GPIO chips implementation over 1:
>   - Attempted to implement 2 GPIO chips, but ran into couple of
> issues in the kernel, so we couldn't get it to work.
>   - It was decided to postpone this change, since it is not
> critical
> 
> Changes in v6:
>   - MFD driver:
>   - Used non-zero return values from regmap_write/read() calls
> to detect error conditions
> 
> Changes in v5:
>   - MFD driver:
>   - Fixed Kconfig description text
>   - Addressed other comments from Lee, related to formatting
> 
>   - GPIO driver:
>   - Formatted the file header text
> 
>   - Opregion driver:
>   - Formatted the file header text
> 
> Changes in v4:
>   - MFD driver:
>   - Removed board specific code and FIXME comment
>   - Moved i2c.h include from tps68470.h to tps68470.c
>   - Moved the TPS68470 REVID read code after PMIC reset
>   - Fixed typo in debug error message (on failure of
> devm_mfd_add_devices() )
>   - Enhanced dependency on I2C by changing it to I2C=y
> (to fix build errors if I2C is built as module
>  e.g tps68470.c:71: undefined reference to
> `__devm_regmap_init_i2c'
>  tps68470.c:117: undefined reference to `i2c_register_driver')
>   - Removed most of the unused header file definitions
>   - Moved devm_mfd_add_devices() after PMIC resett
>   - Used probe_new() and removed i2c_device_id table
> 
> The following patch from Andy is needed for the driver to be
> probed.
> http://marc.info/?l=linux-acpi=150030081523885=2
> 
>   - GPIO driver:
>   - Added newline at the end of Kconfig description
>   - Updated commit message about the descriptive
> names for the GPIOs and the typical usage model
> of the GPIO driver
> 
>   - Opregion driver:
>   - Added dependency on MFD_TPS68470
>   - Converted 2 liner into one line code
> 
> Changes in v3:
>   - MFD driver:
>   - Removed GPIO lookup table
>   - Reverted to probe() for consistency
>   - Addressed other comments from Andy
> 
>   - GPIO driver:
>   - Removed the code that initializes the default values
> of GPIOs to zeros
>   - Used gpiochip_get_data() to access data inside the gpio_chip
> 
> Changes in v2:
>   - MFD driver:
>   - Removed tps68470_* wrappers around regmap_* calls
>   - Removed "struct tps68470"
>   - used devm_mfd_add_devices and removed mutex in mfd driver
>   - Added reasoning about the need of having mfd driver
> as bool/builtin
> 
>   - Opregion driver:
>   - renamed opregion driver file / internal symbol names
> with tps68470_pmic*
>   - Made opregion driver tables as const
>   - Removed unused *handler_context in common handler
>   - Replaced "int" with "unsi

RE: [PATCH v6 0/3] TPS68470 PMIC drivers

2017-08-09 Thread Mani, Rajmohan
Hi All,

Now that Lee has applied the MFD patch 
(https://git.kernel.org/pub/scm/linux/kernel/git/lee/mfd.git/commit/?h=for-mfd-next=6a58f36b0c49c8179804bead579f5ff6304f0245),
 can someone help clarify the next steps for the GPIO and ACPI / PMIC OpRegion 
patches of this series?

Both these patches depend on the MFD patch (MFD_TPS68470 config option) to 
compile.

Thanks
Raj

> -Original Message-
> From: Mani, Rajmohan
> Sent: Friday, July 28, 2017 5:30 PM
> To: linux-kernel@vger.kernel.org; linux-g...@vger.kernel.org; linux-
> a...@vger.kernel.org
> Cc: Lee Jones ; Linus Walleij
> ; Alexandre Courbot ; Rafael
> J. Wysocki ; Len Brown ;
> sakari.ai...@linux.intel.com; Andy Shevchenko
> ; Mani, Rajmohan
> 
> Subject: [PATCH v6 0/3] TPS68470 PMIC drivers
> 
> This is the patch series for TPS68470 PMIC that works as a camera PMIC.
> 
> The patch series provide the following 3 drivers, to help configure the 
> voltage
> regulators, clocks and GPIOs provided by the TPS68470 PMIC, to be able to
> use the camera sensors connected to this PMIC.
> 
> TPS68470 MFD driver:
> This is the multi function driver that initializes the TPS68470 PMIC and
> supports the GPIO and Op Region functions.
> 
> TPS68470 GPIO driver:
> This is the PMIC GPIO driver that will be used by the OS GPIO layer, when the
> BIOS / firmware triggered GPIO access is done.
> 
> TPS68470 Op Region driver:
> This is the driver that will be invoked, when the BIOS / firmware configures
> the voltage / clock for the sensors / vcm devices connected to the PMIC.
> 
> ---
> 
> Update on 2 GPIO chips implementation over 1:
>   - Attempted to implement 2 GPIO chips, but ran into couple of
> issues in the kernel, so we couldn't get it to work.
>   - It was decided to postpone this change, since it is not
> critical
> 
> Changes in v6:
>   - MFD driver:
>   - Used non-zero return values from regmap_write/read() calls
> to detect error conditions
> 
> Changes in v5:
>   - MFD driver:
>   - Fixed Kconfig description text
>   - Addressed other comments from Lee, related to formatting
> 
>   - GPIO driver:
>   - Formatted the file header text
> 
>   - Opregion driver:
>   - Formatted the file header text
> 
> Changes in v4:
>   - MFD driver:
>   - Removed board specific code and FIXME comment
>   - Moved i2c.h include from tps68470.h to tps68470.c
>   - Moved the TPS68470 REVID read code after PMIC reset
>   - Fixed typo in debug error message (on failure of
> devm_mfd_add_devices() )
>   - Enhanced dependency on I2C by changing it to I2C=y
> (to fix build errors if I2C is built as module
>  e.g tps68470.c:71: undefined reference to
> `__devm_regmap_init_i2c'
>  tps68470.c:117: undefined reference to `i2c_register_driver')
>   - Removed most of the unused header file definitions
>   - Moved devm_mfd_add_devices() after PMIC resett
>   - Used probe_new() and removed i2c_device_id table
> 
> The following patch from Andy is needed for the driver to be
> probed.
> http://marc.info/?l=linux-acpi=150030081523885=2
> 
>   - GPIO driver:
>   - Added newline at the end of Kconfig description
>   - Updated commit message about the descriptive
> names for the GPIOs and the typical usage model
> of the GPIO driver
> 
>   - Opregion driver:
>   - Added dependency on MFD_TPS68470
>   - Converted 2 liner into one line code
> 
> Changes in v3:
>   - MFD driver:
>   - Removed GPIO lookup table
>   - Reverted to probe() for consistency
>   - Addressed other comments from Andy
> 
>   - GPIO driver:
>   - Removed the code that initializes the default values
> of GPIOs to zeros
>   - Used gpiochip_get_data() to access data inside the gpio_chip
> 
> Changes in v2:
>   - MFD driver:
>   - Removed tps68470_* wrappers around regmap_* calls
>   - Removed "struct tps68470"
>   - used devm_mfd_add_devices and removed mutex in mfd driver
>   - Added reasoning about the need of having mfd driver
> as bool/builtin
> 
>   - Opregion driver:
>   - renamed opregion driver file / internal symbol names
> with tps68470_pmic*
>   - Made opregion driver tables as const
>   - Removed unused *handler_context in common handler
>   - Replaced "int" with "unsigned int"
>   - Changed to WARN macro to dev_warn()
>   - Destroyed mutex on error
>   - Added reasoning about the need of having Opregion driver
> as bool/bu

RE: [PATCH v6 1/3] mfd: Add new mfd device TPS68470

2017-08-08 Thread Mani, Rajmohan
Thanks Lee.

Sorry for the noise, as some keystrokes sent out the empty response earlier.

Raj

> -Original Message-
> From: Mani, Rajmohan
> Sent: Tuesday, August 08, 2017 11:58 AM
> To: 'Lee Jones' <lee.jo...@linaro.org>
> Cc: linux-kernel@vger.kernel.org; linux-g...@vger.kernel.org; linux-
> a...@vger.kernel.org; Linus Walleij <linus.wall...@linaro.org>; Alexandre
> Courbot <gnu...@gmail.com>; Rafael J. Wysocki <r...@rjwysocki.net>; Len
> Brown <l...@kernel.org>; sakari.ai...@linux.intel.com; Andy Shevchenko
> <andy.shevche...@gmail.com>
> Subject: RE: [PATCH v6 1/3] mfd: Add new mfd device TPS68470
> 
> 
> 
> > -Original Message-
> > From: Lee Jones [mailto:lee.jo...@linaro.org]
> > Sent: Tuesday, August 08, 2017 12:40 AM
> > To: Mani, Rajmohan <rajmohan.m...@intel.com>
> > Cc: linux-kernel@vger.kernel.org; linux-g...@vger.kernel.org; linux-
> > a...@vger.kernel.org; Linus Walleij <linus.wall...@linaro.org>;
> > Alexandre Courbot <gnu...@gmail.com>; Rafael J. Wysocki
> > <r...@rjwysocki.net>; Len Brown <l...@kernel.org>;
> > sakari.ai...@linux.intel.com; Andy Shevchenko
> > <andy.shevche...@gmail.com>
> > Subject: Re: [PATCH v6 1/3] mfd: Add new mfd device TPS68470
> >
> > On Fri, 28 Jul 2017, Rajmohan Mani wrote:
> >
> > > The TPS68470 device is an advanced power management unit that
> powers
> > a
> > > Compact Camera Module (CCM), generates clocks for image sensors,
> > > drives a dual LED for Flash and incorporates two LED drivers for
> > > general purpose indicators.
> > >
> > > This patch adds support for TPS68470 mfd device.
> > >
> > > Signed-off-by: Rajmohan Mani <rajmohan.m...@intel.com>
> > > ---
> > >  drivers/mfd/Kconfig  |  18 
> > >  drivers/mfd/Makefile |   1 +
> > >  drivers/mfd/tps68470.c   | 106
> > +++
> > >  include/linux/mfd/tps68470.h |  97
> > > +++
> > >  4 files changed, 222 insertions(+)
> > >  create mode 100644 drivers/mfd/tps68470.c  create mode 100644
> > > include/linux/mfd/tps68470.h
> >
> > Applied, thanks.
> >
> > --
> > Lee Jones
> > Linaro STMicroelectronics Landing Team Lead Linaro.org │ Open source
> > software for ARM SoCs Follow Linaro: Facebook | Twitter | Blog


RE: [PATCH v6 1/3] mfd: Add new mfd device TPS68470

2017-08-08 Thread Mani, Rajmohan
Thanks Lee.

Sorry for the noise, as some keystrokes sent out the empty response earlier.

Raj

> -Original Message-
> From: Mani, Rajmohan
> Sent: Tuesday, August 08, 2017 11:58 AM
> To: 'Lee Jones' 
> Cc: linux-kernel@vger.kernel.org; linux-g...@vger.kernel.org; linux-
> a...@vger.kernel.org; Linus Walleij ; Alexandre
> Courbot ; Rafael J. Wysocki ; Len
> Brown ; sakari.ai...@linux.intel.com; Andy Shevchenko
> 
> Subject: RE: [PATCH v6 1/3] mfd: Add new mfd device TPS68470
> 
> 
> 
> > -Original Message-
> > From: Lee Jones [mailto:lee.jo...@linaro.org]
> > Sent: Tuesday, August 08, 2017 12:40 AM
> > To: Mani, Rajmohan 
> > Cc: linux-kernel@vger.kernel.org; linux-g...@vger.kernel.org; linux-
> > a...@vger.kernel.org; Linus Walleij ;
> > Alexandre Courbot ; Rafael J. Wysocki
> > ; Len Brown ;
> > sakari.ai...@linux.intel.com; Andy Shevchenko
> > 
> > Subject: Re: [PATCH v6 1/3] mfd: Add new mfd device TPS68470
> >
> > On Fri, 28 Jul 2017, Rajmohan Mani wrote:
> >
> > > The TPS68470 device is an advanced power management unit that
> powers
> > a
> > > Compact Camera Module (CCM), generates clocks for image sensors,
> > > drives a dual LED for Flash and incorporates two LED drivers for
> > > general purpose indicators.
> > >
> > > This patch adds support for TPS68470 mfd device.
> > >
> > > Signed-off-by: Rajmohan Mani 
> > > ---
> > >  drivers/mfd/Kconfig  |  18 
> > >  drivers/mfd/Makefile |   1 +
> > >  drivers/mfd/tps68470.c   | 106
> > +++
> > >  include/linux/mfd/tps68470.h |  97
> > > +++
> > >  4 files changed, 222 insertions(+)
> > >  create mode 100644 drivers/mfd/tps68470.c  create mode 100644
> > > include/linux/mfd/tps68470.h
> >
> > Applied, thanks.
> >
> > --
> > Lee Jones
> > Linaro STMicroelectronics Landing Team Lead Linaro.org │ Open source
> > software for ARM SoCs Follow Linaro: Facebook | Twitter | Blog


RE: [PATCH v6 1/3] mfd: Add new mfd device TPS68470

2017-08-08 Thread Mani, Rajmohan


> -Original Message-
> From: Lee Jones [mailto:lee.jo...@linaro.org]
> Sent: Tuesday, August 08, 2017 12:40 AM
> To: Mani, Rajmohan <rajmohan.m...@intel.com>
> Cc: linux-kernel@vger.kernel.org; linux-g...@vger.kernel.org; linux-
> a...@vger.kernel.org; Linus Walleij <linus.wall...@linaro.org>; Alexandre
> Courbot <gnu...@gmail.com>; Rafael J. Wysocki <r...@rjwysocki.net>; Len
> Brown <l...@kernel.org>; sakari.ai...@linux.intel.com; Andy Shevchenko
> <andy.shevche...@gmail.com>
> Subject: Re: [PATCH v6 1/3] mfd: Add new mfd device TPS68470
> 
> On Fri, 28 Jul 2017, Rajmohan Mani wrote:
> 
> > The TPS68470 device is an advanced power management unit that powers
> a
> > Compact Camera Module (CCM), generates clocks for image sensors,
> > drives a dual LED for Flash and incorporates two LED drivers for
> > general purpose indicators.
> >
> > This patch adds support for TPS68470 mfd device.
> >
> > Signed-off-by: Rajmohan Mani <rajmohan.m...@intel.com>
> > ---
> >  drivers/mfd/Kconfig  |  18 
> >  drivers/mfd/Makefile |   1 +
> >  drivers/mfd/tps68470.c   | 106
> +++
> >  include/linux/mfd/tps68470.h |  97
> > +++
> >  4 files changed, 222 insertions(+)
> >  create mode 100644 drivers/mfd/tps68470.c  create mode 100644
> > include/linux/mfd/tps68470.h
> 
> Applied, thanks.
> 
> --
> Lee Jones
> Linaro STMicroelectronics Landing Team Lead Linaro.org │ Open source
> software for ARM SoCs Follow Linaro: Facebook | Twitter | Blog


RE: [PATCH v6 1/3] mfd: Add new mfd device TPS68470

2017-08-08 Thread Mani, Rajmohan


> -Original Message-
> From: Lee Jones [mailto:lee.jo...@linaro.org]
> Sent: Tuesday, August 08, 2017 12:40 AM
> To: Mani, Rajmohan 
> Cc: linux-kernel@vger.kernel.org; linux-g...@vger.kernel.org; linux-
> a...@vger.kernel.org; Linus Walleij ; Alexandre
> Courbot ; Rafael J. Wysocki ; Len
> Brown ; sakari.ai...@linux.intel.com; Andy Shevchenko
> 
> Subject: Re: [PATCH v6 1/3] mfd: Add new mfd device TPS68470
> 
> On Fri, 28 Jul 2017, Rajmohan Mani wrote:
> 
> > The TPS68470 device is an advanced power management unit that powers
> a
> > Compact Camera Module (CCM), generates clocks for image sensors,
> > drives a dual LED for Flash and incorporates two LED drivers for
> > general purpose indicators.
> >
> > This patch adds support for TPS68470 mfd device.
> >
> > Signed-off-by: Rajmohan Mani 
> > ---
> >  drivers/mfd/Kconfig  |  18 
> >  drivers/mfd/Makefile |   1 +
> >  drivers/mfd/tps68470.c   | 106
> +++
> >  include/linux/mfd/tps68470.h |  97
> > +++
> >  4 files changed, 222 insertions(+)
> >  create mode 100644 drivers/mfd/tps68470.c  create mode 100644
> > include/linux/mfd/tps68470.h
> 
> Applied, thanks.
> 
> --
> Lee Jones
> Linaro STMicroelectronics Landing Team Lead Linaro.org │ Open source
> software for ARM SoCs Follow Linaro: Facebook | Twitter | Blog


[PATCH v6 1/3] mfd: Add new mfd device TPS68470

2017-07-28 Thread Rajmohan Mani
The TPS68470 device is an advanced power management
unit that powers a Compact Camera Module (CCM),
generates clocks for image sensors, drives a dual
LED for Flash and incorporates two LED drivers for
general purpose indicators.

This patch adds support for TPS68470 mfd device.

Signed-off-by: Rajmohan Mani <rajmohan.m...@intel.com>
---
 drivers/mfd/Kconfig  |  18 
 drivers/mfd/Makefile |   1 +
 drivers/mfd/tps68470.c   | 106 +++
 include/linux/mfd/tps68470.h |  97 +++
 4 files changed, 222 insertions(+)
 create mode 100644 drivers/mfd/tps68470.c
 create mode 100644 include/linux/mfd/tps68470.h

diff --git a/drivers/mfd/Kconfig b/drivers/mfd/Kconfig
index 94ad2c1..74f41a1 100644
--- a/drivers/mfd/Kconfig
+++ b/drivers/mfd/Kconfig
@@ -1337,6 +1337,24 @@ config MFD_TPS65217
  This driver can also be built as a module.  If so, the module
  will be called tps65217.
 
+config MFD_TPS68470
+   bool "TI TPS68470 Power Management / LED chips"
+   depends on ACPI && I2C=y
+   select MFD_CORE
+   select REGMAP_I2C
+   select I2C_DESIGNWARE_PLATFORM
+   help
+ If you say yes here you get support for the TPS68470 series of
+ Power Management / LED chips.
+
+ These include voltage regulators, LEDs and other features
+ that are often used in portable devices.
+
+ This option is a bool as it provides an ACPI operation
+ region, which must be available before any of the devices
+ using this are probed. This option also configures the
+ designware-i2c driver to be built-in, for the same reason.
+
 config MFD_TI_LP873X
tristate "TI LP873X Power Management IC"
depends on I2C
diff --git a/drivers/mfd/Makefile b/drivers/mfd/Makefile
index 080793b..0b1fd82 100644
--- a/drivers/mfd/Makefile
+++ b/drivers/mfd/Makefile
@@ -83,6 +83,7 @@ obj-$(CONFIG_MFD_TPS65910)+= tps65910.o
 obj-$(CONFIG_MFD_TPS65912) += tps65912-core.o
 obj-$(CONFIG_MFD_TPS65912_I2C) += tps65912-i2c.o
 obj-$(CONFIG_MFD_TPS65912_SPI)  += tps65912-spi.o
+obj-$(CONFIG_MFD_TPS68470) += tps68470.o
 obj-$(CONFIG_MFD_TPS80031) += tps80031.o
 obj-$(CONFIG_MENELAUS) += menelaus.o
 
diff --git a/drivers/mfd/tps68470.c b/drivers/mfd/tps68470.c
new file mode 100644
index 000..189efae
--- /dev/null
+++ b/drivers/mfd/tps68470.c
@@ -0,0 +1,106 @@
+/*
+ * TPS68470 chip Parent driver
+ *
+ * Copyright (C) 2017 Intel Corporation
+ *
+ * Authors:
+ * Rajmohan Mani <rajmohan.m...@intel.com>
+ * Tianshu Qiu <tian.shu@intel.com>
+ * Jian Xu Zheng <jian.xu.zh...@intel.com>
+ * Yuning Pu <yuning...@intel.com>
+ *
+ * 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 version 2.
+ *
+ * This program is distributed "as is" WITHOUT ANY WARRANTY of any
+ * kind, whether express or implied; without even the implied warranty
+ * of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ */
+
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+
+static const struct mfd_cell tps68470s[] = {
+   { .name = "tps68470-gpio" },
+   { .name = "tps68470_pmic_opregion" },
+};
+
+static const struct regmap_config tps68470_regmap_config = {
+   .reg_bits = 8,
+   .val_bits = 8,
+   .max_register = TPS68470_REG_MAX,
+};
+
+static int tps68470_chip_init(struct device *dev, struct regmap *regmap)
+{
+   unsigned int version;
+   int ret;
+
+   /* Force software reset */
+   ret = regmap_write(regmap, TPS68470_REG_RESET, TPS68470_REG_RESET_MASK);
+   if (ret)
+   return ret;
+
+   ret = regmap_read(regmap, TPS68470_REG_REVID, );
+   if (ret) {
+   dev_err(dev, "Failed to read revision register: %d\n", ret);
+   return ret;
+   }
+
+   dev_info(dev, "TPS68470 REVID: 0x%x\n", version);
+
+   return 0;
+}
+
+static int tps68470_probe(struct i2c_client *client)
+{
+   struct device *dev = >dev;
+   struct regmap *regmap;
+   int ret;
+
+   regmap = devm_regmap_init_i2c(client, _regmap_config);
+   if (IS_ERR(regmap)) {
+   dev_err(dev, "devm_regmap_init_i2c Error %ld\n",
+   PTR_ERR(regmap));
+   return PTR_ERR(regmap);
+   }
+
+   i2c_set_clientdata(client, regmap);
+
+   ret = tps68470_chip_init(dev, regmap);
+   if (ret < 0) {
+   dev_err(dev, "TPS68470 Init Error %d\n", ret);
+   return ret;
+   }
+
+   ret = devm_mfd_add_devices(dev, PLATFORM_DEVID_NONE, tps68470s,
+  

[PATCH v6 1/3] mfd: Add new mfd device TPS68470

2017-07-28 Thread Rajmohan Mani
The TPS68470 device is an advanced power management
unit that powers a Compact Camera Module (CCM),
generates clocks for image sensors, drives a dual
LED for Flash and incorporates two LED drivers for
general purpose indicators.

This patch adds support for TPS68470 mfd device.

Signed-off-by: Rajmohan Mani 
---
 drivers/mfd/Kconfig  |  18 
 drivers/mfd/Makefile |   1 +
 drivers/mfd/tps68470.c   | 106 +++
 include/linux/mfd/tps68470.h |  97 +++
 4 files changed, 222 insertions(+)
 create mode 100644 drivers/mfd/tps68470.c
 create mode 100644 include/linux/mfd/tps68470.h

diff --git a/drivers/mfd/Kconfig b/drivers/mfd/Kconfig
index 94ad2c1..74f41a1 100644
--- a/drivers/mfd/Kconfig
+++ b/drivers/mfd/Kconfig
@@ -1337,6 +1337,24 @@ config MFD_TPS65217
  This driver can also be built as a module.  If so, the module
  will be called tps65217.
 
+config MFD_TPS68470
+   bool "TI TPS68470 Power Management / LED chips"
+   depends on ACPI && I2C=y
+   select MFD_CORE
+   select REGMAP_I2C
+   select I2C_DESIGNWARE_PLATFORM
+   help
+ If you say yes here you get support for the TPS68470 series of
+ Power Management / LED chips.
+
+ These include voltage regulators, LEDs and other features
+ that are often used in portable devices.
+
+ This option is a bool as it provides an ACPI operation
+ region, which must be available before any of the devices
+ using this are probed. This option also configures the
+ designware-i2c driver to be built-in, for the same reason.
+
 config MFD_TI_LP873X
tristate "TI LP873X Power Management IC"
depends on I2C
diff --git a/drivers/mfd/Makefile b/drivers/mfd/Makefile
index 080793b..0b1fd82 100644
--- a/drivers/mfd/Makefile
+++ b/drivers/mfd/Makefile
@@ -83,6 +83,7 @@ obj-$(CONFIG_MFD_TPS65910)+= tps65910.o
 obj-$(CONFIG_MFD_TPS65912) += tps65912-core.o
 obj-$(CONFIG_MFD_TPS65912_I2C) += tps65912-i2c.o
 obj-$(CONFIG_MFD_TPS65912_SPI)  += tps65912-spi.o
+obj-$(CONFIG_MFD_TPS68470) += tps68470.o
 obj-$(CONFIG_MFD_TPS80031) += tps80031.o
 obj-$(CONFIG_MENELAUS) += menelaus.o
 
diff --git a/drivers/mfd/tps68470.c b/drivers/mfd/tps68470.c
new file mode 100644
index 000..189efae
--- /dev/null
+++ b/drivers/mfd/tps68470.c
@@ -0,0 +1,106 @@
+/*
+ * TPS68470 chip Parent driver
+ *
+ * Copyright (C) 2017 Intel Corporation
+ *
+ * Authors:
+ * Rajmohan Mani 
+ * Tianshu Qiu 
+ * Jian Xu Zheng 
+ * Yuning Pu 
+ *
+ * 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 version 2.
+ *
+ * This program is distributed "as is" WITHOUT ANY WARRANTY of any
+ * kind, whether express or implied; without even the implied warranty
+ * of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ */
+
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+
+static const struct mfd_cell tps68470s[] = {
+   { .name = "tps68470-gpio" },
+   { .name = "tps68470_pmic_opregion" },
+};
+
+static const struct regmap_config tps68470_regmap_config = {
+   .reg_bits = 8,
+   .val_bits = 8,
+   .max_register = TPS68470_REG_MAX,
+};
+
+static int tps68470_chip_init(struct device *dev, struct regmap *regmap)
+{
+   unsigned int version;
+   int ret;
+
+   /* Force software reset */
+   ret = regmap_write(regmap, TPS68470_REG_RESET, TPS68470_REG_RESET_MASK);
+   if (ret)
+   return ret;
+
+   ret = regmap_read(regmap, TPS68470_REG_REVID, );
+   if (ret) {
+   dev_err(dev, "Failed to read revision register: %d\n", ret);
+   return ret;
+   }
+
+   dev_info(dev, "TPS68470 REVID: 0x%x\n", version);
+
+   return 0;
+}
+
+static int tps68470_probe(struct i2c_client *client)
+{
+   struct device *dev = >dev;
+   struct regmap *regmap;
+   int ret;
+
+   regmap = devm_regmap_init_i2c(client, _regmap_config);
+   if (IS_ERR(regmap)) {
+   dev_err(dev, "devm_regmap_init_i2c Error %ld\n",
+   PTR_ERR(regmap));
+   return PTR_ERR(regmap);
+   }
+
+   i2c_set_clientdata(client, regmap);
+
+   ret = tps68470_chip_init(dev, regmap);
+   if (ret < 0) {
+   dev_err(dev, "TPS68470 Init Error %d\n", ret);
+   return ret;
+   }
+
+   ret = devm_mfd_add_devices(dev, PLATFORM_DEVID_NONE, tps68470s,
+ ARRAY_SIZE(tps68470s), NULL, 0, NULL);
+   if (ret < 0) {
+   dev_err(dev, "devm_mfd_add_devices failed: %d\n", ret);

[PATCH v6 0/3] TPS68470 PMIC drivers

2017-07-28 Thread Rajmohan Mani
This is the patch series for TPS68470 PMIC that works as a camera PMIC.

The patch series provide the following 3 drivers, to help configure the voltage 
regulators, clocks and GPIOs provided by the TPS68470 PMIC, to be able to use 
the camera sensors connected to this PMIC.

TPS68470 MFD driver:
This is the multi function driver that initializes the TPS68470 PMIC and 
supports the GPIO and Op Region functions.

TPS68470 GPIO driver:
This is the PMIC GPIO driver that will be used by the OS GPIO layer, when the 
BIOS / firmware triggered GPIO access is done.

TPS68470 Op Region driver:
This is the driver that will be invoked, when the BIOS / firmware configures 
the voltage / clock for the sensors / vcm devices connected to the PMIC.

---

Update on 2 GPIO chips implementation over 1:
- Attempted to implement 2 GPIO chips, but ran into couple of
  issues in the kernel, so we couldn't get it to work.
- It was decided to postpone this change, since it is not
  critical

Changes in v6:
- MFD driver:
- Used non-zero return values from regmap_write/read() calls
  to detect error conditions

Changes in v5:
- MFD driver:
- Fixed Kconfig description text
- Addressed other comments from Lee, related to formatting

- GPIO driver:
- Formatted the file header text

- Opregion driver:
- Formatted the file header text

Changes in v4:
- MFD driver:
- Removed board specific code and FIXME comment
- Moved i2c.h include from tps68470.h to tps68470.c
- Moved the TPS68470 REVID read code after PMIC reset
- Fixed typo in debug error message (on failure of
  devm_mfd_add_devices() )
- Enhanced dependency on I2C by changing it to I2C=y
  (to fix build errors if I2C is built as module
   e.g tps68470.c:71: undefined reference to `__devm_regmap_init_i2c'
   tps68470.c:117: undefined reference to `i2c_register_driver')
- Removed most of the unused header file definitions
- Moved devm_mfd_add_devices() after PMIC resett
- Used probe_new() and removed i2c_device_id table
  
  The following patch from Andy is needed for the driver to be
  probed.
  http://marc.info/?l=linux-acpi=150030081523885=2  
  
- GPIO driver:
- Added newline at the end of Kconfig description
- Updated commit message about the descriptive
  names for the GPIOs and the typical usage model
  of the GPIO driver

- Opregion driver:
- Added dependency on MFD_TPS68470
- Converted 2 liner into one line code

Changes in v3:
- MFD driver:
- Removed GPIO lookup table
- Reverted to probe() for consistency
- Addressed other comments from Andy

- GPIO driver:
- Removed the code that initializes the default values
  of GPIOs to zeros
- Used gpiochip_get_data() to access data inside the gpio_chip
 
Changes in v2:
- MFD driver:
- Removed tps68470_* wrappers around regmap_* calls
- Removed "struct tps68470"
- used devm_mfd_add_devices and removed mutex in mfd driver
- Added reasoning about the need of having mfd driver
  as bool/builtin

- Opregion driver:
- renamed opregion driver file / internal symbol names
  with tps68470_pmic*
- Made opregion driver tables as const
- Removed unused *handler_context in common handler
- Replaced "int" with "unsigned int"
- Changed to WARN macro to dev_warn()
- Destroyed mutex on error
- Added reasoning about the need of having Opregion driver
  as bool/builtin

- GPIO driver:
- Implemented get_direction() in the GPIO driver
- Setup gpio_chip.names
- Moved the GPIO lookup table code inside mfd driver
- Added reasoning about the need of having GPIO driver
  as bool/builtin

---

Rajmohan Mani (3):
  mfd: Add new mfd device TPS68470
  gpio: Add support for TPS68470 GPIOs
  ACPI / PMIC: Add TI PMIC TPS68470 operation region driver

 drivers/acpi/Kconfig  |  16 ++
 drivers/acpi/Makefile |   2 +
 drivers/acpi/pmic/tps68470_pmic.c | 455 ++
 drivers/gpio/Kconfig  |  15 ++
 drivers/gpio/Makefile |   1 +
 drivers/gpio/gpio-tps68470.c  | 176 +++
 drivers/mfd/Kconfig   |  18 ++
 drivers/mfd/Makefile  |   1 +
 drivers/mfd/tps68470.c| 106 +
 include/linux/mfd/tps68470.h  |  97 
 10 files changed, 887 insertions(+)
 create mode 100644 drivers/acpi/pmic/tps68470_pmic.c
 create mode 100644 drivers/gpio/gpio-tps68470.c
 create mode 100644 drivers/mfd/tps68470.c
 create mode 100644 include/linux/mfd/tps68470.h

-- 
1.9.1



[PATCH v6 0/3] TPS68470 PMIC drivers

2017-07-28 Thread Rajmohan Mani
This is the patch series for TPS68470 PMIC that works as a camera PMIC.

The patch series provide the following 3 drivers, to help configure the voltage 
regulators, clocks and GPIOs provided by the TPS68470 PMIC, to be able to use 
the camera sensors connected to this PMIC.

TPS68470 MFD driver:
This is the multi function driver that initializes the TPS68470 PMIC and 
supports the GPIO and Op Region functions.

TPS68470 GPIO driver:
This is the PMIC GPIO driver that will be used by the OS GPIO layer, when the 
BIOS / firmware triggered GPIO access is done.

TPS68470 Op Region driver:
This is the driver that will be invoked, when the BIOS / firmware configures 
the voltage / clock for the sensors / vcm devices connected to the PMIC.

---

Update on 2 GPIO chips implementation over 1:
- Attempted to implement 2 GPIO chips, but ran into couple of
  issues in the kernel, so we couldn't get it to work.
- It was decided to postpone this change, since it is not
  critical

Changes in v6:
- MFD driver:
- Used non-zero return values from regmap_write/read() calls
  to detect error conditions

Changes in v5:
- MFD driver:
- Fixed Kconfig description text
- Addressed other comments from Lee, related to formatting

- GPIO driver:
- Formatted the file header text

- Opregion driver:
- Formatted the file header text

Changes in v4:
- MFD driver:
- Removed board specific code and FIXME comment
- Moved i2c.h include from tps68470.h to tps68470.c
- Moved the TPS68470 REVID read code after PMIC reset
- Fixed typo in debug error message (on failure of
  devm_mfd_add_devices() )
- Enhanced dependency on I2C by changing it to I2C=y
  (to fix build errors if I2C is built as module
   e.g tps68470.c:71: undefined reference to `__devm_regmap_init_i2c'
   tps68470.c:117: undefined reference to `i2c_register_driver')
- Removed most of the unused header file definitions
- Moved devm_mfd_add_devices() after PMIC resett
- Used probe_new() and removed i2c_device_id table
  
  The following patch from Andy is needed for the driver to be
  probed.
  http://marc.info/?l=linux-acpi=150030081523885=2  
  
- GPIO driver:
- Added newline at the end of Kconfig description
- Updated commit message about the descriptive
  names for the GPIOs and the typical usage model
  of the GPIO driver

- Opregion driver:
- Added dependency on MFD_TPS68470
- Converted 2 liner into one line code

Changes in v3:
- MFD driver:
- Removed GPIO lookup table
- Reverted to probe() for consistency
- Addressed other comments from Andy

- GPIO driver:
- Removed the code that initializes the default values
  of GPIOs to zeros
- Used gpiochip_get_data() to access data inside the gpio_chip
 
Changes in v2:
- MFD driver:
- Removed tps68470_* wrappers around regmap_* calls
- Removed "struct tps68470"
- used devm_mfd_add_devices and removed mutex in mfd driver
- Added reasoning about the need of having mfd driver
  as bool/builtin

- Opregion driver:
- renamed opregion driver file / internal symbol names
  with tps68470_pmic*
- Made opregion driver tables as const
- Removed unused *handler_context in common handler
- Replaced "int" with "unsigned int"
- Changed to WARN macro to dev_warn()
- Destroyed mutex on error
- Added reasoning about the need of having Opregion driver
  as bool/builtin

- GPIO driver:
- Implemented get_direction() in the GPIO driver
- Setup gpio_chip.names
- Moved the GPIO lookup table code inside mfd driver
- Added reasoning about the need of having GPIO driver
  as bool/builtin

---

Rajmohan Mani (3):
  mfd: Add new mfd device TPS68470
  gpio: Add support for TPS68470 GPIOs
  ACPI / PMIC: Add TI PMIC TPS68470 operation region driver

 drivers/acpi/Kconfig  |  16 ++
 drivers/acpi/Makefile |   2 +
 drivers/acpi/pmic/tps68470_pmic.c | 455 ++
 drivers/gpio/Kconfig  |  15 ++
 drivers/gpio/Makefile |   1 +
 drivers/gpio/gpio-tps68470.c  | 176 +++
 drivers/mfd/Kconfig   |  18 ++
 drivers/mfd/Makefile  |   1 +
 drivers/mfd/tps68470.c| 106 +
 include/linux/mfd/tps68470.h  |  97 
 10 files changed, 887 insertions(+)
 create mode 100644 drivers/acpi/pmic/tps68470_pmic.c
 create mode 100644 drivers/gpio/gpio-tps68470.c
 create mode 100644 drivers/mfd/tps68470.c
 create mode 100644 include/linux/mfd/tps68470.h

-- 
1.9.1



[PATCH v6 3/3] ACPI / PMIC: Add TI PMIC TPS68470 operation region driver

2017-07-28 Thread Rajmohan Mani
The Kabylake platform coreboot (Chrome OS equivalent of
BIOS) has defined 4 operation regions for the TI TPS68470 PMIC.
These operation regions are to enable/disable voltage
regulators, configure voltage regulators, enable/disable
clocks and to configure clocks.

This config adds ACPI operation region support for TI TPS68470 PMIC.
TPS68470 device is an advanced power management unit that powers
a Compact Camera Module (CCM), generates clocks for image sensors,
drives a dual LED for flash and incorporates two LED drivers for
general purpose indicators.
This driver enables ACPI operation region support to control voltage
regulators and clocks for the TPS68470 PMIC.

Signed-off-by: Rajmohan Mani <rajmohan.m...@intel.com>
---
 drivers/acpi/Kconfig  |  16 ++
 drivers/acpi/Makefile |   2 +
 drivers/acpi/pmic/tps68470_pmic.c | 455 ++
 3 files changed, 473 insertions(+)
 create mode 100644 drivers/acpi/pmic/tps68470_pmic.c

diff --git a/drivers/acpi/Kconfig b/drivers/acpi/Kconfig
index 1ce52f8..e124a82d 100644
--- a/drivers/acpi/Kconfig
+++ b/drivers/acpi/Kconfig
@@ -535,4 +535,20 @@ if ARM64
 source "drivers/acpi/arm64/Kconfig"
 endif
 
+config TPS68470_PMIC_OPREGION
+   bool "ACPI operation region support for TPS68470 PMIC"
+   depends on MFD_TPS68470
+   help
+ This config adds ACPI operation region support for TI TPS68470 PMIC.
+ TPS68470 device is an advanced power management unit that powers
+ a Compact Camera Module (CCM), generates clocks for image sensors,
+ drives a dual LED for flash and incorporates two LED drivers for
+ general purpose indicators.
+ This driver enables ACPI operation region support control voltage
+ regulators and clocks.
+
+ This option is a bool as it provides an ACPI operation
+ region, which must be available before any of the devices
+ using this, are probed.
+
 endif  # ACPI
diff --git a/drivers/acpi/Makefile b/drivers/acpi/Makefile
index b1aacfc..2d70a7f 100644
--- a/drivers/acpi/Makefile
+++ b/drivers/acpi/Makefile
@@ -106,6 +106,8 @@ obj-$(CONFIG_CHT_WC_PMIC_OPREGION) += 
pmic/intel_pmic_chtwc.o
 
 obj-$(CONFIG_ACPI_CONFIGFS)+= acpi_configfs.o
 
+obj-$(CONFIG_TPS68470_PMIC_OPREGION)   += pmic/tps68470_pmic.o
+
 video-objs += acpi_video.o video_detect.o
 obj-y  += dptf/
 
diff --git a/drivers/acpi/pmic/tps68470_pmic.c 
b/drivers/acpi/pmic/tps68470_pmic.c
new file mode 100644
index 000..7f3c567
--- /dev/null
+++ b/drivers/acpi/pmic/tps68470_pmic.c
@@ -0,0 +1,455 @@
+/*
+ * TI TPS68470 PMIC operation region driver
+ *
+ * Copyright (C) 2017 Intel Corporation. All rights reserved.
+ *
+ * Author: Rajmohan Mani <rajmohan.m...@intel.com>
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License version
+ * 2 as published by the Free Software Foundation.
+ *
+ * This program is distributed "as is" WITHOUT ANY WARRANTY of any
+ * kind, whether express or implied; without even the implied warranty
+ * of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * Based on drivers/acpi/pmic/intel_pmic* drivers
+ */
+
+#include 
+#include 
+#include 
+#include 
+#include 
+
+struct tps68470_pmic_table {
+   u32 address;/* operation region address */
+   u32 reg;/* corresponding register */
+   u32 bitmask;/* bit mask for power, clock */
+};
+
+#define TI_PMIC_POWER_OPREGION_ID  0xB0
+#define TI_PMIC_VR_VAL_OPREGION_ID 0xB1
+#define TI_PMIC_CLOCK_OPREGION_ID  0xB2
+#define TI_PMIC_CLKFREQ_OPREGION_ID0xB3
+
+struct tps68470_pmic_opregion {
+   struct mutex lock;
+   struct regmap *regmap;
+};
+
+#define S_IO_I2C_EN(BIT(0) | BIT(1))
+
+static const struct tps68470_pmic_table power_table[] = {
+   {
+   .address = 0x00,
+   .reg = TPS68470_REG_S_I2C_CTL,
+   .bitmask = S_IO_I2C_EN,
+   /* S_I2C_CTL */
+   },
+   {
+   .address = 0x04,
+   .reg = TPS68470_REG_VCMCTL,
+   .bitmask = BIT(0),
+   /* VCMCTL */
+   },
+   {
+   .address = 0x08,
+   .reg = TPS68470_REG_VAUX1CTL,
+   .bitmask = BIT(0),
+   /* VAUX1_CTL */
+   },
+   {
+   .address = 0x0C,
+   .reg = TPS68470_REG_VAUX2CTL,
+   .bitmask = BIT(0),
+   /* VAUX2CTL */
+   },
+   {
+   .address = 0x10,
+   .reg = TPS68470_REG_VACTL,
+   .bitmask = BIT(0),
+   /* VACTL */
+   },
+   {
+   .address = 0x14,
+   .reg = TPS68470_R

[PATCH v6 3/3] ACPI / PMIC: Add TI PMIC TPS68470 operation region driver

2017-07-28 Thread Rajmohan Mani
The Kabylake platform coreboot (Chrome OS equivalent of
BIOS) has defined 4 operation regions for the TI TPS68470 PMIC.
These operation regions are to enable/disable voltage
regulators, configure voltage regulators, enable/disable
clocks and to configure clocks.

This config adds ACPI operation region support for TI TPS68470 PMIC.
TPS68470 device is an advanced power management unit that powers
a Compact Camera Module (CCM), generates clocks for image sensors,
drives a dual LED for flash and incorporates two LED drivers for
general purpose indicators.
This driver enables ACPI operation region support to control voltage
regulators and clocks for the TPS68470 PMIC.

Signed-off-by: Rajmohan Mani 
---
 drivers/acpi/Kconfig  |  16 ++
 drivers/acpi/Makefile |   2 +
 drivers/acpi/pmic/tps68470_pmic.c | 455 ++
 3 files changed, 473 insertions(+)
 create mode 100644 drivers/acpi/pmic/tps68470_pmic.c

diff --git a/drivers/acpi/Kconfig b/drivers/acpi/Kconfig
index 1ce52f8..e124a82d 100644
--- a/drivers/acpi/Kconfig
+++ b/drivers/acpi/Kconfig
@@ -535,4 +535,20 @@ if ARM64
 source "drivers/acpi/arm64/Kconfig"
 endif
 
+config TPS68470_PMIC_OPREGION
+   bool "ACPI operation region support for TPS68470 PMIC"
+   depends on MFD_TPS68470
+   help
+ This config adds ACPI operation region support for TI TPS68470 PMIC.
+ TPS68470 device is an advanced power management unit that powers
+ a Compact Camera Module (CCM), generates clocks for image sensors,
+ drives a dual LED for flash and incorporates two LED drivers for
+ general purpose indicators.
+ This driver enables ACPI operation region support control voltage
+ regulators and clocks.
+
+ This option is a bool as it provides an ACPI operation
+ region, which must be available before any of the devices
+ using this, are probed.
+
 endif  # ACPI
diff --git a/drivers/acpi/Makefile b/drivers/acpi/Makefile
index b1aacfc..2d70a7f 100644
--- a/drivers/acpi/Makefile
+++ b/drivers/acpi/Makefile
@@ -106,6 +106,8 @@ obj-$(CONFIG_CHT_WC_PMIC_OPREGION) += 
pmic/intel_pmic_chtwc.o
 
 obj-$(CONFIG_ACPI_CONFIGFS)+= acpi_configfs.o
 
+obj-$(CONFIG_TPS68470_PMIC_OPREGION)   += pmic/tps68470_pmic.o
+
 video-objs += acpi_video.o video_detect.o
 obj-y  += dptf/
 
diff --git a/drivers/acpi/pmic/tps68470_pmic.c 
b/drivers/acpi/pmic/tps68470_pmic.c
new file mode 100644
index 000..7f3c567
--- /dev/null
+++ b/drivers/acpi/pmic/tps68470_pmic.c
@@ -0,0 +1,455 @@
+/*
+ * TI TPS68470 PMIC operation region driver
+ *
+ * Copyright (C) 2017 Intel Corporation. All rights reserved.
+ *
+ * Author: Rajmohan Mani 
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License version
+ * 2 as published by the Free Software Foundation.
+ *
+ * This program is distributed "as is" WITHOUT ANY WARRANTY of any
+ * kind, whether express or implied; without even the implied warranty
+ * of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * Based on drivers/acpi/pmic/intel_pmic* drivers
+ */
+
+#include 
+#include 
+#include 
+#include 
+#include 
+
+struct tps68470_pmic_table {
+   u32 address;/* operation region address */
+   u32 reg;/* corresponding register */
+   u32 bitmask;/* bit mask for power, clock */
+};
+
+#define TI_PMIC_POWER_OPREGION_ID  0xB0
+#define TI_PMIC_VR_VAL_OPREGION_ID 0xB1
+#define TI_PMIC_CLOCK_OPREGION_ID  0xB2
+#define TI_PMIC_CLKFREQ_OPREGION_ID0xB3
+
+struct tps68470_pmic_opregion {
+   struct mutex lock;
+   struct regmap *regmap;
+};
+
+#define S_IO_I2C_EN(BIT(0) | BIT(1))
+
+static const struct tps68470_pmic_table power_table[] = {
+   {
+   .address = 0x00,
+   .reg = TPS68470_REG_S_I2C_CTL,
+   .bitmask = S_IO_I2C_EN,
+   /* S_I2C_CTL */
+   },
+   {
+   .address = 0x04,
+   .reg = TPS68470_REG_VCMCTL,
+   .bitmask = BIT(0),
+   /* VCMCTL */
+   },
+   {
+   .address = 0x08,
+   .reg = TPS68470_REG_VAUX1CTL,
+   .bitmask = BIT(0),
+   /* VAUX1_CTL */
+   },
+   {
+   .address = 0x0C,
+   .reg = TPS68470_REG_VAUX2CTL,
+   .bitmask = BIT(0),
+   /* VAUX2CTL */
+   },
+   {
+   .address = 0x10,
+   .reg = TPS68470_REG_VACTL,
+   .bitmask = BIT(0),
+   /* VACTL */
+   },
+   {
+   .address = 0x14,
+   .reg = TPS68470_REG_VDCTL,
+   .bitmask = BIT(0),
+   /* VDCTL */
+   },

  1   2   3   >