diff options
| author | Linus Torvalds <torvalds@linux-foundation.org> | 2010-08-12 13:06:29 -0400 |
|---|---|---|
| committer | Linus Torvalds <torvalds@linux-foundation.org> | 2010-08-12 13:06:29 -0400 |
| commit | 1c00650c233c404fadf9347329214d55283bd17a (patch) | |
| tree | 9de7cda2fe2e54411cc24ff3befd758c9cb9cd74 | |
| parent | 26df0766a73a859bb93dc58e747c5028557a23fd (diff) | |
| parent | 7f528135da9704d67db1f727162024b078e1cd8f (diff) | |
Merge branch 'i2c-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/jdelvare/staging
* 'i2c-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/jdelvare/staging:
i2c: I2C bus multiplexer driver pca954x
i2c: Multiplexed I2C bus core support
i2c: Use a separate mutex for userspace client lists
i2c: Make i2c_default_probe self-sufficient
i2c: Drop dummy variable
i2c: Move adapter locking helpers to i2c-core
V4L/DVB: Use custom I2C probing function mechanism
i2c: Add support for custom probe function
i2c-dev: Use memdup_user
i2c-dev: Remove unnecessary kmalloc casts
| -rw-r--r-- | Documentation/i2c/instantiating-devices | 2 | ||||
| -rw-r--r-- | drivers/i2c/Kconfig | 13 | ||||
| -rw-r--r-- | drivers/i2c/Makefile | 3 | ||||
| -rw-r--r-- | drivers/i2c/i2c-core.c | 158 | ||||
| -rw-r--r-- | drivers/i2c/i2c-dev.c | 66 | ||||
| -rw-r--r-- | drivers/i2c/i2c-mux.c | 165 | ||||
| -rw-r--r-- | drivers/i2c/muxes/Kconfig | 18 | ||||
| -rw-r--r-- | drivers/i2c/muxes/Makefile | 8 | ||||
| -rw-r--r-- | drivers/i2c/muxes/pca954x.c | 301 | ||||
| -rw-r--r-- | drivers/macintosh/therm_windtunnel.c | 4 | ||||
| -rw-r--r-- | drivers/media/video/bt8xx/bttv-i2c.c | 2 | ||||
| -rw-r--r-- | drivers/media/video/cx18/cx18-i2c.c | 3 | ||||
| -rw-r--r-- | drivers/media/video/cx23885/cx23885-i2c.c | 15 | ||||
| -rw-r--r-- | drivers/media/video/cx88/cx88-i2c.c | 19 | ||||
| -rw-r--r-- | drivers/media/video/em28xx/em28xx-cards.c | 2 | ||||
| -rw-r--r-- | drivers/media/video/ivtv/ivtv-i2c.c | 9 | ||||
| -rw-r--r-- | drivers/media/video/v4l2-common.c | 3 | ||||
| -rw-r--r-- | drivers/usb/host/ohci-pnx4008.c | 2 | ||||
| -rw-r--r-- | drivers/video/matrox/i2c-matroxfb.c | 2 | ||||
| -rw-r--r-- | include/linux/i2c-mux.h | 46 | ||||
| -rw-r--r-- | include/linux/i2c.h | 33 | ||||
| -rw-r--r-- | include/linux/i2c/pca954x.h | 47 |
22 files changed, 805 insertions, 116 deletions
diff --git a/Documentation/i2c/instantiating-devices b/Documentation/i2c/instantiating-devices index e89490270ab..87da405a859 100644 --- a/Documentation/i2c/instantiating-devices +++ b/Documentation/i2c/instantiating-devices | |||
| @@ -102,7 +102,7 @@ static int __devinit usb_hcd_pnx4008_probe(struct platform_device *pdev) | |||
| 102 | memset(&i2c_info, 0, sizeof(struct i2c_board_info)); | 102 | memset(&i2c_info, 0, sizeof(struct i2c_board_info)); |
| 103 | strlcpy(i2c_info.name, "isp1301_pnx", I2C_NAME_SIZE); | 103 | strlcpy(i2c_info.name, "isp1301_pnx", I2C_NAME_SIZE); |
| 104 | isp1301_i2c_client = i2c_new_probed_device(i2c_adap, &i2c_info, | 104 | isp1301_i2c_client = i2c_new_probed_device(i2c_adap, &i2c_info, |
| 105 | normal_i2c); | 105 | normal_i2c, NULL); |
| 106 | i2c_put_adapter(i2c_adap); | 106 | i2c_put_adapter(i2c_adap); |
| 107 | (...) | 107 | (...) |
| 108 | } | 108 | } |
diff --git a/drivers/i2c/Kconfig b/drivers/i2c/Kconfig index d06083fdffb..30f06e956bf 100644 --- a/drivers/i2c/Kconfig +++ b/drivers/i2c/Kconfig | |||
| @@ -47,6 +47,19 @@ config I2C_CHARDEV | |||
| 47 | This support is also available as a module. If so, the module | 47 | This support is also available as a module. If so, the module |
| 48 | will be called i2c-dev. | 48 | will be called i2c-dev. |
| 49 | 49 | ||
| 50 | config I2C_MUX | ||
| 51 | tristate "I2C bus multiplexing support" | ||
| 52 | depends on EXPERIMENTAL | ||
| 53 | help | ||
| 54 | Say Y here if you want the I2C core to support the ability to | ||
| 55 | handle multiplexed I2C bus topologies, by presenting each | ||
| 56 | multiplexed segment as a I2C adapter. | ||
| 57 | |||
| 58 | This support is also available as a module. If so, the module | ||
| 59 | will be called i2c-mux. | ||
| 60 | |||
| 61 | source drivers/i2c/muxes/Kconfig | ||
| 62 | |||
| 50 | config I2C_HELPER_AUTO | 63 | config I2C_HELPER_AUTO |
| 51 | bool "Autoselect pertinent helper modules" | 64 | bool "Autoselect pertinent helper modules" |
| 52 | default y | 65 | default y |
diff --git a/drivers/i2c/Makefile b/drivers/i2c/Makefile index a7d9b4be9bb..c00fd66388f 100644 --- a/drivers/i2c/Makefile +++ b/drivers/i2c/Makefile | |||
| @@ -6,7 +6,8 @@ obj-$(CONFIG_I2C_BOARDINFO) += i2c-boardinfo.o | |||
| 6 | obj-$(CONFIG_I2C) += i2c-core.o | 6 | obj-$(CONFIG_I2C) += i2c-core.o |
| 7 | obj-$(CONFIG_I2C_SMBUS) += i2c-smbus.o | 7 | obj-$(CONFIG_I2C_SMBUS) += i2c-smbus.o |
| 8 | obj-$(CONFIG_I2C_CHARDEV) += i2c-dev.o | 8 | obj-$(CONFIG_I2C_CHARDEV) += i2c-dev.o |
| 9 | obj-y += algos/ busses/ | 9 | obj-$(CONFIG_I2C_MUX) += i2c-mux.o |
| 10 | obj-y += algos/ busses/ muxes/ | ||
| 10 | 11 | ||
| 11 | ifeq ($(CONFIG_I2C_DEBUG_CORE),y) | 12 | ifeq ($(CONFIG_I2C_DEBUG_CORE),y) |
| 12 | EXTRA_CFLAGS += -DDEBUG | 13 | EXTRA_CFLAGS += -DDEBUG |
diff --git a/drivers/i2c/i2c-core.c b/drivers/i2c/i2c-core.c index df937df845e..6649176de94 100644 --- a/drivers/i2c/i2c-core.c +++ b/drivers/i2c/i2c-core.c | |||
| @@ -20,7 +20,9 @@ | |||
| 20 | /* With some changes from Kyösti Mälkki <kmalkki@cc.hut.fi>. | 20 | /* With some changes from Kyösti Mälkki <kmalkki@cc.hut.fi>. |
| 21 | All SMBus-related things are written by Frodo Looijaard <frodol@dds.nl> | 21 | All SMBus-related things are written by Frodo Looijaard <frodol@dds.nl> |
| 22 | SMBus 2.0 support by Mark Studebaker <mdsxyz123@yahoo.com> and | 22 | SMBus 2.0 support by Mark Studebaker <mdsxyz123@yahoo.com> and |
| 23 | Jean Delvare <khali@linux-fr.org> */ | 23 | Jean Delvare <khali@linux-fr.org> |
| 24 | Mux support by Rodolfo Giometti <giometti@enneenne.com> and | ||
| 25 | Michael Lawnick <michael.lawnick.ext@nsn.com> */ | ||
| 24 | 26 | ||
| 25 | #include <linux/module.h> | 27 | #include <linux/module.h> |
| 26 | #include <linux/kernel.h> | 28 | #include <linux/kernel.h> |
| @@ -423,11 +425,87 @@ static int __i2c_check_addr_busy(struct device *dev, void *addrp) | |||
| 423 | return 0; | 425 | return 0; |
| 424 | } | 426 | } |
| 425 | 427 | ||
| 428 | /* walk up mux tree */ | ||
| 429 | static int i2c_check_mux_parents(struct i2c_adapter *adapter, int addr) | ||
| 430 | { | ||
| 431 | int result; | ||
| 432 | |||
| 433 | result = device_for_each_child(&adapter->dev, &addr, | ||
| 434 | __i2c_check_addr_busy); | ||
| 435 | |||
| 436 | if (!result && i2c_parent_is_i2c_adapter(adapter)) | ||
| 437 | result = i2c_check_mux_parents( | ||
| 438 | to_i2c_adapter(adapter->dev.parent), addr); | ||
| 439 | |||
| 440 | return result; | ||
| 441 | } | ||
| 442 | |||
| 443 | /* recurse down mux tree */ | ||
| 444 | static int i2c_check_mux_children(struct device *dev, void *addrp) | ||
| 445 | { | ||
| 446 | int result; | ||
| 447 | |||
| 448 | if (dev->type == &i2c_adapter_type) | ||
| 449 | result = device_for_each_child(dev, addrp, | ||
| 450 | i2c_check_mux_children); | ||
| 451 | else | ||
| 452 | result = __i2c_check_addr_busy(dev, addrp); | ||
| 453 | |||
| 454 | return result; | ||
| 455 | } | ||
| 456 | |||
| 426 | static int i2c_check_addr_busy(struct i2c_adapter *adapter, int addr) | 457 | static int i2c_check_addr_busy(struct i2c_adapter *adapter, int addr) |
| 427 | { | 458 | { |
| 428 | return device_for_each_child(&adapter->dev, &addr, | 459 | int result = 0; |
| 429 | __i2c_check_addr_busy); | 460 | |
| 461 | if (i2c_parent_is_i2c_adapter(adapter)) | ||
| 462 | result = i2c_check_mux_parents( | ||
| 463 | to_i2c_adapter(adapter->dev.parent), addr); | ||
| 464 | |||
| 465 | if (!result) | ||
| 466 | result = device_for_each_child(&adapter->dev, &addr, | ||
| 467 | i2c_check_mux_children); | ||
| 468 | |||
| 469 | return result; | ||
| 470 | } | ||
| 471 | |||
| 472 | /** | ||
| 473 | * i2c_lock_adapter - Get exclusive access to an I2C bus segment | ||
| 474 | * @adapter: Target I2C bus segment | ||
| 475 | */ | ||
| 476 | void i2c_lock_adapter(struct i2c_adapter *adapter) | ||
| 477 | { | ||
| 478 | if (i2c_parent_is_i2c_adapter(adapter)) | ||
| 479 | i2c_lock_adapter(to_i2c_adapter(adapter->dev.parent)); | ||
| 480 | else | ||
| 481 | rt_mutex_lock(&adapter->bus_lock); | ||
| 482 | } | ||
| 483 | EXPORT_SYMBOL_GPL(i2c_lock_adapter); | ||
| 484 | |||
| 485 | /** | ||
| 486 | * i2c_trylock_adapter - Try to get exclusive access to an I2C bus segment | ||
| 487 | * @adapter: Target I2C bus segment | ||
| 488 | */ | ||
| 489 | static int i2c_trylock_adapter(struct i2c_adapter *adapter) | ||
| 490 | { | ||
| 491 | if (i2c_parent_is_i2c_adapter(adapter)) | ||
| 492 | return i2c_trylock_adapter(to_i2c_adapter(adapter->dev.parent)); | ||
| 493 | else | ||
| 494 | return rt_mutex_trylock(&adapter->bus_lock); | ||
| 495 | } | ||
| 496 | |||
| 497 | /** | ||
| 498 | * i2c_unlock_adapter - Release exclusive access to an I2C bus segment | ||
| 499 | * @adapter: Target I2C bus segment | ||
| 500 | */ | ||
| 501 | void i2c_unlock_adapter(struct i2c_adapter *adapter) | ||
| 502 | { | ||
| 503 | if (i2c_parent_is_i2c_adapter(adapter)) | ||
| 504 | i2c_unlock_adapter(to_i2c_adapter(adapter->dev.parent)); | ||
| 505 | else | ||
| 506 | rt_mutex_unlock(&adapter->bus_lock); | ||
| 430 | } | 507 | } |
| 508 | EXPORT_SYMBOL_GPL(i2c_unlock_adapter); | ||
| 431 | 509 | ||
| 432 | /** | 510 | /** |
| 433 | * i2c_new_device - instantiate an i2c device | 511 | * i2c_new_device - instantiate an i2c device |
| @@ -633,9 +711,9 @@ i2c_sysfs_new_device(struct device *dev, struct device_attribute *attr, | |||
| 633 | return -EINVAL; | 711 | return -EINVAL; |
| 634 | 712 | ||
| 635 | /* Keep track of the added device */ | 713 | /* Keep track of the added device */ |
| 636 | i2c_lock_adapter(adap); | 714 | mutex_lock(&adap->userspace_clients_lock); |
| 637 | list_add_tail(&client->detected, &adap->userspace_clients); | 715 | list_add_tail(&client->detected, &adap->userspace_clients); |
| 638 | i2c_unlock_adapter(adap); | 716 | mutex_unlock(&adap->userspace_clients_lock); |
| 639 | dev_info(dev, "%s: Instantiated device %s at 0x%02hx\n", "new_device", | 717 | dev_info(dev, "%s: Instantiated device %s at 0x%02hx\n", "new_device", |
| 640 | info.type, info.addr); | 718 | info.type, info.addr); |
| 641 | 719 | ||
| @@ -674,7 +752,7 @@ i2c_sysfs_delete_device(struct device | |||
