Merge ../linux-2.6 by hand
[powerpc.git] / drivers / i2c / busses / i2c-viapro.c
index 5cf8fe1..c9366b5 100644 (file)
 */
 
 /*
-   Supports Via devices:
-       82C596A/B (0x3050)
-       82C596B (0x3051)
-       82C686A/B
-       8231
-       8233
-       8233A (0x3147 and 0x3177)
-       8235
-       8237
+   Supports the following VIA south bridges:
+
+   Chip name          PCI ID  REV     I2C block
+   VT82C596A          0x3050             no
+   VT82C596B          0x3051             no
+   VT82C686A          0x3057  0x30       no
+   VT82C686B          0x3057  0x40       yes
+   VT8231             0x8235             no?
+   VT8233             0x3074             yes
+   VT8233A            0x3147             yes?
+   VT8235             0x3177             yes
+   VT8237R            0x3227             yes
+
    Note: we assume there can only be one device, with one SMBus interface.
 */
 
@@ -100,17 +104,40 @@ static struct i2c_adapter vt596_adapter;
 #define FEATURE_I2CBLOCK       (1<<0)
 static unsigned int vt596_features;
 
+#ifdef DEBUG
+static void vt596_dump_regs(const char *msg, u8 size)
+{
+       dev_dbg(&vt596_adapter.dev, "%s: STS=%02x CNT=%02x CMD=%02x ADD=%02x "
+               "DAT=%02x,%02x\n", msg, inb_p(SMBHSTSTS), inb_p(SMBHSTCNT),
+               inb_p(SMBHSTCMD), inb_p(SMBHSTADD), inb_p(SMBHSTDAT0),
+               inb_p(SMBHSTDAT1));
+
+       if (size == VT596_BLOCK_DATA
+        || size == VT596_I2C_BLOCK_DATA) {
+               int i;
+
+               dev_dbg(&vt596_adapter.dev, "BLK=");
+               for (i = 0; i < I2C_SMBUS_BLOCK_MAX / 2; i++)
+                       printk("%02x,", inb_p(SMBBLKDAT));
+               printk("\n");
+               dev_dbg(&vt596_adapter.dev, "    ");
+               for (; i < I2C_SMBUS_BLOCK_MAX - 1; i++)
+                       printk("%02x,", inb_p(SMBBLKDAT));
+               printk("%02x\n", inb_p(SMBBLKDAT));
+       }
+}
+#else
+static inline void vt596_dump_regs(const char *msg, u8 size) { }
+#endif
+
 /* Return -1 on error, 0 on success */
-static int vt596_transaction(void)
+static int vt596_transaction(u8 size)
 {
        int temp;
        int result = 0;
        int timeout = 0;
 
-       dev_dbg(&vt596_adapter.dev, "Transaction (pre): CNT=%02x, CMD=%02x, "
-               "ADD=%02x, DAT0=%02x, DAT1=%02x\n", inb_p(SMBHSTCNT),
-               inb_p(SMBHSTCMD), inb_p(SMBHSTADD), inb_p(SMBHSTDAT0),
-               inb_p(SMBHSTDAT1));
+       vt596_dump_regs("Transaction (pre)", size);
 
        /* Make sure the SMBus host is ready to start transmitting */
        if ((temp = inb_p(SMBHSTSTS)) & 0x1F) {
@@ -127,7 +154,7 @@ static int vt596_transaction(void)
        }
 
        /* Start the transaction by setting bit 6 */
-       outb_p(inb(SMBHSTCNT) | 0x40, SMBHSTCNT);
+       outb_p(0x40 | (size & 0x3C), SMBHSTCNT);
 
        /* We will always wait for a fraction of a second */
        do {
@@ -165,10 +192,7 @@ static int vt596_transaction(void)
        if (temp & 0x1F)
                outb_p(temp, SMBHSTSTS);
 
-       dev_dbg(&vt596_adapter.dev, "Transaction (post): CNT=%02x, CMD=%02x, "
-               "ADD=%02x, DAT0=%02x, DAT1=%02x\n", inb_p(SMBHSTCNT),
-               inb_p(SMBHSTCMD), inb_p(SMBHSTADD), inb_p(SMBHSTDAT0),
-               inb_p(SMBHSTDAT1));
+       vt596_dump_regs("Transaction (post)", size);
 
        return result;
 }
@@ -228,9 +252,8 @@ static s32 vt596_access(struct i2c_adapter *adap, u16 addr,
        }
 
        outb_p(((addr & 0x7f) << 1) | read_write, SMBHSTADD);
-       outb_p((size & 0x3C), SMBHSTCNT);
 
-       if (vt596_transaction()) /* Error in transaction */
+       if (vt596_transaction(size)) /* Error in transaction */
                return -1;
 
        if ((read_write == I2C_SMBUS_WRITE) || (size == VT596_QUICK))
@@ -416,6 +439,7 @@ static struct pci_device_id vt596_ids[] = {
 MODULE_DEVICE_TABLE(pci, vt596_ids);
 
 static struct pci_driver vt596_driver = {
+       .owner          = THIS_MODULE,
        .name           = "vt596_smbus",
        .id_table       = vt596_ids,
        .probe          = vt596_probe,