#include "i2c-core.h"
-/* core_lock protects i2c_adapter_idr, userspace_devices, and guarantees
+/* core_lock protects i2c_adapter_idr, and guarantees
that device detection, deletion of detected devices, and attach_adapter
and detach_adapter calls are serialized */
static DEFINE_MUTEX(core_lock);
static DEFINE_IDR(i2c_adapter_idr);
-static LIST_HEAD(userspace_devices);
static struct device_type i2c_client_type;
static int i2c_check_addr(struct i2c_adapter *adapter, int addr);
return -EEXIST;
/* Keep track of the added device */
- mutex_lock(&core_lock);
- list_add_tail(&client->detected, &userspace_devices);
- mutex_unlock(&core_lock);
+ i2c_lock_adapter(adap);
+ list_add_tail(&client->detected, &adap->userspace_clients);
+ i2c_unlock_adapter(adap);
dev_info(dev, "%s: Instantiated device %s at 0x%02hx\n", "new_device",
info.type, info.addr);
/* Make sure the device was added through sysfs */
res = -ENOENT;
- mutex_lock(&core_lock);
- list_for_each_entry_safe(client, next, &userspace_devices, detected) {
- if (client->addr == addr && client->adapter == adap) {
+ i2c_lock_adapter(adap);
+ list_for_each_entry_safe(client, next, &adap->userspace_clients,
+ detected) {
+ if (client->addr == addr) {
dev_info(dev, "%s: Deleting device %s at 0x%02hx\n",
"delete_device", client->name, client->addr);
break;
}
}
- mutex_unlock(&core_lock);
+ i2c_unlock_adapter(adap);
if (res < 0)
dev_err(dev, "%s: Can't find device in list\n",
}
rt_mutex_init(&adap->bus_lock);
+ INIT_LIST_HEAD(&adap->userspace_clients);
/* Set default timeout to 1 second if not already set */
if (adap->timeout == 0)
return res;
/* Remove devices instantiated from sysfs */
- list_for_each_entry_safe(client, next, &userspace_devices, detected) {
- if (client->adapter == adap) {
- dev_dbg(&adap->dev, "Removing %s at 0x%x\n",
- client->name, client->addr);
- list_del(&client->detected);
- i2c_unregister_device(client);
- }
+ i2c_lock_adapter(adap);
+ list_for_each_entry_safe(client, next, &adap->userspace_clients,
+ detected) {
+ dev_dbg(&adap->dev, "Removing %s at 0x%x\n", client->name,
+ client->addr);
+ list_del(&client->detected);
+ i2c_unregister_device(client);
}
+ i2c_unlock_adapter(adap);
/* Detach any active clients. This can't fail, thus we do not
checking the returned value. */