public inbox for linux-omap@vger.kernel.org
 help / color / mirror / Atom feed
* [PATCH 0/2] OMAP: I2C: reprogram OCP_SYSCONFIG after device reset
@ 2008-10-14 12:19 Paul Walmsley
  2008-10-14 12:19 ` [PATCH 1/2] OMAP: I2C: convert 'rev1' flag to generic 'rev' u8 Paul Walmsley
                   ` (3 more replies)
  0 siblings, 4 replies; 6+ messages in thread
From: Paul Walmsley @ 2008-10-14 12:19 UTC (permalink / raw)
  To: linux-omap; +Cc: Richard Woodruff

Hello,

This patch set programs the I2C controller OCP_SYSCONFIG register
after the driver resets the device.  It is derived from the changes
mentioned by Richard Woodruff <r-woodruff2@ti.com> at

http://git.omapzoom.org/?p=omapkernel;a=blob;f=drivers/i2c/busses/i2c-omap.c;hb=d0b4bad4926f9a147a73498f7a62a0ae1cf6f83a

however, the CLOCKACTIVITY change on clk_enable()/clk_disable() in that
code currently seems pointless, so it has been excluded until more
information is available from TI or until problems are encountered.

This patchset should only change behavior on OMAP2x30 and OMAP3xxx devices.

Boot-tested on 2430SDP and 3430SDP; compile-tested with the 5912OSK (OMAP1)
defconfig.  Comments welcome,


- Paul

---

  text    data     bss     dec      hex filename
3472584  160600  105760 3738944  390d40 vmlinux.3430sdp.orig
3472616  160600  105760 3738976  390d60 vmlinux.3430sdp

 drivers/i2c/busses/i2c-omap.c |   65 ++++++++++++++++++++++++++++++++---------
 1 files changed, 50 insertions(+), 15 deletions(-)


^ permalink raw reply	[flat|nested] 6+ messages in thread

* [PATCH 1/2] OMAP: I2C: convert 'rev1' flag to generic 'rev' u8
  2008-10-14 12:19 [PATCH 0/2] OMAP: I2C: reprogram OCP_SYSCONFIG after device reset Paul Walmsley
@ 2008-10-14 12:19 ` Paul Walmsley
  2008-10-14 12:19 ` [PATCH 2/2] OMAP2/3 I2C: reprogram OCP_SYSCONFIG register after reset Paul Walmsley
                   ` (2 subsequent siblings)
  3 siblings, 0 replies; 6+ messages in thread
From: Paul Walmsley @ 2008-10-14 12:19 UTC (permalink / raw)
  To: linux-omap; +Cc: Paul Walmsley

i2c-omap discriminates only between "revision 1" or "greater than
revision 1."  A following patch introduces code that must also
discriminate between rev2.x, rev3.6, and rev3.12 controllers.  Support
this by storing the full revision data from the I2C_REV register, rather
than just a single bit.

The revision definitions may need to be extended for other ES levels
that aren't currently available here.  rev3.6 is what's present on the
2430SDP here (unknown ES revision); rev3.12 is used on the 3430ES2
here.

Signed-off-by: Paul Walmsley <paul@pwsan.com>
---
 drivers/i2c/busses/i2c-omap.c |   25 ++++++++++++++++---------
 1 files changed, 16 insertions(+), 9 deletions(-)

diff --git a/drivers/i2c/busses/i2c-omap.c b/drivers/i2c/busses/i2c-omap.c
index a999606..12bdb69 100644
--- a/drivers/i2c/busses/i2c-omap.c
+++ b/drivers/i2c/busses/i2c-omap.c
@@ -38,6 +38,13 @@
 #include <linux/clk.h>
 #include <linux/io.h>
 
+/* I2C controller revisions */
+#define OMAP_I2C_REV_2			0x20
+
+/* I2C controller revisions present on specific hardware */
+#define OMAP_I2C_REV_ON_2430		0x36
+#define OMAP_I2C_REV_ON_3430		0x3C
+
 /* timeout waiting for the controller to respond */
 #define OMAP_I2C_TIMEOUT (msecs_to_jiffies(1000))
 
@@ -139,7 +146,7 @@ struct omap_i2c_dev {
 						 * fifo_size==0 implies no fifo
 						 * if set, should be trsh+1
 						 */
-	unsigned		rev1:1;
+	u8			rev;
 	unsigned		b_hw:1;		/* bad h/w fixes */
 	unsigned		idle:1;
 	u16			iestate;	/* Saved interrupt register */
@@ -220,7 +227,7 @@ static void omap_i2c_idle(struct omap_i2c_dev *dev)
 
 	dev->iestate = omap_i2c_read_reg(dev, OMAP_I2C_IE_REG);
 	omap_i2c_write_reg(dev, OMAP_I2C_IE_REG, 0);
-	if (dev->rev1)
+	if (dev->rev < OMAP_I2C_REV_2)
 		iv = omap_i2c_read_reg(dev, OMAP_I2C_IV_REG); /* Read clears */
 	else
 		omap_i2c_write_reg(dev, OMAP_I2C_STAT_REG, dev->iestate);
@@ -244,7 +251,7 @@ static int omap_i2c_init(struct omap_i2c_dev *dev)
 	unsigned long timeout;
 	unsigned long internal_clk = 0;
 
-	if (!dev->rev1) {
+	if (dev->rev >= OMAP_I2C_REV_2) {
 		omap_i2c_write_reg(dev, OMAP_I2C_SYSC_REG, OMAP_I2C_SYSC_SRST);
 		/* For some reason we need to set the EN bit before the
 		 * reset done bit gets set. */
@@ -718,6 +725,7 @@ omap_i2c_probe(struct platform_device *pdev)
 	struct omap_i2c_dev	*dev;
 	struct i2c_adapter	*adap;
 	struct resource		*mem, *irq, *ioarea;
+	void *isr;
 	int r;
 	u32 *speed = NULL;
 
@@ -769,8 +777,7 @@ omap_i2c_probe(struct platform_device *pdev)
 
 	omap_i2c_unidle(dev);
 
-	if (cpu_is_omap15xx())
-		dev->rev1 = omap_i2c_read_reg(dev, OMAP_I2C_REV_REG) < 0x20;
+	dev->rev = omap_i2c_read_reg(dev, OMAP_I2C_REV_REG) & 0xff;
 
 	if (cpu_is_omap2430() || cpu_is_omap34xx()) {
 		u16 s;
@@ -791,16 +798,16 @@ omap_i2c_probe(struct platform_device *pdev)
 	/* reset ASAP, clearing any IRQs */
 	omap_i2c_init(dev);
 
-	r = request_irq(dev->irq, dev->rev1 ? omap_i2c_rev1_isr : omap_i2c_isr,
-			0, pdev->name, dev);
+	isr = (dev->rev < OMAP_I2C_REV_2) ? omap_i2c_rev1_isr : omap_i2c_isr;
+	r = request_irq(dev->irq, isr, 0, pdev->name, dev);
 
 	if (r) {
 		dev_err(dev->dev, "failure requesting irq %i\n", dev->irq);
 		goto err_unuse_clocks;
 	}
-	r = omap_i2c_read_reg(dev, OMAP_I2C_REV_REG) & 0xff;
+
 	dev_info(dev->dev, "bus %d rev%d.%d at %d kHz\n",
-		 pdev->id, r >> 4, r & 0xf, dev->speed);
+		 pdev->id, dev->rev >> 4, dev->rev & 0xf, dev->speed);
 
 	omap_i2c_idle(dev);
 



^ permalink raw reply related	[flat|nested] 6+ messages in thread

* [PATCH 2/2] OMAP2/3 I2C: reprogram OCP_SYSCONFIG register after reset
  2008-10-14 12:19 [PATCH 0/2] OMAP: I2C: reprogram OCP_SYSCONFIG after device reset Paul Walmsley
  2008-10-14 12:19 ` [PATCH 1/2] OMAP: I2C: convert 'rev1' flag to generic 'rev' u8 Paul Walmsley
@ 2008-10-14 12:19 ` Paul Walmsley
  2008-10-19 13:12   ` Woodruff, Richard
  2008-10-19 13:06 ` [PATCH 0/2] OMAP: I2C: reprogram OCP_SYSCONFIG after device reset Woodruff, Richard
  2008-11-21 21:34 ` Tony Lindgren
  3 siblings, 1 reply; 6+ messages in thread
From: Paul Walmsley @ 2008-10-14 12:19 UTC (permalink / raw)
  To: linux-omap; +Cc: Paul Walmsley, Richard Woodruff

The I2C controller clears its OCP_SYSCONFIG register after an OCP soft reset.
Reprogram OCP_SYSCONFIG for maximum power savings on rev3.6 controllers
and beyond.  On 2430, this involves setting the module AUTOIDLE bit.
On 3430, this includes module AUTOIDLE, wakeup enable, slave smart-idle,
and considers only the module functional clock state for idle-ack.

Boot-tested on 2430SDP and 3430SDP.

Signed-off-by: Paul Walmsley <paul@pwsan.com>
Cc: Richard Woodruff <r-woodruff2@ti.com>
---
 drivers/i2c/busses/i2c-omap.c |   40 ++++++++++++++++++++++++++++++++++------
 1 files changed, 34 insertions(+), 6 deletions(-)

diff --git a/drivers/i2c/busses/i2c-omap.c b/drivers/i2c/busses/i2c-omap.c
index 12bdb69..d012ad7 100644
--- a/drivers/i2c/busses/i2c-omap.c
+++ b/drivers/i2c/busses/i2c-omap.c
@@ -123,11 +123,19 @@
 #define OMAP_I2C_SYSTEST_SDA_O		(1 << 0)	/* SDA line drive out */
 #endif
 
-/* I2C System Status register (OMAP_I2C_SYSS): */
-#define OMAP_I2C_SYSS_RDONE		(1 << 0)	/* Reset Done */
+/* OCP_SYSSTATUS bit definitions */
+#define SYSS_RESETDONE_MASK		(1 << 0)
+
+/* OCP_SYSCONFIG bit definitions */
+#define SYSC_CLOCKACTIVITY_MASK		(0x3 << 8)
+#define SYSC_SIDLEMODE_MASK		(0x3 << 3)
+#define SYSC_ENAWAKEUP_MASK		(1 << 2)
+#define SYSC_SOFTRESET_MASK		(1 << 1)
+#define SYSC_AUTOIDLE_MASK		(1 << 0)
+
+#define SYSC_IDLEMODE_SMART		0x2
+#define SYSC_CLOCKACTIVITY_FCLK		0x2
 
-/* I2C System Configuration Register (OMAP_I2C_SYSC): */
-#define OMAP_I2C_SYSC_SRST		(1 << 1)	/* Soft Reset */
 
 struct omap_i2c_dev {
 	struct device		*dev;
@@ -252,13 +260,13 @@ static int omap_i2c_init(struct omap_i2c_dev *dev)
 	unsigned long internal_clk = 0;
 
 	if (dev->rev >= OMAP_I2C_REV_2) {
-		omap_i2c_write_reg(dev, OMAP_I2C_SYSC_REG, OMAP_I2C_SYSC_SRST);
+		omap_i2c_write_reg(dev, OMAP_I2C_SYSC_REG, SYSC_SOFTRESET_MASK);
 		/* For some reason we need to set the EN bit before the
 		 * reset done bit gets set. */
 		timeout = jiffies + OMAP_I2C_TIMEOUT;
 		omap_i2c_write_reg(dev, OMAP_I2C_CON_REG, OMAP_I2C_CON_EN);
 		while (!(omap_i2c_read_reg(dev, OMAP_I2C_SYSS_REG) &
-			 OMAP_I2C_SYSS_RDONE)) {
+			 SYSS_RESETDONE_MASK)) {
 			if (time_after(jiffies, timeout)) {
 				dev_warn(dev->dev, "timeout waiting "
 						"for controller reset\n");
@@ -266,6 +274,26 @@ static int omap_i2c_init(struct omap_i2c_dev *dev)
 			}
 			msleep(1);
 		}
+
+		/* SYSC register is cleared by the reset; rewrite it */
+		if (dev->rev == OMAP_I2C_REV_ON_2430) {
+
+			omap_i2c_write_reg(dev, OMAP_I2C_SYSC_REG,
+					   SYSC_AUTOIDLE_MASK);
+
+		} else if (dev->rev >= OMAP_I2C_REV_ON_3430) {
+			u32 v;
+
+			v = SYSC_AUTOIDLE_MASK;
+			v |= SYSC_ENAWAKEUP_MASK;
+			v |= (SYSC_IDLEMODE_SMART <<
+			      __ffs(SYSC_SIDLEMODE_MASK));
+			v |= (SYSC_CLOCKACTIVITY_FCLK <<
+			      __ffs(SYSC_CLOCKACTIVITY_MASK));
+
+			omap_i2c_write_reg(dev, OMAP_I2C_SYSC_REG, v);
+
+		}
 	}
 	omap_i2c_write_reg(dev, OMAP_I2C_CON_REG, 0);
 



^ permalink raw reply related	[flat|nested] 6+ messages in thread

* RE: [PATCH 0/2] OMAP: I2C: reprogram OCP_SYSCONFIG after device reset
  2008-10-14 12:19 [PATCH 0/2] OMAP: I2C: reprogram OCP_SYSCONFIG after device reset Paul Walmsley
  2008-10-14 12:19 ` [PATCH 1/2] OMAP: I2C: convert 'rev1' flag to generic 'rev' u8 Paul Walmsley
  2008-10-14 12:19 ` [PATCH 2/2] OMAP2/3 I2C: reprogram OCP_SYSCONFIG register after reset Paul Walmsley
@ 2008-10-19 13:06 ` Woodruff, Richard
  2008-11-21 21:34 ` Tony Lindgren
  3 siblings, 0 replies; 6+ messages in thread
From: Woodruff, Richard @ 2008-10-19 13:06 UTC (permalink / raw)
  To: Paul Walmsley, linux-omap@vger.kernel.org

> however, the CLOCKACTIVITY change on clk_enable()/clk_disable() in that
> code currently seems pointless, so it has been excluded until more
> information is available from TI or until problems are encountered.

IIRC CLOCKACTIVITY settings mainly had to do with if I2C was master or slave.  Part of TI patch set allows slave mode.  Seems like some GPS chip needed to be master or something along those lines.  One of the TI-ASP groups needed it.

Guidance was you should treat internal clocks differently at ocp-segment-idle-request time if you were the one generating the clock or it was coming in from the outside world.  It was reported not doing this correctly would result in possible data being lost.

McBSP and audio have a similar relationship when you do master/slave and your sample clock comes from the outside.

------------
GPTIMER CLOCKACTIVTY is more easily understood.  At ocp-segment-idle-request for the system heart beat you want to keep that FCLK running so you set it so.  There could be a case with other timers that you just let them be shut down.

Regards,
Richard W.

^ permalink raw reply	[flat|nested] 6+ messages in thread

* RE: [PATCH 2/2] OMAP2/3 I2C: reprogram OCP_SYSCONFIG register after reset
  2008-10-14 12:19 ` [PATCH 2/2] OMAP2/3 I2C: reprogram OCP_SYSCONFIG register after reset Paul Walmsley
@ 2008-10-19 13:12   ` Woodruff, Richard
  0 siblings, 0 replies; 6+ messages in thread
From: Woodruff, Richard @ 2008-10-19 13:12 UTC (permalink / raw)
  To: Paul Walmsley, linux-omap@vger.kernel.org


> From: Paul Walmsley [mailto:paul@pwsan.com]
> Sent: Tuesday, October 14, 2008 7:20 AM

From a quick glance that looks ok.

I'll restate old news posted here before:

For OMAP2 the smart-idle handshake for I2C did not make it to the module and was tied off at prcm level.  This required a hack to ensure data was not lost if effective power management was in use.  McBSP also had this issue.

On OMAP3 it is all hooked up as expected so modifying handshakes does what is expected.

The OMAP2 errata did mention this.

Regards,
Richard W.

^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: [PATCH 0/2] OMAP: I2C: reprogram OCP_SYSCONFIG after device reset
  2008-10-14 12:19 [PATCH 0/2] OMAP: I2C: reprogram OCP_SYSCONFIG after device reset Paul Walmsley
                   ` (2 preceding siblings ...)
  2008-10-19 13:06 ` [PATCH 0/2] OMAP: I2C: reprogram OCP_SYSCONFIG after device reset Woodruff, Richard
@ 2008-11-21 21:34 ` Tony Lindgren
  3 siblings, 0 replies; 6+ messages in thread
From: Tony Lindgren @ 2008-11-21 21:34 UTC (permalink / raw)
  To: Paul Walmsley; +Cc: linux-omap, Richard Woodruff

* Paul Walmsley <paul@pwsan.com> [081014 10:47]:
> Hello,
> 
> This patch set programs the I2C controller OCP_SYSCONFIG register
> after the driver resets the device.  It is derived from the changes
> mentioned by Richard Woodruff <r-woodruff2@ti.com> at
> 
> http://git.omapzoom.org/?p=omapkernel;a=blob;f=drivers/i2c/busses/i2c-omap.c;hb=d0b4bad4926f9a147a73498f7a62a0ae1cf6f83a
> 
> however, the CLOCKACTIVITY change on clk_enable()/clk_disable() in that
> code currently seems pointless, so it has been excluded until more
> information is available from TI or until problems are encountered.
> 
> This patchset should only change behavior on OMAP2x30 and OMAP3xxx devices.
> 
> Boot-tested on 2430SDP and 3430SDP; compile-tested with the 5912OSK (OMAP1)
> defconfig.  Comments welcome,

Pushing both to l-o today, also adding to upstream i2c-omap queue.

Tony

> 
> 
> - Paul
> 
> ---
> 
>   text    data     bss     dec      hex filename
> 3472584  160600  105760 3738944  390d40 vmlinux.3430sdp.orig
> 3472616  160600  105760 3738976  390d60 vmlinux.3430sdp
> 
>  drivers/i2c/busses/i2c-omap.c |   65 ++++++++++++++++++++++++++++++++---------
>  1 files changed, 50 insertions(+), 15 deletions(-)
> 
> --
> To unsubscribe from this list: send the line "unsubscribe linux-omap" in
> the body of a message to majordomo@vger.kernel.org
> More majordomo info at  http://vger.kernel.org/majordomo-info.html

^ permalink raw reply	[flat|nested] 6+ messages in thread

end of thread, other threads:[~2008-11-21 21:34 UTC | newest]

Thread overview: 6+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2008-10-14 12:19 [PATCH 0/2] OMAP: I2C: reprogram OCP_SYSCONFIG after device reset Paul Walmsley
2008-10-14 12:19 ` [PATCH 1/2] OMAP: I2C: convert 'rev1' flag to generic 'rev' u8 Paul Walmsley
2008-10-14 12:19 ` [PATCH 2/2] OMAP2/3 I2C: reprogram OCP_SYSCONFIG register after reset Paul Walmsley
2008-10-19 13:12   ` Woodruff, Richard
2008-10-19 13:06 ` [PATCH 0/2] OMAP: I2C: reprogram OCP_SYSCONFIG after device reset Woodruff, Richard
2008-11-21 21:34 ` Tony Lindgren

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