[lm-sensors] [PATCH 2.6] cleanup of i2c-nforce2, support of MCP51 and MCP55
Hans-Frieder Vogt
hfvogt at gmx.net
Tue Dec 27 01:02:30 CET 2005
Hello Jean,
I invested a little bit of time into the nforce2/3/4 SMBus driver and changed
the following things:
- general cleanup:
o removed code for the unsupported I2C block transfer mode
o removed detail warnings about unsupported modes that are covered in a
general warning (unsupported transaction...) anyway
o removed necessity of a definition of struct i2c_adapter
o moved definition of struct i2c_algorithm, making forward declarations of
nforce2_access and nforce2_func unnecessary
- improvements:
o support MCP51 and MCP55 southbridges
o advertise I2C_FUNC_SMBUS_BLOCK_DATA, so that it really can be used
the patch is relative to 2.6.15-rc7 with your patch
i2c-nforce2-support-nforce4-mcp04.patch of 18 december (thanks) already
applied. If preferred, I can of course also send a full patch relative to
2.6.15-rc7 (which should be applicable to other kernel versions as well).
Signed-off-by: Hans-Frieder Vogt <hfvogt at arcor.de>
--- linux-2.6.15-rc7-jean/include/linux/pci_ids.h 2005-12-26
13:15:06.582626423 +0100
+++ linux-2.6.15-rc7/include/linux/pci_ids.h 2005-12-26 13:15:34.625804868
+0100
@@ -1091,9 +1091,11 @@
#define PCI_DEVICE_ID_NVIDIA_QUADRO4_900XGL 0x0258
#define PCI_DEVICE_ID_NVIDIA_QUADRO4_750XGL 0x0259
#define PCI_DEVICE_ID_NVIDIA_QUADRO4_700XGL 0x025B
+#define PCI_DEVICE_ID_NVIDIA_NFORCE_MCP51_SMBUS 0x0264
#define PCI_DEVICE_ID_NVIDIA_NFORCE_MCP51_IDE 0x0265
#define PCI_DEVICE_ID_NVIDIA_NFORCE_MCP51_SATA 0x0266
#define PCI_DEVICE_ID_NVIDIA_NFORCE_MCP51_SATA2 0x0267
+#define PCI_DEVICE_ID_NVIDIA_NFORCE_MCP55_SMBUS 0x0368
#define PCI_DEVICE_ID_NVIDIA_NFORCE_MCP55_IDE 0x036E
#define PCI_DEVICE_ID_NVIDIA_NFORCE_MCP55_SATA 0x037E
#define PCI_DEVICE_ID_NVIDIA_NFORCE_MCP55_SATA2 0x037F
--- linux-2.6.15-rc7-jean/Documentation/i2c/busses/i2c-nforce2 2005-12-26
13:10:06.125382505 +0100
+++ linux-2.6.15-rc7/Documentation/i2c/busses/i2c-nforce2 2005-12-26
13:11:48.400743251 +0100
@@ -7,6 +7,8 @@
* nForce3 250Gb MCP 10de:00E4
* nForce4 MCP 10de:0052
* nForce4 MCP-04 10de:0034
+ * nForce MCP-51 10de:0264
+ * nForce MCP-55 10de:0368
Datasheet: not publically available, but seems to be similar to the
AMD-8111 SMBus 2.0 adapter.
--- linux-2.6.15-rc7-jean/drivers/i2c/busses/i2c-nforce2.c 2005-12-26
13:12:48.669359700 +0100
+++ linux-2.6.15-rc7/drivers/i2c/busses/i2c-nforce2.c 2005-12-27
00:21:24.719391220 +0100
@@ -31,6 +31,8 @@
nForce3 250Gb MCP 00E4
nForce4 MCP 0052
nForce4 MCP-04 0034
+ nForce MCP-51 0264
+ nForce MCP-55 0368
This driver supports the 2 SMBuses that are included in the MCP of the
nForce2/3/4 chipsets.
@@ -100,24 +102,7 @@
static struct pci_driver nforce2_driver;
-static s32 nforce2_access(struct i2c_adapter *adap, u16 addr,
- unsigned short flags, char read_write,
- u8 command, int size, union i2c_smbus_data *data);
-static u32 nforce2_func(struct i2c_adapter *adapter);
-
-static struct i2c_algorithm smbus_algorithm = {
- .smbus_xfer = nforce2_access,
- .functionality = nforce2_func,
-};
-
-static struct i2c_adapter nforce2_adapter = {
- .owner = THIS_MODULE,
- .class = I2C_CLASS_HWMON,
- .algo = &smbus_algorithm,
-};
-
-/* Return -1 on error. See smbus.h for more information */
static s32 nforce2_access(struct i2c_adapter * adap, u16 addr,
unsigned short flags, char read_write,
u8 command, int size, union i2c_smbus_data * data)
@@ -171,24 +156,6 @@
protocol |= NVIDIA_SMB_PRTCL_BLOCK_DATA | pec;
break;
- case I2C_SMBUS_I2C_BLOCK_DATA:
- len = min_t(u8, data->block[0], 32);
- outb_p(command, NVIDIA_SMB_CMD);
- outb_p(len, NVIDIA_SMB_BCNT);
- if (read_write == I2C_SMBUS_WRITE)
- for (i = 0; i < len; i++)
- outb_p(data->block[i + 1], NVIDIA_SMB_DATA+i);
- protocol |= NVIDIA_SMB_PRTCL_I2C_BLOCK_DATA;
- break;
-
- case I2C_SMBUS_PROC_CALL:
- dev_err(&adap->dev, "I2C_SMBUS_PROC_CALL not supported!\n");
- return -1;
-
- case I2C_SMBUS_BLOCK_PROC_CALL:
- dev_err(&adap->dev, "I2C_SMBUS_BLOCK_PROC_CALL not supported!\n");
- return -1;
-
default:
dev_err(&adap->dev, "Unsupported transaction %d\n", size);
return -1;
@@ -224,15 +191,12 @@
break;
case I2C_SMBUS_WORD_DATA:
- /* case I2C_SMBUS_PROC_CALL: not supported */
data->word = inb_p(NVIDIA_SMB_DATA) | (inb_p(NVIDIA_SMB_DATA+1) << 8);
break;
case I2C_SMBUS_BLOCK_DATA:
- /* case I2C_SMBUS_BLOCK_PROC_CALL: not supported */
len = inb_p(NVIDIA_SMB_BCNT);
len = min_t(u8, len, 32);
- case I2C_SMBUS_I2C_BLOCK_DATA:
for (i = 0; i < len; i++)
data->block[i+1] = inb_p(NVIDIA_SMB_DATA + i);
data->block[0] = len;
@@ -247,10 +211,15 @@
{
/* other functionality might be possible, but is not tested */
return I2C_FUNC_SMBUS_QUICK | I2C_FUNC_SMBUS_BYTE |
- I2C_FUNC_SMBUS_BYTE_DATA | I2C_FUNC_SMBUS_WORD_DATA /* |
- I2C_FUNC_SMBUS_BLOCK_DATA */;
+ I2C_FUNC_SMBUS_BYTE_DATA | I2C_FUNC_SMBUS_WORD_DATA |
+ I2C_FUNC_SMBUS_BLOCK_DATA;
}
+static struct i2c_algorithm smbus_algorithm = {
+ .smbus_xfer = nforce2_access,
+ .functionality = nforce2_func,
+};
+
static struct pci_device_id nforce2_ids[] = {
{ PCI_DEVICE(PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_NFORCE2_SMBUS) },
@@ -259,6 +228,8 @@
{ PCI_DEVICE(PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_NFORCE3S_SMBUS) },
{ PCI_DEVICE(PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_NFORCE4_SMBUS) },
{ PCI_DEVICE(PCI_VENDOR_ID_NVIDIA,
PCI_DEVICE_ID_NVIDIA_NFORCE_MCP04_SMBUS) },
+ { PCI_DEVICE(PCI_VENDOR_ID_NVIDIA,
PCI_DEVICE_ID_NVIDIA_NFORCE_MCP51_SMBUS) },
+ { PCI_DEVICE(PCI_VENDOR_ID_NVIDIA,
PCI_DEVICE_ID_NVIDIA_NFORCE_MCP55_SMBUS) },
{ 0 }
};
@@ -278,14 +249,16 @@
}
smbus->dev = dev;
smbus->base = iobase & 0xfffc;
- smbus->size = 8;
+ smbus->size = 64;
if (!request_region(smbus->base, smbus->size, nforce2_driver.name)) {
dev_err(&smbus->adapter.dev, "Error requesting region %02x .. %02X for
%s\n",
smbus->base, smbus->base+smbus->size-1, name);
return -1;
}
- smbus->adapter = nforce2_adapter;
+ smbus->adapter.owner = THIS_MODULE;
+ smbus->adapter.class = I2C_CLASS_HWMON;
+ smbus->adapter.algo = &smbus_algorithm;
smbus->adapter.algo_data = smbus;
smbus->adapter.dev.parent = &dev->dev;
snprintf(smbus->adapter.name, I2C_NAME_SIZE,
@@ -318,6 +291,7 @@
dev_err(&dev->dev, "Error probing SMB1.\n");
smbuses[0].base = 0; /* to have a check value */
}
+ /* SMBus adapter 2 */
res2 = nforce2_probe_smb (dev, NFORCE_PCI_SMB2, &smbuses[1], "SMB2");
if (res2 < 0) {
dev_err(&dev->dev, "Error probing SMB2.\n");
--
--
Hans-Frieder Vogt e-mail: hfvogt <at> arcor .dot. de
hfvogt <at> gmx .dot. net
More information about the lm-sensors
mailing list