usb: chipidea: add host role

This adds EHCI host support to the chipidea driver. We want it to be
part of the hdrc driver and not a standalone (sub-)driver module, as
the structure of ehci-hcd.c suggests, so for chipidea controller we
hack it to not provide platform-related code, but only the ehci hcd.

The ehci-platform driver won't work for us here too, because the
controller uses the same registers for both device and host mode and
also otg-related bits, so it's not really possible to put ehci registers
into a separate resource.

This is not a pretty solution, but the alternative is exporting symbols
from the chipidea driver to a ehci-chipidea driver and doing all the
module refcounting.

Signed-off-by: Alexander Shishkin <alexander.shishkin@linux.intel.com>
Cc: Alan Stern <stern@rowland.harvard.edu>
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
diff --git a/drivers/usb/chipidea/ci.h b/drivers/usb/chipidea/ci.h
index 0ab8341..c605acc 100644
--- a/drivers/usb/chipidea/ci.h
+++ b/drivers/usb/chipidea/ci.h
@@ -15,6 +15,7 @@
 
 #include <linux/list.h>
 #include <linux/irqreturn.h>
+#include <linux/usb.h>
 #include <linux/usb/gadget.h>
 
 /******************************************************************************
@@ -84,6 +85,7 @@
 /**
  * struct hw_bank - hardware register mapping representation
  * @lpm: set if the device is LPM capable
+ * @phys: physical address of the controller's registers
  * @abs: absolute address of the beginning of register window
  * @cap: capability registers
  * @op: operational registers
@@ -92,6 +94,7 @@
  */
 struct hw_bank {
 	unsigned	lpm;
+	resource_size_t	phys;
 	void __iomem	*abs;
 	void __iomem	*cap;
 	void __iomem	*op;
@@ -128,6 +131,7 @@
  * @udc_driver: platform specific information supplied by parent device
  * @vbus_active: is VBUS active
  * @transceiver: pointer to USB PHY, if any
+ * @hcd: pointer to usb_hcd for ehci host driver
  */
 struct ci13xxx {
 	struct device			*dev;
@@ -160,6 +164,7 @@
 	struct ci13xxx_udc_driver	*udc_driver;
 	int				vbus_active;
 	struct usb_phy			*transceiver;
+	struct usb_hcd			*hcd;
 };
 
 static inline struct ci_role_driver *ci_role(struct ci13xxx *ci)
@@ -302,7 +307,7 @@
 	return (val & mask) >> ffs_nr(mask);
 }
 
-int hw_device_reset(struct ci13xxx *ci);
+int hw_device_reset(struct ci13xxx *ci, u32 mode);
 
 int hw_port_test_set(struct ci13xxx *ci, u8 mode);