本节中实现nand write.yaffs2
之前版本的uboot是支持write.yaffs2
的,但是此版本中已经找不到nand的这个命令了。
nand write
和nand write.yaffs2
之间的差别是,nand write
在写完一页数据之后计算出OOB的数据然后写入,但是在write.yaffs2
中,本身自带OOB数据,只需写入即可。
对照之前版本的uboot源码,做如下修改
1. 修改cmd/nand.c
修改do_nand
函数
#ifdef CONFIG_CMD_NAND_TRIMFFS
} else if (!strcmp(s, ".trimffs")) {
if (read) {
printf("Unknown nand command suffix '%s'\n", s);
return 1;
}
ret = nand_write_skip_bad(mtd, off, &rwsize, NULL,
maxsize, (u_char *)addr,
WITH_DROP_FFS | WITH_WR_VERIFY);
#endif
#ifdef CONFIG_CMD_NAND_YAFFS
} else if (!strcmp(s, ".yaffs2")) {
if (read) {
printf("Unknown nand command suffix ‘%s‘.\n", s);
return 1;
}
ret = nand_write_skip_bad(mtd, off, &rwsize,NULL,//这里参数和老版比要修改下
maxsize,(u_char *)addr,
WITH_YAFFS_OOB);
#endif
} else if (!strcmp(s, ".oob")) {
/* out-of-band data */
mtd_oob_ops_t ops = {
.oobbuf = (u8 *)addr,
.ooblen = rwsize,
.mode = MTD_OPS_RAW
};
修改帮助信息nand_help_text
#ifdef CONFIG_CMD_NAND_YAFFS
"nand write.yaffs2 - addr off|partition size\n"
" write ‘size‘ bytes starting at offset ‘off‘ with yaffs format\n"
" from memory address ‘addr‘, skipping bad blocks.\n"
#endif
2. 修改drivers/mtd/nand/nand_util.c
修改nand_write_skip_bad
函数
if (actual)
*actual = 0;
#ifdef CONFIG_CMD_NAND_YAFFS
if (flags & WITH_YAFFS_OOB)
{
if (flags & ~WITH_YAFFS_OOB)
return -EINVAL;
int pages;
pages = mtd->erasesize / mtd->writesize;
blocksize = (pages * mtd->oobsize) + mtd->erasesize;
if (*length % (mtd->writesize + mtd->oobsize))
{
printf ("Attempt to write incomplete page"
" in yaffs mode\n");
return -EINVAL;
}
}
else
#endif
{
blocksize = mtd->erasesize;
}
/*
* nand_write() handles unaligned, partial page writes.
*
* We allow length to be unaligned, for convenience in
* using the $filesize variable.
if (left_to_write < (blocksize - block_offset))
write_size = left_to_write;
else
write_size = blocksize - block_offset;
#ifdef CONFIG_CMD_NAND_YAFFS
if (flags & WITH_YAFFS_OOB)
{
int page, pages;
size_t pagesize = mtd->writesize;
size_t pagesize_oob = pagesize + mtd->oobsize;
struct mtd_oob_ops ops;
ops.len = pagesize;
ops.ooblen = mtd->oobsize;
ops.mode = MTD_OPS_RAW; //这里要改为RAW
ops.ooboffs = 0;
pages = write_size / pagesize_oob;
for (page = 0; page < pages; page++)
{
WATCHDOG_RESET();
ops.datbuf = p_buffer;
ops.oobbuf = ops.datbuf + pagesize;
rval = mtd->_write_oob(mtd, offset, &ops);
if (rval != 0)
break;
offset += pagesize;
p_buffer += pagesize_oob;
}
}
else
#endif
{
truncated_write_size = write_size;
#ifdef CONFIG_CMD_NAND_TRIMFFS
if (flags & WITH_DROP_FFS)
truncated_write_size = drop_ffs(mtd, p_buffer,
&write_size);
#endif
rval = nand_write(mtd, offset, &truncated_write_size,
p_buffer);
if ((flags & WITH_WR_VERIFY) && !rval)
rval = nand_verify(mtd, offset,
truncated_write_size, p_buffer);
offset += write_size;
p_buffer += write_size;
}
if (rval != 0) {
printf("NAND write to offset %llx failed %d\n",
offset, rval);
*length -= left_to_write;
return rval;
}
3. 修改include/configs/smdk2440.h
#define CONFIG_CMD_NAND_YAFFS
4. 修改include/nand.h
#ifdef CONFIG_CMD_NAND_YAFFS
#define WITH_YAFFS_OOB (1 << 0)
#define WITH_DROP_FFS (1 << 0)
#endif
编译之后就可以使用以下命令下载文件系统了
nfs 30000000 136.17.69.70:/home/shuimu/more/LinuxDriver/qt_opia.yaffs2
nand erase.part rootfs
nand write.yaffs2 30000000 rootfs ****
最后的值为nfs传输的文件系统的字节数,16进制
其中的修改参考了https://www.cnblogs.com/jetli-/p/5361807.html
,谢谢!