xref: /rk3399_rockchip-uboot/test/rockchip/test-storage.c (revision 25fbb41f6739e72525dd4ae75a35dd90ede3426f)
199d14b01SJoseph Chen /*
299d14b01SJoseph Chen  * (C) Copyright 2019 Rockchip Electronics Co., Ltd
399d14b01SJoseph Chen  *
499d14b01SJoseph Chen  * SPDX-License-Identifier:     GPL-2.0+
599d14b01SJoseph Chen  */
699d14b01SJoseph Chen 
799d14b01SJoseph Chen #include <common.h>
8bc18ede0SKever Yang #ifdef CONFIG_DM_RAMDISK
999d14b01SJoseph Chen #include <boot_rkimg.h>
10bc18ede0SKever Yang #endif
1199d14b01SJoseph Chen #include <cli.h>
1299d14b01SJoseph Chen #include <dm.h>
1399d14b01SJoseph Chen #include <environment.h>
1499d14b01SJoseph Chen #include <malloc.h>
1599d14b01SJoseph Chen #include <misc.h>
1654108d04SKever Yang #ifdef CONFIG_RKIMG_BOOTLOADER
1799d14b01SJoseph Chen #include <sysmem.h>
1854108d04SKever Yang #endif
1999d14b01SJoseph Chen #include <linux/ctype.h>
20bc18ede0SKever Yang #ifdef CONFIG_ROCKCHIP_VENDOR_PARTITION
2199d14b01SJoseph Chen #include <asm/arch/vendor.h>
22bc18ede0SKever Yang #endif
2399d14b01SJoseph Chen #include "test-rockchip.h"
2499d14b01SJoseph Chen 
2599d14b01SJoseph Chen #define DEFAULT_STORAGE_RW_PART		"userdata"
blk_get_type_by_name_and_num(char * devtype,int devnum)269cde1b1dSJon Lin static enum if_type blk_get_type_by_name_and_num(char *devtype, int devnum)
27e80ec83dSKever Yang {
28e80ec83dSKever Yang 	int type = -1;
2999d14b01SJoseph Chen 
30e80ec83dSKever Yang 	if (!strcmp(devtype, "mmc"))
31e80ec83dSKever Yang 		type = IF_TYPE_MMC;
329cde1b1dSJon Lin #if defined(CONFIG_RKNAND) || defined(CONFIG_RKNANDC_NAND)
33e80ec83dSKever Yang 	else if (!strcmp(devtype, "rknand"))
34e80ec83dSKever Yang 		type = IF_TYPE_RKNAND;
35bc18ede0SKever Yang #endif
36bc18ede0SKever Yang #ifdef CONFIG_RKSFC_NAND
379cde1b1dSJon Lin 	else if (!strcmp(devtype, "rksfc") && devnum == 0)
38e80ec83dSKever Yang 		type = IF_TYPE_SPINAND;
39bc18ede0SKever Yang #endif
40bc18ede0SKever Yang #ifdef CONFIG_RKSFC_NOR
419cde1b1dSJon Lin 	else if (!strcmp(devtype, "rksfc") && devnum == 1)
42e80ec83dSKever Yang 		type = IF_TYPE_SPINOR;
43bc18ede0SKever Yang #endif
44bc18ede0SKever Yang #ifdef CONFIG_DM_RAMDISK
45e80ec83dSKever Yang 	else if (!strcmp(devtype, "ramdisk"))
46e80ec83dSKever Yang 		type = IF_TYPE_RAMDISK;
47bc18ede0SKever Yang #endif
48bc18ede0SKever Yang #ifdef CONFIG_MTD_BLK
49e80ec83dSKever Yang 	else if (!strcmp(devtype, "mtd"))
50e80ec83dSKever Yang 		type = IF_TYPE_MTD;
51bc18ede0SKever Yang #endif
52*25fbb41fSYifeng Zhao #ifdef CONFIG_SCSI
53*25fbb41fSYifeng Zhao 	else if (!strcmp(devtype, "scsi"))
54*25fbb41fSYifeng Zhao 		type = IF_TYPE_SCSI;
55*25fbb41fSYifeng Zhao #endif
56e80ec83dSKever Yang 	else if (!strcmp(devtype, "usb"))
57e80ec83dSKever Yang 		type = IF_TYPE_USB;
58e80ec83dSKever Yang 
59e80ec83dSKever Yang 	return type;
60e80ec83dSKever Yang }
61e80ec83dSKever Yang 
629cde1b1dSJon Lin #if defined(CONFIG_MMC) ||\
639cde1b1dSJon Lin 	defined(CONFIG_RKNAND) ||\
649cde1b1dSJon Lin 	defined(CONFIG_DM_RAMDISK) ||\
659cde1b1dSJon Lin 	defined(CONFIG_USB_HOST) ||\
669cde1b1dSJon Lin 	defined(CONFIG_RKNANDC_NAND) ||\
679cde1b1dSJon Lin 	defined(CONFIG_RKSFC_NAND) ||\
689cde1b1dSJon Lin 	defined(CONFIG_RKSFC_NOR)
do_test_storage(cmd_tbl_t * cmdtp,int flag,int argc,char * const argv[],const char * devtype,const char * devnum,const char * label)6999d14b01SJoseph Chen static int do_test_storage(cmd_tbl_t *cmdtp, int flag,
7099d14b01SJoseph Chen 			   int argc, char *const argv[],
7199d14b01SJoseph Chen 			   const char *devtype,
7299d14b01SJoseph Chen 			   const char *devnum,
7399d14b01SJoseph Chen 			   const char *label)
7499d14b01SJoseph Chen {
7599d14b01SJoseph Chen 	struct blk_desc *dev_desc;
76474718ffSJoseph Chen 	disk_partition_t part;
7799d14b01SJoseph Chen 	u32 blocks, round, sector;
7899d14b01SJoseph Chen 	char *w_buf, *r_buf;
7999d14b01SJoseph Chen 	char cmd[64];
8099d14b01SJoseph Chen 	int i, ret;
8199d14b01SJoseph Chen 	ulong ts;
8299d14b01SJoseph Chen 
83e80ec83dSKever Yang 	/* 1. Switch to device type/num */
84e80ec83dSKever Yang 	if (devtype && !strcmp(devtype, "usb")) {
85e80ec83dSKever Yang 		if (run_command("usb start", 0)) {
86e80ec83dSKever Yang 			printf("Switch to %s%s failed\n", devtype, devnum);
87e80ec83dSKever Yang 			ret = -ENODEV;
88e80ec83dSKever Yang 			goto err1;
89e80ec83dSKever Yang 		}
90e80ec83dSKever Yang 	} else if (devtype) {
91e80ec83dSKever Yang 		snprintf(cmd, sizeof(cmd), "%s dev %s", devtype, devnum);
92e80ec83dSKever Yang 		if (run_command(cmd, 0)) {
93e80ec83dSKever Yang 			printf("Switch to %s%s failed\n", devtype, devnum);
94e80ec83dSKever Yang 			ret = -ENODEV;
95e80ec83dSKever Yang 			goto err1;
96e80ec83dSKever Yang 		}
97e80ec83dSKever Yang 	}
98e80ec83dSKever Yang 	if (!devtype) {
99e80ec83dSKever Yang 		/* For blk test only */
100bc18ede0SKever Yang #ifdef CONFIG_DM_RAMDISK
10199d14b01SJoseph Chen 		dev_desc = rockchip_get_bootdev();
102bc18ede0SKever Yang #else
103bc18ede0SKever Yang 		printf("%s Not support devtype!\n", __func__);
104bc18ede0SKever Yang 		return -EINVAL;
105bc18ede0SKever Yang #endif
106e80ec83dSKever Yang 	} else {
107e80ec83dSKever Yang 		int if_type;
108e80ec83dSKever Yang 		int num = simple_strtoul(devnum, NULL, 10);
1099cde1b1dSJon Lin 
1109cde1b1dSJon Lin 		if_type = blk_get_type_by_name_and_num((char *)devtype, num);
111e80ec83dSKever Yang 		dev_desc = blk_get_devnum_by_type(if_type, num);
112e80ec83dSKever Yang 	}
11399d14b01SJoseph Chen 	if (!dev_desc) {
114443feaabSJoseph Chen 		ut_err("%s: failed to get blk desc\n", label);
11599d14b01SJoseph Chen 		return -ENODEV;
11699d14b01SJoseph Chen 	}
11799d14b01SJoseph Chen 
118e80ec83dSKever Yang 	/* 2. Get test partition */
11999d14b01SJoseph Chen 	if (part_get_info_by_name(dev_desc,
12099d14b01SJoseph Chen 				  DEFAULT_STORAGE_RW_PART, &part) < 0) {
121443feaabSJoseph Chen 		ut_err("%s: failed to find %s partition\n", label,
122443feaabSJoseph Chen 		       DEFAULT_STORAGE_RW_PART);
12399d14b01SJoseph Chen 		return -EINVAL;
12499d14b01SJoseph Chen 	}
12599d14b01SJoseph Chen 
12699d14b01SJoseph Chen 	/* 32MB */
12799d14b01SJoseph Chen 	sector = part.start;
1289cde1b1dSJon Lin 	if (part.start + part.size > dev_desc->lba)
1299cde1b1dSJon Lin 		part.size = dev_desc->lba - part.start;
13099d14b01SJoseph Chen 	blocks = part.size > 0x10000 ? 0x10000 : part.size;
13199d14b01SJoseph Chen 	round  = 4;
13299d14b01SJoseph Chen 
13399d14b01SJoseph Chen 	/* Round up */
13499d14b01SJoseph Chen 	if (blocks % 2)
13599d14b01SJoseph Chen 		blocks += 1;
13699d14b01SJoseph Chen 
13799d14b01SJoseph Chen 	printf("%s RW sectors on %s 0x%08x - 0x%08x(size: %ld MiB) for %d round\n\n",
138474718ffSJoseph Chen 	       label, DEFAULT_STORAGE_RW_PART,
13999d14b01SJoseph Chen 	       sector, sector + blocks,
14099d14b01SJoseph Chen 	       (blocks * dev_desc->blksz) >> 20, round);
14199d14b01SJoseph Chen 
14299d14b01SJoseph Chen 	/* 3. Prepare memory */
14354108d04SKever Yang #ifdef CONFIG_RKIMG_BOOTLOADER
14499d14b01SJoseph Chen 	w_buf = sysmem_alloc_by_name("storage_w", blocks * dev_desc->blksz);
14554108d04SKever Yang #else
14654108d04SKever Yang 	w_buf = memalign(CONFIG_SYS_CACHELINE_SIZE, blocks * dev_desc->blksz);
14754108d04SKever Yang #endif
14899d14b01SJoseph Chen 	if (!w_buf) {
149443feaabSJoseph Chen 		ut_err("%s: no sysmem for w_buf\n", label);
15099d14b01SJoseph Chen 		ret = -ENOMEM;
15199d14b01SJoseph Chen 		goto err1;
15299d14b01SJoseph Chen 	}
15354108d04SKever Yang #ifdef CONFIG_RKIMG_BOOTLOADER
15499d14b01SJoseph Chen 	r_buf = sysmem_alloc_by_name("storage_r", blocks * dev_desc->blksz);
15554108d04SKever Yang #else
15654108d04SKever Yang 	r_buf = memalign(CONFIG_SYS_CACHELINE_SIZE, blocks * dev_desc->blksz);
15754108d04SKever Yang #endif
15899d14b01SJoseph Chen 	if (!r_buf) {
159443feaabSJoseph Chen 		ut_err("%s: no sysmem for r_buf\n", label);
16099d14b01SJoseph Chen 		ret = -ENOMEM;
16199d14b01SJoseph Chen 		goto err2;
16299d14b01SJoseph Chen 	}
16399d14b01SJoseph Chen 
16499d14b01SJoseph Chen 	for (i = 0; i < blocks * dev_desc->blksz; i++) {
16599d14b01SJoseph Chen 		w_buf[i] = i;
16699d14b01SJoseph Chen 		r_buf[i] = 0;
16799d14b01SJoseph Chen 	}
16899d14b01SJoseph Chen 
16999d14b01SJoseph Chen 	/* 4. Write test */
17099d14b01SJoseph Chen 	ts = get_timer(0);
17199d14b01SJoseph Chen 	if (devtype) {
17299d14b01SJoseph Chen 		snprintf(cmd, sizeof(cmd), "%s write 0x%x 0x%x 0x%x",
17399d14b01SJoseph Chen 			 devtype, (u32)(ulong)w_buf, sector, blocks);
17499d14b01SJoseph Chen 		for (i = 0; i < round; i++) {
17599d14b01SJoseph Chen 			if (run_command(cmd, 0)) {
176443feaabSJoseph Chen 				ut_err("%s: failed to write @%d round\n", label, i);
17799d14b01SJoseph Chen 				ret = -EIO;
17899d14b01SJoseph Chen 				goto err3;
17999d14b01SJoseph Chen 			}
18099d14b01SJoseph Chen 		}
18199d14b01SJoseph Chen 	} else {
18299d14b01SJoseph Chen 		for (i = 0; i < round; i++) {
18399d14b01SJoseph Chen 			ret = blk_dwrite(dev_desc, sector, blocks, w_buf);
18499d14b01SJoseph Chen 			if (ret != blocks) {
185443feaabSJoseph Chen 				ut_err("%s: failed to write @%d round\n", label, i);
18699d14b01SJoseph Chen 				ret = -EIO;
18799d14b01SJoseph Chen 				goto err3;
18899d14b01SJoseph Chen 			}
18999d14b01SJoseph Chen 		}
19099d14b01SJoseph Chen 	}
19199d14b01SJoseph Chen 
19299d14b01SJoseph Chen 	ts = get_timer(0) - ts;
19399d14b01SJoseph Chen 	printf("\n%s write: size %dMB, used %ldms, speed %ldMB/s\n",
19499d14b01SJoseph Chen 	       label, blocks * round / 2048, ts, (blocks * round >> 1) / ts);
19599d14b01SJoseph Chen 
19699d14b01SJoseph Chen 	/* 5. Read test */
19799d14b01SJoseph Chen 	ts = get_timer(0);
19899d14b01SJoseph Chen 	if (devtype) {
19999d14b01SJoseph Chen 		snprintf(cmd, sizeof(cmd), "%s read 0x%x 0x%x 0x%x",
20099d14b01SJoseph Chen 			 devtype, (u32)(ulong)r_buf, sector, blocks);
20199d14b01SJoseph Chen 
20299d14b01SJoseph Chen 		for (i = 0; i < round; i++) {
20399d14b01SJoseph Chen 			if (run_command(cmd, 0)) {
204443feaabSJoseph Chen 				ut_err("%s: failed to read @%d round\n", label, i);
20599d14b01SJoseph Chen 				ret = -EIO;
20699d14b01SJoseph Chen 				goto err3;
20799d14b01SJoseph Chen 			}
20899d14b01SJoseph Chen 		}
20999d14b01SJoseph Chen 	} else {
21099d14b01SJoseph Chen 		for (i = 0; i < round; i++) {
21199d14b01SJoseph Chen 			ret = blk_dread(dev_desc, sector, blocks, r_buf);
21299d14b01SJoseph Chen 			if (ret != blocks) {
213443feaabSJoseph Chen 				ut_err("%s: failed to read @%d round\n", label, i);
21499d14b01SJoseph Chen 				ret = -EIO;
21599d14b01SJoseph Chen 				goto err3;
21699d14b01SJoseph Chen 			}
21799d14b01SJoseph Chen 		}
21899d14b01SJoseph Chen 	}
21999d14b01SJoseph Chen 
22099d14b01SJoseph Chen 	ts = get_timer(0) - ts;
22199d14b01SJoseph Chen 	printf("\n%s read: size %dMB, used %ldms, speed %ldMB/s\n",
22299d14b01SJoseph Chen 	       label, blocks * round / 2048, ts, (blocks * round >> 1) / ts);
22399d14b01SJoseph Chen 
22499d14b01SJoseph Chen 	/* 6. Verify the context */
22599d14b01SJoseph Chen 	for (i = 0; i < blocks * dev_desc->blksz; i++) {
22699d14b01SJoseph Chen 		if (w_buf[i] != r_buf[i]) {
227443feaabSJoseph Chen 			ut_err("%s: context compare error\n", label);
22899d14b01SJoseph Chen 			ret = -EINVAL;
22999d14b01SJoseph Chen 			goto err3;
23099d14b01SJoseph Chen 		}
23199d14b01SJoseph Chen 	}
23299d14b01SJoseph Chen 
23399d14b01SJoseph Chen 	/* 7. Switch back to default system devnum */
2349c7862b8SKever Yang 	if (devtype && !strcmp(devtype, "mmc") && env_get("devnum") &&
23599d14b01SJoseph Chen 	    strcmp(devnum, env_get("devnum"))) {
23699d14b01SJoseph Chen 		ret = run_command(cmd, 0);
23799d14b01SJoseph Chen 		if (ret) {
238443feaabSJoseph Chen 			ut_err("%s: failed to switch to mmc1\n", label);
23999d14b01SJoseph Chen 			ret = -ENODEV;
24099d14b01SJoseph Chen 			goto err3;
24199d14b01SJoseph Chen 		}
24299d14b01SJoseph Chen 	}
24399d14b01SJoseph Chen 
24499d14b01SJoseph Chen 	ret = 0;
24599d14b01SJoseph Chen err3:
24654108d04SKever Yang #ifdef CONFIG_RKIMG_BOOTLOADER
24799d14b01SJoseph Chen 	sysmem_free((phys_addr_t)r_buf);
24899d14b01SJoseph Chen err2:
24999d14b01SJoseph Chen 	sysmem_free((phys_addr_t)w_buf);
25054108d04SKever Yang #else
251fb09b071SKever Yang 	free(r_buf);
25254108d04SKever Yang err2:
253fb09b071SKever Yang 	free(w_buf);
25454108d04SKever Yang #endif
25599d14b01SJoseph Chen err1:
25699d14b01SJoseph Chen 
25799d14b01SJoseph Chen 	return ret;
25899d14b01SJoseph Chen }
25999d14b01SJoseph Chen 
26099d14b01SJoseph Chen #ifdef CONFIG_MMC
do_test_emmc(cmd_tbl_t * cmdtp,int flag,int argc,char * const argv[])26199d14b01SJoseph Chen static int do_test_emmc(cmd_tbl_t *cmdtp, int flag,
26299d14b01SJoseph Chen 			int argc, char *const argv[])
26399d14b01SJoseph Chen {
26499d14b01SJoseph Chen 	return do_test_storage(cmdtp, flag, argc, argv, "mmc", "0", "MMC0");
26599d14b01SJoseph Chen }
26699d14b01SJoseph Chen 
do_test_sdmmc(cmd_tbl_t * cmdtp,int flag,int argc,char * const argv[])26799d14b01SJoseph Chen static int do_test_sdmmc(cmd_tbl_t *cmdtp, int flag,
26899d14b01SJoseph Chen 			 int argc, char *const argv[])
26999d14b01SJoseph Chen {
27099d14b01SJoseph Chen 	return do_test_storage(cmdtp, flag, argc, argv, "mmc", "1", "MMC1");
27199d14b01SJoseph Chen }
27299d14b01SJoseph Chen #endif
27399d14b01SJoseph Chen 
2749cde1b1dSJon Lin #if defined(CONFIG_RKNAND) || defined(CONFIG_RKNANDC_NAND)
do_test_rknand(cmd_tbl_t * cmdtp,int flag,int argc,char * const argv[])27599d14b01SJoseph Chen static int do_test_rknand(cmd_tbl_t *cmdtp, int flag,
27699d14b01SJoseph Chen 			  int argc, char *const argv[])
27799d14b01SJoseph Chen {
27899d14b01SJoseph Chen 	return do_test_storage(cmdtp, flag, argc, argv, "rknand", "0", "RKNAND0");
27999d14b01SJoseph Chen }
28099d14b01SJoseph Chen #endif
28199d14b01SJoseph Chen 
2829cde1b1dSJon Lin #ifdef CONFIG_RKSFC_NAND
do_test_rkflash_spinand(cmd_tbl_t * cmdtp,int flag,int argc,char * const argv[])2839cde1b1dSJon Lin static int do_test_rkflash_spinand(cmd_tbl_t *cmdtp, int flag,
2849cde1b1dSJon Lin 				   int argc, char *const argv[])
2859cde1b1dSJon Lin {
2869cde1b1dSJon Lin 	return do_test_storage(cmdtp, flag, argc, argv, "rksfc", "0", "RKSFC0");
2879cde1b1dSJon Lin }
2889cde1b1dSJon Lin #endif
2899cde1b1dSJon Lin 
2909cde1b1dSJon Lin #ifdef CONFIG_RKSFC_NOR
do_test_rkflash_spinor(cmd_tbl_t * cmdtp,int flag,int argc,char * const argv[])2919cde1b1dSJon Lin static int do_test_rkflash_spinor(cmd_tbl_t *cmdtp, int flag,
2929cde1b1dSJon Lin 				  int argc, char *const argv[])
2939cde1b1dSJon Lin {
2949cde1b1dSJon Lin 	return do_test_storage(cmdtp, flag, argc, argv, "rksfc", "1", "RKSFC1");
2959cde1b1dSJon Lin }
2969cde1b1dSJon Lin #endif
2979cde1b1dSJon Lin 
298bc18ede0SKever Yang #ifdef CONFIG_DM_RAMDISK
do_test_blk(cmd_tbl_t * cmdtp,int flag,int argc,char * const argv[])29999d14b01SJoseph Chen static int do_test_blk(cmd_tbl_t *cmdtp, int flag,
30099d14b01SJoseph Chen 		       int argc, char *const argv[])
30199d14b01SJoseph Chen {
30299d14b01SJoseph Chen 	return do_test_storage(cmdtp, flag, argc, argv, NULL, NULL, "BLK");
30399d14b01SJoseph Chen }
304bc18ede0SKever Yang #endif
305*25fbb41fSYifeng Zhao 
306*25fbb41fSYifeng Zhao #ifdef CONFIG_SCSI
do_test_scsi(cmd_tbl_t * cmdtp,int flag,int argc,char * const argv[])307*25fbb41fSYifeng Zhao static int do_test_scsi(cmd_tbl_t *cmdtp, int flag,
308*25fbb41fSYifeng Zhao 			int argc, char *const argv[])
309*25fbb41fSYifeng Zhao {
310*25fbb41fSYifeng Zhao 	return do_test_storage(cmdtp, flag, argc, argv, "scsi", "0", "BLK");
311*25fbb41fSYifeng Zhao }
312*25fbb41fSYifeng Zhao #endif
313*25fbb41fSYifeng Zhao 
3149cde1b1dSJon Lin #endif/* defined(CONFIG_MMC) ||\
3159cde1b1dSJon Lin        * defined(CONFIG_RKNAND) ||\
3169cde1b1dSJon Lin        * defined(CONFIG_DM_RAMDISK) ||\
3179cde1b1dSJon Lin        * defined(CONFIG_USB_HOST) ||\
3189cde1b1dSJon Lin        * defined(CONFIG_RKNANDC_NAND) ||\
3199cde1b1dSJon Lin        * defined(CONFIG_RKSFC_NAND) ||\
3209cde1b1dSJon Lin        * defined(CONFIG_RKSFC_NOR)
3219cde1b1dSJon Lin        */
32299d14b01SJoseph Chen 
32399d14b01SJoseph Chen #if defined(CONFIG_OPTEE_CLIENT) && defined(CONFIG_MMC)
do_test_secure_storage(cmd_tbl_t * cmdtp,int flag,int argc,char * const argv[])32499d14b01SJoseph Chen static int do_test_secure_storage(cmd_tbl_t *cmdtp, int flag,
32599d14b01SJoseph Chen 				  int argc, char *const argv[])
32699d14b01SJoseph Chen {
32799d14b01SJoseph Chen 	return run_command("mmc testsecurestorage", 0);
32899d14b01SJoseph Chen }
32999d14b01SJoseph Chen #endif
33099d14b01SJoseph Chen 
33199d14b01SJoseph Chen #if defined(CONFIG_CMD_SAVEENV) && !defined(CONFIG_ENV_IS_NOWHERE) && \
33299d14b01SJoseph Chen 	!defined(CONFIG_SPL_BUILD)
do_test_env(cmd_tbl_t * cmdtp,int flag,int argc,char * const argv[])33399d14b01SJoseph Chen static int do_test_env(cmd_tbl_t *cmdtp, int flag,
33499d14b01SJoseph Chen 		       int argc, char *const argv[])
33599d14b01SJoseph Chen {
33699d14b01SJoseph Chen 	int ret;
33799d14b01SJoseph Chen 
33899d14b01SJoseph Chen 	ret = env_save();
339443feaabSJoseph Chen 	if (ret) {
340443feaabSJoseph Chen 		ut_err("env: failed to save, ret=%d\n", ret);
34199d14b01SJoseph Chen 		return ret;
342443feaabSJoseph Chen 	}
34399d14b01SJoseph Chen 
34499d14b01SJoseph Chen 	return env_load();
34599d14b01SJoseph Chen }
34699d14b01SJoseph Chen #endif
34799d14b01SJoseph Chen 
34899d14b01SJoseph Chen #ifdef CONFIG_ROCKCHIP_VENDOR_PARTITION
do_test_vendor(cmd_tbl_t * cmdtp,int flag,int argc,char * const argv[])34999d14b01SJoseph Chen static int do_test_vendor(cmd_tbl_t *cmdtp, int flag,
35099d14b01SJoseph Chen 			  int argc, char *const argv[])
35199d14b01SJoseph Chen {
35299d14b01SJoseph Chen 	return vendor_storage_test();
35399d14b01SJoseph Chen }
35499d14b01SJoseph Chen #endif
35599d14b01SJoseph Chen 
35699d14b01SJoseph Chen #ifdef CONFIG_ROCKCHIP_EFUSE
do_test_efuse(cmd_tbl_t * cmdtp,int flag,int argc,char * const argv[])35799d14b01SJoseph Chen static int do_test_efuse(cmd_tbl_t *cmdtp, int flag,
35899d14b01SJoseph Chen 			 int argc, char *const argv[])
35999d14b01SJoseph Chen {
36099d14b01SJoseph Chen 	struct udevice *dev;
36199d14b01SJoseph Chen 	u8 fuses[128] = {0};
36299d14b01SJoseph Chen 	int ret;
36399d14b01SJoseph Chen 
36499d14b01SJoseph Chen 	ret = uclass_get_device(UCLASS_MISC, 0, &dev);
36599d14b01SJoseph Chen 	if (ret) {
366443feaabSJoseph Chen 		ut_err("efuse: failed to get device, ret=%d\n", ret);
36799d14b01SJoseph Chen 		return 0;
36899d14b01SJoseph Chen 	}
36999d14b01SJoseph Chen 
37099d14b01SJoseph Chen 	ret = misc_read(dev, 0, &fuses, sizeof(fuses));
37199d14b01SJoseph Chen 	if (ret) {
372443feaabSJoseph Chen 		ut_err("efuse: failed to read, ret=%d\n", ret);
37399d14b01SJoseph Chen 		return 0;
37499d14b01SJoseph Chen 	}
37599d14b01SJoseph Chen 
37699d14b01SJoseph Chen 	printf("Efuse-content:\n");
37799d14b01SJoseph Chen 	print_buffer(0, fuses, 1, 128, 16);
37899d14b01SJoseph Chen 
37999d14b01SJoseph Chen 	return 0;
38099d14b01SJoseph Chen }
38199d14b01SJoseph Chen #endif
38299d14b01SJoseph Chen 
38399d14b01SJoseph Chen #ifdef CONFIG_ROCKCHIP_OTP
do_test_otp(cmd_tbl_t * cmdtp,int flag,int argc,char * const argv[])38499d14b01SJoseph Chen static int do_test_otp(cmd_tbl_t *cmdtp, int flag,
38599d14b01SJoseph Chen 		       int argc, char *const argv[])
38699d14b01SJoseph Chen {
38799d14b01SJoseph Chen 	struct udevice *dev;
38899d14b01SJoseph Chen 	u8 otps[64] = {0};
38999d14b01SJoseph Chen 	int ret;
39099d14b01SJoseph Chen 
39199d14b01SJoseph Chen 	/* retrieve the device */
39299d14b01SJoseph Chen 	ret = uclass_get_device_by_driver(UCLASS_MISC, 0, &dev);
39399d14b01SJoseph Chen 	if (ret) {
394443feaabSJoseph Chen 		ut_err("otp: failed to get device, ret=%d\n", ret);
39599d14b01SJoseph Chen 		return 0;
39699d14b01SJoseph Chen 	}
39799d14b01SJoseph Chen 
39899d14b01SJoseph Chen 	ret = misc_read(dev, 0, &otps, sizeof(otps));
39999d14b01SJoseph Chen 	if (ret) {
400443feaabSJoseph Chen 		ut_err("otp: failed to read, ret=%d\n", ret);
40199d14b01SJoseph Chen 		return 0;
40299d14b01SJoseph Chen 	}
40399d14b01SJoseph Chen 
40499d14b01SJoseph Chen 	printf("Otp-content:\n");
40599d14b01SJoseph Chen 	print_buffer(0, otps, 1, 64, 16);
40699d14b01SJoseph Chen 
40799d14b01SJoseph Chen 	return 0;
40899d14b01SJoseph Chen }
40999d14b01SJoseph Chen #endif
41099d14b01SJoseph Chen 
41199d14b01SJoseph Chen #ifdef CONFIG_PARTITIONS
do_test_part(cmd_tbl_t * cmdtp,int flag,int argc,char * const argv[])41299d14b01SJoseph Chen static int do_test_part(cmd_tbl_t *cmdtp, int flag,
41399d14b01SJoseph Chen 			int argc, char *const argv[])
41499d14b01SJoseph Chen {
41599d14b01SJoseph Chen 	return run_command("part list ${devtype} ${devnum}", 0);
41699d14b01SJoseph Chen }
41799d14b01SJoseph Chen #endif
41899d14b01SJoseph Chen 
419e80ec83dSKever Yang #ifdef CONFIG_USB_HOST
do_test_usb(cmd_tbl_t * cmdtp,int flag,int argc,char * const argv[])420e80ec83dSKever Yang static int do_test_usb(cmd_tbl_t *cmdtp, int flag,
421e80ec83dSKever Yang 		       int argc, char *const argv[])
422e80ec83dSKever Yang {
423e80ec83dSKever Yang 	run_command("usb start", 0);
424e80ec83dSKever Yang 	return do_test_storage(cmdtp, flag, argc, argv, "usb", "0", "usb0");
425e80ec83dSKever Yang }
426e80ec83dSKever Yang #endif
427e80ec83dSKever Yang 
42899d14b01SJoseph Chen static cmd_tbl_t sub_cmd[] = {
429bc18ede0SKever Yang #ifdef CONFIG_DM_RAMDISK
43099d14b01SJoseph Chen 	UNIT_CMD_DEFINE(blk, 0),
43199d14b01SJoseph Chen #endif
43299d14b01SJoseph Chen #ifdef CONFIG_MMC
43399d14b01SJoseph Chen 	UNIT_CMD_DEFINE(emmc, 0),
43499d14b01SJoseph Chen #endif
43599d14b01SJoseph Chen #ifdef CONFIG_ROCKCHIP_EFUSE
43699d14b01SJoseph Chen 	UNIT_CMD_DEFINE(efuse, 0),
43799d14b01SJoseph Chen #endif
43899d14b01SJoseph Chen #if defined(CONFIG_CMD_SAVEENV) && !defined(CONFIG_ENV_IS_NOWHERE) && \
43999d14b01SJoseph Chen 	!defined(CONFIG_SPL_BUILD)
44099d14b01SJoseph Chen 	UNIT_CMD_DEFINE(env, 0),
44199d14b01SJoseph Chen #endif
44299d14b01SJoseph Chen #ifdef CONFIG_ROCKCHIP_OTP
44399d14b01SJoseph Chen 	UNIT_CMD_DEFINE(otp, 0),
44499d14b01SJoseph Chen #endif
4459cde1b1dSJon Lin #if defined(CONFIG_RKNAND) || defined(CONFIG_RKNANDC_NAND)
44699d14b01SJoseph Chen 	UNIT_CMD_DEFINE(rknand, 0),
44799d14b01SJoseph Chen #endif
4489cde1b1dSJon Lin #ifdef CONFIG_RKSFC_NAND
4499cde1b1dSJon Lin 	UNIT_CMD_DEFINE(rkflash_spinand, 0),
4509cde1b1dSJon Lin #endif
4519cde1b1dSJon Lin #ifdef CONFIG_RKSFC_NOR
4529cde1b1dSJon Lin 	UNIT_CMD_DEFINE(rkflash_spinor, 0),
4539cde1b1dSJon Lin #endif
45499d14b01SJoseph Chen #if defined(CONFIG_OPTEE_CLIENT) && defined(CONFIG_MMC)
45599d14b01SJoseph Chen 	UNIT_CMD_DEFINE(secure_storage, 0),
45699d14b01SJoseph Chen #endif
45799d14b01SJoseph Chen #ifdef CONFIG_PARTITIONS
45899d14b01SJoseph Chen 	UNIT_CMD_DEFINE(part, 0),
45999d14b01SJoseph Chen #endif
460e80ec83dSKever Yang #ifdef CONFIG_USB_HOST
461e80ec83dSKever Yang 	UNIT_CMD_DEFINE(usb, 0),
462e80ec83dSKever Yang #endif
46399d14b01SJoseph Chen #ifdef CONFIG_MMC
46499d14b01SJoseph Chen 	UNIT_CMD_DEFINE(sdmmc, 0),
46599d14b01SJoseph Chen #endif
46699d14b01SJoseph Chen #ifdef CONFIG_ROCKCHIP_VENDOR_PARTITION
46799d14b01SJoseph Chen 	UNIT_CMD_DEFINE(vendor, 0),
46899d14b01SJoseph Chen #endif
469*25fbb41fSYifeng Zhao #ifdef CONFIG_SCSI
470*25fbb41fSYifeng Zhao 	UNIT_CMD_DEFINE(scsi, 0),
471*25fbb41fSYifeng Zhao #endif
47299d14b01SJoseph Chen };
47399d14b01SJoseph Chen 
47499d14b01SJoseph Chen static char sub_cmd_help[] =
475bc18ede0SKever Yang #ifdef CONFIG_DM_RAMDISK
47699d14b01SJoseph Chen "    [.] rktest blk                         - test blk layer read/write\n"
47799d14b01SJoseph Chen #endif
47899d14b01SJoseph Chen #ifdef CONFIG_MMC
479474718ffSJoseph Chen "    [.] rktest emmc                        - test emmc read/write speed\n"
48099d14b01SJoseph Chen "    [.] rktest sdmmc                       - test sd card and fat fs read/write\n"
48199d14b01SJoseph Chen #endif
4829cde1b1dSJon Lin #if defined(CONFIG_RKNAND) || defined(CONFIG_RKNANDC_NAND)
483474718ffSJoseph Chen "    [.] rktest rknand                      - test rknand read/write speed\n"
48499d14b01SJoseph Chen #endif
4859cde1b1dSJon Lin #ifdef CONFIG_RKSFC_NAND
4869cde1b1dSJon Lin "    [.] rktest rkflash_spinand             - test RKFLASH DM driver spinand read/write speed\n"
4879cde1b1dSJon Lin #endif
4889cde1b1dSJon Lin #ifdef CONFIG_RKSFC_NOR
4899cde1b1dSJon Lin "    [.] rktest rkflash_spinor              - test RKFLASH DM driver read/write speed\n"
4909cde1b1dSJon Lin #endif
49199d14b01SJoseph Chen #if defined(CONFIG_OPTEE_CLIENT) && defined(CONFIG_MMC)
49299d14b01SJoseph Chen "    [.] rktest secure_storage              - test secure storage\n"
49399d14b01SJoseph Chen #endif
49499d14b01SJoseph Chen #ifdef CONFIG_ROCKCHIP_VENDOR_PARTITION
49599d14b01SJoseph Chen "    [.] rktest vendor                      - test vendor storage read/write\n"
49699d14b01SJoseph Chen #endif
49799d14b01SJoseph Chen #ifdef CONFIG_ROCKCHIP_EFUSE
49899d14b01SJoseph Chen "    [.] rktest efuse                       - test efuse, dump content\n"
49999d14b01SJoseph Chen #endif
50099d14b01SJoseph Chen #ifdef CONFIG_ROCKCHIP_OTP
50199d14b01SJoseph Chen "    [.] rktest otp                         - test otp, dump content\n"
50299d14b01SJoseph Chen #endif
50399d14b01SJoseph Chen #if defined(CONFIG_CMD_SAVEENV) && !defined(CONFIG_ENV_IS_NOWHERE) && \
50499d14b01SJoseph Chen 	!defined(CONFIG_SPL_BUILD)
50599d14b01SJoseph Chen "    [.] rktest env                         - test save env to storage\n"
50699d14b01SJoseph Chen #endif
50799d14b01SJoseph Chen #ifdef CONFIG_PARTITIONS
50899d14b01SJoseph Chen "    [.] rktest part                        - test part list\n"
50999d14b01SJoseph Chen #endif
510e80ec83dSKever Yang #ifdef CONFIG_USB_HOST
511e80ec83dSKever Yang "    [.] rktest usb                         - test usb disk\n"
512e80ec83dSKever Yang #endif
513*25fbb41fSYifeng Zhao #ifdef CONFIG_SCSI
514*25fbb41fSYifeng Zhao "    [.] rktest scsi                        - test sata disk\n"
515*25fbb41fSYifeng Zhao #endif
51699d14b01SJoseph Chen ;
51799d14b01SJoseph Chen 
51899d14b01SJoseph Chen const struct cmd_group cmd_grp_storage = {
51999d14b01SJoseph Chen 	.id	= TEST_ID_STORAGE,
52099d14b01SJoseph Chen 	.help	= sub_cmd_help,
52199d14b01SJoseph Chen 	.cmd	= sub_cmd,
52299d14b01SJoseph Chen 	.cmd_n	= ARRAY_SIZE(sub_cmd),
52399d14b01SJoseph Chen };
524