diff options
author | Linus Torvalds <torvalds@woody.linux-foundation.org> | 2007-11-26 22:25:23 -0500 |
---|---|---|
committer | Linus Torvalds <torvalds@woody.linux-foundation.org> | 2007-11-26 22:25:23 -0500 |
commit | 64d0793109a98abcc2f4bf0c7d8b000fd220cdcd (patch) | |
tree | 3ae4440db0e67a622d8cb9ad4f467b9306a40c32 | |
parent | bb40784f4aeae7b9d70c49b422f78ffdfc539739 (diff) | |
parent | 1dff314451fa24d6b107aa05393d3169e56a7e0a (diff) |
Merge branch 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/drzeus/mmc
* 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/drzeus/mmc:
mmc: Avoid re-using minor numbers before the original device is closed.
tifm_sd: handle non-power-of-2 block sizes
mmc_block: check card state after write
-rw-r--r-- | drivers/mmc/card/block.c | 22 | ||||
-rw-r--r-- | drivers/mmc/host/tifm_sd.c | 18 |
2 files changed, 20 insertions, 20 deletions
diff --git a/drivers/mmc/card/block.c b/drivers/mmc/card/block.c index e38d5a3b2a89..aeb32a93f6a0 100644 --- a/drivers/mmc/card/block.c +++ b/drivers/mmc/card/block.c | |||
@@ -44,6 +44,9 @@ | |||
44 | * max 8 partitions per card | 44 | * max 8 partitions per card |
45 | */ | 45 | */ |
46 | #define MMC_SHIFT 3 | 46 | #define MMC_SHIFT 3 |
47 | #define MMC_NUM_MINORS (256 >> MMC_SHIFT) | ||
48 | |||
49 | static unsigned long dev_use[MMC_NUM_MINORS/(8*sizeof(unsigned long))]; | ||
47 | 50 | ||
48 | /* | 51 | /* |
49 | * There is one mmc_blk_data per slot. | 52 | * There is one mmc_blk_data per slot. |
@@ -80,6 +83,9 @@ static void mmc_blk_put(struct mmc_blk_data *md) | |||
80 | mutex_lock(&open_lock); | 83 | mutex_lock(&open_lock); |
81 | md->usage--; | 84 | md->usage--; |
82 | if (md->usage == 0) { | 85 | if (md->usage == 0) { |
86 | int devidx = md->disk->first_minor >> MMC_SHIFT; | ||
87 | __clear_bit(devidx, dev_use); | ||
88 | |||
83 | put_disk(md->disk); | 89 | put_disk(md->disk); |
84 | kfree(md); | 90 | kfree(md); |
85 | } | 91 | } |
@@ -321,7 +327,13 @@ static int mmc_blk_issue_rq(struct mmc_queue *mq, struct request *req) | |||
321 | req->rq_disk->disk_name, err); | 327 | req->rq_disk->disk_name, err); |
322 | goto cmd_err; | 328 | goto cmd_err; |
323 | } | 329 | } |
324 | } while (!(cmd.resp[0] & R1_READY_FOR_DATA)); | 330 | /* |
331 | * Some cards mishandle the status bits, | ||
332 | * so make sure to check both the busy | ||
333 | * indication and the card state. | ||
334 | */ | ||
335 | } while (!(cmd.resp[0] & R1_READY_FOR_DATA) || | ||
336 | (R1_CURRENT_STATE(cmd.resp[0]) == 7)); | ||
325 | 337 | ||
326 | #if 0 | 338 | #if 0 |
327 | if (cmd.resp[0] & ~0x00000900) | 339 | if (cmd.resp[0] & ~0x00000900) |
@@ -400,9 +412,6 @@ static int mmc_blk_issue_rq(struct mmc_queue *mq, struct request *req) | |||
400 | return 0; | 412 | return 0; |
401 | } | 413 | } |
402 | 414 | ||
403 | #define MMC_NUM_MINORS (256 >> MMC_SHIFT) | ||
404 | |||
405 | static unsigned long dev_use[MMC_NUM_MINORS/(8*sizeof(unsigned long))]; | ||
406 | 415 | ||
407 | static inline int mmc_blk_readonly(struct mmc_card *card) | 416 | static inline int mmc_blk_readonly(struct mmc_card *card) |
408 | { | 417 | { |
@@ -568,17 +577,12 @@ static void mmc_blk_remove(struct mmc_card *card) | |||
568 | struct mmc_blk_data *md = mmc_get_drvdata(card); | 577 | struct mmc_blk_data *md = mmc_get_drvdata(card); |
569 | 578 | ||
570 | if (md) { | 579 | if (md) { |
571 | int devidx; | ||
572 | |||
573 | /* Stop new requests from getting into the queue */ | 580 | /* Stop new requests from getting into the queue */ |
574 | del_gendisk(md->disk); | 581 | del_gendisk(md->disk); |
575 | 582 | ||
576 | /* Then flush out any already in there */ | 583 | /* Then flush out any already in there */ |
577 | mmc_cleanup_queue(&md->queue); | 584 | mmc_cleanup_queue(&md->queue); |
578 | 585 | ||
579 | devidx = md->disk->first_minor >> MMC_SHIFT; | ||
580 | __clear_bit(devidx, dev_use); | ||
581 | |||
582 | mmc_blk_put(md); | 586 | mmc_blk_put(md); |
583 | } | 587 | } |
584 | mmc_set_drvdata(card, NULL); | 588 | mmc_set_drvdata(card, NULL); |
diff --git a/drivers/mmc/host/tifm_sd.c b/drivers/mmc/host/tifm_sd.c index c11a3d256051..20d5c7bd940a 100644 --- a/drivers/mmc/host/tifm_sd.c +++ b/drivers/mmc/host/tifm_sd.c | |||
@@ -16,7 +16,6 @@ | |||
16 | #include <linux/mmc/host.h> | 16 | #include <linux/mmc/host.h> |
17 | #include <linux/highmem.h> | 17 | #include <linux/highmem.h> |
18 | #include <linux/scatterlist.h> | 18 | #include <linux/scatterlist.h> |
19 | #include <linux/log2.h> | ||
20 | #include <asm/io.h> | 19 | #include <asm/io.h> |
21 | 20 | ||
22 | #define DRIVER_NAME "tifm_sd" | 21 | #define DRIVER_NAME "tifm_sd" |
@@ -638,17 +637,15 @@ static void tifm_sd_request(struct mmc_host *mmc, struct mmc_request *mrq) | |||
638 | goto err_out; | 637 | goto err_out; |
639 | } | 638 | } |
640 | 639 | ||
641 | if (mrq->data && !is_power_of_2(mrq->data->blksz)) { | ||
642 | printk(KERN_ERR "%s: Unsupported block size (%d bytes)\n", | ||
643 | sock->dev.bus_id, mrq->data->blksz); | ||
644 | mrq->cmd->error = -EINVAL; | ||
645 | goto err_out; | ||
646 | } | ||
647 | |||
648 | host->cmd_flags = 0; | 640 | host->cmd_flags = 0; |
649 | host->block_pos = 0; | 641 | host->block_pos = 0; |
650 | host->sg_pos = 0; | 642 | host->sg_pos = 0; |
651 | 643 | ||
644 | if (mrq->data && !is_power_of_2(mrq->data->blksz)) | ||
645 | host->no_dma = 1; | ||
646 | else | ||
647 | host->no_dma = no_dma ? 1 : 0; | ||
648 | |||
652 | if (r_data) { | 649 | if (r_data) { |
653 | tifm_sd_set_data_timeout(host, r_data); | 650 | tifm_sd_set_data_timeout(host, r_data); |
654 | 651 | ||
@@ -676,7 +673,7 @@ static void tifm_sd_request(struct mmc_host *mmc, struct mmc_request *mrq) | |||
676 | : PCI_DMA_FROMDEVICE)) { | 673 | : PCI_DMA_FROMDEVICE)) { |
677 | printk(KERN_ERR "%s : scatterlist map failed\n", | 674 | printk(KERN_ERR "%s : scatterlist map failed\n", |
678 | sock->dev.bus_id); | 675 | sock->dev.bus_id); |
679 | spin_unlock_irqrestore(&sock->lock, flags); | 676 | mrq->cmd->error = -ENOMEM; |
680 | goto err_out; | 677 | goto err_out; |
681 | } | 678 | } |
682 | host->sg_len = tifm_map_sg(sock, r_data->sg, | 679 | host->sg_len = tifm_map_sg(sock, r_data->sg, |
@@ -692,7 +689,7 @@ static void tifm_sd_request(struct mmc_host *mmc, struct mmc_request *mrq) | |||
692 | r_data->flags & MMC_DATA_WRITE | 689 | r_data->flags & MMC_DATA_WRITE |
693 | ? PCI_DMA_TODEVICE | 690 | ? PCI_DMA_TODEVICE |
694 | : PCI_DMA_FROMDEVICE); | 691 | : PCI_DMA_FROMDEVICE); |
695 | spin_unlock_irqrestore(&sock->lock, flags); | 692 | mrq->cmd->error = -ENOMEM; |
696 | goto err_out; | 693 | goto err_out; |
697 | } | 694 | } |
698 | 695 | ||
@@ -966,7 +963,6 @@ static int tifm_sd_probe(struct tifm_dev *sock) | |||
966 | return -ENOMEM; | 963 | return -ENOMEM; |
967 | 964 | ||
968 | host = mmc_priv(mmc); | 965 | host = mmc_priv(mmc); |
969 | host->no_dma = no_dma; | ||
970 | tifm_set_drvdata(sock, mmc); | 966 | tifm_set_drvdata(sock, mmc); |
971 | host->dev = sock; | 967 | host->dev = sock; |
972 | host->timeout_jiffies = msecs_to_jiffies(1000); | 968 | host->timeout_jiffies = msecs_to_jiffies(1000); |