diff options
author | Andrea Bastoni <bastoni@cs.unc.edu> | 2010-05-30 19:16:45 -0400 |
---|---|---|
committer | Andrea Bastoni <bastoni@cs.unc.edu> | 2010-05-30 19:16:45 -0400 |
commit | ada47b5fe13d89735805b566185f4885f5a3f750 (patch) | |
tree | 644b88f8a71896307d71438e9b3af49126ffb22b /drivers/i2c/i2c-core.c | |
parent | 43e98717ad40a4ae64545b5ba047c7b86aa44f4f (diff) | |
parent | 3280f21d43ee541f97f8cda5792150d2dbec20d5 (diff) |
Merge branch 'wip-2.6.34' into old-private-masterarchived-private-master
Diffstat (limited to 'drivers/i2c/i2c-core.c')
-rw-r--r-- | drivers/i2c/i2c-core.c | 319 |
1 files changed, 164 insertions, 155 deletions
diff --git a/drivers/i2c/i2c-core.c b/drivers/i2c/i2c-core.c index 296504355142..c2258a51fe0c 100644 --- a/drivers/i2c/i2c-core.c +++ b/drivers/i2c/i2c-core.c | |||
@@ -34,17 +34,17 @@ | |||
34 | #include <linux/hardirq.h> | 34 | #include <linux/hardirq.h> |
35 | #include <linux/irqflags.h> | 35 | #include <linux/irqflags.h> |
36 | #include <linux/rwsem.h> | 36 | #include <linux/rwsem.h> |
37 | #include <linux/pm_runtime.h> | ||
37 | #include <asm/uaccess.h> | 38 | #include <asm/uaccess.h> |
38 | 39 | ||
39 | #include "i2c-core.h" | 40 | #include "i2c-core.h" |
40 | 41 | ||
41 | 42 | ||
42 | /* core_lock protects i2c_adapter_idr, userspace_devices, and guarantees | 43 | /* core_lock protects i2c_adapter_idr, and guarantees |
43 | that device detection, deletion of detected devices, and attach_adapter | 44 | that device detection, deletion of detected devices, and attach_adapter |
44 | and detach_adapter calls are serialized */ | 45 | and detach_adapter calls are serialized */ |
45 | static DEFINE_MUTEX(core_lock); | 46 | static DEFINE_MUTEX(core_lock); |
46 | static DEFINE_IDR(i2c_adapter_idr); | 47 | static DEFINE_IDR(i2c_adapter_idr); |
47 | static LIST_HEAD(userspace_devices); | ||
48 | 48 | ||
49 | static struct device_type i2c_client_type; | 49 | static struct device_type i2c_client_type; |
50 | static int i2c_check_addr(struct i2c_adapter *adapter, int addr); | 50 | static int i2c_check_addr(struct i2c_adapter *adapter, int addr); |
@@ -116,8 +116,10 @@ static int i2c_device_probe(struct device *dev) | |||
116 | dev_dbg(dev, "probe\n"); | 116 | dev_dbg(dev, "probe\n"); |
117 | 117 | ||
118 | status = driver->probe(client, i2c_match_id(driver->id_table, client)); | 118 | status = driver->probe(client, i2c_match_id(driver->id_table, client)); |
119 | if (status) | 119 | if (status) { |
120 | client->driver = NULL; | 120 | client->driver = NULL; |
121 | i2c_set_clientdata(client, NULL); | ||
122 | } | ||
121 | return status; | 123 | return status; |
122 | } | 124 | } |
123 | 125 | ||
@@ -138,8 +140,10 @@ static int i2c_device_remove(struct device *dev) | |||
138 | dev->driver = NULL; | 140 | dev->driver = NULL; |
139 | status = 0; | 141 | status = 0; |
140 | } | 142 | } |
141 | if (status == 0) | 143 | if (status == 0) { |
142 | client->driver = NULL; | 144 | client->driver = NULL; |
145 | i2c_set_clientdata(client, NULL); | ||
146 | } | ||
143 | return status; | 147 | return status; |
144 | } | 148 | } |
145 | 149 | ||
@@ -155,6 +159,81 @@ static void i2c_device_shutdown(struct device *dev) | |||
155 | driver->shutdown(client); | 159 | driver->shutdown(client); |
156 | } | 160 | } |
157 | 161 | ||
162 | #ifdef CONFIG_SUSPEND | ||
163 | static int i2c_device_pm_suspend(struct device *dev) | ||
164 | { | ||
165 | const struct dev_pm_ops *pm; | ||
166 | |||
167 | if (!dev->driver) | ||
168 | return 0; | ||
169 | pm = dev->driver->pm; | ||
170 | if (!pm || !pm->suspend) | ||
171 | return 0; | ||
172 | return pm->suspend(dev); | ||
173 | } | ||
174 | |||
175 | static int i2c_device_pm_resume(struct device *dev) | ||
176 | { | ||
177 | const struct dev_pm_ops *pm; | ||
178 | |||
179 | if (!dev->driver) | ||
180 | return 0; | ||
181 | pm = dev->driver->pm; | ||
182 | if (!pm || !pm->resume) | ||
183 | return 0; | ||
184 | return pm->resume(dev); | ||
185 | } | ||
186 | #else | ||
187 | #define i2c_device_pm_suspend NULL | ||
188 | #define i2c_device_pm_resume NULL | ||
189 | #endif | ||
190 | |||
191 | #ifdef CONFIG_PM_RUNTIME | ||
192 | static int i2c_device_runtime_suspend(struct device *dev) | ||
193 | { | ||
194 | const struct dev_pm_ops *pm; | ||
195 | |||
196 | if (!dev->driver) | ||
197 | return 0; | ||
198 | pm = dev->driver->pm; | ||
199 | if (!pm || !pm->runtime_suspend) | ||
200 | return 0; | ||
201 | return pm->runtime_suspend(dev); | ||
202 | } | ||
203 | |||
204 | static int i2c_device_runtime_resume(struct device *dev) | ||
205 | { | ||
206 | const struct dev_pm_ops *pm; | ||
207 | |||
208 | if (!dev->driver) | ||
209 | return 0; | ||
210 | pm = dev->driver->pm; | ||
211 | if (!pm || !pm->runtime_resume) | ||
212 | return 0; | ||
213 | return pm->runtime_resume(dev); | ||
214 | } | ||
215 | |||
216 | static int i2c_device_runtime_idle(struct device *dev) | ||
217 | { | ||
218 | const struct dev_pm_ops *pm = NULL; | ||
219 | int ret; | ||
220 | |||
221 | if (dev->driver) | ||
222 | pm = dev->driver->pm; | ||
223 | if (pm && pm->runtime_idle) { | ||
224 | ret = pm->runtime_idle(dev); | ||
225 | if (ret) | ||
226 | return ret; | ||
227 | } | ||
228 | |||
229 | return pm_runtime_suspend(dev); | ||
230 | } | ||
231 | #else | ||
232 | #define i2c_device_runtime_suspend NULL | ||
233 | #define i2c_device_runtime_resume NULL | ||
234 | #define i2c_device_runtime_idle NULL | ||
235 | #endif | ||
236 | |||
158 | static int i2c_device_suspend(struct device *dev, pm_message_t mesg) | 237 | static int i2c_device_suspend(struct device *dev, pm_message_t mesg) |
159 | { | 238 | { |
160 | struct i2c_client *client = i2c_verify_client(dev); | 239 | struct i2c_client *client = i2c_verify_client(dev); |
@@ -219,6 +298,14 @@ static const struct attribute_group *i2c_dev_attr_groups[] = { | |||
219 | NULL | 298 | NULL |
220 | }; | 299 | }; |
221 | 300 | ||
301 | static const struct dev_pm_ops i2c_device_pm_ops = { | ||
302 | .suspend = i2c_device_pm_suspend, | ||
303 | .resume = i2c_device_pm_resume, | ||
304 | .runtime_suspend = i2c_device_runtime_suspend, | ||
305 | .runtime_resume = i2c_device_runtime_resume, | ||
306 | .runtime_idle = i2c_device_runtime_idle, | ||
307 | }; | ||
308 | |||
222 | struct bus_type i2c_bus_type = { | 309 | struct bus_type i2c_bus_type = { |
223 | .name = "i2c", | 310 | .name = "i2c", |
224 | .match = i2c_device_match, | 311 | .match = i2c_device_match, |
@@ -227,6 +314,7 @@ struct bus_type i2c_bus_type = { | |||
227 | .shutdown = i2c_device_shutdown, | 314 | .shutdown = i2c_device_shutdown, |
228 | .suspend = i2c_device_suspend, | 315 | .suspend = i2c_device_suspend, |
229 | .resume = i2c_device_resume, | 316 | .resume = i2c_device_resume, |
317 | .pm = &i2c_device_pm_ops, | ||
230 | }; | 318 | }; |
231 | EXPORT_SYMBOL_GPL(i2c_bus_type); | 319 | EXPORT_SYMBOL_GPL(i2c_bus_type); |
232 | 320 | ||
@@ -453,9 +541,9 @@ i2c_sysfs_new_device(struct device *dev, struct device_attribute *attr, | |||
453 | return -EEXIST; | 541 | return -EEXIST; |
454 | 542 | ||
455 | /* Keep track of the added device */ | 543 | /* Keep track of the added device */ |
456 | mutex_lock(&core_lock); | 544 | i2c_lock_adapter(adap); |
457 | list_add_tail(&client->detected, &userspace_devices); | 545 | list_add_tail(&client->detected, &adap->userspace_clients); |
458 | mutex_unlock(&core_lock); | 546 | i2c_unlock_adapter(adap); |
459 | dev_info(dev, "%s: Instantiated device %s at 0x%02hx\n", "new_device", | 547 | dev_info(dev, "%s: Instantiated device %s at 0x%02hx\n", "new_device", |
460 | info.type, info.addr); | 548 | info.type, info.addr); |
461 | 549 | ||
@@ -494,9 +582,10 @@ i2c_sysfs_delete_device(struct device *dev, struct device_attribute *attr, | |||
494 | 582 | ||
495 | /* Make sure the device was added through sysfs */ | 583 | /* Make sure the device was added through sysfs */ |
496 | res = -ENOENT; | 584 | res = -ENOENT; |
497 | mutex_lock(&core_lock); | 585 | i2c_lock_adapter(adap); |
498 | list_for_each_entry_safe(client, next, &userspace_devices, detected) { | 586 | list_for_each_entry_safe(client, next, &adap->userspace_clients, |
499 | if (client->addr == addr && client->adapter == adap) { | 587 | detected) { |
588 | if (client->addr == addr) { | ||
500 | dev_info(dev, "%s: Deleting device %s at 0x%02hx\n", | 589 | dev_info(dev, "%s: Deleting device %s at 0x%02hx\n", |
501 | "delete_device", client->name, client->addr); | 590 | "delete_device", client->name, client->addr); |
502 | 591 | ||
@@ -506,7 +595,7 @@ i2c_sysfs_delete_device(struct device *dev, struct device_attribute *attr, | |||
506 | break; | 595 | break; |
507 | } | 596 | } |
508 | } | 597 | } |
509 | mutex_unlock(&core_lock); | 598 | i2c_unlock_adapter(adap); |
510 | 599 | ||
511 | if (res < 0) | 600 | if (res < 0) |
512 | dev_err(dev, "%s: Can't find device in list\n", | 601 | dev_err(dev, "%s: Can't find device in list\n", |
@@ -558,11 +647,9 @@ static void i2c_scan_static_board_info(struct i2c_adapter *adapter) | |||
558 | up_read(&__i2c_board_lock); | 647 | up_read(&__i2c_board_lock); |
559 | } | 648 | } |
560 | 649 | ||
561 | static int i2c_do_add_adapter(struct device_driver *d, void *data) | 650 | static int i2c_do_add_adapter(struct i2c_driver *driver, |
651 | struct i2c_adapter *adap) | ||
562 | { | 652 | { |
563 | struct i2c_driver *driver = to_i2c_driver(d); | ||
564 | struct i2c_adapter *adap = data; | ||
565 | |||
566 | /* Detect supported devices on that bus, and instantiate them */ | 653 | /* Detect supported devices on that bus, and instantiate them */ |
567 | i2c_detect(adap, driver); | 654 | i2c_detect(adap, driver); |
568 | 655 | ||
@@ -574,6 +661,11 @@ static int i2c_do_add_adapter(struct device_driver *d, void *data) | |||
574 | return 0; | 661 | return 0; |
575 | } | 662 | } |
576 | 663 | ||
664 | static int __process_new_adapter(struct device_driver *d, void *data) | ||
665 | { | ||
666 | return i2c_do_add_adapter(to_i2c_driver(d), data); | ||
667 | } | ||
668 | |||
577 | static int i2c_register_adapter(struct i2c_adapter *adap) | 669 | static int i2c_register_adapter(struct i2c_adapter *adap) |
578 | { | 670 | { |
579 | int res = 0, dummy; | 671 | int res = 0, dummy; |
@@ -584,7 +676,8 @@ static int i2c_register_adapter(struct i2c_adapter *adap) | |||
584 | goto out_list; | 676 | goto out_list; |
585 | } | 677 | } |
586 | 678 | ||
587 | mutex_init(&adap->bus_lock); | 679 | rt_mutex_init(&adap->bus_lock); |
680 | INIT_LIST_HEAD(&adap->userspace_clients); | ||
588 | 681 | ||
589 | /* Set default timeout to 1 second if not already set */ | 682 | /* Set default timeout to 1 second if not already set */ |
590 | if (adap->timeout == 0) | 683 | if (adap->timeout == 0) |
@@ -614,7 +707,7 @@ static int i2c_register_adapter(struct i2c_adapter *adap) | |||
614 | /* Notify drivers */ | 707 | /* Notify drivers */ |
615 | mutex_lock(&core_lock); | 708 | mutex_lock(&core_lock); |
616 | dummy = bus_for_each_drv(&i2c_bus_type, NULL, adap, | 709 | dummy = bus_for_each_drv(&i2c_bus_type, NULL, adap, |
617 | i2c_do_add_adapter); | 710 | __process_new_adapter); |
618 | mutex_unlock(&core_lock); | 711 | mutex_unlock(&core_lock); |
619 | 712 | ||
620 | return 0; | 713 | return 0; |
@@ -715,10 +808,9 @@ retry: | |||
715 | } | 808 | } |
716 | EXPORT_SYMBOL_GPL(i2c_add_numbered_adapter); | 809 | EXPORT_SYMBOL_GPL(i2c_add_numbered_adapter); |
717 | 810 | ||
718 | static int i2c_do_del_adapter(struct device_driver *d, void *data) | 811 | static int i2c_do_del_adapter(struct i2c_driver *driver, |
812 | struct i2c_adapter *adapter) | ||
719 | { | 813 | { |
720 | struct i2c_driver *driver = to_i2c_driver(d); | ||
721 | struct i2c_adapter *adapter = data; | ||
722 | struct i2c_client *client, *_n; | 814 | struct i2c_client *client, *_n; |
723 | int res; | 815 | int res; |
724 | 816 | ||
@@ -750,6 +842,11 @@ static int __unregister_client(struct device *dev, void *dummy) | |||
750 | return 0; | 842 | return 0; |
751 | } | 843 | } |
752 | 844 | ||
845 | static int __process_removed_adapter(struct device_driver *d, void *data) | ||
846 | { | ||
847 | return i2c_do_del_adapter(to_i2c_driver(d), data); | ||
848 | } | ||
849 | |||
753 | /** | 850 | /** |
754 | * i2c_del_adapter - unregister I2C adapter | 851 | * i2c_del_adapter - unregister I2C adapter |
755 | * @adap: the adapter being unregistered | 852 | * @adap: the adapter being unregistered |
@@ -777,20 +874,21 @@ int i2c_del_adapter(struct i2c_adapter *adap) | |||
777 | /* Tell drivers about this removal */ | 874 | /* Tell drivers about this removal */ |
778 | mutex_lock(&core_lock); | 875 | mutex_lock(&core_lock); |
779 | res = bus_for_each_drv(&i2c_bus_type, NULL, adap, | 876 | res = bus_for_each_drv(&i2c_bus_type, NULL, adap, |
780 | i2c_do_del_adapter); | 877 | __process_removed_adapter); |
781 | mutex_unlock(&core_lock); | 878 | mutex_unlock(&core_lock); |
782 | if (res) | 879 | if (res) |
783 | return res; | 880 | return res; |
784 | 881 | ||
785 | /* Remove devices instantiated from sysfs */ | 882 | /* Remove devices instantiated from sysfs */ |
786 | list_for_each_entry_safe(client, next, &userspace_devices, detected) { | 883 | i2c_lock_adapter(adap); |
787 | if (client->adapter == adap) { | 884 | list_for_each_entry_safe(client, next, &adap->userspace_clients, |
788 | dev_dbg(&adap->dev, "Removing %s at 0x%x\n", | 885 | detected) { |
789 | client->name, client->addr); | 886 | dev_dbg(&adap->dev, "Removing %s at 0x%x\n", client->name, |
790 | list_del(&client->detected); | 887 | client->addr); |
791 | i2c_unregister_device(client); | 888 | list_del(&client->detected); |
792 | } | 889 | i2c_unregister_device(client); |
793 | } | 890 | } |
891 | i2c_unlock_adapter(adap); | ||
794 | 892 | ||
795 | /* Detach any active clients. This can't fail, thus we do not | 893 | /* Detach any active clients. This can't fail, thus we do not |
796 | checking the returned value. */ | 894 | checking the returned value. */ |
@@ -801,6 +899,9 @@ int i2c_del_adapter(struct i2c_adapter *adap) | |||
801 | adap->dev.parent); | 899 | adap->dev.parent); |
802 | #endif | 900 | #endif |
803 | 901 | ||
902 | /* device name is gone after device_unregister */ | ||
903 | dev_dbg(&adap->dev, "adapter [%s] unregistered\n", adap->name); | ||
904 | |||
804 | /* clean up the sysfs representation */ | 905 | /* clean up the sysfs representation */ |
805 | init_completion(&adap->dev_released); | 906 | init_completion(&adap->dev_released); |
806 | device_unregister(&adap->dev); | 907 | device_unregister(&adap->dev); |
@@ -813,8 +914,6 @@ int i2c_del_adapter(struct i2c_adapter *adap) | |||
813 | idr_remove(&i2c_adapter_idr, adap->nr); | 914 | idr_remove(&i2c_adapter_idr, adap->nr); |
814 | mutex_unlock(&core_lock); | 915 | mutex_unlock(&core_lock); |
815 | 916 | ||
816 | dev_dbg(&adap->dev, "adapter [%s] unregistered\n", adap->name); | ||
817 | |||
818 | /* Clear the device structure in case this adapter is ever going to be | 917 | /* Clear the device structure in case this adapter is ever going to be |
819 | added again */ | 918 | added again */ |
820 | memset(&adap->dev, 0, sizeof(adap->dev)); | 919 | memset(&adap->dev, 0, sizeof(adap->dev)); |
@@ -826,22 +925,11 @@ EXPORT_SYMBOL(i2c_del_adapter); | |||
826 | 925 | ||
827 | /* ------------------------------------------------------------------------- */ | 926 | /* ------------------------------------------------------------------------- */ |
828 | 927 | ||
829 | static int __attach_adapter(struct device *dev, void *data) | 928 | static int __process_new_driver(struct device *dev, void *data) |
830 | { | 929 | { |
831 | struct i2c_adapter *adapter; | ||
832 | struct i2c_driver *driver = data; | ||
833 | |||
834 | if (dev->type != &i2c_adapter_type) | 930 | if (dev->type != &i2c_adapter_type) |
835 | return 0; | 931 | return 0; |
836 | adapter = to_i2c_adapter(dev); | 932 | return i2c_do_add_adapter(data, to_i2c_adapter(dev)); |
837 | |||
838 | i2c_detect(adapter, driver); | ||
839 | |||
840 | /* Legacy drivers scan i2c busses directly */ | ||
841 | if (driver->attach_adapter) | ||
842 | driver->attach_adapter(adapter); | ||
843 | |||
844 | return 0; | ||
845 | } | 933 | } |
846 | 934 | ||
847 | /* | 935 | /* |
@@ -873,40 +961,18 @@ int i2c_register_driver(struct module *owner, struct i2c_driver *driver) | |||
873 | INIT_LIST_HEAD(&driver->clients); | 961 | INIT_LIST_HEAD(&driver->clients); |
874 | /* Walk the adapters that are already present */ | 962 | /* Walk the adapters that are already present */ |
875 | mutex_lock(&core_lock); | 963 | mutex_lock(&core_lock); |
876 | bus_for_each_dev(&i2c_bus_type, NULL, driver, __attach_adapter); | 964 | bus_for_each_dev(&i2c_bus_type, NULL, driver, __process_new_driver); |
877 | mutex_unlock(&core_lock); | 965 | mutex_unlock(&core_lock); |
878 | 966 | ||
879 | return 0; | 967 | return 0; |
880 | } | 968 | } |
881 | EXPORT_SYMBOL(i2c_register_driver); | 969 | EXPORT_SYMBOL(i2c_register_driver); |
882 | 970 | ||
883 | static int __detach_adapter(struct device *dev, void *data) | 971 | static int __process_removed_driver(struct device *dev, void *data) |
884 | { | 972 | { |
885 | struct i2c_adapter *adapter; | ||
886 | struct i2c_driver *driver = data; | ||
887 | struct i2c_client *client, *_n; | ||
888 | |||
889 | if (dev->type != &i2c_adapter_type) | 973 | if (dev->type != &i2c_adapter_type) |
890 | return 0; | 974 | return 0; |
891 | adapter = to_i2c_adapter(dev); | 975 | return i2c_do_del_adapter(data, to_i2c_adapter(dev)); |
892 | |||
893 | /* Remove the devices we created ourselves as the result of hardware | ||
894 | * probing (using a driver's detect method) */ | ||
895 | list_for_each_entry_safe(client, _n, &driver->clients, detected) { | ||
896 | dev_dbg(&adapter->dev, "Removing %s at 0x%x\n", | ||
897 | client->name, client->addr); | ||
898 | list_del(&client->detected); | ||
899 | i2c_unregister_device(client); | ||
900 | } | ||
901 | |||
902 | if (driver->detach_adapter) { | ||
903 | if (driver->detach_adapter(adapter)) | ||
904 | dev_err(&adapter->dev, | ||
905 | "detach_adapter failed for driver [%s]\n", | ||
906 | driver->driver.name); | ||
907 | } | ||
908 | |||
909 | return 0; | ||
910 | } | 976 | } |
911 | 977 | ||
912 | /** | 978 | /** |
@@ -917,7 +983,7 @@ static int __detach_adapter(struct device *dev, void *data) | |||
917 | void i2c_del_driver(struct i2c_driver *driver) | 983 | void i2c_del_driver(struct i2c_driver *driver) |
918 | { | 984 | { |
919 | mutex_lock(&core_lock); | 985 | mutex_lock(&core_lock); |
920 | bus_for_each_dev(&i2c_bus_type, NULL, driver, __detach_adapter); | 986 | bus_for_each_dev(&i2c_bus_type, NULL, driver, __process_removed_driver); |
921 | mutex_unlock(&core_lock); | 987 | mutex_unlock(&core_lock); |
922 | 988 | ||
923 | driver_unregister(&driver->driver); | 989 | driver_unregister(&driver->driver); |
@@ -1092,12 +1158,12 @@ int i2c_transfer(struct i2c_adapter *adap, struct i2c_msg *msgs, int num) | |||
1092 | #endif | 1158 | #endif |
1093 | 1159 | ||
1094 | if (in_atomic() || irqs_disabled()) { | 1160 | if (in_atomic() || irqs_disabled()) { |
1095 | ret = mutex_trylock(&adap->bus_lock); | 1161 | ret = rt_mutex_trylock(&adap->bus_lock); |
1096 | if (!ret) | 1162 | if (!ret) |
1097 | /* I2C activity is ongoing. */ | 1163 | /* I2C activity is ongoing. */ |
1098 | return -EAGAIN; | 1164 | return -EAGAIN; |
1099 | } else { | 1165 | } else { |
1100 | mutex_lock_nested(&adap->bus_lock, adap->level); | 1166 | rt_mutex_lock(&adap->bus_lock); |
1101 | } | 1167 | } |
1102 | 1168 | ||
1103 | /* Retry automatically on arbitration loss */ | 1169 | /* Retry automatically on arbitration loss */ |
@@ -1109,7 +1175,7 @@ int i2c_transfer(struct i2c_adapter *adap, struct i2c_msg *msgs, int num) | |||
1109 | if (time_after(jiffies, orig_jiffies + adap->timeout)) | 1175 | if (time_after(jiffies, orig_jiffies + adap->timeout)) |
1110 | break; | 1176 | break; |
1111 | } | 1177 | } |
1112 | mutex_unlock(&adap->bus_lock); | 1178 | rt_mutex_unlock(&adap->bus_lock); |
1113 | 1179 | ||
1114 | return ret; | 1180 | return ret; |
1115 | } else { | 1181 | } else { |
@@ -1123,7 +1189,7 @@ EXPORT_SYMBOL(i2c_transfer); | |||
1123 | * i2c_master_send - issue a single I2C message in master transmit mode | 1189 | * i2c_master_send - issue a single I2C message in master transmit mode |
1124 | * @client: Handle to slave device | 1190 | * @client: Handle to slave device |
1125 | * @buf: Data that will be written to the slave | 1191 | * @buf: Data that will be written to the slave |
1126 | * @count: How many bytes to write | 1192 | * @count: How many bytes to write, must be less than 64k since msg.len is u16 |
1127 | * | 1193 | * |
1128 | * Returns negative errno, or else the number of bytes written. | 1194 | * Returns negative errno, or else the number of bytes written. |
1129 | */ | 1195 | */ |
@@ -1150,7 +1216,7 @@ EXPORT_SYMBOL(i2c_master_send); | |||
1150 | * i2c_master_recv - issue a single I2C message in master receive mode | 1216 | * i2c_master_recv - issue a single I2C message in master receive mode |
1151 | * @client: Handle to slave device | 1217 | * @client: Handle to slave device |
1152 | * @buf: Where to store data read from slave | 1218 | * @buf: Where to store data read from slave |
1153 | * @count: How many bytes to read | 1219 | * @count: How many bytes to read, must be less than 64k since msg.len is u16 |
1154 | * | 1220 | * |
1155 | * Returns negative errno, or else the number of bytes read. | 1221 | * Returns negative errno, or else the number of bytes read. |
1156 | */ | 1222 | */ |
@@ -1180,7 +1246,7 @@ EXPORT_SYMBOL(i2c_master_recv); | |||
1180 | * ---------------------------------------------------- | 1246 | * ---------------------------------------------------- |
1181 | */ | 1247 | */ |
1182 | 1248 | ||
1183 | static int i2c_detect_address(struct i2c_client *temp_client, int kind, | 1249 | static int i2c_detect_address(struct i2c_client *temp_client, |
1184 | struct i2c_driver *driver) | 1250 | struct i2c_driver *driver) |
1185 | { | 1251 | { |
1186 | struct i2c_board_info info; | 1252 | struct i2c_board_info info; |
@@ -1199,22 +1265,29 @@ static int i2c_detect_address(struct i2c_client *temp_client, int kind, | |||
1199 | if (i2c_check_addr(adapter, addr)) | 1265 | if (i2c_check_addr(adapter, addr)) |
1200 | return 0; | 1266 | return 0; |
1201 | 1267 | ||
1202 | /* Make sure there is something at this address, unless forced */ | 1268 | /* Make sure there is something at this address */ |
1203 | if (kind < 0) { | 1269 | if (addr == 0x73 && (adapter->class & I2C_CLASS_HWMON)) { |
1204 | if (i2c_smbus_xfer(adapter, addr, 0, 0, 0, | 1270 | /* Special probe for FSC hwmon chips */ |
1271 | union i2c_smbus_data dummy; | ||
1272 | |||
1273 | if (i2c_smbus_xfer(adapter, addr, 0, I2C_SMBUS_READ, 0, | ||
1274 | I2C_SMBUS_BYTE_DATA, &dummy) < 0) | ||
1275 | return 0; | ||
1276 | } else { | ||
1277 | if (i2c_smbus_xfer(adapter, addr, 0, I2C_SMBUS_WRITE, 0, | ||
1205 | I2C_SMBUS_QUICK, NULL) < 0) | 1278 | I2C_SMBUS_QUICK, NULL) < 0) |
1206 | return 0; | 1279 | return 0; |
1207 | 1280 | ||
1208 | /* prevent 24RF08 corruption */ | 1281 | /* Prevent 24RF08 corruption */ |
1209 | if ((addr & ~0x0f) == 0x50) | 1282 | if ((addr & ~0x0f) == 0x50) |
1210 | i2c_smbus_xfer(adapter, addr, 0, 0, 0, | 1283 | i2c_smbus_xfer(adapter, addr, 0, I2C_SMBUS_WRITE, 0, |
1211 | I2C_SMBUS_QUICK, NULL); | 1284 | I2C_SMBUS_QUICK, NULL); |
1212 | } | 1285 | } |
1213 | 1286 | ||
1214 | /* Finally call the custom detection function */ | 1287 | /* Finally call the custom detection function */ |
1215 | memset(&info, 0, sizeof(struct i2c_board_info)); | 1288 | memset(&info, 0, sizeof(struct i2c_board_info)); |
1216 | info.addr = addr; | 1289 | info.addr = addr; |
1217 | err = driver->detect(temp_client, kind, &info); | 1290 | err = driver->detect(temp_client, &info); |
1218 | if (err) { | 1291 | if (err) { |
1219 | /* -ENODEV is returned if the detection fails. We catch it | 1292 | /* -ENODEV is returned if the detection fails. We catch it |
1220 | here as this isn't an error. */ | 1293 | here as this isn't an error. */ |
@@ -1244,13 +1317,13 @@ static int i2c_detect_address(struct i2c_client *temp_client, int kind, | |||
1244 | 1317 | ||
1245 | static int i2c_detect(struct i2c_adapter *adapter, struct i2c_driver *driver) | 1318 | static int i2c_detect(struct i2c_adapter *adapter, struct i2c_driver *driver) |
1246 | { | 1319 | { |
1247 | const struct i2c_client_address_data *address_data; | 1320 | const unsigned short *address_list; |
1248 | struct i2c_client *temp_client; | 1321 | struct i2c_client *temp_client; |
1249 | int i, err = 0; | 1322 | int i, err = 0; |
1250 | int adap_id = i2c_adapter_id(adapter); | 1323 | int adap_id = i2c_adapter_id(adapter); |
1251 | 1324 | ||
1252 | address_data = driver->address_data; | 1325 | address_list = driver->address_list; |
1253 | if (!driver->detect || !address_data) | 1326 | if (!driver->detect || !address_list) |
1254 | return 0; | 1327 | return 0; |
1255 | 1328 | ||
1256 | /* Set up a temporary client to help detect callback */ | 1329 | /* Set up a temporary client to help detect callback */ |
@@ -1259,40 +1332,13 @@ static int i2c_detect(struct i2c_adapter *adapter, struct i2c_driver *driver) | |||
1259 | return -ENOMEM; | 1332 | return -ENOMEM; |
1260 | temp_client->adapter = adapter; | 1333 | temp_client->adapter = adapter; |
1261 | 1334 | ||
1262 | /* Force entries are done first, and are not affected by ignore | ||
1263 | entries */ | ||
1264 | if (address_data->forces) { | ||
1265 | const unsigned short * const *forces = address_data->forces; | ||
1266 | int kind; | ||
1267 | |||
1268 | for (kind = 0; forces[kind]; kind++) { | ||
1269 | for (i = 0; forces[kind][i] != I2C_CLIENT_END; | ||
1270 | i += 2) { | ||
1271 | if (forces[kind][i] == adap_id | ||
1272 | || forces[kind][i] == ANY_I2C_BUS) { | ||
1273 | dev_dbg(&adapter->dev, "found force " | ||
1274 | "parameter for adapter %d, " | ||
1275 | "addr 0x%02x, kind %d\n", | ||
1276 | adap_id, forces[kind][i + 1], | ||
1277 | kind); | ||
1278 | temp_client->addr = forces[kind][i + 1]; | ||
1279 | err = i2c_detect_address(temp_client, | ||
1280 | kind, driver); | ||
1281 | if (err) | ||
1282 | goto exit_free; | ||
1283 | } | ||
1284 | } | ||
1285 | } | ||
1286 | } | ||
1287 | |||
1288 | /* Stop here if the classes do not match */ | 1335 | /* Stop here if the classes do not match */ |
1289 | if (!(adapter->class & driver->class)) | 1336 | if (!(adapter->class & driver->class)) |
1290 | goto exit_free; | 1337 | goto exit_free; |
1291 | 1338 | ||
1292 | /* Stop here if we can't use SMBUS_QUICK */ | 1339 | /* Stop here if we can't use SMBUS_QUICK */ |
1293 | if (!i2c_check_functionality(adapter, I2C_FUNC_SMBUS_QUICK)) { | 1340 | if (!i2c_check_functionality(adapter, I2C_FUNC_SMBUS_QUICK)) { |
1294 | if (address_data->probe[0] == I2C_CLIENT_END | 1341 | if (address_list[0] == I2C_CLIENT_END) |
1295 | && address_data->normal_i2c[0] == I2C_CLIENT_END) | ||
1296 | goto exit_free; | 1342 | goto exit_free; |
1297 | 1343 | ||
1298 | dev_warn(&adapter->dev, "SMBus Quick command not supported, " | 1344 | dev_warn(&adapter->dev, "SMBus Quick command not supported, " |
@@ -1301,48 +1347,11 @@ static int i2c_detect(struct i2c_adapter *adapter, struct i2c_driver *driver) | |||
1301 | goto exit_free; | 1347 | goto exit_free; |
1302 | } | 1348 | } |
1303 | 1349 | ||
1304 | /* Probe entries are done second, and are not affected by ignore | 1350 | for (i = 0; address_list[i] != I2C_CLIENT_END; i += 1) { |
1305 | entries either */ | ||
1306 | for (i = 0; address_data->probe[i] != I2C_CLIENT_END; i += 2) { | ||
1307 | if (address_data->probe[i] == adap_id | ||
1308 | || address_data->probe[i] == ANY_I2C_BUS) { | ||
1309 | dev_dbg(&adapter->dev, "found probe parameter for " | ||
1310 | "adapter %d, addr 0x%02x\n", adap_id, | ||
1311 | address_data->probe[i + 1]); | ||
1312 | temp_client->addr = address_data->probe[i + 1]; | ||
1313 | err = i2c_detect_address(temp_client, -1, driver); | ||
1314 | if (err) | ||
1315 | goto exit_free; | ||
1316 | } | ||
1317 | } | ||
1318 | |||
1319 | /* Normal entries are done last, unless shadowed by an ignore entry */ | ||
1320 | for (i = 0; address_data->normal_i2c[i] != I2C_CLIENT_END; i += 1) { | ||
1321 | int j, ignore; | ||
1322 | |||
1323 | ignore = 0; | ||
1324 | for (j = 0; address_data->ignore[j] != I2C_CLIENT_END; | ||
1325 | j += 2) { | ||
1326 | if ((address_data->ignore[j] == adap_id || | ||
1327 | address_data->ignore[j] == ANY_I2C_BUS) | ||
1328 | && address_data->ignore[j + 1] | ||
1329 | == address_data->normal_i2c[i]) { | ||
1330 | dev_dbg(&adapter->dev, "found ignore " | ||
1331 | "parameter for adapter %d, " | ||
1332 | "addr 0x%02x\n", adap_id, | ||
1333 | address_data->ignore[j + 1]); | ||
1334 | ignore = 1; | ||
1335 | break; | ||
1336 | } | ||
1337 | } | ||
1338 | if (ignore) | ||
1339 | continue; | ||
1340 | |||
1341 | dev_dbg(&adapter->dev, "found normal entry for adapter %d, " | 1351 | dev_dbg(&adapter->dev, "found normal entry for adapter %d, " |
1342 | "addr 0x%02x\n", adap_id, | 1352 | "addr 0x%02x\n", adap_id, address_list[i]); |
1343 | address_data->normal_i2c[i]); | 1353 | temp_client->addr = address_list[i]; |
1344 | temp_client->addr = address_data->normal_i2c[i]; | 1354 | err = i2c_detect_address(temp_client, driver); |
1345 | err = i2c_detect_address(temp_client, -1, driver); | ||
1346 | if (err) | 1355 | if (err) |
1347 | goto exit_free; | 1356 | goto exit_free; |
1348 | } | 1357 | } |
@@ -1913,7 +1922,7 @@ s32 i2c_smbus_xfer(struct i2c_adapter *adapter, u16 addr, unsigned short flags, | |||
1913 | flags &= I2C_M_TEN | I2C_CLIENT_PEC; | 1922 | flags &= I2C_M_TEN | I2C_CLIENT_PEC; |
1914 | 1923 | ||
1915 | if (adapter->algo->smbus_xfer) { | 1924 | if (adapter->algo->smbus_xfer) { |
1916 | mutex_lock(&adapter->bus_lock); | 1925 | rt_mutex_lock(&adapter->bus_lock); |
1917 | 1926 | ||
1918 | /* Retry automatically on arbitration loss */ | 1927 | /* Retry automatically on arbitration loss */ |
1919 | orig_jiffies = jiffies; | 1928 | orig_jiffies = jiffies; |
@@ -1927,7 +1936,7 @@ s32 i2c_smbus_xfer(struct i2c_adapter *adapter, u16 addr, unsigned short flags, | |||
1927 | orig_jiffies + adapter->timeout)) | 1936 | orig_jiffies + adapter->timeout)) |
1928 | break; | 1937 | break; |
1929 | } | 1938 | } |
1930 | mutex_unlock(&adapter->bus_lock); | 1939 | rt_mutex_unlock(&adapter->bus_lock); |
1931 | } else | 1940 | } else |
1932 | res = i2c_smbus_xfer_emulated(adapter,addr,flags,read_write, | 1941 | res = i2c_smbus_xfer_emulated(adapter,addr,flags,read_write, |
1933 | command, protocol, data); | 1942 | command, protocol, data); |