blob: cf4ea161b964ab36c8b4da95d9f3d209d9ca66be [file] [log] [blame]
Andy Fleming272cc702008-10-30 16:41:01 -05001/*
2 * Copyright 2008, Freescale Semiconductor, Inc
3 * Andy Fleming
4 *
5 * Based vaguely on the Linux code
6 *
7 * See file CREDITS for list of people who contributed to this
8 * project.
9 *
10 * This program is free software; you can redistribute it and/or
11 * modify it under the terms of the GNU General Public License as
12 * published by the Free Software Foundation; either version 2 of
13 * the License, or (at your option) any later version.
14 *
15 * This program is distributed in the hope that it will be useful,
16 * but WITHOUT ANY WARRANTY; without even the implied warranty of
17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 * GNU General Public License for more details.
19 *
20 * You should have received a copy of the GNU General Public License
21 * along with this program; if not, write to the Free Software
22 * Foundation, Inc., 59 Temple Place, Suite 330, Boston,
23 * MA 02111-1307 USA
24 */
25
26#include <config.h>
27#include <common.h>
28#include <command.h>
29#include <mmc.h>
30#include <part.h>
31#include <malloc.h>
32#include <linux/list.h>
33#include <mmc.h>
Rabin Vincent9b1f9422009-04-05 13:30:54 +053034#include <div64.h>
Andy Fleming272cc702008-10-30 16:41:01 -050035
36static struct list_head mmc_devices;
37static int cur_dev_num = -1;
38
Stefano Babic11fdade2010-02-05 15:04:43 +010039int __board_mmc_getcd(u8 *cd, struct mmc *mmc) {
40 return -1;
41}
42
43int board_mmc_getcd(u8 *cd, struct mmc *mmc)__attribute__((weak,
44 alias("__board_mmc_getcd")));
45
Andy Fleming272cc702008-10-30 16:41:01 -050046int mmc_send_cmd(struct mmc *mmc, struct mmc_cmd *cmd, struct mmc_data *data)
47{
48 return mmc->send_cmd(mmc, cmd, data);
49}
50
51int mmc_set_blocklen(struct mmc *mmc, int len)
52{
53 struct mmc_cmd cmd;
54
55 cmd.cmdidx = MMC_CMD_SET_BLOCKLEN;
56 cmd.resp_type = MMC_RSP_R1;
57 cmd.cmdarg = len;
58 cmd.flags = 0;
59
60 return mmc_send_cmd(mmc, &cmd, NULL);
61}
62
63struct mmc *find_mmc_device(int dev_num)
64{
65 struct mmc *m;
66 struct list_head *entry;
67
68 list_for_each(entry, &mmc_devices) {
69 m = list_entry(entry, struct mmc, link);
70
71 if (m->block_dev.dev == dev_num)
72 return m;
73 }
74
75 printf("MMC Device %d not found\n", dev_num);
76
77 return NULL;
78}
79
80static ulong
81mmc_bwrite(int dev_num, ulong start, lbaint_t blkcnt, const void*src)
82{
83 struct mmc_cmd cmd;
84 struct mmc_data data;
85 int err;
86 int stoperr = 0;
87 struct mmc *mmc = find_mmc_device(dev_num);
88 int blklen;
89
90 if (!mmc)
91 return -1;
92
93 blklen = mmc->write_bl_len;
94
95 err = mmc_set_blocklen(mmc, mmc->write_bl_len);
96
97 if (err) {
98 printf("set write bl len failed\n\r");
99 return err;
100 }
101
102 if (blkcnt > 1)
103 cmd.cmdidx = MMC_CMD_WRITE_MULTIPLE_BLOCK;
104 else
105 cmd.cmdidx = MMC_CMD_WRITE_SINGLE_BLOCK;
106
107 if (mmc->high_capacity)
108 cmd.cmdarg = start;
109 else
110 cmd.cmdarg = start * blklen;
111
112 cmd.resp_type = MMC_RSP_R1;
113 cmd.flags = 0;
114
115 data.src = src;
116 data.blocks = blkcnt;
117 data.blocksize = blklen;
118 data.flags = MMC_DATA_WRITE;
119
120 err = mmc_send_cmd(mmc, &cmd, &data);
121
122 if (err) {
123 printf("mmc write failed\n\r");
124 return err;
125 }
126
127 if (blkcnt > 1) {
128 cmd.cmdidx = MMC_CMD_STOP_TRANSMISSION;
129 cmd.cmdarg = 0;
130 cmd.resp_type = MMC_RSP_R1b;
131 cmd.flags = 0;
132 stoperr = mmc_send_cmd(mmc, &cmd, NULL);
133 }
134
135 return blkcnt;
136}
137
138int mmc_read_block(struct mmc *mmc, void *dst, uint blocknum)
139{
140 struct mmc_cmd cmd;
141 struct mmc_data data;
142
143 cmd.cmdidx = MMC_CMD_READ_SINGLE_BLOCK;
144
145 if (mmc->high_capacity)
146 cmd.cmdarg = blocknum;
147 else
148 cmd.cmdarg = blocknum * mmc->read_bl_len;
149
150 cmd.resp_type = MMC_RSP_R1;
151 cmd.flags = 0;
152
153 data.dest = dst;
154 data.blocks = 1;
155 data.blocksize = mmc->read_bl_len;
156 data.flags = MMC_DATA_READ;
157
158 return mmc_send_cmd(mmc, &cmd, &data);
159}
160
161int mmc_read(struct mmc *mmc, u64 src, uchar *dst, int size)
162{
163 char *buffer;
164 int i;
165 int blklen = mmc->read_bl_len;
Rabin Vincent9b1f9422009-04-05 13:30:54 +0530166 int startblock = lldiv(src, mmc->read_bl_len);
167 int endblock = lldiv(src + size - 1, mmc->read_bl_len);
Andy Fleming272cc702008-10-30 16:41:01 -0500168 int err = 0;
169
170 /* Make a buffer big enough to hold all the blocks we might read */
171 buffer = malloc(blklen);
172
173 if (!buffer) {
174 printf("Could not allocate buffer for MMC read!\n");
175 return -1;
176 }
177
178 /* We always do full block reads from the card */
179 err = mmc_set_blocklen(mmc, mmc->read_bl_len);
180
181 if (err)
Wolfgang Denk8c4444f2010-03-11 23:35:43 +0100182 goto free_buffer;
Andy Fleming272cc702008-10-30 16:41:01 -0500183
184 for (i = startblock; i <= endblock; i++) {
185 int segment_size;
186 int offset;
187
188 err = mmc_read_block(mmc, buffer, i);
189
190 if (err)
191 goto free_buffer;
192
193 /*
194 * The first block may not be aligned, so we
195 * copy from the desired point in the block
196 */
197 offset = (src & (blklen - 1));
198 segment_size = MIN(blklen - offset, size);
199
200 memcpy(dst, buffer + offset, segment_size);
201
202 dst += segment_size;
203 src += segment_size;
204 size -= segment_size;
205 }
206
207free_buffer:
208 free(buffer);
209
210 return err;
211}
212
213static ulong mmc_bread(int dev_num, ulong start, lbaint_t blkcnt, void *dst)
214{
215 int err;
216 int i;
217 struct mmc *mmc = find_mmc_device(dev_num);
218
219 if (!mmc)
220 return 0;
221
222 /* We always do full block reads from the card */
223 err = mmc_set_blocklen(mmc, mmc->read_bl_len);
224
225 if (err) {
226 return 0;
227 }
228
229 for (i = start; i < start + blkcnt; i++, dst += mmc->read_bl_len) {
230 err = mmc_read_block(mmc, dst, i);
231
232 if (err) {
233 printf("block read failed: %d\n", err);
234 return i - start;
235 }
236 }
237
238 return blkcnt;
239}
240
241int mmc_go_idle(struct mmc* mmc)
242{
243 struct mmc_cmd cmd;
244 int err;
245
246 udelay(1000);
247
248 cmd.cmdidx = MMC_CMD_GO_IDLE_STATE;
249 cmd.cmdarg = 0;
250 cmd.resp_type = MMC_RSP_NONE;
251 cmd.flags = 0;
252
253 err = mmc_send_cmd(mmc, &cmd, NULL);
254
255 if (err)
256 return err;
257
258 udelay(2000);
259
260 return 0;
261}
262
263int
264sd_send_op_cond(struct mmc *mmc)
265{
266 int timeout = 1000;
267 int err;
268 struct mmc_cmd cmd;
269
270 do {
271 cmd.cmdidx = MMC_CMD_APP_CMD;
272 cmd.resp_type = MMC_RSP_R1;
273 cmd.cmdarg = 0;
274 cmd.flags = 0;
275
276 err = mmc_send_cmd(mmc, &cmd, NULL);
277
278 if (err)
279 return err;
280
281 cmd.cmdidx = SD_CMD_APP_SEND_OP_COND;
282 cmd.resp_type = MMC_RSP_R3;
Stefano Babic250de122010-01-20 18:20:39 +0100283
284 /*
285 * Most cards do not answer if some reserved bits
286 * in the ocr are set. However, Some controller
287 * can set bit 7 (reserved for low voltages), but
288 * how to manage low voltages SD card is not yet
289 * specified.
290 */
291 cmd.cmdarg = mmc->voltages & 0xff8000;
Andy Fleming272cc702008-10-30 16:41:01 -0500292
293 if (mmc->version == SD_VERSION_2)
294 cmd.cmdarg |= OCR_HCS;
295
296 err = mmc_send_cmd(mmc, &cmd, NULL);
297
298 if (err)
299 return err;
300
301 udelay(1000);
302 } while ((!(cmd.response[0] & OCR_BUSY)) && timeout--);
303
304 if (timeout <= 0)
305 return UNUSABLE_ERR;
306
307 if (mmc->version != SD_VERSION_2)
308 mmc->version = SD_VERSION_1_0;
309
Rabin Vincent998be3d2009-04-05 13:30:56 +0530310 mmc->ocr = cmd.response[0];
Andy Fleming272cc702008-10-30 16:41:01 -0500311
312 mmc->high_capacity = ((mmc->ocr & OCR_HCS) == OCR_HCS);
313 mmc->rca = 0;
314
315 return 0;
316}
317
318int mmc_send_op_cond(struct mmc *mmc)
319{
320 int timeout = 1000;
321 struct mmc_cmd cmd;
322 int err;
323
324 /* Some cards seem to need this */
325 mmc_go_idle(mmc);
326
327 do {
328 cmd.cmdidx = MMC_CMD_SEND_OP_COND;
329 cmd.resp_type = MMC_RSP_R3;
330 cmd.cmdarg = OCR_HCS | mmc->voltages;
331 cmd.flags = 0;
332
333 err = mmc_send_cmd(mmc, &cmd, NULL);
334
335 if (err)
336 return err;
337
338 udelay(1000);
339 } while (!(cmd.response[0] & OCR_BUSY) && timeout--);
340
341 if (timeout <= 0)
342 return UNUSABLE_ERR;
343
344 mmc->version = MMC_VERSION_UNKNOWN;
Rabin Vincent998be3d2009-04-05 13:30:56 +0530345 mmc->ocr = cmd.response[0];
Andy Fleming272cc702008-10-30 16:41:01 -0500346
347 mmc->high_capacity = ((mmc->ocr & OCR_HCS) == OCR_HCS);
348 mmc->rca = 0;
349
350 return 0;
351}
352
353
354int mmc_send_ext_csd(struct mmc *mmc, char *ext_csd)
355{
356 struct mmc_cmd cmd;
357 struct mmc_data data;
358 int err;
359
360 /* Get the Card Status Register */
361 cmd.cmdidx = MMC_CMD_SEND_EXT_CSD;
362 cmd.resp_type = MMC_RSP_R1;
363 cmd.cmdarg = 0;
364 cmd.flags = 0;
365
366 data.dest = ext_csd;
367 data.blocks = 1;
368 data.blocksize = 512;
369 data.flags = MMC_DATA_READ;
370
371 err = mmc_send_cmd(mmc, &cmd, &data);
372
373 return err;
374}
375
376
377int mmc_switch(struct mmc *mmc, u8 set, u8 index, u8 value)
378{
379 struct mmc_cmd cmd;
380
381 cmd.cmdidx = MMC_CMD_SWITCH;
382 cmd.resp_type = MMC_RSP_R1b;
383 cmd.cmdarg = (MMC_SWITCH_MODE_WRITE_BYTE << 24) |
384 (index << 16) |
385 (value << 8);
386 cmd.flags = 0;
387
388 return mmc_send_cmd(mmc, &cmd, NULL);
389}
390
391int mmc_change_freq(struct mmc *mmc)
392{
393 char ext_csd[512];
394 char cardtype;
395 int err;
396
397 mmc->card_caps = 0;
398
399 /* Only version 4 supports high-speed */
400 if (mmc->version < MMC_VERSION_4)
401 return 0;
402
403 mmc->card_caps |= MMC_MODE_4BIT;
404
405 err = mmc_send_ext_csd(mmc, ext_csd);
406
407 if (err)
408 return err;
409
410 if (ext_csd[212] || ext_csd[213] || ext_csd[214] || ext_csd[215])
411 mmc->high_capacity = 1;
412
413 cardtype = ext_csd[196] & 0xf;
414
415 err = mmc_switch(mmc, EXT_CSD_CMD_SET_NORMAL, EXT_CSD_HS_TIMING, 1);
416
417 if (err)
418 return err;
419
420 /* Now check to see that it worked */
421 err = mmc_send_ext_csd(mmc, ext_csd);
422
423 if (err)
424 return err;
425
426 /* No high-speed support */
427 if (!ext_csd[185])
428 return 0;
429
430 /* High Speed is set, there are two types: 52MHz and 26MHz */
431 if (cardtype & MMC_HS_52MHZ)
432 mmc->card_caps |= MMC_MODE_HS_52MHz | MMC_MODE_HS;
433 else
434 mmc->card_caps |= MMC_MODE_HS;
435
436 return 0;
437}
438
439int sd_switch(struct mmc *mmc, int mode, int group, u8 value, u8 *resp)
440{
441 struct mmc_cmd cmd;
442 struct mmc_data data;
443
444 /* Switch the frequency */
445 cmd.cmdidx = SD_CMD_SWITCH_FUNC;
446 cmd.resp_type = MMC_RSP_R1;
447 cmd.cmdarg = (mode << 31) | 0xffffff;
448 cmd.cmdarg &= ~(0xf << (group * 4));
449 cmd.cmdarg |= value << (group * 4);
450 cmd.flags = 0;
451
452 data.dest = (char *)resp;
453 data.blocksize = 64;
454 data.blocks = 1;
455 data.flags = MMC_DATA_READ;
456
457 return mmc_send_cmd(mmc, &cmd, &data);
458}
459
460
461int sd_change_freq(struct mmc *mmc)
462{
463 int err;
464 struct mmc_cmd cmd;
465 uint scr[2];
466 uint switch_status[16];
467 struct mmc_data data;
468 int timeout;
469
470 mmc->card_caps = 0;
471
472 /* Read the SCR to find out if this card supports higher speeds */
473 cmd.cmdidx = MMC_CMD_APP_CMD;
474 cmd.resp_type = MMC_RSP_R1;
475 cmd.cmdarg = mmc->rca << 16;
476 cmd.flags = 0;
477
478 err = mmc_send_cmd(mmc, &cmd, NULL);
479
480 if (err)
481 return err;
482
483 cmd.cmdidx = SD_CMD_APP_SEND_SCR;
484 cmd.resp_type = MMC_RSP_R1;
485 cmd.cmdarg = 0;
486 cmd.flags = 0;
487
488 timeout = 3;
489
490retry_scr:
491 data.dest = (char *)&scr;
492 data.blocksize = 8;
493 data.blocks = 1;
494 data.flags = MMC_DATA_READ;
495
496 err = mmc_send_cmd(mmc, &cmd, &data);
497
498 if (err) {
499 if (timeout--)
500 goto retry_scr;
501
502 return err;
503 }
504
Yauhen Kharuzhy4e3d89b2009-05-07 00:43:30 +0300505 mmc->scr[0] = __be32_to_cpu(scr[0]);
506 mmc->scr[1] = __be32_to_cpu(scr[1]);
Andy Fleming272cc702008-10-30 16:41:01 -0500507
508 switch ((mmc->scr[0] >> 24) & 0xf) {
509 case 0:
510 mmc->version = SD_VERSION_1_0;
511 break;
512 case 1:
513 mmc->version = SD_VERSION_1_10;
514 break;
515 case 2:
516 mmc->version = SD_VERSION_2;
517 break;
518 default:
519 mmc->version = SD_VERSION_1_0;
520 break;
521 }
522
523 /* Version 1.0 doesn't support switching */
524 if (mmc->version == SD_VERSION_1_0)
525 return 0;
526
527 timeout = 4;
528 while (timeout--) {
529 err = sd_switch(mmc, SD_SWITCH_CHECK, 0, 1,
530 (u8 *)&switch_status);
531
532 if (err)
533 return err;
534
535 /* The high-speed function is busy. Try again */
Yauhen Kharuzhy4e3d89b2009-05-07 00:43:30 +0300536 if (!(__be32_to_cpu(switch_status[7]) & SD_HIGHSPEED_BUSY))
Andy Fleming272cc702008-10-30 16:41:01 -0500537 break;
538 }
539
540 if (mmc->scr[0] & SD_DATA_4BIT)
541 mmc->card_caps |= MMC_MODE_4BIT;
542
543 /* If high-speed isn't supported, we return */
Yauhen Kharuzhy4e3d89b2009-05-07 00:43:30 +0300544 if (!(__be32_to_cpu(switch_status[3]) & SD_HIGHSPEED_SUPPORTED))
Andy Fleming272cc702008-10-30 16:41:01 -0500545 return 0;
546
547 err = sd_switch(mmc, SD_SWITCH_SWITCH, 0, 1, (u8 *)&switch_status);
548
549 if (err)
550 return err;
551
Yauhen Kharuzhy4e3d89b2009-05-07 00:43:30 +0300552 if ((__be32_to_cpu(switch_status[4]) & 0x0f000000) == 0x01000000)
Andy Fleming272cc702008-10-30 16:41:01 -0500553 mmc->card_caps |= MMC_MODE_HS;
554
555 return 0;
556}
557
558/* frequency bases */
559/* divided by 10 to be nice to platforms without floating point */
560int fbase[] = {
561 10000,
562 100000,
563 1000000,
564 10000000,
565};
566
567/* Multiplier values for TRAN_SPEED. Multiplied by 10 to be nice
568 * to platforms without floating point.
569 */
570int multipliers[] = {
571 0, /* reserved */
572 10,
573 12,
574 13,
575 15,
576 20,
577 25,
578 30,
579 35,
580 40,
581 45,
582 50,
583 55,
584 60,
585 70,
586 80,
587};
588
589void mmc_set_ios(struct mmc *mmc)
590{
591 mmc->set_ios(mmc);
592}
593
594void mmc_set_clock(struct mmc *mmc, uint clock)
595{
596 if (clock > mmc->f_max)
597 clock = mmc->f_max;
598
599 if (clock < mmc->f_min)
600 clock = mmc->f_min;
601
602 mmc->clock = clock;
603
604 mmc_set_ios(mmc);
605}
606
607void mmc_set_bus_width(struct mmc *mmc, uint width)
608{
609 mmc->bus_width = width;
610
611 mmc_set_ios(mmc);
612}
613
614int mmc_startup(struct mmc *mmc)
615{
616 int err;
617 uint mult, freq;
618 u64 cmult, csize;
619 struct mmc_cmd cmd;
620
621 /* Put the Card in Identify Mode */
622 cmd.cmdidx = MMC_CMD_ALL_SEND_CID;
623 cmd.resp_type = MMC_RSP_R2;
624 cmd.cmdarg = 0;
625 cmd.flags = 0;
626
627 err = mmc_send_cmd(mmc, &cmd, NULL);
628
629 if (err)
630 return err;
631
632 memcpy(mmc->cid, cmd.response, 16);
633
634 /*
635 * For MMC cards, set the Relative Address.
636 * For SD cards, get the Relatvie Address.
637 * This also puts the cards into Standby State
638 */
639 cmd.cmdidx = SD_CMD_SEND_RELATIVE_ADDR;
640 cmd.cmdarg = mmc->rca << 16;
641 cmd.resp_type = MMC_RSP_R6;
642 cmd.flags = 0;
643
644 err = mmc_send_cmd(mmc, &cmd, NULL);
645
646 if (err)
647 return err;
648
649 if (IS_SD(mmc))
Rabin Vincent998be3d2009-04-05 13:30:56 +0530650 mmc->rca = (cmd.response[0] >> 16) & 0xffff;
Andy Fleming272cc702008-10-30 16:41:01 -0500651
652 /* Get the Card-Specific Data */
653 cmd.cmdidx = MMC_CMD_SEND_CSD;
654 cmd.resp_type = MMC_RSP_R2;
655 cmd.cmdarg = mmc->rca << 16;
656 cmd.flags = 0;
657
658 err = mmc_send_cmd(mmc, &cmd, NULL);
659
660 if (err)
661 return err;
662
Rabin Vincent998be3d2009-04-05 13:30:56 +0530663 mmc->csd[0] = cmd.response[0];
664 mmc->csd[1] = cmd.response[1];
665 mmc->csd[2] = cmd.response[2];
666 mmc->csd[3] = cmd.response[3];
Andy Fleming272cc702008-10-30 16:41:01 -0500667
668 if (mmc->version == MMC_VERSION_UNKNOWN) {
Rabin Vincent0b453ff2009-04-05 13:30:55 +0530669 int version = (cmd.response[0] >> 26) & 0xf;
Andy Fleming272cc702008-10-30 16:41:01 -0500670
671 switch (version) {
672 case 0:
673 mmc->version = MMC_VERSION_1_2;
674 break;
675 case 1:
676 mmc->version = MMC_VERSION_1_4;
677 break;
678 case 2:
679 mmc->version = MMC_VERSION_2_2;
680 break;
681 case 3:
682 mmc->version = MMC_VERSION_3;
683 break;
684 case 4:
685 mmc->version = MMC_VERSION_4;
686 break;
687 default:
688 mmc->version = MMC_VERSION_1_2;
689 break;
690 }
691 }
692
693 /* divide frequency by 10, since the mults are 10x bigger */
Rabin Vincent0b453ff2009-04-05 13:30:55 +0530694 freq = fbase[(cmd.response[0] & 0x7)];
695 mult = multipliers[((cmd.response[0] >> 3) & 0xf)];
Andy Fleming272cc702008-10-30 16:41:01 -0500696
697 mmc->tran_speed = freq * mult;
698
Rabin Vincent998be3d2009-04-05 13:30:56 +0530699 mmc->read_bl_len = 1 << ((cmd.response[1] >> 16) & 0xf);
Andy Fleming272cc702008-10-30 16:41:01 -0500700
701 if (IS_SD(mmc))
702 mmc->write_bl_len = mmc->read_bl_len;
703 else
Rabin Vincent998be3d2009-04-05 13:30:56 +0530704 mmc->write_bl_len = 1 << ((cmd.response[3] >> 22) & 0xf);
Andy Fleming272cc702008-10-30 16:41:01 -0500705
706 if (mmc->high_capacity) {
707 csize = (mmc->csd[1] & 0x3f) << 16
708 | (mmc->csd[2] & 0xffff0000) >> 16;
709 cmult = 8;
710 } else {
711 csize = (mmc->csd[1] & 0x3ff) << 2
712 | (mmc->csd[2] & 0xc0000000) >> 30;
713 cmult = (mmc->csd[2] & 0x00038000) >> 15;
714 }
715
716 mmc->capacity = (csize + 1) << (cmult + 2);
717 mmc->capacity *= mmc->read_bl_len;
718
719 if (mmc->read_bl_len > 512)
720 mmc->read_bl_len = 512;
721
722 if (mmc->write_bl_len > 512)
723 mmc->write_bl_len = 512;
724
725 /* Select the card, and put it into Transfer Mode */
726 cmd.cmdidx = MMC_CMD_SELECT_CARD;
727 cmd.resp_type = MMC_RSP_R1b;
728 cmd.cmdarg = mmc->rca << 16;
729 cmd.flags = 0;
730 err = mmc_send_cmd(mmc, &cmd, NULL);
731
732 if (err)
733 return err;
734
735 if (IS_SD(mmc))
736 err = sd_change_freq(mmc);
737 else
738 err = mmc_change_freq(mmc);
739
740 if (err)
741 return err;
742
743 /* Restrict card's capabilities by what the host can do */
744 mmc->card_caps &= mmc->host_caps;
745
746 if (IS_SD(mmc)) {
747 if (mmc->card_caps & MMC_MODE_4BIT) {
748 cmd.cmdidx = MMC_CMD_APP_CMD;
749 cmd.resp_type = MMC_RSP_R1;
750 cmd.cmdarg = mmc->rca << 16;
751 cmd.flags = 0;
752
753 err = mmc_send_cmd(mmc, &cmd, NULL);
754 if (err)
755 return err;
756
757 cmd.cmdidx = SD_CMD_APP_SET_BUS_WIDTH;
758 cmd.resp_type = MMC_RSP_R1;
759 cmd.cmdarg = 2;
760 cmd.flags = 0;
761 err = mmc_send_cmd(mmc, &cmd, NULL);
762 if (err)
763 return err;
764
765 mmc_set_bus_width(mmc, 4);
766 }
767
768 if (mmc->card_caps & MMC_MODE_HS)
769 mmc_set_clock(mmc, 50000000);
770 else
771 mmc_set_clock(mmc, 25000000);
772 } else {
773 if (mmc->card_caps & MMC_MODE_4BIT) {
774 /* Set the card to use 4 bit*/
775 err = mmc_switch(mmc, EXT_CSD_CMD_SET_NORMAL,
776 EXT_CSD_BUS_WIDTH,
777 EXT_CSD_BUS_WIDTH_4);
778
779 if (err)
780 return err;
781
782 mmc_set_bus_width(mmc, 4);
783 } else if (mmc->card_caps & MMC_MODE_8BIT) {
784 /* Set the card to use 8 bit*/
785 err = mmc_switch(mmc, EXT_CSD_CMD_SET_NORMAL,
786 EXT_CSD_BUS_WIDTH,
787 EXT_CSD_BUS_WIDTH_8);
788
789 if (err)
790 return err;
791
792 mmc_set_bus_width(mmc, 8);
793 }
794
795 if (mmc->card_caps & MMC_MODE_HS) {
796 if (mmc->card_caps & MMC_MODE_HS_52MHz)
797 mmc_set_clock(mmc, 52000000);
798 else
799 mmc_set_clock(mmc, 26000000);
800 } else
801 mmc_set_clock(mmc, 20000000);
802 }
803
804 /* fill in device description */
805 mmc->block_dev.lun = 0;
806 mmc->block_dev.type = 0;
807 mmc->block_dev.blksz = mmc->read_bl_len;
Rabin Vincent9b1f9422009-04-05 13:30:54 +0530808 mmc->block_dev.lba = lldiv(mmc->capacity, mmc->read_bl_len);
Rabin Vincent0b453ff2009-04-05 13:30:55 +0530809 sprintf(mmc->block_dev.vendor, "Man %06x Snr %08x", mmc->cid[0] >> 8,
810 (mmc->cid[2] << 8) | (mmc->cid[3] >> 24));
811 sprintf(mmc->block_dev.product, "%c%c%c%c%c", mmc->cid[0] & 0xff,
812 (mmc->cid[1] >> 24), (mmc->cid[1] >> 16) & 0xff,
813 (mmc->cid[1] >> 8) & 0xff, mmc->cid[1] & 0xff);
814 sprintf(mmc->block_dev.revision, "%d.%d", mmc->cid[2] >> 28,
815 (mmc->cid[2] >> 24) & 0xf);
Andy Fleming272cc702008-10-30 16:41:01 -0500816 init_part(&mmc->block_dev);
817
818 return 0;
819}
820
821int mmc_send_if_cond(struct mmc *mmc)
822{
823 struct mmc_cmd cmd;
824 int err;
825
826 cmd.cmdidx = SD_CMD_SEND_IF_COND;
827 /* We set the bit if the host supports voltages between 2.7 and 3.6 V */
828 cmd.cmdarg = ((mmc->voltages & 0xff8000) != 0) << 8 | 0xaa;
829 cmd.resp_type = MMC_RSP_R7;
830 cmd.flags = 0;
831
832 err = mmc_send_cmd(mmc, &cmd, NULL);
833
834 if (err)
835 return err;
836
Rabin Vincent998be3d2009-04-05 13:30:56 +0530837 if ((cmd.response[0] & 0xff) != 0xaa)
Andy Fleming272cc702008-10-30 16:41:01 -0500838 return UNUSABLE_ERR;
839 else
840 mmc->version = SD_VERSION_2;
841
842 return 0;
843}
844
845int mmc_register(struct mmc *mmc)
846{
847 /* Setup the universal parts of the block interface just once */
848 mmc->block_dev.if_type = IF_TYPE_MMC;
849 mmc->block_dev.dev = cur_dev_num++;
850 mmc->block_dev.removable = 1;
851 mmc->block_dev.block_read = mmc_bread;
852 mmc->block_dev.block_write = mmc_bwrite;
853
854 INIT_LIST_HEAD (&mmc->link);
855
856 list_add_tail (&mmc->link, &mmc_devices);
857
858 return 0;
859}
860
861block_dev_desc_t *mmc_get_dev(int dev)
862{
863 struct mmc *mmc = find_mmc_device(dev);
864
Rabin Vincente85649c2009-04-05 13:30:53 +0530865 return mmc ? &mmc->block_dev : NULL;
Andy Fleming272cc702008-10-30 16:41:01 -0500866}
867
868int mmc_init(struct mmc *mmc)
869{
870 int err;
871
872 err = mmc->init(mmc);
873
874 if (err)
875 return err;
876
Ilya Yanokb86b85e2009-06-29 17:53:16 +0400877 mmc_set_bus_width(mmc, 1);
878 mmc_set_clock(mmc, 1);
879
Andy Fleming272cc702008-10-30 16:41:01 -0500880 /* Reset the Card */
881 err = mmc_go_idle(mmc);
882
883 if (err)
884 return err;
885
886 /* Test for SD version 2 */
887 err = mmc_send_if_cond(mmc);
888
Andy Fleming272cc702008-10-30 16:41:01 -0500889 /* Now try to get the SD card's operating condition */
890 err = sd_send_op_cond(mmc);
891
892 /* If the command timed out, we check for an MMC card */
893 if (err == TIMEOUT) {
894 err = mmc_send_op_cond(mmc);
895
896 if (err) {
897 printf("Card did not respond to voltage select!\n");
898 return UNUSABLE_ERR;
899 }
900 }
901
902 return mmc_startup(mmc);
903}
904
905/*
906 * CPU and board-specific MMC initializations. Aliased function
907 * signals caller to move on
908 */
909static int __def_mmc_init(bd_t *bis)
910{
911 return -1;
912}
913
Peter Tyserf9a109b2009-04-20 11:08:46 -0500914int cpu_mmc_init(bd_t *bis) __attribute__((weak, alias("__def_mmc_init")));
915int board_mmc_init(bd_t *bis) __attribute__((weak, alias("__def_mmc_init")));
Andy Fleming272cc702008-10-30 16:41:01 -0500916
917void print_mmc_devices(char separator)
918{
919 struct mmc *m;
920 struct list_head *entry;
921
922 list_for_each(entry, &mmc_devices) {
923 m = list_entry(entry, struct mmc, link);
924
925 printf("%s: %d", m->name, m->block_dev.dev);
926
927 if (entry->next != &mmc_devices)
928 printf("%c ", separator);
929 }
930
931 printf("\n");
932}
933
934int mmc_initialize(bd_t *bis)
935{
936 INIT_LIST_HEAD (&mmc_devices);
937 cur_dev_num = 0;
938
939 if (board_mmc_init(bis) < 0)
940 cpu_mmc_init(bis);
941
942 print_mmc_devices(',');
943
944 return 0;
945}