/*
* Copyright (C) 2017 Amlogic, Inc. All rights reserved.
* *
This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
* *
This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
* *
You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
* *
Description:
*/


#include "../include/phynand.h"

extern int amlnand_init(unsigned char flag);
extern void amlchip_dumpinfo(struct amlnand_chip *aml_chip);
extern void amldev_dumpinfo(struct amlnand_phydev *phydev);
//static int plane_mode = 0;
//struct aml_nftl_dev * nftl_device;

/* just like memset function but the paraments' type is  little different */
void *memset_nand_test(void *s, u32 c, size_t count)
{
	u32 *sl = (u32 *) s;
	u32 cl = 0;
	//char *s8;
	int i;

	/* do it one word at a time (32 bits or 64 bits) while possible */
	if ( ((ulong)s & (sizeof(*sl) - 1)) == 0) {

		for (i = 0; i < sizeof(*sl); i++) {
			cl <<= 8;
			cl |= c & 0xff;
			c =c >>8;
		}
		while (count >= sizeof(*sl)) {
			*sl++ = cl;
			count -= sizeof(*sl);
		}
	}
	/* fill 8 bits at a time */
	/*s8 = (char *)sl;            //this can write one byte
	while (count--)
		*s8++ = c;*/

	return s;
}
static int nand_erase_ops_test(struct amlnand_phydev *phydev, uint64_t off, uint64_t len)
{
	//struct amlnand_chip *aml_chip = phydev->priv;
	struct phydev_ops *devops = &(phydev->ops);
	//struct hw_controller *controller = &(aml_chip->controller);
	//struct chip_operation *operation = &(aml_chip->operation);
	//struct chip_ops_para *ops_para = &(aml_chip->ops_para);

	uint64_t erase_addr, erase_len, erase_off;
	int ret = 0;

	erase_addr = erase_off = off;
	erase_len = len ;

	if ((erase_off+erase_len) > phydev->size ) {
		aml_nand_msg("nand write size is out of space");
		ret= -NAND_ERASE_FAILED;
		goto exit_error;
	}

	for (; erase_addr < erase_off + erase_len; erase_addr +=  phydev->erasesize) {

		memset(devops, 0x0, sizeof(struct phydev_ops));
		devops->addr = erase_addr;
		devops->len = phydev->erasesize;
		devops->mode = NAND_HW_ECC;

		 ret = phydev->block_isbad(phydev);
		if (ret > 0) {
			aml_nand_msg("Skipping bad block at 0x%08llx", erase_addr);
			continue;

		} else if (ret < 0) {
			aml_nand_msg("nand get bad block failed: ret=%d at addr=%llx",ret, erase_addr);
			ret =  -NAND_ERASE_FAILED;
		}
		extern int nand_erase(struct amlnand_phydev *phydev);
		ret = nand_erase(phydev);
		if (ret < 0) {
			aml_nand_msg("nand Erase failure: %d %llx", ret, erase_addr);
			ret =  -NAND_ERASE_FAILED;
		}
	}


exit_error:

	return ret;
}

static int nand_read_ops_test(struct amlnand_phydev *phydev,uint64_t off , uint64_t len , unsigned char * dat_buf)
{
	//struct amlnand_chip *aml_chip =phydev->priv;
	struct phydev_ops *devops = &(phydev->ops);
	uint64_t offset , write_len;
	unsigned char * buffer = NULL;
	int ret = 0;

	offset = off;
	write_len = len;
	buffer = aml_nand_malloc(2 * phydev->writesize);
	if (!buffer) {
		aml_nand_msg("nand read test malloc failed");
		ret = -NAND_READ_FAILED;
		goto exit_error;
	}

	if (!dat_buf) {
		aml_nand_msg("nand read no buf");
		return -NAND_READ_FAILED;
	}

	if ((offset & (phydev->writesize - 1)) != 0 ||(write_len & (phydev->writesize - 1)) != 0) {
		aml_nand_msg ("Attempt to read non page aligned data");
		return -NAND_READ_FAILED;
	}

	if ((offset + write_len) > phydev->size) {
		aml_nand_msg("Attemp to read out side the dev area");
		return -NAND_READ_FAILED;
	}
	memset(devops, 0x0, sizeof(struct phydev_ops));
	devops->addr = offset;
	devops->len = phydev->writesize;
	devops->datbuf = buffer;
	devops->oobbuf = NULL;
	devops->mode = NAND_HW_ECC;
	aml_nand_dbg("phydev->writesize= %x",phydev->writesize);
	do {
		if ((devops->addr % phydev->erasesize) == 0 ) {
			ret =  phydev->block_isbad(phydev);
			if (ret > 0) {
				aml_nand_msg("Skipping bad block at %llx", devops->addr);
				devops->addr += phydev->erasesize;
				continue;
			} else if (ret < 0) {
				aml_nand_msg("AMLNAND get bad block failed: ret=%d at addr=%llx",ret, devops->addr);
				return -1;
			}
		}
		memset(buffer,0x0,(2 * phydev->writesize));
		ret = phydev->read(phydev);
		if ((ret)) {
			aml_nand_msg("nand read failed at %llx",devops->addr);
		}
		if (memcmp(buffer,dat_buf,phydev->writesize)) {
			aml_nand_msg("nand read test verify failed");
			break;
		}
		devops->addr +=  phydev->writesize;

	}while(devops->addr < (offset + write_len));


exit_error:

	if (buffer) {
		aml_nand_free(buffer);
	}

	return ret;
}
#if 0
static int nand_read_oob_ops_test(struct amlnand_phydev *phydev,uint64_t off , uint64_t len , unsigned char * dat_buf)
{
	//struct amlnand_chip *aml_chip =phydev->priv;
	struct phydev_ops *devops = &(phydev->ops);
	uint64_t offset , write_len;
	unsigned char * buffer = NULL;
	int ret = 0;

	offset = off;
	write_len = len;
	buffer = aml_nand_malloc(2 * phydev->writesize);
	if (!buffer) {
		aml_nand_msg("nand read oob test malloc failed");
		ret = -NAND_READ_FAILED;
		goto exit_error;
	}

	if (!dat_buf) {
		aml_nand_msg("nand read oob no buf");
		return -NAND_READ_FAILED;
	}

	if ((offset & (phydev->writesize - 1)) != 0 ||(write_len & (phydev->writesize - 1)) != 0) {
		aml_nand_msg ("Attempt to read non page aligned data");
		return -NAND_READ_FAILED;
	}

	if ((offset + write_len) > phydev->size) {
		aml_nand_msg("Attemp to read out side the dev area");
		return -NAND_READ_FAILED;
	}
	memset(devops, 0x0, sizeof(struct phydev_ops));
	devops->addr = offset;
	devops->len = phydev->writesize;
	devops->datbuf = NULL;
	devops->oobbuf = buffer;
	devops->mode = NAND_HW_ECC;
	aml_nand_dbg("phydev->writesize= %x",phydev->writesize);
	do {
		if ((devops->addr % phydev->erasesize) == 0 ) {
			ret =  phydev->block_isbad(phydev);
			if (ret > 0) {
				aml_nand_msg("Skipping bad block at %llx", devops->addr);
				devops->addr += phydev->erasesize;
				continue;
			} else if (ret < 0) {
				aml_nand_msg("AMLNAND get bad block failed: ret=%d at addr=%llx",ret, devops->addr);
				return -1;
			}
		}
		memset(buffer,0x0,(2 * phydev->writesize));
		ret = phydev->read_oob(phydev);
		if ((ret)) {
			aml_nand_msg("nand read oob failed at %llx",devops->addr);
		}
		if (memcmp(buffer,dat_buf,phydev->writesize)) {
			aml_nand_msg("nand read oob test verify failed");
			break;
		}
		devops->addr +=  phydev->writesize;

	}while(devops->addr < (offset + write_len));


exit_error:

	if (buffer) {
		aml_nand_free(buffer);
	}

	return ret;
}
#endif

static int nand_write_ops_test(struct amlnand_phydev *phydev , uint64_t off, uint64_t len, unsigned char * dat_buf, int flag)
{
	//struct amlnand_chip *aml_chip = phydev->priv;
	struct phydev_ops *devops = &(phydev->ops);
	unsigned char * verify_buf =NULL;
	unsigned char * buffer = NULL;
	uint64_t offset , write_len;
	int ret = 0;

	offset = off;
	write_len = len;
	buffer = dat_buf;
	flag = 1; /* fixme, verify flag! */
	if (!buffer) {
		aml_nand_msg("nand write no buf");
		return -NAND_WRITE_FAILED;
	}

	if ((offset & (phydev->writesize - 1)) != 0 ||(write_len & (phydev->writesize - 1)) != 0) {
		aml_nand_msg ("Attempt to write non page aligned data");
		return -NAND_WRITE_FAILED;
	}

	if ((offset + write_len) > phydev->size) {
		aml_nand_msg("Attemp to write out side the dev area : %llx, %llx",(offset + write_len),phydev->size);
		return -NAND_WRITE_FAILED;
	}

	if (flag == 1) {
		verify_buf = aml_nand_malloc(2*phydev->writesize);
		if (!verify_buf) {
			aml_nand_msg("Attemp to write out side the dev area");
			ret =  -NAND_WRITE_FAILED;
			goto exit_error;
		}
	}
	memset(devops, 0x0, sizeof(struct phydev_ops));
	devops->addr = offset;
	devops->len = phydev->writesize;
	devops->datbuf = buffer;
	devops->oobbuf = NULL;
	devops->mode = NAND_HW_ECC;
	aml_nand_dbg("phydev->writesize= %x",phydev->writesize);
	do {
		if ((devops->addr % phydev->erasesize) == 0 ) {
			ret =  phydev->block_isbad(phydev);
			if (ret > 0) {
				aml_nand_msg("Skipping bad block at %llx", devops->addr);
				devops->addr += phydev->erasesize;
				continue;
			} else if (ret < 0) {
				aml_nand_msg("AMLNAND get bad block failed: ret=%d at addr=%llx",ret, devops->addr);
				return -1;
			}
		}
		ret = phydev->write(phydev);
		if (ret < 0) {
			aml_nand_msg("nand write failed at %llx",devops->addr);
			ret = -NAND_WRITE_FAILED;
			goto exit_error;
		}

		if (flag == 1) { // verify data
			memset(verify_buf, 0x0, (2*phydev->writesize));
			devops->datbuf = verify_buf;
			ret = phydev->read(phydev);
			if (ret) {
				aml_nand_msg("nand test read data failed at  %llx",devops->addr);
				ret = -NAND_WRITE_FAILED;
				goto exit_error;
			}
			if (memcmp(verify_buf, buffer, phydev->writesize)) {
				aml_nand_msg("nand test verify data failed at  %llx",devops->addr);
				ret = -NAND_WRITE_FAILED;
				goto exit_error;
			}
			devops->datbuf = buffer;
		}

		devops->addr +=  phydev->writesize;

		if ((((phydev->offset + devops->addr) % phydev->erasesize) == 0))
			aml_nand_msg("aml nand write devops->addr %llx OK",devops->addr);

	}while(devops->addr < (offset + write_len));


exit_error:

	if (flag == 1) {
		if (verify_buf) {
			aml_nand_free(verify_buf);
		}
	}
	return ret;
}
//nand_test  4 write and read  every block test
static int amlnand_test4(void)
{
    struct amlnand_phydev *phydev = NULL;
    //struct amlnand_chip *aml_chip;
    //struct phydev_ops  *devops;

    int ret =0, j = 0, verify_lag  =0;
    unsigned char * data_buf = NULL;
    uint64_t offset = 0 , write_len = 0,read_len=0;
    uint64_t erase_len, erase_off;

    list_for_each_entry(phydev,&nphy_dev_list,list){
        data_buf = aml_nand_malloc( phydev->writesize);
        if (!data_buf) {
            aml_nand_msg("malloc failed");
            goto exit_0;
        }
    memset(data_buf, 0xa5, phydev->writesize);
    if (strncmp(phydev->name,NAND_BOOT_NAME,strlen((const char*)NAND_BOOT_NAME))) {
        aml_nand_msg("nand test 4 : phydev->name %s",phydev->name);
        //aml_chip = (struct amlnand_chip *)phydev->priv;
        //devops = &phydev->ops;
//erase
        erase_off = 0;
        erase_len = phydev->size ;
        ret = nand_erase_ops_test(phydev, erase_off, erase_len);
        if (ret < 0) {
            aml_nand_msg("nand test 4 : erase failed ");
            ret= -NAND_ERASE_FAILED;
            goto exit_0;
        }
        aml_nand_msg("nand test 4 : erase %d times OK ",j);
//write
        offset = 0;
        write_len =  phydev->size;
        verify_lag = 0;  // 1 indicate verify data when write
        ret = nand_write_ops_test(phydev, offset, write_len,data_buf,verify_lag);
        if (ret < 0 ) {
            aml_nand_msg("nand test 4 : write failed ");
            ret= -NAND_WRITE_FAILED;
            goto exit_0;
        }
        aml_nand_msg("nand test 4 : write %d times OK ",j);
//read disturb
        offset = 0;
        read_len =  phydev->size;
        ret = nand_read_ops_test(phydev, offset, read_len,data_buf);
        if (ret < 0 ) {
            aml_nand_msg("nand test 4 : read failed ");
            ret= -NAND_READ_FAILED;
            goto exit_0;
        }
        aml_nand_msg("nand test 4 : read %d times OK ",j);
    }
    if (data_buf)
       {
        kfree(data_buf);
        data_buf = NULL;
       }
    }

exit_0:
    if (data_buf) {
        kfree(data_buf);
        data_buf = NULL;
    }

    return ret;

}

static int amlnand_test3(void)
{
    struct amlnand_phydev *phydev = NULL;
    //struct amlnand_chip *aml_chip;
    //struct phydev_ops  *devops;

    int ret =0, verify_lag  =0;
    unsigned char * data_buf = NULL;
    uint64_t offset = 0 , write_len = 0,read_len=0, i = 0;
    uint64_t erase_len, erase_off;

    list_for_each_entry(phydev,&nphy_dev_list,list){
        data_buf = aml_nand_malloc( phydev->writesize);
        if (!data_buf) {
            aml_nand_msg("malloc failed");
            goto exit_0;
        }
    memset(data_buf, 0xa5, phydev->writesize);
    if (strncmp(phydev->name,NAND_BOOT_NAME,strlen((const char*)NAND_BOOT_NAME))) {
        aml_nand_msg("nand test 3 : phydev->name %s",phydev->name);
        //aml_chip = (struct amlnand_chip *)phydev->priv;
        //devops = &phydev->ops;
        aml_nand_msg("nand test 3 : phydev->size=%llx ",phydev->size);
//erase
        erase_off = 0;
        erase_len = phydev->size ;
        ret = nand_erase_ops_test(phydev, erase_off, erase_len);
        if (ret < 0) {
            aml_nand_msg("nand test 3 : erase failed ");
            ret= -NAND_ERASE_FAILED;
            goto exit_0;
        }
        aml_nand_msg("nand test 3 : erase OK ");
        for (i=0;i<(phydev->size>>phydev->erasesize_shift)-1;i++) {
    //write
            offset = i<<phydev->erasesize_shift;
            write_len =  (i&0xff)*phydev->writesize;
            verify_lag = 1;  // 1 indicate verify data when write
            aml_nand_msg("nand test 3 : poffset=%llx ",offset);
            ret = nand_write_ops_test(phydev, offset, write_len,data_buf,verify_lag);
            if (ret < 0 ) {
                aml_nand_msg("nand test 3 : write failed ");
                ret= -NAND_WRITE_FAILED;
                goto exit_0;
            }
            aml_nand_msg("nand test 3 : write OK ");
    //read disturb
            offset = i<<phydev->erasesize_shift;
            read_len =  (i&0xff)*phydev->writesize;
            ret = nand_read_ops_test(phydev, offset, read_len,data_buf);
            if (ret < 0 ) {
                aml_nand_msg("nand test 3 : read failed ");
                ret= -NAND_READ_FAILED;
                goto exit_0;
            }
            aml_nand_msg("nand test 3 : read OK ");
        }
    }
    if (data_buf)
       {
        kfree(data_buf);
        data_buf = NULL;
       }
    }

exit_0:
    if (data_buf) {
        kfree(data_buf);
        data_buf = NULL;
    }

    return ret;

}

//nand_test  2 Endurance test
static int amlnand_test2(void)
{
    struct amlnand_phydev *phydev = NULL;
    //struct amlnand_chip *aml_chip;
    //struct phydev_ops  *devops;

    int ret =0, j = 0, verify_lag  =0;
    unsigned char * data_buf = NULL;
    uint64_t offset = 0 , write_len = 0,read_len=0;
    uint64_t erase_len, erase_off;
    //int read_times  = 1000;

    list_for_each_entry(phydev,&nphy_dev_list,list){
        data_buf = aml_nand_malloc( phydev->writesize);
        if (!data_buf) {
            aml_nand_msg("malloc failed");
            goto exit_0;
        }
        for (j=1;j<3000;j++)
        {
            memset(data_buf, 0xa5, phydev->writesize);
        if (strncmp(phydev->name,NAND_BOOT_NAME,strlen((const char*)NAND_BOOT_NAME))) {
            aml_nand_msg("nand test 2 : phydev->name %s",phydev->name);
            //aml_chip = (struct amlnand_chip *)phydev->priv;
            //devops = &phydev->ops;
//erase
            erase_off = 0;
            erase_len = phydev->size ;
            ret = nand_erase_ops_test(phydev, erase_off, erase_len);
            if (ret < 0) {
                aml_nand_msg("nand test 2 : erase failed ");
                ret= -NAND_ERASE_FAILED;
                goto exit_0;
            }
            aml_nand_msg("nand test 2 : erase %d times OK ",j);
//write
            offset = 0;
            write_len =  phydev->size;
            verify_lag = 0;  // 1 indicate verify data when write
            ret = nand_write_ops_test(phydev, offset, write_len,data_buf,verify_lag);
            if (ret < 0 ) {
                aml_nand_msg("nand test 2 : write failed ");
                ret= -NAND_WRITE_FAILED;
                goto exit_0;
            }
            aml_nand_msg("nand test 2 : write %d times OK ",j);
//read disturb
            offset = 0;
            read_len =  phydev->size;
            ret = nand_read_ops_test(phydev, offset, read_len,data_buf);
            if (ret < 0 ) {
                aml_nand_msg("nand test 2 : read failed ");
                ret= -NAND_READ_FAILED;
                goto exit_0;
            }
            aml_nand_msg("nand test 2 : read %d times OK ",j);
        }
     }
    if (data_buf)
       {
        kfree(data_buf);
        data_buf = NULL;
       }
    }

exit_0:
    if (data_buf) {
        kfree(data_buf);
        data_buf = NULL;
    }

    return ret;


}
//nand_test  1 Read Distub test
static int amlnand_test1(void)
{
	struct amlnand_phydev *phydev = NULL;
	//struct amlnand_chip *aml_chip;
	//struct phydev_ops  *devops;

	int ret =0, i = 0, verify_lag  =0;
	unsigned char * data_buf = NULL;
	uint64_t offset = 0 , write_len = 0,read_len=0;
	uint64_t erase_len, erase_off;
	int read_times  = 10000;

	list_for_each_entry(phydev,&nphy_dev_list,list){
		data_buf = aml_nand_malloc( phydev->writesize);
		if (!data_buf) {
			aml_nand_msg("malloc failed");
			goto exit_0;
		}
		memset(data_buf, 0xa5, phydev->writesize);

		if (strncmp(phydev->name,NAND_BOOT_NAME,strlen((const char*)NAND_BOOT_NAME))) {
			aml_nand_msg("nand test 1 : phydev->name %s",phydev->name);
			// aml_chip = (struct amlnand_chip *)phydev->priv;
			// devops = &phydev->ops;
//erase
			erase_off = 0;
			erase_len = phydev->size ;
			ret = nand_erase_ops_test(phydev, erase_off, erase_len);
			if (ret < 0) {
				aml_nand_msg("nand test 1 : erase failed ");
				ret= -NAND_ERASE_FAILED;
				goto exit_0;
			}
            aml_nand_msg("nand test 1 : erase OK");
//write
			offset = 0;
			write_len =  phydev->size;
			verify_lag = 0;  // 1 indicate verify data when write
			ret = nand_write_ops_test(phydev, offset, write_len,data_buf,verify_lag);
			if (ret < 0 ) {
				aml_nand_msg("nand test 1 : write failed ");
				ret= -NAND_WRITE_FAILED;
				goto exit_0;
			}
            aml_nand_msg("nand test 1 : write OK");
//read disturb
			for (i = 0; i < read_times; i++) {
				offset = 0;
				read_len =	4*phydev->erasesize;
				ret = nand_read_ops_test(phydev, offset, read_len,data_buf);
				if (ret < 0 ) {
					aml_nand_msg("nand test 1 : read failed ");
					ret= -NAND_WRITE_FAILED;
					goto exit_0;
				}
                aml_nand_msg("nand test 1 : read %d times OK",i);
			}

//erase
			erase_off = 0;
			erase_len = phydev->size ;
			ret = nand_erase_ops_test(phydev, erase_off, erase_len);
			if (ret < 0) {
				aml_nand_msg("nand test 1 : erase failed ");
				ret= -NAND_ERASE_FAILED;
				goto exit_0;
			}

		}

		if (data_buf) {
			kfree(data_buf);
			data_buf = NULL;
		}

	}

exit_0:
	if (data_buf) {
		kfree(data_buf);
		data_buf = NULL;
	}

	return ret;
}
//nand_test  0 E/P/R Cycle Whole chip
static int amlnand_test0(void)
{
	struct amlnand_phydev *phydev = NULL;
	//struct amlnand_chip *aml_chip;
	//struct phydev_ops  *devops;

	int ret =0, verify_lag  =0;
	unsigned char * data_buf = NULL;
	uint64_t offset = 0 , write_len = 0,read_len=0;
	uint64_t erase_len, erase_off;

	list_for_each_entry(phydev,&nphy_dev_list,list){

		data_buf = aml_nand_malloc(phydev->writesize);
		if (!data_buf) {
			aml_nand_msg("malloc failed");
			ret = -1;
			goto exit_0;
		}
		memset(data_buf, 0xa5, phydev->writesize);

		if (strncmp(phydev->name,NAND_BOOT_NAME,strlen((const char*)NAND_BOOT_NAME))) {
			aml_nand_msg("nand test 0 : phydev->name %s",phydev->name);
			// aml_chip = (struct amlnand_chip *)phydev->priv;
			// devops = &phydev->ops;
//erase
			aml_nand_msg("nand test 0 : erase");
			erase_off = 0;
			erase_len = phydev->size ;
			ret = nand_erase_ops_test(phydev, erase_off, erase_len);
			if (ret < 0) {
				aml_nand_msg("nand test 0 : erase failed ");
				ret= -NAND_ERASE_FAILED;
				goto exit_0;
			}
//write
			aml_nand_msg("nand test 0 : write");
			offset = 0;
			write_len =  phydev->size;
			verify_lag = 0;  // 1 indicate verify data when write
			ret = nand_write_ops_test(phydev, offset, write_len,data_buf,verify_lag);
			if (ret < 0 ) {
				aml_nand_msg("nand test 0 : write failed ");
				ret= -NAND_WRITE_FAILED;
				goto exit_0;
			}
//read
			aml_nand_msg("nand test 0 : read");
			offset = 0;
			read_len =  phydev->size;
			ret = nand_read_ops_test(phydev, offset, read_len,data_buf);
			if (ret < 0 ) {
				aml_nand_msg("nand test 0 : read failed ");
				ret= -NAND_WRITE_FAILED;
				goto exit_0;
			}
//erase
			erase_off = 0;
			erase_len = phydev->size ;
			ret = nand_erase_ops_test(phydev, erase_off, erase_len);
			if (ret < 0) {
				aml_nand_msg("nand test 0 : erase failed ");
				ret= -NAND_ERASE_FAILED;
				goto exit_0;
			}

		}

		if (data_buf) {
			kfree(data_buf);
			data_buf = NULL;
		}
	}

exit_0:
	if (data_buf) {
		kfree(data_buf);
		data_buf = NULL;
	}

	return ret;
}


int do_amlnand_test(cmd_tbl_t * cmdtp, int flag, int argc, char * const argv[])
{
	int ret = 0;
	//ulong addr;
	//ulong data_write;
	//loff_t off, size;
	char *cmd;

	if (argc < 2) {
		printf("argc less than 2 :\n");
		goto usage;
	}

	cmd = argv[1];

	if (strncmp(cmd, "0", 1) == 0) {
		ret = amlnand_test0();
		if (ret < 0) {
			aml_nand_msg("amlnand_test0: E/P/R Cycle failed");
		}else
			aml_nand_msg("amlnand_test0: E/P/R Cycle OK");
		return 0;
	}else if (strncmp(cmd, "1", 1) == 0){
		ret = amlnand_test1();
		if (ret < 0) {
			aml_nand_msg("amlnand_test1: Read Distub test failed");
		}else
			aml_nand_msg("amlnand_test1: Read Distub test OK");
		return 0;
	}else if (strncmp(cmd, "2", 1) == 0){
		ret = amlnand_test2();
		if (ret < 0) {
			aml_nand_msg("amlnand_test2: Endurance test failed");
		}else
			aml_nand_msg("amlnand_test2: Endurance test OK");
		return 0;
	}else if (strncmp(cmd, "3", 1) == 0){
		ret = amlnand_test3();
		if (ret < 0) {
			aml_nand_msg("amlnand_test3: write and read random pages of every block test failed");
		}else
			aml_nand_msg("amlnand_test3: write and read random pages of every block test OK");

		return 0;
	}else if (strncmp(cmd, "4", 1) == 0){
		ret = amlnand_test4();
		if (ret < 0) {
			aml_nand_msg("amlnand_test4: READ all page  every block test failed");
		}else
			aml_nand_msg("amlnand_test4: READ all page  every block test OK");

		return 0;
	}else{
			goto usage;
	}

usage:
	cmd_usage(cmdtp);
	return 1;

}

U_BOOT_CMD(amlnf_test, CONFIG_SYS_MAXARGS, 1, do_amlnand_test,
	"AMLPHYNAND sub-system",
	"amlnf_test  0 E/P/R Cycle Whole chip \n"
	"amlnf_test  1 Read Distub test,read block 0~3 10k times \n"
	"amlnf_test  2 Endurance test, E/W/R 10 block 3000 times  \n"
	"amlnf_test  3 write and read random pages of every block test \n"
	"amlnf_test  4 READ all page every block   \n"
	"amlnf_test  5 ...... \n"
	"amlnf_test  8 exit sync \n"
);


