From 6e2a851e71e65d4ec5bbc51802c36a61322d792b Mon Sep 17 00:00:00 2001 From: Seth Heasley Date: Tue, 24 May 2011 20:58:49 +0200 Subject: i2c-i801: SMBus patch for Intel Panther Point DeviceIDs This patch adds the SMBus controller DeviceID for the Intel Panther Point PCH. Signed-off-by: Seth Heasley Signed-off-by: Jean Delvare --- drivers/i2c/busses/Kconfig | 1 + drivers/i2c/busses/i2c-i801.c | 4 +++- 2 files changed, 4 insertions(+), 1 deletion(-) (limited to 'drivers') diff --git a/drivers/i2c/busses/Kconfig b/drivers/i2c/busses/Kconfig index 326652f673f7..b24ca4e98ef8 100644 --- a/drivers/i2c/busses/Kconfig +++ b/drivers/i2c/busses/Kconfig @@ -101,6 +101,7 @@ config I2C_I801 6 Series (PCH) Patsburg (PCH) DH89xxCC (PCH) + Panther Point (PCH) This driver can also be built as a module. If so, the module will be called i2c-i801. diff --git a/drivers/i2c/busses/i2c-i801.c b/drivers/i2c/busses/i2c-i801.c index ec36208c9977..6d36ad628caa 100644 --- a/drivers/i2c/busses/i2c-i801.c +++ b/drivers/i2c/busses/i2c-i801.c @@ -50,6 +50,7 @@ Patsburg (PCH) IDF 0x1d71 32 hard yes yes yes Patsburg (PCH) IDF 0x1d72 32 hard yes yes yes DH89xxCC (PCH) 0x2330 32 hard yes yes yes + Panther Point (PCH) 0x1e22 32 hard yes yes yes Features supported by this driver: Software PEC no @@ -137,11 +138,11 @@ /* Older devices have their ID defined in */ #define PCI_DEVICE_ID_INTEL_COUGARPOINT_SMBUS 0x1c22 #define PCI_DEVICE_ID_INTEL_PATSBURG_SMBUS 0x1d22 -#define PCI_DEVICE_ID_INTEL_PANTHERPOINT_SMBUS 0x1e22 /* Patsburg also has three 'Integrated Device Function' SMBus controllers */ #define PCI_DEVICE_ID_INTEL_PATSBURG_SMBUS_IDF0 0x1d70 #define PCI_DEVICE_ID_INTEL_PATSBURG_SMBUS_IDF1 0x1d71 #define PCI_DEVICE_ID_INTEL_PATSBURG_SMBUS_IDF2 0x1d72 +#define PCI_DEVICE_ID_INTEL_PANTHERPOINT_SMBUS 0x1e22 #define PCI_DEVICE_ID_INTEL_DH89XXCC_SMBUS 0x2330 #define PCI_DEVICE_ID_INTEL_5_3400_SERIES_SMBUS 0x3b30 @@ -629,6 +630,7 @@ static const struct pci_device_id i801_ids[] = { { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_PATSBURG_SMBUS_IDF1) }, { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_PATSBURG_SMBUS_IDF2) }, { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_DH89XXCC_SMBUS) }, + { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_PANTHERPOINT_SMBUS) }, { 0, } }; -- cgit v1.2.3 From e7198fbf50fd5db4cc9681beed760403f794320d Mon Sep 17 00:00:00 2001 From: Jean Delvare Date: Tue, 24 May 2011 20:58:49 +0200 Subject: i2c-i801: Don't probe for slaves on IDF channels I don't know if Fujitsu is ever going to produce Patsburg-based machines, but if they do, I'd rather not probe the secondary (IDF) SMBus channels. At least not until we have a good reason for doing so. On a side note, I'm not even sure if it is right to enable detection of HWMON and DDC devices on the IDF channels. Time will tell... Signed-off-by: Jean Delvare Acked-by: Hans de Goede Acked-by: David Woodhouse --- drivers/i2c/busses/i2c-i801.c | 46 +++++++++++++++++++++++++++++-------------- 1 file changed, 31 insertions(+), 15 deletions(-) (limited to 'drivers') diff --git a/drivers/i2c/busses/i2c-i801.c b/drivers/i2c/busses/i2c-i801.c index 6d36ad628caa..4228691ffde8 100644 --- a/drivers/i2c/busses/i2c-i801.c +++ b/drivers/i2c/busses/i2c-i801.c @@ -160,6 +160,8 @@ static struct pci_driver i801_driver; #define FEATURE_BLOCK_BUFFER (1 << 1) #define FEATURE_BLOCK_PROC (1 << 2) #define FEATURE_I2C_BLOCK_READ (1 << 3) +/* Not really a feature, but it's convenient to handle it as such */ +#define FEATURE_IDF (1 << 15) static const char *i801_feature_names[] = { "SMBus PEC", @@ -738,6 +740,29 @@ static void __devinit dmi_check_onboard_devices(const struct dmi_header *dm, } #endif +/* Register optional slaves */ +static void __devinit i801_probe_optional_slaves(struct i801_priv *priv) +{ + /* Only register slaves on main SMBus channel */ + if (priv->features & FEATURE_IDF) + return; + +#if defined CONFIG_INPUT_APANEL || defined CONFIG_INPUT_APANEL_MODULE + if (apanel_addr) { + struct i2c_board_info info; + + memset(&info, 0, sizeof(struct i2c_board_info)); + info.addr = apanel_addr; + strlcpy(info.type, "fujitsu_apanel", I2C_NAME_SIZE); + i2c_new_device(&priv->adapter, &info); + } +#endif +#if defined CONFIG_SENSORS_FSCHMD || defined CONFIG_SENSORS_FSCHMD_MODULE + if (dmi_name_in_vendors("FUJITSU")) + dmi_walk(dmi_check_onboard_devices, &priv->adapter); +#endif +} + static int __devinit i801_probe(struct pci_dev *dev, const struct pci_device_id *id) { @@ -756,6 +781,11 @@ static int __devinit i801_probe(struct pci_dev *dev, priv->pci_dev = dev; switch (dev->device) { + case PCI_DEVICE_ID_INTEL_PATSBURG_SMBUS_IDF0: + case PCI_DEVICE_ID_INTEL_PATSBURG_SMBUS_IDF1: + case PCI_DEVICE_ID_INTEL_PATSBURG_SMBUS_IDF2: + priv->features |= FEATURE_IDF; + /* fall through */ default: priv->features |= FEATURE_I2C_BLOCK_READ; /* fall through */ @@ -841,21 +871,7 @@ static int __devinit i801_probe(struct pci_dev *dev, goto exit_release; } - /* Register optional slaves */ -#if defined CONFIG_INPUT_APANEL || defined CONFIG_INPUT_APANEL_MODULE - if (apanel_addr) { - struct i2c_board_info info; - - memset(&info, 0, sizeof(struct i2c_board_info)); - info.addr = apanel_addr; - strlcpy(info.type, "fujitsu_apanel", I2C_NAME_SIZE); - i2c_new_device(&priv->adapter, &info); - } -#endif -#if defined CONFIG_SENSORS_FSCHMD || defined CONFIG_SENSORS_FSCHMD_MODULE - if (dmi_name_in_vendors("FUJITSU")) - dmi_walk(dmi_check_onboard_devices, &priv->adapter); -#endif + i801_probe_optional_slaves(priv); pci_set_drvdata(dev, priv); return 0; -- cgit v1.2.3 From 6aa1464d5482cc8f6f026ebb12d94b77a58c823b Mon Sep 17 00:00:00 2001 From: Jean Delvare Date: Tue, 24 May 2011 20:58:49 +0200 Subject: i2c-i801: Check for vendor Fujitsu before probing for apanel Scanning the BIOS memory for the apanel information is costly, so avoid doing it on non-Fujitsu machines. Signed-off-by: Jean Delvare --- drivers/i2c/busses/i2c-i801.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) (limited to 'drivers') diff --git a/drivers/i2c/busses/i2c-i801.c b/drivers/i2c/busses/i2c-i801.c index 4228691ffde8..1aa5be019cfc 100644 --- a/drivers/i2c/busses/i2c-i801.c +++ b/drivers/i2c/busses/i2c-i801.c @@ -931,7 +931,8 @@ static struct pci_driver i801_driver = { static int __init i2c_i801_init(void) { - input_apanel_init(); + if (dmi_name_in_vendors("FUJITSU")) + input_apanel_init(); return pci_register_driver(&i801_driver); } -- cgit v1.2.3 From 8eacfcebf0274310a751924c02c5c31cbdf057b3 Mon Sep 17 00:00:00 2001 From: Jean Delvare Date: Tue, 24 May 2011 20:58:49 +0200 Subject: i2c-i801: Don't depend on other kernel driver config options Don't let other driver config options influence us, as it makes the code more complex and fragile for a small benefit. There's nothing wrong with instantiating I2C devices even if they don't have a driver. And we're talking about 835 extra bytes in the binary on x86-64, that's hardly worth arguing about. Signed-off-by: Jean Delvare Cc: David Woodhouse Cc: Hans de Goede --- drivers/i2c/busses/Kconfig | 1 + drivers/i2c/busses/i2c-i801.c | 16 ++++++---------- 2 files changed, 7 insertions(+), 10 deletions(-) (limited to 'drivers') diff --git a/drivers/i2c/busses/Kconfig b/drivers/i2c/busses/Kconfig index b24ca4e98ef8..428d098c35ef 100644 --- a/drivers/i2c/busses/Kconfig +++ b/drivers/i2c/busses/Kconfig @@ -79,6 +79,7 @@ config I2C_AMD8111 config I2C_I801 tristate "Intel 82801 (ICH/PCH)" depends on PCI + select CHECK_SIGNATURE if X86 && DMI help If you say yes to this option, support will be included for the Intel 801 family of mainboard I2C interfaces. Specifically, the following diff --git a/drivers/i2c/busses/i2c-i801.c b/drivers/i2c/busses/i2c-i801.c index 1aa5be019cfc..ab26840d0c70 100644 --- a/drivers/i2c/busses/i2c-i801.c +++ b/drivers/i2c/busses/i2c-i801.c @@ -638,7 +638,7 @@ static const struct pci_device_id i801_ids[] = { MODULE_DEVICE_TABLE(pci, i801_ids); -#if defined CONFIG_INPUT_APANEL || defined CONFIG_INPUT_APANEL_MODULE +#if defined CONFIG_X86 && defined CONFIG_DMI static unsigned char apanel_addr; /* Scan the system ROM for the signature "FJKEYINF" */ @@ -668,11 +668,7 @@ static void __init input_apanel_init(void) } iounmap(bios); } -#else -static void __init input_apanel_init(void) {} -#endif -#if defined CONFIG_SENSORS_FSCHMD || defined CONFIG_SENSORS_FSCHMD_MODULE struct dmi_onboard_device_info { const char *name; u8 type; @@ -738,7 +734,6 @@ static void __devinit dmi_check_onboard_devices(const struct dmi_header *dm, dmi_check_onboard_device(type, name, adap); } } -#endif /* Register optional slaves */ static void __devinit i801_probe_optional_slaves(struct i801_priv *priv) @@ -747,7 +742,6 @@ static void __devinit i801_probe_optional_slaves(struct i801_priv *priv) if (priv->features & FEATURE_IDF) return; -#if defined CONFIG_INPUT_APANEL || defined CONFIG_INPUT_APANEL_MODULE if (apanel_addr) { struct i2c_board_info info; @@ -756,12 +750,14 @@ static void __devinit i801_probe_optional_slaves(struct i801_priv *priv) strlcpy(info.type, "fujitsu_apanel", I2C_NAME_SIZE); i2c_new_device(&priv->adapter, &info); } -#endif -#if defined CONFIG_SENSORS_FSCHMD || defined CONFIG_SENSORS_FSCHMD_MODULE + if (dmi_name_in_vendors("FUJITSU")) dmi_walk(dmi_check_onboard_devices, &priv->adapter); -#endif } +#else +static void __init input_apanel_init(void) {} +static void __devinit i801_probe_optional_slaves(struct i801_priv *priv) {} +#endif /* CONFIG_X86 && CONFIG_DMI */ static int __devinit i801_probe(struct pci_dev *dev, const struct pci_device_id *id) -- cgit v1.2.3 From 07da0372dd6ca5517400ce95040861def25930c8 Mon Sep 17 00:00:00 2001 From: Jean Delvare Date: Tue, 24 May 2011 20:58:49 +0200 Subject: i2c-parport: Various cleanups * Fix white space. * Rename labels to something meaningful. * Prefix defines with PORT_ to avoid collision with macros from . * Add const markers where possible. Signed-off-by: Jean Delvare --- drivers/i2c/busses/i2c-parport-light.c | 10 ++--- drivers/i2c/busses/i2c-parport.c | 30 +++++++------- drivers/i2c/busses/i2c-parport.h | 74 ++++++++++++++++------------------ 3 files changed, 55 insertions(+), 59 deletions(-) (limited to 'drivers') diff --git a/drivers/i2c/busses/i2c-parport-light.c b/drivers/i2c/busses/i2c-parport-light.c index fc5fbd1012c9..4b95f7a63a3b 100644 --- a/drivers/i2c/busses/i2c-parport-light.c +++ b/drivers/i2c/busses/i2c-parport-light.c @@ -2,13 +2,13 @@ * i2c-parport-light.c I2C bus over parallel port * * ------------------------------------------------------------------------ * Copyright (C) 2003-2010 Jean Delvare - + Based on older i2c-velleman.c driver Copyright (C) 1995-2000 Simon G. Vogl With some changes from: Frodo Looijaard Kyösti Mälkki - + 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 the Free Software Foundation; either version 2 of the License, or @@ -114,7 +114,7 @@ static struct i2c_algo_bit_data parport_algo_data = { .getscl = parport_getscl, .udelay = 50, .timeout = HZ, -}; +}; /* ----- Driver registration ---------------------------------------------- */ @@ -132,7 +132,7 @@ static struct i2c_smbus_alert_setup alert_data = { static struct i2c_client *ara; static struct lineop parport_ctrl_irq = { .val = (1 << 4), - .port = CTRL, + .port = PORT_CTRL, }; static int __devinit i2c_parport_probe(struct platform_device *pdev) @@ -245,7 +245,7 @@ static int __init i2c_parport_init(void) if (irq != 0) pr_info(DRVNAME ": using irq %d\n", irq); - if (!adapter_parm[type].getscl.val) + if (!adapter_parm[type].getscl.val) parport_algo_data.getscl = NULL; /* Sets global pdev as a side effect */ diff --git a/drivers/i2c/busses/i2c-parport.c b/drivers/i2c/busses/i2c-parport.c index 2dbba163b102..24565687ac9b 100644 --- a/drivers/i2c/busses/i2c-parport.c +++ b/drivers/i2c/busses/i2c-parport.c @@ -2,13 +2,13 @@ * i2c-parport.c I2C bus over parallel port * * ------------------------------------------------------------------------ * Copyright (C) 2003-2011 Jean Delvare - + Based on older i2c-philips-par.c driver Copyright (C) 1995-2000 Simon G. Vogl With some changes from: Frodo Looijaard Kyösti Mälkki - + 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 the Free Software Foundation; either version 2 of the License, or @@ -78,13 +78,13 @@ static unsigned char port_read_control(struct parport *p) return parport_read_control(p); } -static void (*port_write[])(struct parport *, unsigned char) = { +static void (* const port_write[])(struct parport *, unsigned char) = { port_write_data, NULL, port_write_control, }; -static unsigned char (*port_read[])(struct parport *) = { +static unsigned char (* const port_read[])(struct parport *) = { port_read_data, port_read_status, port_read_control, @@ -147,7 +147,7 @@ static const struct i2c_algo_bit_data parport_algo_data = { .getscl = parport_getscl, .udelay = 10, /* ~50 kbps */ .timeout = HZ, -}; +}; /* ----- I2c and parallel port call-back functions and structures --------- */ @@ -164,10 +164,10 @@ void i2c_parport_irq(void *data) "SMBus alert received but no ARA client!\n"); } -static void i2c_parport_attach (struct parport *port) +static void i2c_parport_attach(struct parport *port) { struct i2c_par *adapter; - + adapter = kzalloc(sizeof(struct i2c_par), GFP_KERNEL); if (adapter == NULL) { printk(KERN_ERR "i2c-parport: Failed to kzalloc\n"); @@ -180,7 +180,7 @@ static void i2c_parport_attach (struct parport *port) NULL, NULL, i2c_parport_irq, PARPORT_FLAG_EXCL, adapter); if (!adapter->pdev) { printk(KERN_ERR "i2c-parport: Unable to register with parport\n"); - goto ERROR0; + goto err_free; } /* Fill the rest of the structure */ @@ -200,7 +200,7 @@ static void i2c_parport_attach (struct parport *port) if (parport_claim_or_block(adapter->pdev) < 0) { printk(KERN_ERR "i2c-parport: Could not claim parallel port\n"); - goto ERROR1; + goto err_unregister; } /* Reset hardware to a sane state (SCL and SDA high) */ @@ -215,7 +215,7 @@ static void i2c_parport_attach (struct parport *port) if (i2c_bit_add_bus(&adapter->adapter) < 0) { printk(KERN_ERR "i2c-parport: Unable to register with I2C\n"); - goto ERROR1; + goto err_unregister; } /* Setup SMBus alert if supported */ @@ -234,16 +234,16 @@ static void i2c_parport_attach (struct parport *port) mutex_lock(&adapter_list_lock); list_add_tail(&adapter->node, &adapter_list); mutex_unlock(&adapter_list_lock); - return; + return; -ERROR1: + err_unregister: parport_release(adapter->pdev); parport_unregister_device(adapter->pdev); -ERROR0: + err_free: kfree(adapter); } -static void i2c_parport_detach (struct parport *port) +static void i2c_parport_detach(struct parport *port) { struct i2c_par *adapter, *_n; @@ -260,7 +260,7 @@ static void i2c_parport_detach (struct parport *port) /* Un-init if needed (power off...) */ if (adapter_parm[type].init.val) line_set(port, 0, &adapter_parm[type].init); - + parport_release(adapter->pdev); parport_unregister_device(adapter->pdev); list_del(&adapter->node); diff --git a/drivers/i2c/busses/i2c-parport.h b/drivers/i2c/busses/i2c-parport.h index a9f66816546c..3fe652302ea7 100644 --- a/drivers/i2c/busses/i2c-parport.h +++ b/drivers/i2c/busses/i2c-parport.h @@ -2,7 +2,7 @@ * i2c-parport.h I2C bus over parallel port * * ------------------------------------------------------------------------ * Copyright (C) 2003-2010 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 the Free Software Foundation; either version 2 of the License, or @@ -18,13 +18,9 @@ Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. * ------------------------------------------------------------------------ */ -#ifdef DATA -#undef DATA -#endif - -#define DATA 0 -#define STAT 1 -#define CTRL 2 +#define PORT_DATA 0 +#define PORT_STAT 1 +#define PORT_CTRL 2 struct lineop { u8 val; @@ -41,61 +37,61 @@ struct adapter_parm { unsigned int smbus_alert:1; }; -static struct adapter_parm adapter_parm[] = { +static const struct adapter_parm adapter_parm[] = { /* type 0: Philips adapter */ { - .setsda = { 0x80, DATA, 1 }, - .setscl = { 0x08, CTRL, 0 }, - .getsda = { 0x80, STAT, 0 }, - .getscl = { 0x08, STAT, 0 }, + .setsda = { 0x80, PORT_DATA, 1 }, + .setscl = { 0x08, PORT_CTRL, 0 }, + .getsda = { 0x80, PORT_STAT, 0 }, + .getscl = { 0x08, PORT_STAT, 0 }, }, /* type 1: home brew teletext adapter */ { - .setsda = { 0x02, DATA, 0 }, - .setscl = { 0x01, DATA, 0 }, - .getsda = { 0x80, STAT, 1 }, + .setsda = { 0x02, PORT_DATA, 0 }, + .setscl = { 0x01, PORT_DATA, 0 }, + .getsda = { 0x80, PORT_STAT, 1 }, }, /* type 2: Velleman K8000 adapter */ { - .setsda = { 0x02, CTRL, 1 }, - .setscl = { 0x08, CTRL, 1 }, - .getsda = { 0x10, STAT, 0 }, + .setsda = { 0x02, PORT_CTRL, 1 }, + .setscl = { 0x08, PORT_CTRL, 1 }, + .getsda = { 0x10, PORT_STAT, 0 }, }, /* type 3: ELV adapter */ { - .setsda = { 0x02, DATA, 1 }, - .setscl = { 0x01, DATA, 1 }, - .getsda = { 0x40, STAT, 1 }, - .getscl = { 0x08, STAT, 1 }, + .setsda = { 0x02, PORT_DATA, 1 }, + .setscl = { 0x01, PORT_DATA, 1 }, + .getsda = { 0x40, PORT_STAT, 1 }, + .getscl = { 0x08, PORT_STAT, 1 }, }, /* type 4: ADM1032 evaluation board */ { - .setsda = { 0x02, DATA, 1 }, - .setscl = { 0x01, DATA, 1 }, - .getsda = { 0x10, STAT, 1 }, - .init = { 0xf0, DATA, 0 }, + .setsda = { 0x02, PORT_DATA, 1 }, + .setscl = { 0x01, PORT_DATA, 1 }, + .getsda = { 0x10, PORT_STAT, 1 }, + .init = { 0xf0, PORT_DATA, 0 }, .smbus_alert = 1, }, /* type 5: ADM1025, ADM1030 and ADM1031 evaluation boards */ { - .setsda = { 0x02, DATA, 1 }, - .setscl = { 0x01, DATA, 1 }, - .getsda = { 0x10, STAT, 1 }, + .setsda = { 0x02, PORT_DATA, 1 }, + .setscl = { 0x01, PORT_DATA, 1 }, + .getsda = { 0x10, PORT_STAT, 1 }, }, /* type 6: Barco LPT->DVI (K5800236) adapter */ { - .setsda = { 0x02, DATA, 1 }, - .setscl = { 0x01, DATA, 1 }, - .getsda = { 0x20, STAT, 0 }, - .getscl = { 0x40, STAT, 0 }, - .init = { 0xfc, DATA, 0 }, + .setsda = { 0x02, PORT_DATA, 1 }, + .setscl = { 0x01, PORT_DATA, 1 }, + .getsda = { 0x20, PORT_STAT, 0 }, + .getscl = { 0x40, PORT_STAT, 0 }, + .init = { 0xfc, PORT_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 }, + .setsda = { 0x01, PORT_DATA, 0 }, + .setscl = { 0x02, PORT_DATA, 0 }, + .getsda = { 0x80, PORT_STAT, 1 }, + .init = { 0x04, PORT_DATA, 1 }, }, }; -- cgit v1.2.3