diff options
Diffstat (limited to 'drivers')
-rw-r--r-- | drivers/macintosh/therm_pm72.c | 95 |
1 files changed, 47 insertions, 48 deletions
diff --git a/drivers/macintosh/therm_pm72.c b/drivers/macintosh/therm_pm72.c index 817607e2af6a..a028598af2d3 100644 --- a/drivers/macintosh/therm_pm72.c +++ b/drivers/macintosh/therm_pm72.c | |||
@@ -287,22 +287,6 @@ struct fcu_fan_table fcu_fans[] = { | |||
287 | }; | 287 | }; |
288 | 288 | ||
289 | /* | 289 | /* |
290 | * i2c_driver structure to attach to the host i2c controller | ||
291 | */ | ||
292 | |||
293 | static int therm_pm72_attach(struct i2c_adapter *adapter); | ||
294 | static int therm_pm72_detach(struct i2c_adapter *adapter); | ||
295 | |||
296 | static struct i2c_driver therm_pm72_driver = | ||
297 | { | ||
298 | .driver = { | ||
299 | .name = "therm_pm72", | ||
300 | }, | ||
301 | .attach_adapter = therm_pm72_attach, | ||
302 | .detach_adapter = therm_pm72_detach, | ||
303 | }; | ||
304 | |||
305 | /* | ||
306 | * Utility function to create an i2c_client structure and | 290 | * Utility function to create an i2c_client structure and |
307 | * attach it to one of u3 adapters | 291 | * attach it to one of u3 adapters |
308 | */ | 292 | */ |
@@ -310,6 +294,7 @@ static struct i2c_client *attach_i2c_chip(int id, const char *name) | |||
310 | { | 294 | { |
311 | struct i2c_client *clt; | 295 | struct i2c_client *clt; |
312 | struct i2c_adapter *adap; | 296 | struct i2c_adapter *adap; |
297 | struct i2c_board_info info; | ||
313 | 298 | ||
314 | if (id & 0x200) | 299 | if (id & 0x200) |
315 | adap = k2; | 300 | adap = k2; |
@@ -320,31 +305,21 @@ static struct i2c_client *attach_i2c_chip(int id, const char *name) | |||
320 | if (adap == NULL) | 305 | if (adap == NULL) |
321 | return NULL; | 306 | return NULL; |
322 | 307 | ||
323 | clt = kzalloc(sizeof(struct i2c_client), GFP_KERNEL); | 308 | memset(&info, 0, sizeof(struct i2c_board_info)); |
324 | if (clt == NULL) | 309 | info.addr = (id >> 1) & 0x7f; |
325 | return NULL; | 310 | strlcpy(info.type, "therm_pm72", I2C_NAME_SIZE); |
326 | 311 | clt = i2c_new_device(adap, &info); | |
327 | clt->addr = (id >> 1) & 0x7f; | 312 | if (!clt) { |
328 | clt->adapter = adap; | ||
329 | clt->driver = &therm_pm72_driver; | ||
330 | strncpy(clt->name, name, I2C_NAME_SIZE-1); | ||
331 | |||
332 | if (i2c_attach_client(clt)) { | ||
333 | printk(KERN_ERR "therm_pm72: Failed to attach to i2c ID 0x%x\n", id); | 313 | printk(KERN_ERR "therm_pm72: Failed to attach to i2c ID 0x%x\n", id); |
334 | kfree(clt); | ||
335 | return NULL; | 314 | return NULL; |
336 | } | 315 | } |
337 | return clt; | ||
338 | } | ||
339 | 316 | ||
340 | /* | 317 | /* |
341 | * Utility function to get rid of the i2c_client structure | 318 | * Let i2c-core delete that device on driver removal. |
342 | * (will also detach from the adapter hopepfully) | 319 | * This is safe because i2c-core holds the core_lock mutex for us. |
343 | */ | 320 | */ |
344 | static void detach_i2c_chip(struct i2c_client *clt) | 321 | list_add_tail(&clt->detected, &clt->driver->clients); |
345 | { | 322 | return clt; |
346 | i2c_detach_client(clt); | ||
347 | kfree(clt); | ||
348 | } | 323 | } |
349 | 324 | ||
350 | /* | 325 | /* |
@@ -1203,8 +1178,6 @@ static int init_cpu_state(struct cpu_pid_state *state, int index) | |||
1203 | 1178 | ||
1204 | return 0; | 1179 | return 0; |
1205 | fail: | 1180 | fail: |
1206 | if (state->monitor) | ||
1207 | detach_i2c_chip(state->monitor); | ||
1208 | state->monitor = NULL; | 1181 | state->monitor = NULL; |
1209 | 1182 | ||
1210 | return -ENODEV; | 1183 | return -ENODEV; |
@@ -1232,7 +1205,6 @@ static void dispose_cpu_state(struct cpu_pid_state *state) | |||
1232 | device_remove_file(&of_dev->dev, &dev_attr_cpu1_intake_fan_rpm); | 1205 | device_remove_file(&of_dev->dev, &dev_attr_cpu1_intake_fan_rpm); |
1233 | } | 1206 | } |
1234 | 1207 | ||
1235 | detach_i2c_chip(state->monitor); | ||
1236 | state->monitor = NULL; | 1208 | state->monitor = NULL; |
1237 | } | 1209 | } |
1238 | 1210 | ||
@@ -1407,7 +1379,6 @@ static void dispose_backside_state(struct backside_pid_state *state) | |||
1407 | device_remove_file(&of_dev->dev, &dev_attr_backside_temperature); | 1379 | device_remove_file(&of_dev->dev, &dev_attr_backside_temperature); |
1408 | device_remove_file(&of_dev->dev, &dev_attr_backside_fan_pwm); | 1380 | device_remove_file(&of_dev->dev, &dev_attr_backside_fan_pwm); |
1409 | 1381 | ||
1410 | detach_i2c_chip(state->monitor); | ||
1411 | state->monitor = NULL; | 1382 | state->monitor = NULL; |
1412 | } | 1383 | } |
1413 | 1384 | ||
@@ -1532,7 +1503,6 @@ static void dispose_drives_state(struct drives_pid_state *state) | |||
1532 | device_remove_file(&of_dev->dev, &dev_attr_drives_temperature); | 1503 | device_remove_file(&of_dev->dev, &dev_attr_drives_temperature); |
1533 | device_remove_file(&of_dev->dev, &dev_attr_drives_fan_rpm); | 1504 | device_remove_file(&of_dev->dev, &dev_attr_drives_fan_rpm); |
1534 | 1505 | ||
1535 | detach_i2c_chip(state->monitor); | ||
1536 | state->monitor = NULL; | 1506 | state->monitor = NULL; |
1537 | } | 1507 | } |
1538 | 1508 | ||
@@ -1654,7 +1624,6 @@ static void dispose_dimms_state(struct dimm_pid_state *state) | |||
1654 | 1624 | ||
1655 | device_remove_file(&of_dev->dev, &dev_attr_dimms_temperature); | 1625 | device_remove_file(&of_dev->dev, &dev_attr_dimms_temperature); |
1656 | 1626 | ||
1657 | detach_i2c_chip(state->monitor); | ||
1658 | state->monitor = NULL; | 1627 | state->monitor = NULL; |
1659 | } | 1628 | } |
1660 | 1629 | ||
@@ -1779,7 +1748,6 @@ static void dispose_slots_state(struct slots_pid_state *state) | |||
1779 | device_remove_file(&of_dev->dev, &dev_attr_slots_temperature); | 1748 | device_remove_file(&of_dev->dev, &dev_attr_slots_temperature); |
1780 | device_remove_file(&of_dev->dev, &dev_attr_slots_fan_pwm); | 1749 | device_remove_file(&of_dev->dev, &dev_attr_slots_fan_pwm); |
1781 | 1750 | ||
1782 | detach_i2c_chip(state->monitor); | ||
1783 | state->monitor = NULL; | 1751 | state->monitor = NULL; |
1784 | } | 1752 | } |
1785 | 1753 | ||
@@ -2008,8 +1976,6 @@ static int attach_fcu(void) | |||
2008 | */ | 1976 | */ |
2009 | static void detach_fcu(void) | 1977 | static void detach_fcu(void) |
2010 | { | 1978 | { |
2011 | if (fcu) | ||
2012 | detach_i2c_chip(fcu); | ||
2013 | fcu = NULL; | 1979 | fcu = NULL; |
2014 | } | 1980 | } |
2015 | 1981 | ||
@@ -2060,12 +2026,21 @@ static int therm_pm72_attach(struct i2c_adapter *adapter) | |||
2060 | return 0; | 2026 | return 0; |
2061 | } | 2027 | } |
2062 | 2028 | ||
2029 | static int therm_pm72_probe(struct i2c_client *client, | ||
2030 | const struct i2c_device_id *id) | ||
2031 | { | ||
2032 | /* Always succeed, the real work was done in therm_pm72_attach() */ | ||
2033 | return 0; | ||
2034 | } | ||
2035 | |||
2063 | /* | 2036 | /* |
2064 | * Called on every adapter when the driver or the i2c controller | 2037 | * Called when any of the devices which participates into thermal management |
2065 | * is going away. | 2038 | * is going away. |
2066 | */ | 2039 | */ |
2067 | static int therm_pm72_detach(struct i2c_adapter *adapter) | 2040 | static int therm_pm72_remove(struct i2c_client *client) |
2068 | { | 2041 | { |
2042 | struct i2c_adapter *adapter = client->adapter; | ||
2043 | |||
2069 | mutex_lock(&driver_lock); | 2044 | mutex_lock(&driver_lock); |
2070 | 2045 | ||
2071 | if (state != state_detached) | 2046 | if (state != state_detached) |
@@ -2096,6 +2071,30 @@ static int therm_pm72_detach(struct i2c_adapter *adapter) | |||
2096 | return 0; | 2071 | return 0; |
2097 | } | 2072 | } |
2098 | 2073 | ||
2074 | /* | ||
2075 | * i2c_driver structure to attach to the host i2c controller | ||
2076 | */ | ||
2077 | |||
2078 | static const struct i2c_device_id therm_pm72_id[] = { | ||
2079 | /* | ||
2080 | * Fake device name, thermal management is done by several | ||
2081 | * chips but we don't need to differentiate between them at | ||
2082 | * this point. | ||
2083 | */ | ||
2084 | { "therm_pm72", 0 }, | ||
2085 | { } | ||
2086 | }; | ||
2087 | |||
2088 | static struct i2c_driver therm_pm72_driver = { | ||
2089 | .driver = { | ||
2090 | .name = "therm_pm72", | ||
2091 | }, | ||
2092 | .attach_adapter = therm_pm72_attach, | ||
2093 | .probe = therm_pm72_probe, | ||
2094 | .remove = therm_pm72_remove, | ||
2095 | .id_table = therm_pm72_id, | ||
2096 | }; | ||
2097 | |||
2099 | static int fan_check_loc_match(const char *loc, int fan) | 2098 | static int fan_check_loc_match(const char *loc, int fan) |
2100 | { | 2099 | { |
2101 | char tmp[64]; | 2100 | char tmp[64]; |