summaryrefslogtreecommitdiffstats
path: root/sys
diff options
context:
space:
mode:
authorjhb <jhb@FreeBSD.org>2008-06-06 18:40:38 +0000
committerjhb <jhb@FreeBSD.org>2008-06-06 18:40:38 +0000
commita7ed9169932600f570091db7f67266f2b20a938a (patch)
tree346aa1c316fb04052c123bd5fe7a1f78eb204ffc /sys
parent25f7299f0faa77203bcfa578873888fd224fcf61 (diff)
downloadFreeBSD-src-a7ed9169932600f570091db7f67266f2b20a938a.zip
FreeBSD-src-a7ed9169932600f570091db7f67266f2b20a938a.tar.gz
Explicitly lock Giant in smbus_if methods in the bktr_i2c and iicsmb
drivers for now. This can be replaced with driver locks when these drivers are locked.
Diffstat (limited to 'sys')
-rw-r--r--sys/dev/bktr/bktr_i2c.c27
-rw-r--r--sys/dev/iicbus/iicsmb.c49
2 files changed, 67 insertions, 9 deletions
diff --git a/sys/dev/bktr/bktr_i2c.c b/sys/dev/bktr/bktr_i2c.c
index 2f9ca1f..0d733c0 100644
--- a/sys/dev/bktr/bktr_i2c.c
+++ b/sys/dev/bktr/bktr_i2c.c
@@ -128,18 +128,22 @@ int bti2c_smb_callback(device_t dev, int index, void *data)
switch (index) {
case SMB_REQUEST_BUS:
/* XXX test & set */
+ mtx_lock(&Giant);
if (!sc->bus_owned) {
sc->bus_owned = 1;
} else
error = EWOULDBLOCK;
+ mtx_unlock(&Giant);
break;
case SMB_RELEASE_BUS:
/* XXX test & set */
+ mtx_lock(&Giant);
if (sc->bus_owned) {
sc->bus_owned = 0;
} else
error = EINVAL;
+ mtx_unlock(&Giant);
break;
default:
@@ -161,18 +165,22 @@ int bti2c_iic_callback(device_t dev, int index, caddr_t *data)
switch (index) {
case IIC_REQUEST_BUS:
/* XXX test & set */
+ mtx_lock(&Giant);
if (!sc->bus_owned) {
sc->bus_owned = 1;
} else
error = EWOULDBLOCK;
+ mtx_unlock(&Giant);
break;
case IIC_RELEASE_BUS:
/* XXX test & set */
+ mtx_lock(&Giant);
if (sc->bus_owned) {
sc->bus_owned = 0;
} else
error = EINVAL;
+ mtx_unlock(&Giant);
break;
default:
@@ -184,8 +192,10 @@ int bti2c_iic_callback(device_t dev, int index, caddr_t *data)
int bti2c_iic_reset(device_t dev, u_char speed, u_char addr, u_char * oldaddr)
{
+ mtx_lock(&Giant);
if (oldaddr)
*oldaddr = 0; /* XXX */
+ mtx_unlock(&Giant);
return (IIC_ENOADDR);
}
@@ -195,12 +205,14 @@ void bti2c_iic_setsda(device_t dev, int val)
struct bktr_softc *sc = (struct bktr_softc *)device_get_softc(dev);
int clock;
+ mtx_lock(&Giant);
clock = INL(sc, BKTR_I2C_DATA_CTL) & 0x2;
if (val)
OUTL(sc, BKTR_I2C_DATA_CTL, clock | 1);
else
OUTL(sc, BKTR_I2C_DATA_CTL, clock);
+ mtx_unlock(&Giant);
return;
}
@@ -210,12 +222,14 @@ void bti2c_iic_setscl(device_t dev, int val)
struct bktr_softc *sc = (struct bktr_softc *)device_get_softc(dev);
int data;
+ mtx_lock(&Giant);
data = INL(sc, BKTR_I2C_DATA_CTL) & 0x1;
if (val)
OUTL(sc, BKTR_I2C_DATA_CTL, 0x2 | data);
else
OUTL(sc, BKTR_I2C_DATA_CTL, data);
+ mtx_unlock(&Giant);
return;
}
@@ -224,8 +238,12 @@ int
bti2c_iic_getsda(device_t dev)
{
struct bktr_softc *sc = (struct bktr_softc *)device_get_softc(dev);
+ int retval;
- return (INL(sc,BKTR_I2C_DATA_CTL) & 0x1);
+ mtx_lock(&Giant);
+ retval = INL(sc,BKTR_I2C_DATA_CTL) & 0x1;
+ mtx_unlock(&Giant);
+ return (retval);
}
int
@@ -239,6 +257,8 @@ bti2c_write(struct bktr_softc *sc, u_long data)
{
u_long x;
+ mtx_lock(&Giant);
+
/* clear status bits */
OUTL(sc, BKTR_INT_STAT, (BT848_INT_RACK | BT848_INT_I2CDONE));
@@ -257,9 +277,11 @@ bti2c_write(struct bktr_softc *sc, u_long data)
if ( !x || !( INL(sc, BKTR_INT_STAT) & BT848_INT_RACK) ) {
BTI2C_DEBUG(printf("%c%c", (!x)?'+':'-',
(!( INL(sc, BKTR_INT_STAT) & BT848_INT_RACK))?'+':'-'));
+ mtx_unlock(&Giant);
return (SMB_ENOACK);
}
BTI2C_DEBUG(printf("+"));
+ mtx_unlock(&Giant);
/* return OK */
return( 0 );
@@ -305,6 +327,7 @@ bti2c_smb_readb(device_t dev, u_char slave, char cmd, char *byte)
struct bktr_softc *sc = (struct bktr_softc *)device_get_softc(dev);
u_long x;
+ mtx_lock(&Giant);
/* clear status bits */
OUTL(sc,BKTR_INT_STAT, (BT848_INT_RACK | BT848_INT_I2CDONE));
@@ -322,11 +345,13 @@ bti2c_smb_readb(device_t dev, u_char slave, char cmd, char *byte)
if ( !x || !(INL(sc,BKTR_INT_STAT) & BT848_INT_RACK) ) {
BTI2C_DEBUG(printf("r%c%c", (!x)?'+':'-',
(!( INL(sc,BKTR_INT_STAT) & BT848_INT_RACK))?'+':'-'));
+ mtx_unlock(&Giant);
return (SMB_ENOACK);
}
*byte = (char)((INL(sc,BKTR_I2C_DATA_CTL) >> 8) & 0xff);
BTI2C_DEBUG(printf("r%x+", *byte));
+ mtx_unlock(&Giant);
return (0);
}
diff --git a/sys/dev/iicbus/iicsmb.c b/sys/dev/iicbus/iicsmb.c
index 0788184..a8a95ae 100644
--- a/sys/dev/iicbus/iicsmb.c
+++ b/sys/dev/iicbus/iicsmb.c
@@ -46,13 +46,14 @@
*/
#include <sys/param.h>
+#include <sys/bus.h>
#include <sys/kernel.h>
-#include <sys/systm.h>
+#include <sys/lock.h>
#include <sys/module.h>
-#include <sys/bus.h>
+#include <sys/mutex.h>
+#include <sys/systm.h>
#include <sys/uio.h>
-
#include <dev/iicbus/iiconf.h>
#include <dev/iicbus/iicbus.h>
@@ -257,12 +258,16 @@ iicsmb_callback(device_t dev, int index, void *data)
case SMB_REQUEST_BUS:
/* request underlying iicbus */
how = *(int *)data;
+ mtx_lock(&Giant);
error = iicbus_request_bus(parent, dev, how);
+ mtx_unlock(&Giant);
break;
case SMB_RELEASE_BUS:
/* release underlying iicbus */
+ mtx_lock(&Giant);
error = iicbus_release_bus(parent, dev);
+ mtx_unlock(&Giant);
break;
default:
@@ -278,6 +283,7 @@ iicsmb_quick(device_t dev, u_char slave, int how)
device_t parent = device_get_parent(dev);
int error;
+ mtx_lock(&Giant);
switch (how) {
case SMB_QWRITE:
error = iicbus_start(parent, slave & ~LSB, IICBUS_TIMEOUT);
@@ -294,7 +300,8 @@ iicsmb_quick(device_t dev, u_char slave, int how)
if (!error)
error = iicbus_stop(parent);
-
+ mtx_unlock(&Giant);
+
return (error);
}
@@ -304,6 +311,7 @@ iicsmb_sendb(device_t dev, u_char slave, char byte)
device_t parent = device_get_parent(dev);
int error, sent;
+ mtx_lock(&Giant);
error = iicbus_start(parent, slave & ~LSB, IICBUS_TIMEOUT);
if (!error) {
@@ -311,6 +319,7 @@ iicsmb_sendb(device_t dev, u_char slave, char byte)
iicbus_stop(parent);
}
+ mtx_unlock(&Giant);
return (error);
}
@@ -321,6 +330,7 @@ iicsmb_recvb(device_t dev, u_char slave, char *byte)
device_t parent = device_get_parent(dev);
int error, read;
+ mtx_lock(&Giant);
error = iicbus_start(parent, slave | LSB, 0);
if (!error) {
@@ -328,6 +338,7 @@ iicsmb_recvb(device_t dev, u_char slave, char *byte)
iicbus_stop(parent);
}
+ mtx_unlock(&Giant);
return (error);
}
@@ -338,6 +349,7 @@ iicsmb_writeb(device_t dev, u_char slave, char cmd, char byte)
device_t parent = device_get_parent(dev);
int error, sent;
+ mtx_lock(&Giant);
error = iicbus_start(parent, slave & ~LSB, 0);
if (!error) {
@@ -346,6 +358,7 @@ iicsmb_writeb(device_t dev, u_char slave, char cmd, char byte)
iicbus_stop(parent);
}
+ mtx_unlock(&Giant);
return (error);
}
@@ -359,6 +372,7 @@ iicsmb_writew(device_t dev, u_char slave, char cmd, short word)
char low = (char)(word & 0xff);
char high = (char)((word & 0xff00) >> 8);
+ mtx_lock(&Giant);
error = iicbus_start(parent, slave & ~LSB, 0);
if (!error) {
@@ -368,6 +382,7 @@ iicsmb_writew(device_t dev, u_char slave, char cmd, short word)
iicbus_stop(parent);
}
+ mtx_unlock(&Giant);
return (error);
}
@@ -378,8 +393,11 @@ iicsmb_readb(device_t dev, u_char slave, char cmd, char *byte)
device_t parent = device_get_parent(dev);
int error, sent, read;
- if ((error = iicbus_start(parent, slave & ~LSB, IICBUS_TIMEOUT)))
+ mtx_lock(&Giant);
+ if ((error = iicbus_start(parent, slave & ~LSB, IICBUS_TIMEOUT))) {
+ mtx_unlock(&Giant);
return (error);
+ }
if ((error = iicbus_write(parent, &cmd, 1, &sent, IICBUS_TIMEOUT)))
goto error;
@@ -392,6 +410,7 @@ iicsmb_readb(device_t dev, u_char slave, char cmd, char *byte)
error:
iicbus_stop(parent);
+ mtx_unlock(&Giant);
return (error);
}
@@ -405,8 +424,11 @@ iicsmb_readw(device_t dev, u_char slave, char cmd, short *word)
int error, sent, read;
char buf[2];
- if ((error = iicbus_start(parent, slave & ~LSB, IICBUS_TIMEOUT)))
+ mtx_lock(&Giant);
+ if ((error = iicbus_start(parent, slave & ~LSB, IICBUS_TIMEOUT))) {
+ mtx_unlock(&Giant);
return (error);
+ }
if ((error = iicbus_write(parent, &cmd, 1, &sent, IICBUS_TIMEOUT)))
goto error;
@@ -422,6 +444,7 @@ iicsmb_readw(device_t dev, u_char slave, char cmd, short *word)
error:
iicbus_stop(parent);
+ mtx_unlock(&Giant);
return (error);
}
@@ -432,8 +455,11 @@ iicsmb_pcall(device_t dev, u_char slave, char cmd, short sdata, short *rdata)
int error, sent, read;
char buf[2];
- if ((error = iicbus_start(parent, slave & ~LSB, IICBUS_TIMEOUT)))
+ mtx_lock(&Giant);
+ if ((error = iicbus_start(parent, slave & ~LSB, IICBUS_TIMEOUT))) {
+ mtx_unlock(&Giant);
return (error);
+ }
if ((error = iicbus_write(parent, &cmd, 1, &sent, IICBUS_TIMEOUT)))
goto error;
@@ -456,6 +482,7 @@ iicsmb_pcall(device_t dev, u_char slave, char cmd, short sdata, short *rdata)
error:
iicbus_stop(parent);
+ mtx_unlock(&Giant);
return (error);
}
@@ -465,6 +492,7 @@ iicsmb_bwrite(device_t dev, u_char slave, char cmd, u_char count, char *buf)
device_t parent = device_get_parent(dev);
int error, sent;
+ mtx_lock(&Giant);
if ((error = iicbus_start(parent, slave & ~LSB, IICBUS_TIMEOUT)))
goto error;
@@ -478,6 +506,7 @@ iicsmb_bwrite(device_t dev, u_char slave, char cmd, u_char count, char *buf)
goto error;
error:
+ mtx_unlock(&Giant);
return (error);
}
@@ -487,8 +516,11 @@ iicsmb_bread(device_t dev, u_char slave, char cmd, u_char *count, char *buf)
device_t parent = device_get_parent(dev);
int error, sent, read;
- if ((error = iicbus_start(parent, slave & ~LSB, IICBUS_TIMEOUT)))
+ mtx_lock(&Giant);
+ if ((error = iicbus_start(parent, slave & ~LSB, IICBUS_TIMEOUT))) {
+ mtx_unlock(&Giant);
return (error);
+ }
if ((error = iicbus_write(parent, &cmd, 1, &sent, IICBUS_TIMEOUT)))
goto error;
@@ -503,6 +535,7 @@ iicsmb_bread(device_t dev, u_char slave, char cmd, u_char *count, char *buf)
error:
iicbus_stop(parent);
+ mtx_unlock(&Giant);
return (error);
}
OpenPOWER on IntegriCloud