Exemplo n.º 1
0
int mmc_boot_up(int id, int reset)
{
    int err = MMC_ERR_FAILED;
    struct mmc_host *host;

    host = mmc_get_host(id);
    mmc_init_host(host, id);

    msdc_emmc_boot_reset(host, reset);
    
    err = msdc_emmc_boot_start(host, 25000000, 0, EMMC_BOOT_RST_CMD_MODE, 0);
    if (err) {
        printf("[EMMC] Boot Error: %d\n", err);
        goto done;
    }
    err = msdc_emmc_boot_read(host, 128 * 1024, MMC_BUF_ADDR);
    msdc_emmc_boot_stop(host, EMMC_BOOT_RST_CMD_MODE);
done:
    if (!err) {
        int i, j;
        char *buf = MMC_BUF_ADDR;
        for (i = 0; i < 16; i++) {            
            for (j = 0; j < MMC_BLOCK_SIZE; j++) {
                if (j % 16 == 0)
                    printf("\n%.8xh: ", i * MMC_BLOCK_SIZE + j);
                printf("%.2x ",  buf[j]);
            }
            printf("\n");
            buf += MMC_BLOCK_SIZE;
        }
    }
    return err;
}
Exemplo n.º 2
0
int mmc_readback_blks(int dev_id, unsigned long addr, int blks, int bootarea)
{
    int i, j, result = 0;
    u8 val;
    u8 *ext_csd;
    unsigned long blknr = addr / MMC_BLOCK_SIZE;
    unsigned char *buf = (unsigned char*)MMC_BUF_ADDR;
    struct mmc_card *card;
    struct mmc_host *host;

    host = mmc_get_host(dev_id);
    card = mmc_get_card(dev_id);
    ext_csd = &card->raw_ext_csd[0];

    if (bootarea && !mmc_card_sd(card)) {
        /* configure to specified partition */
        val = (ext_csd[EXT_CSD_PART_CFG] & ~0x7) | EXT_CSD_PART_CFG_BOOT_PART_1;
        if (mmc_set_part_config(card, val) != MMC_ERR_NONE) {
            result = -__LINE__;
            goto done;
        }
        if (mmc_read_ext_csd(host, card) != MMC_ERR_NONE) {
            result = -__LINE__;
            goto done;
        }
    }

    printf("[SD%d] Dump %d blks from 0x%x (FLASH)\n", dev_id, blks, 
        blknr * MMC_BLOCK_SIZE);
    for (i = 0; i < blks; i++) {
        memset(buf, 0, MMC_BLOCK_SIZE);
        if (MMC_ERR_NONE != mmc_block_read(dev_id, blknr + i, 1, (unsigned long*)buf)) {
            printf("\n[SD%d] Read from %dth block error\n", dev_id, blknr + i);
            break;
        }
        
        for (j = 0; j < MMC_BLOCK_SIZE; j++) {
            if (j % 16 == 0)
                printf("\n%xh: ", (blknr + i) * MMC_BLOCK_SIZE + j);
            printf("%x ",  buf[j]);
        }
        printf("\n");
        buf += MMC_BLOCK_SIZE;
    }
done:

    if (bootarea && !mmc_card_sd(card)) {
        /* configure to user partition */
        val = (ext_csd[EXT_CSD_PART_CFG] & ~0x7) | EXT_CSD_PART_CFG_DEFT_PART;
        if (mmc_set_part_config(card, val) != MMC_ERR_NONE)
            result = -__LINE__;
        if (mmc_read_ext_csd(host, card) != MMC_ERR_NONE) {
            result = -__LINE__;
        }
    }  

    return result;
}
Exemplo n.º 3
0
int mmc_boot_up_test(int id, int reset, u32 freq, int in_idle)
{
    int err = MMC_ERR_FAILED;
    struct mmc_host *host;
    struct mmc_card *card;

    host = mmc_get_host(id);
    card = mmc_get_card(id);
    mmc_init_host(host, id);

    if (in_idle) {
        printf("[EMMC] Card is in idle mode \n");
        /* card in idle mode */
        //mmc_go_idle(host);
        mmc_init_card(host, card);
        /* note: requires delay before issue boot reset command */
        mdelay(5);
    } else {
        /* card not in idle mode */
        printf("[EMMC] Card is not in idle mode \n");
    }

    msdc_emmc_boot_reset(host, reset);
    
    err = msdc_emmc_boot_start(host, freq, 0, EMMC_BOOT_RST_CMD_MODE, 0);
    if (err) {
        printf("[EMMC] Boot Error: %d\n", err);
        goto done;
    }
    err = msdc_emmc_boot_read(host, 128 * 1024, MMC_BUF_ADDR);
    msdc_emmc_boot_stop(host, EMMC_BOOT_RST_CMD_MODE);
    if (err) {
        printf("[EMMC] Boot Read Error: %d\n", err);
        goto done;
    }

done:
    if (!err) {
        int i, j;
        char *buf = (char*)MMC_BUF_ADDR;
        for (i = 0; i < 16; i++) {            
            for (j = 0; j < MMC_BLOCK_SIZE; j++) {
                if (j % 16 == 0)
                    printf("\n%xh: ", i * MMC_BLOCK_SIZE + j);
                printf("%x ",  buf[j]);
            }
            printf("\n");
            buf += MMC_BLOCK_SIZE;
        }
    }
    return err;
}
Exemplo n.º 4
0
int mmc_boot_enable(int id, int bootpart)
{
    int err = MMC_ERR_FAILED;
    struct mmc_host *host;
    struct mmc_card *card;

    host = mmc_get_host(id);
    card = mmc_get_card(id);

    err = mmc_boot_config(card, EXT_CSD_PART_CFG_EN_ACK,
        bootpart, EXT_CSD_BOOT_BUS_WIDTH_1, EXT_CSD_BOOT_BUS_MODE_DEFT);
    if (err != 0)
        goto done;
    err = mmc_read_ext_csd(host, card);
done:
    return err;
}
Exemplo n.º 5
0
static int scan(int argc, char *argv[])
{
	int	ret;
	int i;
	struct mmc_cid *cid;
	struct mmc_host *host;

	if (argc > 1) {
		usage();

		return -EINVAL;
	}

	for (i = 0; i < MMC_HOST_NUM; i++) {
		host = mmc_get_host(i);
		if(host == NULL && i == 0) {
			printf("Error: Can't Get MMC Host!\n");
			return -ENODEV;
		}

		if (host == NULL) {
			printf("Scan complete\n");
			break;
		}

		ret = mmc_sd_detect_card(host);
		if (ret < 0) {
			printf("Error: No SD Found!\n");
			return -ENODEV;
		}

		cid = (struct mmc_cid* )(host->card.raw_cid);

		printf("Manufacturer ID: %x\n"
				"OEM/Application ID: %x\n"
				"Product Name: %c%c%c%c%c\n"
				"Product serial number: %x\n",
				cid->mid, cid->oid,cid->pnm[4],
				cid->pnm[3],cid->pnm[2],cid->pnm[1],cid->pnm[0],
				cid->psn);
	}

	return 0;
}
Exemplo n.º 6
0
int mmc_download_part(int dev_id, char *part_name, int bootarea)
{
    int ret = -1;
    struct mmc_card *card;
    struct mmc_host *host;
    part_t *part = mt6573_part_get_partition(part_name);

    mmc_download_addr = 0;
    mmc_download_size = 0;
    mmc_image_addr = 0;

    host = mmc_get_host(dev_id);
    card = mmc_get_card(dev_id);

    if (part) {
        printf("[SD%d] Waiting for '%s' image loading from ICE...\n", dev_id, part_name);
        while (!mmc_download_size); /* Wait for loading image from ICE */
        ret = mmc_download(dev_id, mmc_image_addr, mmc_download_size, 
            part->startblk * BLK_SIZE, bootarea);
        if (ret != 0)
            goto done;
        if (bootarea) {
            /* set reset signal function */
            //ret = mmc_set_reset_func(card, 1);
            //if (ret != 0)
            //    goto done;
            /* set boot config */
            ret = mmc_boot_config(card, EXT_CSD_PART_CFG_EN_ACK,
                EXT_CSD_PART_CFG_EN_BOOT_PART_1, EXT_CSD_BOOT_BUS_WIDTH_1, 
                EXT_CSD_BOOT_BUS_MODE_DEFT);
            if (ret != 0)
                goto done;
            ret = mmc_read_ext_csd(host, card);
        }
    }
done:
    return ret;
}
Exemplo n.º 7
0
int mmc_test_mem_card(struct mmc_test_config *cfg)
{
    int id, count, forever;
    int ret, chk_result, tid = 0, result = 0;
    unsigned int chunks, chunk_blks, left_blks, pass = 0, fail = 0;
    unsigned int total_blks;
    unsigned int i, j;
    unsigned int blksz;
    unsigned int clkhz;    
    char pattern = 0;
    char *buf;
    unsigned long blknr;
    struct mmc_host *host;
    struct mmc_card *card;

    id    = cfg->id;
    count = cfg->count;
    buf   = cfg->buf;
    blknr = cfg->blknr;
    blksz = cfg->blksz;

    chk_result = cfg->chk_result;
    chunk_blks = cfg->chunk_blks;
    total_blks = (cfg->total_size + blksz - 1) / blksz;
    forever    = (count == -1) ? 1 : 0;

    host = mmc_get_host(id);
    card = mmc_get_card(id);

    while (forever || count--) {
        printf("[TST] ==============================================\n");
        printf("[TST] BEGIN: %d/%d, No Stop(%d)\n", 
            (cfg->count != -1) ? cfg->count - count : 0, 
            (cfg->count != -1) ? cfg->count : 0, forever);
        printf("[TST] ----------------------------------------------\n");
        printf("[TST] Mode    : %d\n", cfg->mode);
        printf("[TST] Clock   : %d kHz\n", cfg->clock / 1000);
        printf("[TST] BusWidth: %d bits\n", cfg->buswidth);
        printf("[TST] BurstSz : %d bytes\n", 0x1 << cfg->burstsz);
        printf("[TST] BlkAddr : %xh\n", blknr);
        printf("[TST] BlkSize : %dbytes\n", blksz);
        printf("[TST] TstBlks : %d\n", total_blks);
#if defined(BB_MT6575)
        printf("[TST] AutoCMD : 12(%d), 23(%d)\n", 
            (cfg->autocmd & MSDC_AUTOCMD12) ? 1 : 0, 
            (cfg->autocmd & MSDC_AUTOCMD23) ? 1 : 0);
#endif
        printf("[TST] ----------------------------------------------\n");


        if (mmc_init_host(host, id) != 0) {
            result = -__LINE__;
            goto failure;
        }
        if (mmc_init_card(host, card) != 0) {
            result = -__LINE__;
            goto failure;
        }
#if defined(BB_MT6575)
        msdc_set_dma(host, (u8)cfg->burstsz, (u32)cfg->flags);
        msdc_set_autocmd(host, cfg->autocmd, 1);
#endif

        /* change uhs-1 mode */
#if 0        
        if (mmc_card_uhs1(card)) {
            if (mmc_switch_uhs1(host, card, cfg->uhsmode) != 0) {
                result = -__LINE__;
                goto failure;
            }
        }
#endif

        /* change clock */
        if (cfg->clock) {
            clkhz = card->maxhz < cfg->clock ? card->maxhz : cfg->clock;
            mmc_set_clock(host, mmc_card_ddr(card), clkhz); 
        }
        if (mmc_card_sd(card) && cfg->buswidth == HOST_BUS_WIDTH_8) {
            printf("[TST] SD card doesn't support 8-bit bus width (SKIP)\n");
            result = MMC_ERR_NONE;
        }
        if (mmc_set_bus_width(host, card, cfg->buswidth) != 0) {
            result = -__LINE__;
            goto failure;
        }

        /* cmd16 is illegal while card is in ddr mode */
        if (!(mmc_card_mmc(card) && mmc_card_ddr(card))) {
            if (mmc_set_blk_length(host, blksz) != 0) {
                result = -__LINE__;
                goto failure;            
            }
        }

#if defined(BB_MT6575)
        if (cfg->piobits) {
            printf("[TST] PIO bits: %d\n", cfg->piobits);
            msdc_set_pio_bits(host, cfg->piobits);
        }
#endif
        tid = result = 0;        

        if (mmc_erase_start(card, blknr * blksz) != MMC_ERR_NONE) {
            result = -__LINE__;
            goto failure;
        }
        if (mmc_erase_end(card, (blknr + total_blks) * blksz) != MMC_ERR_NONE) {
            result = -__LINE__;
            goto failure;
        }
        if (mmc_erase(card, MMC_ERASE_NORMAL) != MMC_ERR_NONE) {
            result = -__LINE__;
            goto failure;        
        }
        printf("[TST] 0x%x - 0x%x Erased\n", blknr * blksz, 
            (blknr + total_blks) * blksz);

        mmc_send_status(host, card, &status);

        if (cfg->tst_single) {
            /* single block write */
            for (i = 0; i < total_blks; i++) {
                pattern = (i + count) % 256;
                memset(buf, pattern, blksz);
                ret = mmc_block_write(id, blknr + i, 1, (unsigned long*)buf);
                if (ret != MMC_ERR_NONE) {
                    printf("test single block write failed (%d)\n", i);
                    result = -__LINE__;
                    goto failure;
                }
            }

            printf(TC_MSG, host->id, result == 0 ? "PASS" : "FAIL", tid++, 
                "test single block write\n");

            if (result)
                break;
            
            /* single block read */
            for (i = 0; i < total_blks && !result; i++) {
                pattern = (i + count) % 256;
                /* populate buffer with different pattern */
                memset(buf, pattern + 1, blksz);
                ret = mmc_block_read(id, blknr + i, 1, (unsigned long*)buf);
                if (ret != MMC_ERR_NONE) {
                    result = -__LINE__;
                    goto failure;
                }
                if (chk_result) {
                    for (j = 0; j < blksz; j++) {
                        if (buf[j] != pattern) {
                            result = -__LINE__;
                            goto failure;
                        }
                    }
                }
            }
            printf(TC_MSG, host->id, result == 0 ? "PASS" : "FAIL", tid++, 
                "test single block read\n");

            if (result) {
                printf("[SD%d]\t\tread back pattern(0x%.2x) failed\n", 
                    id, pattern);
                goto failure;
            }
        }

        mmc_send_status(host, card, &status);
        
        if (cfg->tst_multiple) {
            /* multiple block write */
            chunks = total_blks / chunk_blks;
            left_blks = total_blks % chunk_blks;   
            for (i = 0; i < chunks; i++) {
                pattern = (i + count) % 256;
                memset(buf, pattern, blksz * chunk_blks);
                ret = mmc_block_write(id, blknr + i * chunk_blks, 
                    chunk_blks, (unsigned long*)buf);
                if (ret != MMC_ERR_NONE) {
                    result = -__LINE__;
                    goto failure;
                }
            }
            
            if (!result && left_blks) {
                pattern = (i + count) % 256;
                memset(buf, pattern, blksz * left_blks);
                ret = mmc_block_write(id, blknr + chunks * chunk_blks, 
                    left_blks, (unsigned long*)buf);
                if (ret != MMC_ERR_NONE) {
                    result = -__LINE__;
                    goto failure;
                }
            }

            printf(TC_MSG, host->id, result == 0 ? "PASS" : "FAIL", tid++, 
                "test multiple block write\n");

            if (result)
                goto failure;

            /* multiple block read */
            for (i = 0; i < chunks; i++) {
                pattern = (i + count) % 256;
                /* populate buffer with different pattern */
                memset(buf, pattern + 1, blksz);
                ret = mmc_block_read(id, blknr + i * chunk_blks, 
                    chunk_blks, (unsigned long*)buf);
                if (ret != MMC_ERR_NONE) {
                    printf("[SD%d]\t\tread %d blks failed(ret = %d blks)\n",
                        host->id, chunk_blks, ret);
                    result = -__LINE__;
                    goto failure;
                }
                if (chk_result) {
                    for (j = 0; j < chunk_blks * blksz; j++) {
                        if (buf[j] == pattern)
                            continue;
                        result = -__LINE__;
                        printf("[SD%d]\t\t%xh = %x (!= %x)\n",
                            host->id, blknr + i * chunk_blks + j, buf[j], pattern);
                        goto failure;
                    }
                }
            }

            if (!result && left_blks) {
                pattern = i % 256;
                /* populate buffer with different pattern */
                memset(buf, pattern + 1, blksz);
                ret = mmc_block_read(id, blknr + chunks * chunk_blks, 
                    left_blks, (unsigned long*)buf);
                if (ret != MMC_ERR_NONE) {
                    printf("[SD%d]\t\tread %d blks failed(ret = %d blks)\n",
                        host->id, left_blks, ret);
                    result = -__LINE__;
                    goto failure;
                }
                if (chk_result) {
                    for (j = 0; j < left_blks * blksz; j++) {
                        if (buf[j] == pattern)
                            continue;
                        printf("[SD%d]\t\t%xh = %x (!= %x)\n",
                            host->id, blknr + chunks * chunk_blks + j, buf[j], pattern);
                        result = -__LINE__;
                        goto failure;
                    }
                }
            }

            printf(TC_MSG, host->id, result == 0 ? "PASS" : "FAIL", tid++, 
                "test multiple block read\n");

            if (result)
                goto failure;
        }

        mmc_send_status(host, card, &status);

        if (cfg->tst_interleave) {
            /* multiple block write */
            chunks = total_blks / chunk_blks;
            left_blks = total_blks % chunk_blks;   
            for (i = 0; i < chunks; i++) {
                pattern = (i + count) % 256;
                memset(buf, pattern, blksz * chunk_blks);
                ret = mmc_block_write(id, blknr + i * chunk_blks, 
                    chunk_blks, (unsigned long*)buf);
                if (ret != MMC_ERR_NONE) {
                    result = -__LINE__;
                    goto failure;
                }

                /* populate buffer with different pattern */
                memset(buf, pattern + 1, blksz * chunk_blks);
                ret = mmc_block_read(id, blknr + i * chunk_blks, 
                    chunk_blks, (unsigned long*)buf);
                if (ret != MMC_ERR_NONE) {
                    result = -__LINE__;
                    goto failure;
                }
                if (chk_result) {
                    for (j = 0; j < chunk_blks * blksz; j++) {
                        if (buf[j] == pattern) 
                            continue;
                        result = -__LINE__;
                        goto failure;
                    }
                }                
            }           

            if (!result && left_blks) {
                pattern = (i + count) % 256;
                memset(buf, pattern, blksz * left_blks);
                ret = mmc_block_write(id, blknr + chunks * chunk_blks, 
                    left_blks, (unsigned long*)buf);
                if (ret != MMC_ERR_NONE) {
                    result = -__LINE__;
                    goto failure;
                }

                /* populate buffer with different pattern */
                memset(buf, pattern + 1, blksz * left_blks);
                ret = mmc_block_read(id, blknr + chunks * chunk_blks, 
                    left_blks, (unsigned long*)buf);
                if (ret != MMC_ERR_NONE) {
                    result = -__LINE__;
                    break;
                }
                if (chk_result) {
                    for (j = 0; j < left_blks * blksz; j++) {
                        if (buf[j] == pattern)
                            continue;
                        result = -__LINE__;
                        goto failure;
                    }
                }
            }

            printf(TC_MSG, host->id, result == 0 ? "PASS" : "FAIL", tid++, 
                "test multiple block interleave write-read\n");

            if (result)
                goto failure;
        }
        if (cfg->desc) {
            printf("[TST] ----------------------------------------------\n");
            printf("[TST] Report - %s \n", cfg->desc);
            printf("[TST] ----------------------------------------------\n");
        }
        mmc_prof_dump(id);

failure:
        if (result) {
            printf("[SD%d] mmc test failed (%d)\n", host->id, result);
            fail++;
        } else {
            pass++;
        }
        printf("[TST] ----------------------------------------------\n");
        printf("[TST] Test Result: TOTAL(%d/%d), PASS(%d), FAIL(%d) \n", 
            cfg->count - count, cfg->count, pass, fail);
        printf("[TST] ----------------------------------------------\n");    
    	//mdelay(1000);
    }

    return result;
}