diff options
author | Dominik Brodowski <linux@dominikbrodowski.net> | 2010-01-16 03:14:11 -0500 |
---|---|---|
committer | Dominik Brodowski <linux@dominikbrodowski.net> | 2010-02-17 11:48:20 -0500 |
commit | 00ce99ff506a17882747a7d6874e3f5206a99043 (patch) | |
tree | 571f5b106f25f35f326d456123c4af85147c3bce | |
parent | 3d3de32fad19e37695e6649136e4cb17f9d46329 (diff) |
pcmcia: simplify locking
replace pcmcia_socket->lock and pcmcia_dev_list_lock by using the
per-socket "ops_mutex", as we do neither need different locks
nor a spinlock here.
Tested-by: Wolfram Sang <w.sang@pengutronix.de>
Signed-off-by: Dominik Brodowski <linux@dominikbrodowski.net>
-rw-r--r-- | drivers/pcmcia/cs.c | 2 | ||||
-rw-r--r-- | drivers/pcmcia/cs_internal.h | 2 | ||||
-rw-r--r-- | drivers/pcmcia/ds.c | 70 | ||||
-rw-r--r-- | drivers/pcmcia/pcmcia_ioctl.c | 36 | ||||
-rw-r--r-- | drivers/pcmcia/rsrc_mgr.c | 6 | ||||
-rw-r--r-- | drivers/pcmcia/socket_sysfs.c | 5 | ||||
-rw-r--r-- | include/pcmcia/ss.h | 7 |
7 files changed, 51 insertions, 77 deletions
diff --git a/drivers/pcmcia/cs.c b/drivers/pcmcia/cs.c index cc0ba8aef59e..13277eebe46a 100644 --- a/drivers/pcmcia/cs.c +++ b/drivers/pcmcia/cs.c | |||
@@ -175,8 +175,6 @@ int pcmcia_register_socket(struct pcmcia_socket *socket) | |||
175 | 175 | ||
176 | dev_dbg(&socket->dev, "pcmcia_register_socket(0x%p)\n", socket->ops); | 176 | dev_dbg(&socket->dev, "pcmcia_register_socket(0x%p)\n", socket->ops); |
177 | 177 | ||
178 | spin_lock_init(&socket->lock); | ||
179 | |||
180 | /* try to obtain a socket number [yes, it gets ugly if we | 178 | /* try to obtain a socket number [yes, it gets ugly if we |
181 | * register more than 2^sizeof(unsigned int) pcmcia | 179 | * register more than 2^sizeof(unsigned int) pcmcia |
182 | * sockets... but the socket number is deprecated | 180 | * sockets... but the socket number is deprecated |
diff --git a/drivers/pcmcia/cs_internal.h b/drivers/pcmcia/cs_internal.h index 76ac4444f0e0..bd386d77845e 100644 --- a/drivers/pcmcia/cs_internal.h +++ b/drivers/pcmcia/cs_internal.h | |||
@@ -182,8 +182,6 @@ int pccard_get_tuple_data(struct pcmcia_socket *s, tuple_t *tuple); | |||
182 | 182 | ||
183 | #ifdef CONFIG_PCMCIA_IOCTL | 183 | #ifdef CONFIG_PCMCIA_IOCTL |
184 | /* ds.c */ | 184 | /* ds.c */ |
185 | extern spinlock_t pcmcia_dev_list_lock; | ||
186 | |||
187 | extern struct pcmcia_device *pcmcia_get_dev(struct pcmcia_device *p_dev); | 185 | extern struct pcmcia_device *pcmcia_get_dev(struct pcmcia_device *p_dev); |
188 | extern void pcmcia_put_dev(struct pcmcia_device *p_dev); | 186 | extern void pcmcia_put_dev(struct pcmcia_device *p_dev); |
189 | 187 | ||
diff --git a/drivers/pcmcia/ds.c b/drivers/pcmcia/ds.c index 0eb242cbed17..4c40db8889d9 100644 --- a/drivers/pcmcia/ds.c +++ b/drivers/pcmcia/ds.c | |||
@@ -42,8 +42,6 @@ MODULE_DESCRIPTION("PCMCIA Driver Services"); | |||
42 | MODULE_LICENSE("GPL"); | 42 | MODULE_LICENSE("GPL"); |
43 | 43 | ||
44 | 44 | ||
45 | spinlock_t pcmcia_dev_list_lock; | ||
46 | |||
47 | /*====================================================================*/ | 45 | /*====================================================================*/ |
48 | 46 | ||
49 | static void pcmcia_check_driver(struct pcmcia_driver *p_drv) | 47 | static void pcmcia_check_driver(struct pcmcia_driver *p_drv) |
@@ -265,7 +263,6 @@ static int pcmcia_device_probe(struct device *dev) | |||
265 | struct pcmcia_device_id *did; | 263 | struct pcmcia_device_id *did; |
266 | struct pcmcia_socket *s; | 264 | struct pcmcia_socket *s; |
267 | cistpl_config_t cis_config; | 265 | cistpl_config_t cis_config; |
268 | unsigned long flags; | ||
269 | int ret = 0; | 266 | int ret = 0; |
270 | 267 | ||
271 | dev = get_device(dev); | 268 | dev = get_device(dev); |
@@ -316,11 +313,11 @@ static int pcmcia_device_probe(struct device *dev) | |||
316 | goto put_module; | 313 | goto put_module; |
317 | } | 314 | } |
318 | 315 | ||
319 | spin_lock_irqsave(&pcmcia_dev_list_lock, flags); | 316 | mutex_lock(&s->ops_mutex); |
320 | if (did && (did->match_flags & PCMCIA_DEV_ID_MATCH_DEVICE_NO) && | 317 | if (did && (did->match_flags & PCMCIA_DEV_ID_MATCH_DEVICE_NO) && |
321 | (p_dev->socket->device_count == 1) && (p_dev->device_no == 0)) | 318 | (p_dev->socket->device_count == 1) && (p_dev->device_no == 0)) |
322 | pcmcia_add_device_later(p_dev->socket, 0); | 319 | pcmcia_add_device_later(p_dev->socket, 0); |
323 | spin_unlock_irqrestore(&pcmcia_dev_list_lock, flags); | 320 | mutex_unlock(&s->ops_mutex); |
324 | 321 | ||
325 | put_module: | 322 | put_module: |
326 | if (ret) | 323 | if (ret) |
@@ -339,28 +336,27 @@ static void pcmcia_card_remove(struct pcmcia_socket *s, struct pcmcia_device *le | |||
339 | { | 336 | { |
340 | struct pcmcia_device *p_dev; | 337 | struct pcmcia_device *p_dev; |
341 | struct pcmcia_device *tmp; | 338 | struct pcmcia_device *tmp; |
342 | unsigned long flags; | ||
343 | 339 | ||
344 | dev_dbg(leftover ? &leftover->dev : &s->dev, | 340 | dev_dbg(leftover ? &leftover->dev : &s->dev, |
345 | "pcmcia_card_remove(%d) %s\n", s->sock, | 341 | "pcmcia_card_remove(%d) %s\n", s->sock, |
346 | leftover ? leftover->devname : ""); | 342 | leftover ? leftover->devname : ""); |
347 | 343 | ||
348 | spin_lock_irqsave(&pcmcia_dev_list_lock, flags); | 344 | mutex_lock(&s->ops_mutex); |
349 | if (!leftover) | 345 | if (!leftover) |
350 | s->device_count = 0; | 346 | s->device_count = 0; |
351 | else | 347 | else |
352 | s->device_count = 1; | 348 | s->device_count = 1; |
353 | spin_unlock_irqrestore(&pcmcia_dev_list_lock, flags); | 349 | mutex_unlock(&s->ops_mutex); |
354 | 350 | ||
355 | /* unregister all pcmcia_devices registered with this socket, except leftover */ | 351 | /* unregister all pcmcia_devices registered with this socket, except leftover */ |
356 | list_for_each_entry_safe(p_dev, tmp, &s->devices_list, socket_device_list) { | 352 | list_for_each_entry_safe(p_dev, tmp, &s->devices_list, socket_device_list) { |
357 | if (p_dev == leftover) | 353 | if (p_dev == leftover) |
358 | continue; | 354 | continue; |
359 | 355 | ||
360 | spin_lock_irqsave(&pcmcia_dev_list_lock, flags); | 356 | mutex_lock(&s->ops_mutex); |
361 | list_del(&p_dev->socket_device_list); | 357 | list_del(&p_dev->socket_device_list); |
362 | p_dev->_removed = 1; | 358 | p_dev->_removed = 1; |
363 | spin_unlock_irqrestore(&pcmcia_dev_list_lock, flags); | 359 | mutex_unlock(&s->ops_mutex); |
364 | 360 | ||
365 | dev_dbg(&p_dev->dev, "unregistering device\n"); | 361 | dev_dbg(&p_dev->dev, "unregistering device\n"); |
366 | device_unregister(&p_dev->dev); | 362 | device_unregister(&p_dev->dev); |
@@ -507,7 +503,6 @@ static DEFINE_MUTEX(device_add_lock); | |||
507 | struct pcmcia_device *pcmcia_device_add(struct pcmcia_socket *s, unsigned int function) | 503 | struct pcmcia_device *pcmcia_device_add(struct pcmcia_socket *s, unsigned int function) |
508 | { | 504 | { |
509 | struct pcmcia_device *p_dev, *tmp_dev; | 505 | struct pcmcia_device *p_dev, *tmp_dev; |
510 | unsigned long flags; | ||
511 | 506 | ||
512 | s = pcmcia_get_socket(s); | 507 | s = pcmcia_get_socket(s); |
513 | if (!s) | 508 | if (!s) |
@@ -521,9 +516,9 @@ struct pcmcia_device *pcmcia_device_add(struct pcmcia_socket *s, unsigned int fu | |||
521 | if (!p_dev) | 516 | if (!p_dev) |
522 | goto err_put; | 517 | goto err_put; |
523 | 518 | ||
524 | spin_lock_irqsave(&pcmcia_dev_list_lock, flags); | 519 | mutex_lock(&s->ops_mutex); |
525 | p_dev->device_no = (s->device_count++); | 520 | p_dev->device_no = (s->device_count++); |
526 | spin_unlock_irqrestore(&pcmcia_dev_list_lock, flags); | 521 | mutex_unlock(&s->ops_mutex); |
527 | 522 | ||
528 | /* max of 4 devices per card */ | 523 | /* max of 4 devices per card */ |
529 | if (p_dev->device_no >= 4) | 524 | if (p_dev->device_no >= 4) |
@@ -546,7 +541,7 @@ struct pcmcia_device *pcmcia_device_add(struct pcmcia_socket *s, unsigned int fu | |||
546 | goto err_free; | 541 | goto err_free; |
547 | dev_dbg(&p_dev->dev, "devname is %s\n", p_dev->devname); | 542 | dev_dbg(&p_dev->dev, "devname is %s\n", p_dev->devname); |
548 | 543 | ||
549 | spin_lock_irqsave(&pcmcia_dev_list_lock, flags); | 544 | mutex_lock(&s->ops_mutex); |
550 | 545 | ||
551 | /* | 546 | /* |
552 | * p_dev->function_config must be the same for all card functions. | 547 | * p_dev->function_config must be the same for all card functions. |
@@ -564,7 +559,7 @@ struct pcmcia_device *pcmcia_device_add(struct pcmcia_socket *s, unsigned int fu | |||
564 | /* Add to the list in pcmcia_bus_socket */ | 559 | /* Add to the list in pcmcia_bus_socket */ |
565 | list_add(&p_dev->socket_device_list, &s->devices_list); | 560 | list_add(&p_dev->socket_device_list, &s->devices_list); |
566 | 561 | ||
567 | spin_unlock_irqrestore(&pcmcia_dev_list_lock, flags); | 562 | mutex_unlock(&s->ops_mutex); |
568 | 563 | ||
569 | if (!p_dev->function_config) { | 564 | if (!p_dev->function_config) { |
570 | dev_dbg(&p_dev->dev, "creating config_t\n"); | 565 | dev_dbg(&p_dev->dev, "creating config_t\n"); |
@@ -589,14 +584,14 @@ struct pcmcia_device *pcmcia_device_add(struct pcmcia_socket *s, unsigned int fu | |||
589 | return p_dev; | 584 | return p_dev; |
590 | 585 | ||
591 | err_unreg: | 586 | err_unreg: |
592 | spin_lock_irqsave(&pcmcia_dev_list_lock, flags); | 587 | mutex_lock(&s->ops_mutex); |
593 | list_del(&p_dev->socket_device_list); | 588 | list_del(&p_dev->socket_device_list); |
594 | spin_unlock_irqrestore(&pcmcia_dev_list_lock, flags); | 589 | mutex_unlock(&s->ops_mutex); |
595 | 590 | ||
596 | err_free: | 591 | err_free: |
597 | spin_lock_irqsave(&pcmcia_dev_list_lock, flags); | 592 | mutex_lock(&s->ops_mutex); |
598 | s->device_count--; | 593 | s->device_count--; |
599 | spin_unlock_irqrestore(&pcmcia_dev_list_lock, flags); | 594 | mutex_unlock(&s->ops_mutex); |
600 | 595 | ||
601 | kfree(p_dev->devname); | 596 | kfree(p_dev->devname); |
602 | kfree(p_dev); | 597 | kfree(p_dev); |
@@ -650,13 +645,12 @@ static void pcmcia_delayed_add_device(struct work_struct *work) | |||
650 | struct pcmcia_socket *s = | 645 | struct pcmcia_socket *s = |
651 | container_of(work, struct pcmcia_socket, device_add); | 646 | container_of(work, struct pcmcia_socket, device_add); |
652 | u8 mfc_pfc; | 647 | u8 mfc_pfc; |
653 | unsigned long flags; | ||
654 | 648 | ||
655 | spin_lock_irqsave(&pcmcia_dev_list_lock, flags); | 649 | mutex_lock(&s->ops_mutex); |
656 | mfc_pfc = s->pcmcia_state.mfc_pfc; | 650 | mfc_pfc = s->pcmcia_state.mfc_pfc; |
657 | s->pcmcia_state.device_add_pending = 0; | 651 | s->pcmcia_state.device_add_pending = 0; |
658 | s->pcmcia_state.mfc_pfc = 0; | 652 | s->pcmcia_state.mfc_pfc = 0; |
659 | spin_unlock_irqrestore(&pcmcia_dev_list_lock, flags); | 653 | mutex_unlock(&s->ops_mutex); |
660 | 654 | ||
661 | dev_dbg(&s->dev, "adding additional device to %d\n", s->sock); | 655 | dev_dbg(&s->dev, "adding additional device to %d\n", s->sock); |
662 | pcmcia_device_add(s, mfc_pfc); | 656 | pcmcia_device_add(s, mfc_pfc); |
@@ -677,15 +671,14 @@ static void pcmcia_bus_rescan(struct pcmcia_socket *skt, int new_cis) | |||
677 | { | 671 | { |
678 | int no_devices = 0; | 672 | int no_devices = 0; |
679 | int ret = 0; | 673 | int ret = 0; |
680 | unsigned long flags; | ||
681 | 674 | ||
682 | /* must be called with skt_mutex held */ | 675 | /* must be called with skt_mutex held */ |
683 | dev_dbg(&skt->dev, "re-scanning socket %d\n", skt->sock); | 676 | dev_dbg(&skt->dev, "re-scanning socket %d\n", skt->sock); |
684 | 677 | ||
685 | spin_lock_irqsave(&pcmcia_dev_list_lock, flags); | 678 | mutex_lock(&skt->ops_mutex); |
686 | if (list_empty(&skt->devices_list)) | 679 | if (list_empty(&skt->devices_list)) |
687 | no_devices = 1; | 680 | no_devices = 1; |
688 | spin_unlock_irqrestore(&pcmcia_dev_list_lock, flags); | 681 | mutex_unlock(&skt->ops_mutex); |
689 | 682 | ||
690 | /* If this is because of a CIS override, start over */ | 683 | /* If this is because of a CIS override, start over */ |
691 | if (new_cis && !no_devices) | 684 | if (new_cis && !no_devices) |
@@ -769,11 +762,9 @@ static int pcmcia_load_firmware(struct pcmcia_device *dev, char * filename) | |||
769 | if (old_funcs > no_funcs) | 762 | if (old_funcs > no_funcs) |
770 | pcmcia_card_remove(s, dev); | 763 | pcmcia_card_remove(s, dev); |
771 | else if (no_funcs > old_funcs) { | 764 | else if (no_funcs > old_funcs) { |
772 | unsigned long flags; | 765 | mutex_lock(&s->ops_mutex); |
773 | |||
774 | spin_lock_irqsave(&pcmcia_dev_list_lock, flags); | ||
775 | pcmcia_add_device_later(s, 1); | 766 | pcmcia_add_device_later(s, 1); |
776 | spin_unlock_irqrestore(&pcmcia_dev_list_lock, flags); | 767 | mutex_unlock(&s->ops_mutex); |
777 | } | 768 | } |
778 | } | 769 | } |
779 | release: | 770 | release: |
@@ -1248,7 +1239,6 @@ static int pcmcia_bus_suspend(struct pcmcia_socket *skt) | |||
1248 | static int ds_event(struct pcmcia_socket *skt, event_t event, int priority) | 1239 | static int ds_event(struct pcmcia_socket *skt, event_t event, int priority) |
1249 | { | 1240 | { |
1250 | struct pcmcia_socket *s = pcmcia_get_socket(skt); | 1241 | struct pcmcia_socket *s = pcmcia_get_socket(skt); |
1251 | unsigned long flags; | ||
1252 | 1242 | ||
1253 | if (!s) { | 1243 | if (!s) { |
1254 | dev_printk(KERN_ERR, &skt->dev, | 1244 | dev_printk(KERN_ERR, &skt->dev, |
@@ -1262,9 +1252,9 @@ static int ds_event(struct pcmcia_socket *skt, event_t event, int priority) | |||
1262 | 1252 | ||
1263 | switch (event) { | 1253 | switch (event) { |
1264 | case CS_EVENT_CARD_REMOVAL: | 1254 | case CS_EVENT_CARD_REMOVAL: |
1265 | spin_lock_irqsave(&pcmcia_dev_list_lock, flags); | 1255 | mutex_lock(&s->ops_mutex); |
1266 | s->pcmcia_state.present = 0; | 1256 | s->pcmcia_state.present = 0; |
1267 | spin_unlock_irqrestore(&pcmcia_dev_list_lock, flags); | 1257 | mutex_unlock(&s->ops_mutex); |
1268 | pcmcia_card_remove(skt, NULL); | 1258 | pcmcia_card_remove(skt, NULL); |
1269 | handle_event(skt, event); | 1259 | handle_event(skt, event); |
1270 | mutex_lock(&s->ops_mutex); | 1260 | mutex_lock(&s->ops_mutex); |
@@ -1273,10 +1263,8 @@ static int ds_event(struct pcmcia_socket *skt, event_t event, int priority) | |||
1273 | break; | 1263 | break; |
1274 | 1264 | ||
1275 | case CS_EVENT_CARD_INSERTION: | 1265 | case CS_EVENT_CARD_INSERTION: |
1276 | spin_lock_irqsave(&pcmcia_dev_list_lock, flags); | ||
1277 | s->pcmcia_state.present = 1; | ||
1278 | spin_unlock_irqrestore(&pcmcia_dev_list_lock, flags); | ||
1279 | mutex_lock(&s->ops_mutex); | 1266 | mutex_lock(&s->ops_mutex); |
1267 | s->pcmcia_state.present = 1; | ||
1280 | destroy_cis_cache(s); /* to be on the safe side... */ | 1268 | destroy_cis_cache(s); /* to be on the safe side... */ |
1281 | mutex_unlock(&s->ops_mutex); | 1269 | mutex_unlock(&s->ops_mutex); |
1282 | pcmcia_card_add(skt); | 1270 | pcmcia_card_add(skt); |
@@ -1321,13 +1309,12 @@ struct pcmcia_device *pcmcia_dev_present(struct pcmcia_device *_p_dev) | |||
1321 | { | 1309 | { |
1322 | struct pcmcia_device *p_dev; | 1310 | struct pcmcia_device *p_dev; |
1323 | struct pcmcia_device *ret = NULL; | 1311 | struct pcmcia_device *ret = NULL; |
1324 | unsigned long flags; | ||
1325 | 1312 | ||
1326 | p_dev = pcmcia_get_dev(_p_dev); | 1313 | p_dev = pcmcia_get_dev(_p_dev); |
1327 | if (!p_dev) | 1314 | if (!p_dev) |
1328 | return NULL; | 1315 | return NULL; |
1329 | 1316 | ||
1330 | spin_lock_irqsave(&pcmcia_dev_list_lock, flags); | 1317 | mutex_lock(&p_dev->socket->ops_mutex); |
1331 | if (!p_dev->socket->pcmcia_state.present) | 1318 | if (!p_dev->socket->pcmcia_state.present) |
1332 | goto out; | 1319 | goto out; |
1333 | 1320 | ||
@@ -1342,7 +1329,7 @@ struct pcmcia_device *pcmcia_dev_present(struct pcmcia_device *_p_dev) | |||
1342 | 1329 | ||
1343 | ret = p_dev; | 1330 | ret = p_dev; |
1344 | out: | 1331 | out: |
1345 | spin_unlock_irqrestore(&pcmcia_dev_list_lock, flags); | 1332 | mutex_unlock(&p_dev->socket->ops_mutex); |
1346 | pcmcia_put_dev(p_dev); | 1333 | pcmcia_put_dev(p_dev); |
1347 | return ret; | 1334 | return ret; |
1348 | } | 1335 | } |
@@ -1406,14 +1393,13 @@ static void pcmcia_bus_remove_socket(struct device *dev, | |||
1406 | struct class_interface *class_intf) | 1393 | struct class_interface *class_intf) |
1407 | { | 1394 | { |
1408 | struct pcmcia_socket *socket = dev_get_drvdata(dev); | 1395 | struct pcmcia_socket *socket = dev_get_drvdata(dev); |
1409 | unsigned long flags; | ||
1410 | 1396 | ||
1411 | if (!socket) | 1397 | if (!socket) |
1412 | return; | 1398 | return; |
1413 | 1399 | ||
1414 | spin_lock_irqsave(&pcmcia_dev_list_lock, flags); | 1400 | mutex_lock(&socket->ops_mutex); |
1415 | socket->pcmcia_state.dead = 1; | 1401 | socket->pcmcia_state.dead = 1; |
1416 | spin_unlock_irqrestore(&pcmcia_dev_list_lock, flags); | 1402 | mutex_unlock(&socket->ops_mutex); |
1417 | 1403 | ||
1418 | pccard_register_pcmcia(socket, NULL); | 1404 | pccard_register_pcmcia(socket, NULL); |
1419 | 1405 | ||
@@ -1455,8 +1441,6 @@ static int __init init_pcmcia_bus(void) | |||
1455 | { | 1441 | { |
1456 | int ret; | 1442 | int ret; |
1457 | 1443 | ||
1458 | spin_lock_init(&pcmcia_dev_list_lock); | ||
1459 | |||
1460 | ret = bus_register(&pcmcia_bus_type); | 1444 | ret = bus_register(&pcmcia_bus_type); |
1461 | if (ret < 0) { | 1445 | if (ret < 0) { |
1462 | printk(KERN_WARNING "pcmcia: bus_register error: %d\n", ret); | 1446 | printk(KERN_WARNING "pcmcia: bus_register error: %d\n", ret); |
diff --git a/drivers/pcmcia/pcmcia_ioctl.c b/drivers/pcmcia/pcmcia_ioctl.c index f73fd5beaa37..db2e3db8008b 100644 --- a/drivers/pcmcia/pcmcia_ioctl.c +++ b/drivers/pcmcia/pcmcia_ioctl.c | |||
@@ -62,16 +62,15 @@ static struct pcmcia_device *get_pcmcia_device(struct pcmcia_socket *s, | |||
62 | unsigned int function) | 62 | unsigned int function) |
63 | { | 63 | { |
64 | struct pcmcia_device *p_dev = NULL; | 64 | struct pcmcia_device *p_dev = NULL; |
65 | unsigned long flags; | ||
66 | 65 | ||
67 | spin_lock_irqsave(&pcmcia_dev_list_lock, flags); | 66 | mutex_lock(&s->ops_mutex); |
68 | list_for_each_entry(p_dev, &s->devices_list, socket_device_list) { | 67 | list_for_each_entry(p_dev, &s->devices_list, socket_device_list) { |
69 | if (p_dev->func == function) { | 68 | if (p_dev->func == function) { |
70 | spin_unlock_irqrestore(&pcmcia_dev_list_lock, flags); | 69 | mutex_unlock(&s->ops_mutex); |
71 | return pcmcia_get_dev(p_dev); | 70 | return pcmcia_get_dev(p_dev); |
72 | } | 71 | } |
73 | } | 72 | } |
74 | spin_unlock_irqrestore(&pcmcia_dev_list_lock, flags); | 73 | mutex_unlock(&s->ops_mutex); |
75 | return NULL; | 74 | return NULL; |
76 | } | 75 | } |
77 | 76 | ||
@@ -169,7 +168,6 @@ static int pcmcia_adjust_resource_info(adjust_t *adj) | |||
169 | { | 168 | { |
170 | struct pcmcia_socket *s; | 169 | struct pcmcia_socket *s; |
171 | int ret = -ENOSYS; | 170 | int ret = -ENOSYS; |
172 | unsigned long flags; | ||
173 | 171 | ||
174 | down_read(&pcmcia_socket_list_rwsem); | 172 | down_read(&pcmcia_socket_list_rwsem); |
175 | list_for_each_entry(s, &pcmcia_socket_list, socket_list) { | 173 | list_for_each_entry(s, &pcmcia_socket_list, socket_list) { |
@@ -182,14 +180,14 @@ static int pcmcia_adjust_resource_info(adjust_t *adj) | |||
182 | 180 | ||
183 | /* you can't use the old interface if the new | 181 | /* you can't use the old interface if the new |
184 | * one was used before */ | 182 | * one was used before */ |
185 | spin_lock_irqsave(&s->lock, flags); | 183 | mutex_lock(&s->ops_mutex); |
186 | if ((s->resource_setup_new) && | 184 | if ((s->resource_setup_new) && |
187 | !(s->resource_setup_old)) { | 185 | !(s->resource_setup_old)) { |
188 | spin_unlock_irqrestore(&s->lock, flags); | 186 | mutex_unlock(&s->ops_mutex); |
189 | continue; | 187 | continue; |
190 | } else if (!(s->resource_setup_old)) | 188 | } else if (!(s->resource_setup_old)) |
191 | s->resource_setup_old = 1; | 189 | s->resource_setup_old = 1; |
192 | spin_unlock_irqrestore(&s->lock, flags); | 190 | mutex_unlock(&s->ops_mutex); |
193 | 191 | ||
194 | switch (adj->Resource) { | 192 | switch (adj->Resource) { |
195 | case RES_MEMORY_RANGE: | 193 | case RES_MEMORY_RANGE: |
@@ -208,9 +206,9 @@ static int pcmcia_adjust_resource_info(adjust_t *adj) | |||
208 | * last call to adjust_resource_info, we | 206 | * last call to adjust_resource_info, we |
209 | * always need to assume this is the latest | 207 | * always need to assume this is the latest |
210 | * one... */ | 208 | * one... */ |
211 | spin_lock_irqsave(&s->lock, flags); | 209 | mutex_lock(&s->ops_mutex); |
212 | s->resource_setup_done = 1; | 210 | s->resource_setup_done = 1; |
213 | spin_unlock_irqrestore(&s->lock, flags); | 211 | mutex_unlock(&s->ops_mutex); |
214 | } | 212 | } |
215 | } | 213 | } |
216 | } | 214 | } |
@@ -470,7 +468,6 @@ static int bind_request(struct pcmcia_socket *s, bind_info_t *bind_info) | |||
470 | struct pcmcia_driver *p_drv; | 468 | struct pcmcia_driver *p_drv; |
471 | struct pcmcia_device *p_dev; | 469 | struct pcmcia_device *p_dev; |
472 | int ret = 0; | 470 | int ret = 0; |
473 | unsigned long flags; | ||
474 | 471 | ||
475 | s = pcmcia_get_socket(s); | 472 | s = pcmcia_get_socket(s); |
476 | if (!s) | 473 | if (!s) |
@@ -490,7 +487,7 @@ static int bind_request(struct pcmcia_socket *s, bind_info_t *bind_info) | |||
490 | goto err_put_driver; | 487 | goto err_put_driver; |
491 | } | 488 | } |
492 | 489 | ||
493 | spin_lock_irqsave(&pcmcia_dev_list_lock, flags); | 490 | mutex_lock(&s->ops_mutex); |
494 | list_for_each_entry(p_dev, &s->devices_list, socket_device_list) { | 491 | list_for_each_entry(p_dev, &s->devices_list, socket_device_list) { |
495 | if (p_dev->func == bind_info->function) { | 492 | if (p_dev->func == bind_info->function) { |
496 | if ((p_dev->dev.driver == &p_drv->drv)) { | 493 | if ((p_dev->dev.driver == &p_drv->drv)) { |
@@ -499,7 +496,7 @@ static int bind_request(struct pcmcia_socket *s, bind_info_t *bind_info) | |||
499 | * registered, and it was registered | 496 | * registered, and it was registered |
500 | * by userspace before, we need to | 497 | * by userspace before, we need to |
501 | * return the "instance". */ | 498 | * return the "instance". */ |
502 | spin_unlock_irqrestore(&pcmcia_dev_list_lock, flags); | 499 | mutex_unlock(&s->ops_mutex); |
503 | bind_info->instance = p_dev; | 500 | bind_info->instance = p_dev; |
504 | ret = -EBUSY; | 501 | ret = -EBUSY; |
505 | goto err_put_module; | 502 | goto err_put_module; |
@@ -507,7 +504,7 @@ static int bind_request(struct pcmcia_socket *s, bind_info_t *bind_info) | |||
507 | /* the correct driver managed to bind | 504 | /* the correct driver managed to bind |
508 | * itself magically to the correct | 505 | * itself magically to the correct |
509 | * device. */ | 506 | * device. */ |
510 | spin_unlock_irqrestore(&pcmcia_dev_list_lock, flags); | 507 | mutex_unlock(&s->ops_mutex); |
511 | p_dev->cardmgr = p_drv; | 508 | p_dev->cardmgr = p_drv; |
512 | ret = 0; | 509 | ret = 0; |
513 | goto err_put_module; | 510 | goto err_put_module; |
@@ -516,12 +513,12 @@ static int bind_request(struct pcmcia_socket *s, bind_info_t *bind_info) | |||
516 | /* there's already a device available where | 513 | /* there's already a device available where |
517 | * no device has been bound to yet. So we don't | 514 | * no device has been bound to yet. So we don't |
518 | * need to register a device! */ | 515 | * need to register a device! */ |
519 | spin_unlock_irqrestore(&pcmcia_dev_list_lock, flags); | 516 | mutex_unlock(&s->ops_mutex); |
520 | goto rescan; | 517 | goto rescan; |
521 | } | 518 | } |
522 | } | 519 | } |
523 | } | 520 | } |
524 | spin_unlock_irqrestore(&pcmcia_dev_list_lock, flags); | 521 | mutex_unlock(&s->ops_mutex); |
525 | 522 | ||
526 | p_dev = pcmcia_device_add(s, bind_info->function); | 523 | p_dev = pcmcia_device_add(s, bind_info->function); |
527 | if (!p_dev) { | 524 | if (!p_dev) { |
@@ -578,7 +575,6 @@ static int get_device_info(struct pcmcia_socket *s, bind_info_t *bind_info, int | |||
578 | dev_node_t *node; | 575 | dev_node_t *node; |
579 | struct pcmcia_device *p_dev; | 576 | struct pcmcia_device *p_dev; |
580 | struct pcmcia_driver *p_drv; | 577 | struct pcmcia_driver *p_drv; |
581 | unsigned long flags; | ||
582 | int ret = 0; | 578 | int ret = 0; |
583 | 579 | ||
584 | #ifdef CONFIG_CARDBUS | 580 | #ifdef CONFIG_CARDBUS |
@@ -617,7 +613,7 @@ static int get_device_info(struct pcmcia_socket *s, bind_info_t *bind_info, int | |||
617 | } | 613 | } |
618 | #endif | 614 | #endif |
619 | 615 | ||
620 | spin_lock_irqsave(&pcmcia_dev_list_lock, flags); | 616 | mutex_lock(&s->ops_mutex); |
621 | list_for_each_entry(p_dev, &s->devices_list, socket_device_list) { | 617 | list_for_each_entry(p_dev, &s->devices_list, socket_device_list) { |
622 | if (p_dev->func == bind_info->function) { | 618 | if (p_dev->func == bind_info->function) { |
623 | p_dev = pcmcia_get_dev(p_dev); | 619 | p_dev = pcmcia_get_dev(p_dev); |
@@ -626,11 +622,11 @@ static int get_device_info(struct pcmcia_socket *s, bind_info_t *bind_info, int | |||
626 | goto found; | 622 | goto found; |
627 | } | 623 | } |
628 | } | 624 | } |
629 | spin_unlock_irqrestore(&pcmcia_dev_list_lock, flags); | 625 | mutex_unlock(&s->ops_mutex); |
630 | return -ENODEV; | 626 | return -ENODEV; |
631 | 627 | ||
632 | found: | 628 | found: |
633 | spin_unlock_irqrestore(&pcmcia_dev_list_lock, flags); | 629 | mutex_unlock(&s->ops_mutex); |
634 | 630 | ||
635 | p_drv = to_pcmcia_drv(p_dev->dev.driver); | 631 | p_drv = to_pcmcia_drv(p_dev->dev.driver); |
636 | if (p_drv && !p_dev->_locked) { | 632 | if (p_drv && !p_dev->_locked) { |
diff --git a/drivers/pcmcia/rsrc_mgr.c b/drivers/pcmcia/rsrc_mgr.c index cdd30c180066..b81586622d02 100644 --- a/drivers/pcmcia/rsrc_mgr.c +++ b/drivers/pcmcia/rsrc_mgr.c | |||
@@ -23,14 +23,12 @@ | |||
23 | 23 | ||
24 | static int static_init(struct pcmcia_socket *s) | 24 | static int static_init(struct pcmcia_socket *s) |
25 | { | 25 | { |
26 | unsigned long flags; | ||
27 | |||
28 | /* the good thing about SS_CAP_STATIC_MAP sockets is | 26 | /* the good thing about SS_CAP_STATIC_MAP sockets is |
29 | * that they don't need a resource database */ | 27 | * that they don't need a resource database */ |
30 | 28 | ||
31 | spin_lock_irqsave(&s->lock, flags); | 29 | mutex_lock(&s->ops_mutex); |
32 | s->resource_setup_done = 1; | 30 | s->resource_setup_done = 1; |
33 | spin_unlock_irqrestore(&s->lock, flags); | 31 | mutex_unlock(&s->ops_mutex); |
34 | 32 | ||
35 | return 0; | 33 | return 0; |
36 | } | 34 | } |
diff --git a/drivers/pcmcia/socket_sysfs.c b/drivers/pcmcia/socket_sysfs.c index 1cba9d38d813..e8826df00a36 100644 --- a/drivers/pcmcia/socket_sysfs.c +++ b/drivers/pcmcia/socket_sysfs.c | |||
@@ -189,16 +189,15 @@ static ssize_t pccard_store_resource(struct device *dev, | |||
189 | struct device_attribute *attr, | 189 | struct device_attribute *attr, |
190 | const char *buf, size_t count) | 190 | const char *buf, size_t count) |
191 | { | 191 | { |
192 | unsigned long flags; | ||
193 | struct pcmcia_socket *s = to_socket(dev); | 192 | struct pcmcia_socket *s = to_socket(dev); |
194 | 193 | ||
195 | if (!count) | 194 | if (!count) |
196 | return -EINVAL; | 195 | return -EINVAL; |
197 | 196 | ||
198 | spin_lock_irqsave(&s->lock, flags); | 197 | mutex_lock(&s->ops_mutex); |
199 | if (!s->resource_setup_done) | 198 | if (!s->resource_setup_done) |
200 | s->resource_setup_done = 1; | 199 | s->resource_setup_done = 1; |
201 | spin_unlock_irqrestore(&s->lock, flags); | 200 | mutex_unlock(&s->ops_mutex); |
202 | 201 | ||
203 | mutex_lock(&s->skt_mutex); | 202 | mutex_lock(&s->skt_mutex); |
204 | if ((s->callback) && | 203 | if ((s->callback) && |
diff --git a/include/pcmcia/ss.h b/include/pcmcia/ss.h index e756069859b5..cfaccc224b50 100644 --- a/include/pcmcia/ss.h +++ b/include/pcmcia/ss.h | |||
@@ -134,7 +134,6 @@ struct pccard_operations { | |||
134 | 134 | ||
135 | struct pcmcia_socket { | 135 | struct pcmcia_socket { |
136 | struct module *owner; | 136 | struct module *owner; |
137 | spinlock_t lock; | ||
138 | socket_state_t socket; | 137 | socket_state_t socket; |
139 | u_int state; | 138 | u_int state; |
140 | u_int suspended_state; /* state before suspend */ | 139 | u_int suspended_state; /* state before suspend */ |
@@ -201,10 +200,12 @@ struct pcmcia_socket { | |||
201 | struct task_struct *thread; | 200 | struct task_struct *thread; |
202 | struct completion thread_done; | 201 | struct completion thread_done; |
203 | unsigned int thread_events; | 202 | unsigned int thread_events; |
204 | /* protects socket h/w state */ | 203 | |
204 | /* For the non-trivial interaction between these locks, | ||
205 | * see Documentation/pcmcia/locking.txt */ | ||
205 | struct mutex skt_mutex; | 206 | struct mutex skt_mutex; |
206 | /* protects PCMCIA state */ | ||
207 | struct mutex ops_mutex; | 207 | struct mutex ops_mutex; |
208 | |||
208 | /* protects thread_events */ | 209 | /* protects thread_events */ |
209 | spinlock_t thread_lock; | 210 | spinlock_t thread_lock; |
210 | 211 | ||