aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/memstick
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/memstick')
-rw-r--r--drivers/memstick/core/memstick.c10
-rw-r--r--drivers/memstick/core/mspro_block.c33
-rw-r--r--drivers/memstick/host/jmb38x_ms.c39
3 files changed, 57 insertions, 25 deletions
diff --git a/drivers/memstick/core/memstick.c b/drivers/memstick/core/memstick.c
index a38005008a20..cea46906408e 100644
--- a/drivers/memstick/core/memstick.c
+++ b/drivers/memstick/core/memstick.c
@@ -185,7 +185,7 @@ static void memstick_free(struct device *dev)
185} 185}
186 186
187static struct class memstick_host_class = { 187static struct class memstick_host_class = {
188 .name = "memstick_host", 188 .name = "memstick_host",
189 .dev_release = memstick_free 189 .dev_release = memstick_free
190}; 190};
191 191
@@ -264,7 +264,7 @@ EXPORT_SYMBOL(memstick_new_req);
264 * @sg - TPC argument 264 * @sg - TPC argument
265 */ 265 */
266void memstick_init_req_sg(struct memstick_request *mrq, unsigned char tpc, 266void memstick_init_req_sg(struct memstick_request *mrq, unsigned char tpc,
267 struct scatterlist *sg) 267 const struct scatterlist *sg)
268{ 268{
269 mrq->tpc = tpc; 269 mrq->tpc = tpc;
270 if (tpc & 8) 270 if (tpc & 8)
@@ -294,7 +294,7 @@ EXPORT_SYMBOL(memstick_init_req_sg);
294 * user supplied buffer. 294 * user supplied buffer.
295 */ 295 */
296void memstick_init_req(struct memstick_request *mrq, unsigned char tpc, 296void memstick_init_req(struct memstick_request *mrq, unsigned char tpc,
297 void *buf, size_t length) 297 const void *buf, size_t length)
298{ 298{
299 mrq->tpc = tpc; 299 mrq->tpc = tpc;
300 if (tpc & 8) 300 if (tpc & 8)
@@ -439,7 +439,7 @@ static void memstick_check(struct work_struct *work)
439 if (!host->card) { 439 if (!host->card) {
440 if (memstick_power_on(host)) 440 if (memstick_power_on(host))
441 goto out_power_off; 441 goto out_power_off;
442 } else 442 } else if (host->card->stop)
443 host->card->stop(host->card); 443 host->card->stop(host->card);
444 444
445 card = memstick_alloc_card(host); 445 card = memstick_alloc_card(host);
@@ -458,7 +458,7 @@ static void memstick_check(struct work_struct *work)
458 || !(host->card->check(host->card))) { 458 || !(host->card->check(host->card))) {
459 device_unregister(&host->card->dev); 459 device_unregister(&host->card->dev);
460 host->card = NULL; 460 host->card = NULL;
461 } else 461 } else if (host->card->start)
462 host->card->start(host->card); 462 host->card->start(host->card);
463 } 463 }
464 464
diff --git a/drivers/memstick/core/mspro_block.c b/drivers/memstick/core/mspro_block.c
index 44b1817f2f2f..d2d2318dafa4 100644
--- a/drivers/memstick/core/mspro_block.c
+++ b/drivers/memstick/core/mspro_block.c
@@ -30,6 +30,8 @@ module_param(major, int, 0644);
30#define MSPRO_BLOCK_SIGNATURE 0xa5c3 30#define MSPRO_BLOCK_SIGNATURE 0xa5c3
31#define MSPRO_BLOCK_MAX_ATTRIBUTES 41 31#define MSPRO_BLOCK_MAX_ATTRIBUTES 41
32 32
33#define MSPRO_BLOCK_PART_SHIFT 3
34
33enum { 35enum {
34 MSPRO_BLOCK_ID_SYSINFO = 0x10, 36 MSPRO_BLOCK_ID_SYSINFO = 0x10,
35 MSPRO_BLOCK_ID_MODELNAME = 0x15, 37 MSPRO_BLOCK_ID_MODELNAME = 0x15,
@@ -195,7 +197,7 @@ static int mspro_block_bd_open(struct inode *inode, struct file *filp)
195static int mspro_block_disk_release(struct gendisk *disk) 197static int mspro_block_disk_release(struct gendisk *disk)
196{ 198{
197 struct mspro_block_data *msb = disk->private_data; 199 struct mspro_block_data *msb = disk->private_data;
198 int disk_id = disk->first_minor >> MEMSTICK_PART_SHIFT; 200 int disk_id = disk->first_minor >> MSPRO_BLOCK_PART_SHIFT;
199 201
200 mutex_lock(&mspro_block_disk_lock); 202 mutex_lock(&mspro_block_disk_lock);
201 203
@@ -877,6 +879,7 @@ static int mspro_block_switch_interface(struct memstick_dev *card)
877 struct mspro_block_data *msb = memstick_get_drvdata(card); 879 struct mspro_block_data *msb = memstick_get_drvdata(card);
878 int rc = 0; 880 int rc = 0;
879 881
882try_again:
880 if (msb->caps & MEMSTICK_CAP_PAR4) 883 if (msb->caps & MEMSTICK_CAP_PAR4)
881 rc = mspro_block_set_interface(card, MEMSTICK_SYS_PAR4); 884 rc = mspro_block_set_interface(card, MEMSTICK_SYS_PAR4);
882 else 885 else
@@ -930,6 +933,18 @@ static int mspro_block_switch_interface(struct memstick_dev *card)
930 rc = memstick_set_rw_addr(card); 933 rc = memstick_set_rw_addr(card);
931 if (!rc) 934 if (!rc)
932 rc = mspro_block_set_interface(card, msb->system); 935 rc = mspro_block_set_interface(card, msb->system);
936
937 if (!rc) {
938 msleep(150);
939 rc = mspro_block_wait_for_ced(card);
940 if (rc)
941 return rc;
942
943 if (msb->caps & MEMSTICK_CAP_PAR8) {
944 msb->caps &= ~MEMSTICK_CAP_PAR8;
945 goto try_again;
946 }
947 }
933 } 948 }
934 return rc; 949 return rc;
935} 950}
@@ -1117,14 +1132,16 @@ static int mspro_block_init_card(struct memstick_dev *card)
1117 return -EIO; 1132 return -EIO;
1118 1133
1119 msb->caps = host->caps; 1134 msb->caps = host->caps;
1120 rc = mspro_block_switch_interface(card); 1135
1136 msleep(150);
1137 rc = mspro_block_wait_for_ced(card);
1121 if (rc) 1138 if (rc)
1122 return rc; 1139 return rc;
1123 1140
1124 msleep(200); 1141 rc = mspro_block_switch_interface(card);
1125 rc = mspro_block_wait_for_ced(card);
1126 if (rc) 1142 if (rc)
1127 return rc; 1143 return rc;
1144
1128 dev_dbg(&card->dev, "card activated\n"); 1145 dev_dbg(&card->dev, "card activated\n");
1129 if (msb->system != MEMSTICK_SYS_SERIAL) 1146 if (msb->system != MEMSTICK_SYS_SERIAL)
1130 msb->caps |= MEMSTICK_CAP_AUTO_GET_INT; 1147 msb->caps |= MEMSTICK_CAP_AUTO_GET_INT;
@@ -1192,12 +1209,12 @@ static int mspro_block_init_disk(struct memstick_dev *card)
1192 if (rc) 1209 if (rc)
1193 return rc; 1210 return rc;
1194 1211
1195 if ((disk_id << MEMSTICK_PART_SHIFT) > 255) { 1212 if ((disk_id << MSPRO_BLOCK_PART_SHIFT) > 255) {
1196 rc = -ENOSPC; 1213 rc = -ENOSPC;
1197 goto out_release_id; 1214 goto out_release_id;
1198 } 1215 }
1199 1216
1200 msb->disk = alloc_disk(1 << MEMSTICK_PART_SHIFT); 1217 msb->disk = alloc_disk(1 << MSPRO_BLOCK_PART_SHIFT);
1201 if (!msb->disk) { 1218 if (!msb->disk) {
1202 rc = -ENOMEM; 1219 rc = -ENOMEM;
1203 goto out_release_id; 1220 goto out_release_id;
@@ -1220,7 +1237,7 @@ static int mspro_block_init_disk(struct memstick_dev *card)
1220 MSPRO_BLOCK_MAX_PAGES * msb->page_size); 1237 MSPRO_BLOCK_MAX_PAGES * msb->page_size);
1221 1238
1222 msb->disk->major = major; 1239 msb->disk->major = major;
1223 msb->disk->first_minor = disk_id << MEMSTICK_PART_SHIFT; 1240 msb->disk->first_minor = disk_id << MSPRO_BLOCK_PART_SHIFT;
1224 msb->disk->fops = &ms_block_bdops; 1241 msb->disk->fops = &ms_block_bdops;
1225 msb->usage_count = 1; 1242 msb->usage_count = 1;
1226 msb->disk->private_data = msb; 1243 msb->disk->private_data = msb;
@@ -1416,7 +1433,7 @@ out_unlock:
1416 1433
1417static struct memstick_device_id mspro_block_id_tbl[] = { 1434static struct memstick_device_id mspro_block_id_tbl[] = {
1418 {MEMSTICK_MATCH_ALL, MEMSTICK_TYPE_PRO, MEMSTICK_CATEGORY_STORAGE_DUO, 1435 {MEMSTICK_MATCH_ALL, MEMSTICK_TYPE_PRO, MEMSTICK_CATEGORY_STORAGE_DUO,
1419 MEMSTICK_CLASS_GENERIC_DUO}, 1436 MEMSTICK_CLASS_DUO},
1420 {} 1437 {}
1421}; 1438};
1422 1439
diff --git a/drivers/memstick/host/jmb38x_ms.c b/drivers/memstick/host/jmb38x_ms.c
index 3485c63d20b0..2fb95a5b72eb 100644
--- a/drivers/memstick/host/jmb38x_ms.c
+++ b/drivers/memstick/host/jmb38x_ms.c
@@ -81,6 +81,8 @@ struct jmb38x_ms {
81#define TPC_CODE_SZ_MASK 0x00000700 81#define TPC_CODE_SZ_MASK 0x00000700
82#define TPC_DATA_SZ_MASK 0x00000007 82#define TPC_DATA_SZ_MASK 0x00000007
83 83
84#define HOST_CONTROL_TDELAY_EN 0x00040000
85#define HOST_CONTROL_HW_OC_P 0x00010000
84#define HOST_CONTROL_RESET_REQ 0x00008000 86#define HOST_CONTROL_RESET_REQ 0x00008000
85#define HOST_CONTROL_REI 0x00004000 87#define HOST_CONTROL_REI 0x00004000
86#define HOST_CONTROL_LED 0x00000400 88#define HOST_CONTROL_LED 0x00000400
@@ -88,6 +90,7 @@ struct jmb38x_ms {
88#define HOST_CONTROL_RESET 0x00000100 90#define HOST_CONTROL_RESET 0x00000100
89#define HOST_CONTROL_POWER_EN 0x00000080 91#define HOST_CONTROL_POWER_EN 0x00000080
90#define HOST_CONTROL_CLOCK_EN 0x00000040 92#define HOST_CONTROL_CLOCK_EN 0x00000040
93#define HOST_CONTROL_REO 0x00000008
91#define HOST_CONTROL_IF_SHIFT 4 94#define HOST_CONTROL_IF_SHIFT 4
92 95
93#define HOST_CONTROL_IF_SERIAL 0x0 96#define HOST_CONTROL_IF_SERIAL 0x0
@@ -133,11 +136,15 @@ struct jmb38x_ms {
133#define PAD_PU_PD_ON_MS_SOCK1 0x0f0f0000 136#define PAD_PU_PD_ON_MS_SOCK1 0x0f0f0000
134 137
135#define CLOCK_CONTROL_40MHZ 0x00000001 138#define CLOCK_CONTROL_40MHZ 0x00000001
136#define CLOCK_CONTROL_50MHZ 0x00000002 139#define CLOCK_CONTROL_50MHZ 0x0000000a
137#define CLOCK_CONTROL_60MHZ 0x00000008 140#define CLOCK_CONTROL_60MHZ 0x00000008
138#define CLOCK_CONTROL_62_5MHZ 0x0000000c 141#define CLOCK_CONTROL_62_5MHZ 0x0000000c
139#define CLOCK_CONTROL_OFF 0x00000000 142#define CLOCK_CONTROL_OFF 0x00000000
140 143
144#define PCI_CTL_CLOCK_DLY_ADDR 0x000000b0
145#define PCI_CTL_CLOCK_DLY_MASK_A 0x00000f00
146#define PCI_CTL_CLOCK_DLY_MASK_B 0x0000f000
147
141enum { 148enum {
142 CMD_READY = 0x01, 149 CMD_READY = 0x01,
143 FIFO_READY = 0x02, 150 FIFO_READY = 0x02,
@@ -367,8 +374,7 @@ static int jmb38x_ms_issue_cmd(struct memstick_host *msh)
367 return host->req->error; 374 return host->req->error;
368 } 375 }
369 376
370 dev_dbg(&msh->dev, "control %08x\n", 377 dev_dbg(&msh->dev, "control %08x\n", readl(host->addr + HOST_CONTROL));
371 readl(host->addr + HOST_CONTROL));
372 dev_dbg(&msh->dev, "status %08x\n", readl(host->addr + INT_STATUS)); 378 dev_dbg(&msh->dev, "status %08x\n", readl(host->addr + INT_STATUS));
373 dev_dbg(&msh->dev, "hstatus %08x\n", readl(host->addr + STATUS)); 379 dev_dbg(&msh->dev, "hstatus %08x\n", readl(host->addr + STATUS));
374 380
@@ -637,7 +643,7 @@ static int jmb38x_ms_reset(struct jmb38x_ms_host *host)
637 ndelay(20); 643 ndelay(20);
638 } 644 }
639 dev_dbg(&host->chip->pdev->dev, "reset_req timeout\n"); 645 dev_dbg(&host->chip->pdev->dev, "reset_req timeout\n");
640 return -EIO; 646 /* return -EIO; */
641 647
642reset_next: 648reset_next:
643 writel(HOST_CONTROL_RESET | HOST_CONTROL_CLOCK_EN 649 writel(HOST_CONTROL_RESET | HOST_CONTROL_CLOCK_EN
@@ -680,7 +686,9 @@ static int jmb38x_ms_set_param(struct memstick_host *msh,
680 686
681 host_ctl = 7; 687 host_ctl = 7;
682 host_ctl |= HOST_CONTROL_POWER_EN 688 host_ctl |= HOST_CONTROL_POWER_EN
683 | HOST_CONTROL_CLOCK_EN; 689 | HOST_CONTROL_CLOCK_EN
690 | HOST_CONTROL_HW_OC_P
691 | HOST_CONTROL_TDELAY_EN;
684 writel(host_ctl, host->addr + HOST_CONTROL); 692 writel(host_ctl, host->addr + HOST_CONTROL);
685 693
686 writel(host->id ? PAD_PU_PD_ON_MS_SOCK1 694 writel(host->id ? PAD_PU_PD_ON_MS_SOCK1
@@ -704,33 +712,40 @@ static int jmb38x_ms_set_param(struct memstick_host *msh,
704 break; 712 break;
705 case MEMSTICK_INTERFACE: 713 case MEMSTICK_INTERFACE:
706 host_ctl &= ~(3 << HOST_CONTROL_IF_SHIFT); 714 host_ctl &= ~(3 << HOST_CONTROL_IF_SHIFT);
715 pci_read_config_dword(host->chip->pdev,
716 PCI_CTL_CLOCK_DLY_ADDR,
717 &clock_delay);
718 clock_delay &= host->id ? ~PCI_CTL_CLOCK_DLY_MASK_B
719 : ~PCI_CTL_CLOCK_DLY_MASK_A;
707 720
708 if (value == MEMSTICK_SERIAL) { 721 if (value == MEMSTICK_SERIAL) {
709 host_ctl &= ~HOST_CONTROL_FAST_CLK; 722 host_ctl &= ~HOST_CONTROL_FAST_CLK;
723 host_ctl &= ~HOST_CONTROL_REO;
710 host_ctl |= HOST_CONTROL_IF_SERIAL 724 host_ctl |= HOST_CONTROL_IF_SERIAL
711 << HOST_CONTROL_IF_SHIFT; 725 << HOST_CONTROL_IF_SHIFT;
712 host_ctl |= HOST_CONTROL_REI; 726 host_ctl |= HOST_CONTROL_REI;
713 clock_ctl = CLOCK_CONTROL_40MHZ; 727 clock_ctl = CLOCK_CONTROL_40MHZ;
714 clock_delay = 0;
715 } else if (value == MEMSTICK_PAR4) { 728 } else if (value == MEMSTICK_PAR4) {
716 host_ctl |= HOST_CONTROL_FAST_CLK; 729 host_ctl |= HOST_CONTROL_FAST_CLK | HOST_CONTROL_REO;
717 host_ctl |= HOST_CONTROL_IF_PAR4 730 host_ctl |= HOST_CONTROL_IF_PAR4
718 << HOST_CONTROL_IF_SHIFT; 731 << HOST_CONTROL_IF_SHIFT;
719 host_ctl &= ~HOST_CONTROL_REI; 732 host_ctl &= ~HOST_CONTROL_REI;
720 clock_ctl = CLOCK_CONTROL_40MHZ; 733 clock_ctl = CLOCK_CONTROL_40MHZ;
721 clock_delay = 4; 734 clock_delay |= host->id ? (4 << 12) : (4 << 8);
722 } else if (value == MEMSTICK_PAR8) { 735 } else if (value == MEMSTICK_PAR8) {
723 host_ctl |= HOST_CONTROL_FAST_CLK; 736 host_ctl |= HOST_CONTROL_FAST_CLK;
724 host_ctl |= HOST_CONTROL_IF_PAR8 737 host_ctl |= HOST_CONTROL_IF_PAR8
725 << HOST_CONTROL_IF_SHIFT; 738 << HOST_CONTROL_IF_SHIFT;
726 host_ctl &= ~HOST_CONTROL_REI; 739 host_ctl &= ~(HOST_CONTROL_REI | HOST_CONTROL_REO);
727 clock_ctl = CLOCK_CONTROL_60MHZ; 740 clock_ctl = CLOCK_CONTROL_50MHZ;
728 clock_delay = 0;
729 } else 741 } else
730 return -EINVAL; 742 return -EINVAL;
743
731 writel(host_ctl, host->addr + HOST_CONTROL); 744 writel(host_ctl, host->addr + HOST_CONTROL);
732 writel(clock_ctl, host->addr + CLOCK_CONTROL); 745 writel(clock_ctl, host->addr + CLOCK_CONTROL);
733 writel(clock_delay, host->addr + CLOCK_DELAY); 746 pci_write_config_dword(host->chip->pdev,
747 PCI_CTL_CLOCK_DLY_ADDR,
748 clock_delay);
734 break; 749 break;
735 }; 750 };
736 return 0; 751 return 0;