From 4e6697fcc194db8b45559a9863947c6cbfeea363 Mon Sep 17 00:00:00 2001 From: Jean Delvare Date: Tue, 13 Feb 2007 22:08:59 +0100 Subject: i2c-piix4: Add support for the ATI SB600 Add support for the ATI SB600 SMBus controller. Signed-off-by: Jean Delvare --- Documentation/i2c/busses/i2c-piix4 | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/i2c/busses/i2c-piix4 b/Documentation/i2c/busses/i2c-piix4 index 921476333235..7cbe43fa2701 100644 --- a/Documentation/i2c/busses/i2c-piix4 +++ b/Documentation/i2c/busses/i2c-piix4 @@ -6,7 +6,7 @@ Supported adapters: Datasheet: Publicly available at the Intel website * ServerWorks OSB4, CSB5, CSB6 and HT-1000 southbridges Datasheet: Only available via NDA from ServerWorks - * ATI IXP southbridges IXP200, IXP300, IXP400 + * ATI IXP200, IXP300, IXP400 and SB600 southbridges Datasheet: Not publicly available * Standard Microsystems (SMSC) SLC90E66 (Victory66) southbridge Datasheet: Publicly available at the SMSC website http://www.smsc.com -- cgit v1.2.3 From 3f9a4790a3818af1228c7fb4286afd66f3201fd0 Mon Sep 17 00:00:00 2001 From: Mike Frysinger Date: Tue, 13 Feb 2007 22:08:59 +0100 Subject: i2c: Fix typo in SMBus Write Word Data description Write data, don't read it. Signed-off-by: Mike Frysinger Signed-off-by: Jean Delvare --- Documentation/i2c/smbus-protocol | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/i2c/smbus-protocol b/Documentation/i2c/smbus-protocol index 09f5e5ca4927..8a653c60d25a 100644 --- a/Documentation/i2c/smbus-protocol +++ b/Documentation/i2c/smbus-protocol @@ -97,7 +97,7 @@ SMBus Write Word Data ===================== This is the opposite operation of the Read Word Data command. 16 bits -of data is read from a device, from a designated register that is +of data is written to a device, to the designated register that is specified through the Comm byte. S Addr Wr [A] Comm [A] DataLow [A] DataHigh [A] P -- cgit v1.2.3 From 099ab118b6b194ad43865f62776a0d36d4b1c7d2 Mon Sep 17 00:00:00 2001 From: Jean Delvare Date: Tue, 13 Feb 2007 22:09:00 +0100 Subject: i2c-i801: Document the SMBus unhiding quirk This is a frequently asked question so it deserves a paragraph in the driver documentation. Signed-off-by: Jean Delvare --- Documentation/i2c/busses/i2c-i801 | 60 +++++++++++++++++++++++++++++++++++---- 1 file changed, 55 insertions(+), 5 deletions(-) (limited to 'Documentation') diff --git a/Documentation/i2c/busses/i2c-i801 b/Documentation/i2c/busses/i2c-i801 index 3db69a086c41..c34f0db78a30 100644 --- a/Documentation/i2c/busses/i2c-i801 +++ b/Documentation/i2c/busses/i2c-i801 @@ -48,14 +48,9 @@ following: The SMBus controller is function 3 in device 1f. Class 0c05 is SMBus Serial Controller. -If you do NOT see the 24x3 device at function 3, and you can't figure out -any way in the BIOS to enable it, - The ICH chips are quite similar to Intel's PIIX4 chip, at least in the SMBus controller. -See the file i2c-piix4 for some additional information. - Process Call Support -------------------- @@ -74,6 +69,61 @@ SMBus 2.0 Support The 82801DB (ICH4) and later chips support several SMBus 2.0 features. + +Hidden ICH SMBus +---------------- + +If your system has an Intel ICH south bridge, but you do NOT see the +SMBus device at 00:1f.3 in lspci, and you can't figure out any way in the +BIOS to enable it, it means it has been hidden by the BIOS code. Asus is +well known for first doing this on their P4B motherboard, and many other +boards after that. Some vendor machines are affected as well. + +The first thing to try is the "i2c_ec" ACPI driver. It could be that the +SMBus was hidden on purpose because it'll be driven by ACPI. If the +i2c_ec driver works for you, just forget about the i2c-i801 driver and +don't try to unhide the ICH SMBus. Even if i2c_ec doesn't work, you +better make sure that the SMBus isn't used by the ACPI code. Try loading +the "fan" and "thermal" drivers, and check in /proc/acpi/fan and +/proc/acpi/thermal_zone. If you find anything there, it's likely that +the ACPI is accessing the SMBus and it's safer not to unhide it. Only +once you are certain that ACPI isn't using the SMBus, you can attempt +to unhide it. + +In order to unhide the SMBus, we need to change the value of a PCI +register before the kernel enumerates the PCI devices. This is done in +drivers/pci/quirks.c, where all affected boards must be listed (see +function asus_hides_smbus_hostbridge.) If the SMBus device is missing, +and you think there's something interesting on the SMBus (e.g. a +hardware monitoring chip), you need to add your board to the list. + +The motherboard is identified using the subvendor and subdevice IDs of the +host bridge PCI device. Get yours with "lspci -n -v -s 00:00.0": + +00:00.0 Class 0600: 8086:2570 (rev 02) + Subsystem: 1043:80f2 + Flags: bus master, fast devsel, latency 0 + Memory at fc000000 (32-bit, prefetchable) [size=32M] + Capabilities: [e4] #09 [2106] + Capabilities: [a0] AGP version 3.0 + +Here the host bridge ID is 2570 (82865G/PE/P), the subvendor ID is 1043 +(Asus) and the subdevice ID is 80f2 (P4P800-X). You can find the symbolic +names for the bridge ID and the subvendor ID in include/linux/pci_ids.h, +and then add a case for your subdevice ID at the right place in +drivers/pci/quirks.c. Then please give it very good testing, to make sure +that the unhidden SMBus doesn't conflict with e.g. ACPI. + +If it works, proves useful (i.e. there are usable chips on the SMBus) +and seems safe, please submit a patch for inclusion into the kernel. + +Note: There's a useful script in lm_sensors 2.10.2 and later, named +unhide_ICH_SMBus (in prog/hotplug), which uses the fakephp driver to +temporarily unhide the SMBus without having to patch and recompile your +kernel. It's very convenient if you just want to check if there's +anything interesting on your hidden ICH SMBus. + + ********************** The lm_sensors project gratefully acknowledges the support of Texas Instruments in the initial development of this driver. -- cgit v1.2.3 From f37dd80ac2a67e4e4e921f99d34a1ceeb2488abb Mon Sep 17 00:00:00 2001 From: David Brownell Date: Tue, 13 Feb 2007 22:09:00 +0100 Subject: i2c: Add driver suspend/resume/shutdown support Driver model updates for the I2C core: - Add new suspend(), resume(), and shutdown() methods. Use them in the standard driver model style; document them. - Minor doc updates to highlight zero-initialized fields in drivers, and the driver model accessors for "clientdata". If any i2c drivers were previously using the old suspend/resume calls in "struct driver", they were getting warning messages ... and will now no longer work. Other than that, this patch changes no behaviors; and it lets I2C drivers use conventional PM and shutdown support. Signed-off-by: David Brownell Signed-off-by: Jean Delvare --- Documentation/i2c/porting-clients | 6 ++++ Documentation/i2c/writing-clients | 58 ++++++++++++++++++++++++++++------ drivers/i2c/i2c-core.c | 65 ++++++++++++++++++++++++++------------- include/linux/i2c.h | 7 ++++- 4 files changed, 105 insertions(+), 31 deletions(-) (limited to 'Documentation') diff --git a/Documentation/i2c/porting-clients b/Documentation/i2c/porting-clients index f03c2a02f806..ca272b263a92 100644 --- a/Documentation/i2c/porting-clients +++ b/Documentation/i2c/porting-clients @@ -129,6 +129,12 @@ Technical changes: structure, those name member should be initialized to a driver name string. i2c_driver itself has no name member anymore. +* [Driver model] Instead of shutdown or reboot notifiers, provide a + shutdown() method in your driver. + +* [Power management] Use the driver model suspend() and resume() + callbacks instead of the obsolete pm_register() calls. + Coding policy: * [Copyright] Use (C), not (c), for copyright. diff --git a/Documentation/i2c/writing-clients b/Documentation/i2c/writing-clients index 3a057c8e5507..fbcff96f4ca1 100644 --- a/Documentation/i2c/writing-clients +++ b/Documentation/i2c/writing-clients @@ -21,20 +21,26 @@ The driver structure Usually, you will implement a single driver structure, and instantiate all clients from it. Remember, a driver structure contains general access -routines, a client structure specific information like the actual I2C -address. +routines, and should be zero-initialized except for fields with data you +provide. A client structure holds device-specific information like the +driver model device node, and its I2C address. static struct i2c_driver foo_driver = { .driver = { .name = "foo", }, - .attach_adapter = &foo_attach_adapter, - .detach_client = &foo_detach_client, - .command = &foo_command /* may be NULL */ + .attach_adapter = foo_attach_adapter, + .detach_client = foo_detach_client, + .shutdown = foo_shutdown, /* optional */ + .suspend = foo_suspend, /* optional */ + .resume = foo_resume, /* optional */ + .command = foo_command, /* optional */ } -The name field must match the driver name, including the case. It must not -contain spaces, and may be up to 31 characters long. +The name field is the driver name, and must not contain spaces. It +should match the module name (if the driver can be compiled as a module), +although you can use MODULE_ALIAS (passing "foo" in this example) to add +another name for the module. All other fields are for call-back functions which will be explained below. @@ -43,11 +49,18 @@ below. Extra client data ================= -The client structure has a special `data' field that can point to any -structure at all. You can use this to keep client-specific data. You +Each client structure has a special `data' field that can point to any +structure at all. You should use this to keep device-specific data, +especially in drivers that handle multiple I2C or SMBUS devices. You do not always need this, but especially for `sensors' drivers, it can be very useful. + /* store the value */ + void i2c_set_clientdata(struct i2c_client *client, void *data); + + /* retrieve the value */ + void *i2c_get_clientdata(struct i2c_client *client); + An example structure is below. struct foo_data { @@ -493,6 +506,33 @@ by `__init_data'. Hose functions and structures can be removed after kernel booting (or module loading) is completed. +Power Management +================ + +If your I2C device needs special handling when entering a system low +power state -- like putting a transceiver into a low power mode, or +activating a system wakeup mechanism -- do that in the suspend() method. +The resume() method should reverse what the suspend() method does. + +These are standard driver model calls, and they work just like they +would for any other driver stack. The calls can sleep, and can use +I2C messaging to the device being suspended or resumed (since their +parent I2C adapter is active when these calls are issued, and IRQs +are still enabled). + + +System Shutdown +=============== + +If your I2C device needs special handling when the system shuts down +or reboots (including kexec) -- like turning something off -- use a +shutdown() method. + +Again, this is a standard driver model call, working just like it +would for any other driver stack: the calls can sleep, and can use +I2C messaging. + + Command function ================ diff --git a/drivers/i2c/i2c-core.c b/drivers/i2c/i2c-core.c index 60f6eb194046..9653f7f81561 100644 --- a/drivers/i2c/i2c-core.c +++ b/drivers/i2c/i2c-core.c @@ -41,49 +41,72 @@ static LIST_HEAD(drivers); static DEFINE_MUTEX(core_lists); static DEFINE_IDR(i2c_adapter_idr); + +/* ------------------------------------------------------------------------- */ + /* match always succeeds, as we want the probe() to tell if we really accept this match */ static int i2c_device_match(struct device *dev, struct device_driver *drv) { return 1; } -static int i2c_bus_suspend(struct device * dev, pm_message_t state) +static int i2c_device_probe(struct device *dev) { - int rc = 0; + return -ENODEV; +} - if (dev->driver && dev->driver->suspend) - rc = dev->driver->suspend(dev, state); - return rc; +static int i2c_device_remove(struct device *dev) +{ + return 0; } -static int i2c_bus_resume(struct device * dev) +static void i2c_device_shutdown(struct device *dev) { - int rc = 0; - - if (dev->driver && dev->driver->resume) - rc = dev->driver->resume(dev); - return rc; + struct i2c_driver *driver; + + if (!dev->driver) + return; + driver = to_i2c_driver(dev->driver); + if (driver->shutdown) + driver->shutdown(to_i2c_client(dev)); } -static int i2c_device_probe(struct device *dev) +static int i2c_device_suspend(struct device * dev, pm_message_t mesg) { - return -ENODEV; + struct i2c_driver *driver; + + if (!dev->driver) + return 0; + driver = to_i2c_driver(dev->driver); + if (!driver->suspend) + return 0; + return driver->suspend(to_i2c_client(dev), mesg); } -static int i2c_device_remove(struct device *dev) +static int i2c_device_resume(struct device * dev) { - return 0; + struct i2c_driver *driver; + + if (!dev->driver) + return 0; + driver = to_i2c_driver(dev->driver); + if (!driver->resume) + return 0; + return driver->resume(to_i2c_client(dev)); } struct bus_type i2c_bus_type = { - .name = "i2c", - .match = i2c_device_match, - .probe = i2c_device_probe, - .remove = i2c_device_remove, - .suspend = i2c_bus_suspend, - .resume = i2c_bus_resume, + .name = "i2c", + .match = i2c_device_match, + .probe = i2c_device_probe, + .remove = i2c_device_remove, + .shutdown = i2c_device_shutdown, + .suspend = i2c_device_suspend, + .resume = i2c_device_resume, }; +/* ------------------------------------------------------------------------- */ + void i2c_adapter_dev_release(struct device *dev) { struct i2c_adapter *adap = dev_to_i2c_adapter(dev); diff --git a/include/linux/i2c.h b/include/linux/i2c.h index 71e50d3e492f..9428092017e3 100644 --- a/include/linux/i2c.h +++ b/include/linux/i2c.h @@ -125,7 +125,12 @@ struct i2c_driver { * it must be freed here. */ int (*detach_client)(struct i2c_client *); - + + /* driver model interfaces that don't relate to enumeration */ + void (*shutdown)(struct i2c_client *); + int (*suspend)(struct i2c_client *, pm_message_t mesg); + int (*resume)(struct i2c_client *); + /* a ioctl like command that can be used to perform specific functions * with the device. */ -- cgit v1.2.3 From ab6a6ed271c757b429ddc68f5b93a41f9592ab8b Mon Sep 17 00:00:00 2001 From: Jean Delvare Date: Tue, 13 Feb 2007 22:09:02 +0100 Subject: i2c-viapro: Add support for the VIA CX700 south bridge We do not have any documentation for the CX700, but it was reported to work fine. Thanks to Claas Langbehn for testing. Signed-off-by: Jean Delvare --- Documentation/i2c/busses/i2c-viapro | 7 +++++++ drivers/i2c/busses/Kconfig | 5 +++-- drivers/i2c/busses/i2c-viapro.c | 6 +++++- 3 files changed, 15 insertions(+), 3 deletions(-) (limited to 'Documentation') diff --git a/Documentation/i2c/busses/i2c-viapro b/Documentation/i2c/busses/i2c-viapro index 25680346e0ac..775f489e86f6 100644 --- a/Documentation/i2c/busses/i2c-viapro +++ b/Documentation/i2c/busses/i2c-viapro @@ -13,6 +13,9 @@ Supported adapters: * VIA Technologies, Inc. VT8235, VT8237R, VT8237A, VT8251 Datasheet: available on request and under NDA from VIA + * VIA Technologies, Inc. CX700 + Datasheet: available on request and under NDA from VIA + Authors: Kyösti Mälkki , Mark D. Studebaker , @@ -44,6 +47,7 @@ Your lspci -n listing must show one of these : device 1106:3227 (VT8237R) device 1106:3337 (VT8237A) device 1106:3287 (VT8251) + device 1106:8324 (CX700) If none of these show up, you should look in the BIOS for settings like enable ACPI / SMBus or even USB. @@ -51,3 +55,6 @@ enable ACPI / SMBus or even USB. Except for the oldest chips (VT82C596A/B, VT82C686A and most probably VT8231), this driver supports I2C block transactions. Such transactions are mainly useful to read from and write to EEPROMs. + +The CX700 additionally appears to support SMBus PEC, although this driver +doesn't implement it yet. diff --git a/drivers/i2c/busses/Kconfig b/drivers/i2c/busses/Kconfig index f2894dec51a5..25d52e0eec2c 100644 --- a/drivers/i2c/busses/Kconfig +++ b/drivers/i2c/busses/Kconfig @@ -500,11 +500,11 @@ config I2C_VIA will be called i2c-via. config I2C_VIAPRO - tristate "VIA 82C596/82C686/82xx" + tristate "VIA VT82C596/82C686/82xx and CX700" depends on I2C && PCI help If you say yes to this option, support will be included for the VIA - 82C596/82C686/82xx I2C interfaces. Specifically, the following + VT82C596 and later SMBus interface. Specifically, the following chipsets are supported: VT82C596A/B VT82C686A/B @@ -513,6 +513,7 @@ config I2C_VIAPRO VT8235 VT8237R/A VT8251 + CX700 This driver can also be built as a module. If so, the module will be called i2c-viapro. diff --git a/drivers/i2c/busses/i2c-viapro.c b/drivers/i2c/busses/i2c-viapro.c index 43a081f16553..03c5fc868548 100644 --- a/drivers/i2c/busses/i2c-viapro.c +++ b/drivers/i2c/busses/i2c-viapro.c @@ -4,7 +4,7 @@ Copyright (c) 1998 - 2002 Frodo Looijaard , Philip Edelbrock , Kyösti Mälkki , Mark D. Studebaker - Copyright (C) 2005 Jean Delvare + Copyright (C) 2005 - 2007 Jean Delvare This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by @@ -36,6 +36,7 @@ VT8237R 0x3227 yes VT8237A 0x3337 yes VT8251 0x3287 yes + CX700 0x8324 yes Note: we assume there can only be one device, with one SMBus interface. */ @@ -384,6 +385,7 @@ found: dev_dbg(&pdev->dev, "VT596_smba = 0x%X\n", vt596_smba); switch (pdev->device) { + case PCI_DEVICE_ID_VIA_CX700: case PCI_DEVICE_ID_VIA_8251: case PCI_DEVICE_ID_VIA_8237: case PCI_DEVICE_ID_VIA_8237A: @@ -443,6 +445,8 @@ static struct pci_device_id vt596_ids[] = { .driver_data = SMBBA1 }, { PCI_DEVICE(PCI_VENDOR_ID_VIA, PCI_DEVICE_ID_VIA_8251), .driver_data = SMBBA3 }, + { PCI_DEVICE(PCI_VENDOR_ID_VIA, PCI_DEVICE_ID_VIA_CX700), + .driver_data = SMBBA3 }, { 0, } }; -- cgit v1.2.3 From 55249cf750e4d9be19c7f8afd502c9ca42de8858 Mon Sep 17 00:00:00 2001 From: Jonathan McDowell Date: Tue, 13 Feb 2007 22:09:02 +0100 Subject: i2c-parport: Add support for One For All remote JP1 interface This simple patch adds support to i2c-parport for the One For All remote JP1 parallel port interfaces which can be found detailed at: http://www.hifi-remote.com/jp1/hardware.shtml These allow access to the internal configuration EEPROM on various remote controls and there are a variety of Windows tools that make use of this hardware. I have tested this patch with the "simple" parallel port device and a One For All URC-7562 and confirmed that the data read using the eeprom i2c driver matches that returned by the Windows "IR" JP1 tool. Signed-off-by: Jonathan McDowell Signed-off-by: Jean Delvare --- Documentation/i2c/busses/i2c-parport | 15 +++++++++++++++ drivers/i2c/busses/i2c-parport.h | 8 ++++++++ 2 files changed, 23 insertions(+) (limited to 'Documentation') diff --git a/Documentation/i2c/busses/i2c-parport b/Documentation/i2c/busses/i2c-parport index 77b995dfca22..dceaba1ad930 100644 --- a/Documentation/i2c/busses/i2c-parport +++ b/Documentation/i2c/busses/i2c-parport @@ -19,6 +19,7 @@ It currently supports the following devices: * (type=4) Analog Devices ADM1032 evaluation board * (type=5) Analog Devices evaluation boards: ADM1025, ADM1030, ADM1031 * (type=6) Barco LPT->DVI (K5800236) adapter + * (type=7) One For All JP1 parallel port adapter These devices use different pinout configurations, so you have to tell the driver what you have, using the type module parameter. There is no @@ -157,3 +158,17 @@ many more, using /dev/velleman. http://home.wanadoo.nl/hihihi/libk8005.htm http://struyve.mine.nu:8080/index.php?block=k8000 http://sourceforge.net/projects/libk8005/ + + +One For All JP1 parallel port adapter +------------------------------------- + +The JP1 project revolves around a set of remote controls which expose +the I2C bus their internal configuration EEPROM lives on via a 6 pin +jumper in the battery compartment. More details can be found at: + +http://www.hifi-remote.com/jp1/ + +Details of the simple parallel port hardware can be found at: + +http://www.hifi-remote.com/jp1/hardware.shtml diff --git a/drivers/i2c/busses/i2c-parport.h b/drivers/i2c/busses/i2c-parport.h index 9ddd816d5d0f..ed69d846cb95 100644 --- a/drivers/i2c/busses/i2c-parport.h +++ b/drivers/i2c/busses/i2c-parport.h @@ -88,6 +88,13 @@ static struct adapter_parm adapter_parm[] = { .getscl = { 0x40, STAT, 0 }, .init = { 0xfc, DATA, 0 }, }, + /* type 7: One For All JP1 parallel port adapter */ + { + .setsda = { 0x01, DATA, 0 }, + .setscl = { 0x02, DATA, 0 }, + .getsda = { 0x80, STAT, 1 }, + .init = { 0x04, DATA, 1 }, + }, }; static int type = -1; @@ -101,4 +108,5 @@ MODULE_PARM_DESC(type, " 4 = ADM1032 evaluation board\n" " 5 = ADM1025, ADM1030 and ADM1031 evaluation boards\n" " 6 = Barco LPT->DVI (K5800236) adapter\n" + " 7 = One For All JP1 parallel port adapter\n" ); -- cgit v1.2.3