Module Name:    src
Committed By:   kiyohara
Date:           Sat Oct 15 15:08:59 UTC 2016

Modified Files:
        src/sys/arch/arm/omap: ti_iic.c ti_iicreg.h

Log Message:
Fix broken settings for AM335X's I2C[12].


To generate a diff of this commit:
cvs rdiff -u -r1.8 -r1.9 src/sys/arch/arm/omap/ti_iic.c
cvs rdiff -u -r1.1 -r1.2 src/sys/arch/arm/omap/ti_iicreg.h

Please note that diffs are not public domain; they are subject to the
copyright notices on the relevant files.

Modified files:

Index: src/sys/arch/arm/omap/ti_iic.c
diff -u src/sys/arch/arm/omap/ti_iic.c:1.8 src/sys/arch/arm/omap/ti_iic.c:1.9
--- src/sys/arch/arm/omap/ti_iic.c:1.8	Sat Oct 15 15:00:12 2016
+++ src/sys/arch/arm/omap/ti_iic.c	Sat Oct 15 15:08:59 2016
@@ -1,4 +1,4 @@
-/* $NetBSD: ti_iic.c,v 1.8 2016/10/15 15:00:12 kiyohara Exp $ */
+/* $NetBSD: ti_iic.c,v 1.9 2016/10/15 15:08:59 kiyohara Exp $ */
 
 /*
  * Copyright (c) 2013 Manuel Bouyer.  All rights reserved.
@@ -50,7 +50,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: ti_iic.c,v 1.8 2016/10/15 15:00:12 kiyohara Exp $");
+__KERNEL_RCSID(0, "$NetBSD: ti_iic.c,v 1.9 2016/10/15 15:08:59 kiyohara Exp $");
 
 #include "opt_omap.h"
 #include "locators.h"
@@ -163,7 +163,7 @@ struct am335x_iic {
 static const struct am335x_iic am335x_iic[] = {
 	{ "I2C0", OMAP2_I2C0_BASE, 70, { AM335X_PRCM_CM_WKUP, 0xb8 } },
 	{ "I2C1", OMAP2_I2C1_BASE, 71, { AM335X_PRCM_CM_PER, 0x48 } },
-	{ "I2C2", OMAP2_I2C1_BASE, 30, { AM335X_PRCM_CM_PER, 0x44 } },
+	{ "I2C2", OMAP2_I2C2_BASE, 30, { AM335X_PRCM_CM_PER, 0x44 } },
 };
 #endif
 
@@ -199,6 +199,7 @@ ti_iic_attach(device_t parent, device_t 
 {
 	struct ti_iic_softc *sc = device_private(self);
 	struct obio_attach_args *obio = opaque;
+	int scheme, major, minor, fifodepth, fifo;
 	uint16_t rev;
 #ifdef TI_AM335X
 	int i;
@@ -219,8 +220,6 @@ ti_iic_attach(device_t parent, device_t 
 	sc->sc_ic.ic_release_bus = ti_iic_release_bus;
 	sc->sc_ic.ic_exec = ti_iic_exec;
 
-	sc->sc_rxthres = sc->sc_txthres = 4;
-
 	if (bus_space_map(obio->obio_iot, obio->obio_addr, obio->obio_size,
 	    0, &sc->sc_ioh) != 0) {
 		aprint_error(": couldn't map address space\n");
@@ -248,27 +247,40 @@ ti_iic_attach(device_t parent, device_t 
 	snprintf(buf, sizeof(buf), "%s_SDA", am335x_iic[i].as_name);
 	if (sitara_cm_padconf_get(buf, &mode, &state) == 0) {
 		aprint_debug(": SDA mode %s state %d ", mode, state);
-	}
-	if (sitara_cm_padconf_set(buf, buf,
-	    (0x01 << 4) | (0x01 << 5) | (0x01 << 6)) != 0) {
-		aprint_error(": can't switch %s pad\n", buf);
-		return;
+
+		if (sitara_cm_padconf_set(buf, buf,
+		    (0x01 << 4) | (0x01 << 5) | (0x01 << 6)) != 0) {
+			aprint_error(": can't switch %s pad\n", buf);
+			return;
+		}
 	}
 	snprintf(buf, sizeof(buf), "%s_SCL", am335x_iic[i].as_name);
 	if (sitara_cm_padconf_get(buf, &mode, &state) == 0) {
 		aprint_debug(": SCL mode %s state %d ", mode, state);
-	}
-	if (sitara_cm_padconf_set(buf, buf,
-	    (0x01 << 4) | (0x01 << 5) | (0x01 << 6)) != 0) {
-		aprint_error(": can't switch %s pad\n", buf);
-		return;
+
+		if (sitara_cm_padconf_set(buf, buf,
+		    (0x01 << 4) | (0x01 << 5) | (0x01 << 6)) != 0) {
+			aprint_error(": can't switch %s pad\n", buf);
+			return;
+		}
 	}
 #endif
 
+	scheme = I2C_REVNB_HI_SCHEME(I2C_READ_REG(sc, OMAP2_I2C_REVNB_HI));
 	rev = I2C_READ_REG(sc, OMAP2_I2C_REVNB_LO);
-	aprint_normal(": rev %d.%d\n",
-	    (int)I2C_REVNB_LO_MAJOR(rev),
-	    (int)I2C_REVNB_LO_MINOR(rev));
+	if (scheme == 0) {
+		major = I2C_REV_SCHEME_0_MAJOR(rev);
+		minor = I2C_REV_SCHEME_0_MINOR(rev);
+	} else {
+		major = I2C_REVNB_LO_MAJOR(rev);
+		minor = I2C_REVNB_LO_MINOR(rev);
+	}
+	aprint_normal(": rev %d.%d, scheme %d\n", major, minor, scheme);
+
+	fifodepth = I2C_BUFSTAT_FIFODEPTH(I2C_READ_REG(sc, OMAP2_I2C_BUFSTAT));
+	fifo = OMAP2_I2C_FIFOBYTES(fifodepth);
+	aprint_normal_dev(self, "%d-bytes FIFO\n", fifo);
+	sc->sc_rxthres = sc->sc_txthres = fifo >> 1;
 
 	ti_iic_reset(sc);
 	ti_iic_flush(sc);
@@ -310,9 +322,9 @@ ti_iic_intr(void *arg)
 	mutex_enter(&sc->sc_mtx);
 	DPRINTF(("ti_iic_intr\n"));
 	stat = I2C_READ_REG(sc, OMAP2_I2C_IRQSTATUS);
-	I2C_WRITE_REG(sc, OMAP2_I2C_IRQSTATUS, stat);
 	DPRINTF(("ti_iic_intr pre handle sc->sc_op eq %#x\n", sc->sc_op));
 	ti_iic_handle_intr(sc, stat);
+	I2C_WRITE_REG(sc, OMAP2_I2C_IRQSTATUS, stat);
 	if (sc->sc_op == TI_I2CERROR || sc->sc_op == TI_I2CDONE) {
 		DPRINTF(("ti_iic_intr post handle sc->sc_op %#x\n", sc->sc_op));
 		cv_signal(&sc->sc_cv);
@@ -418,7 +430,7 @@ ti_iic_reset(struct ti_iic_softc *sc)
 		aprint_error_dev(sc->sc_dev, ": couldn't reset module\n");
 		return 1;
 	}
-			
+
 
 	/* XXX standard speed only */
 	psc = 3;
@@ -451,7 +463,7 @@ ti_iic_op(struct ti_iic_softc *sc, i2c_a
 	int err, retry;
 
 	KASSERT(op == TI_I2CREAD || op == TI_I2CWRITE);
-	DPRINTF(("ti_iic_op: addr %#x op %#x buf %p buflen %#x flags %#x\n", 
+	DPRINTF(("ti_iic_op: addr %#x op %#x buf %p buflen %#x flags %#x\n",
 	    addr, op, buf, (unsigned int) buflen, flags));
 
 	mask = I2C_IRQSTATUS_ARDY | I2C_IRQSTATUS_NACK | I2C_IRQSTATUS_AL;

Index: src/sys/arch/arm/omap/ti_iicreg.h
diff -u src/sys/arch/arm/omap/ti_iicreg.h:1.1 src/sys/arch/arm/omap/ti_iicreg.h:1.2
--- src/sys/arch/arm/omap/ti_iicreg.h:1.1	Wed Apr 17 14:33:06 2013
+++ src/sys/arch/arm/omap/ti_iicreg.h	Sat Oct 15 15:08:59 2016
@@ -1,4 +1,4 @@
-/*	$NetBSD: ti_iicreg.h,v 1.1 2013/04/17 14:33:06 bouyer Exp $	*/
+/*	$NetBSD: ti_iicreg.h,v 1.2 2016/10/15 15:08:59 kiyohara Exp $	*/
 
 /*
  * Copyright (c) 2013 Manuel Bouyer.  All rights reserved.
@@ -36,6 +36,8 @@
 #define		I2C_REVNB_LO_MAJOR(x)		(((x) >>  8) & 0x007)
 #define		I2C_REVNB_LO_CUSTOM(x)		(((x) >>  6) & 0x003)
 #define		I2C_REVNB_LO_MINOR(x)		(((x) >>  0) & 0x01f)
+#define		I2C_REV_SCHEME_0_MAJOR(r)	(((r) >> 4) && 0xf)
+#define		I2C_REV_SCHEME_0_MINOR(r)	(((r) >> 0) && 0xf)
 #define OMAP2_I2C_REVNB_HI		0x04
 #define		I2C_REVNB_HI_SCHEME(x)		(((x) >> 14) & 0x003)
 #define		I2C_REVNB_HI_FUNC(x)		(((x) >>  0) & 0xfff)

Reply via email to