[U-Boot] [PATCH 3/7] mtd: nand: Consolidate nand spl loaders implementation
Pau Pajuelo
ppajuelo at iseebcn.com
Thu Apr 6 17:20:14 UTC 2017
Tested-by: Pau Pajuelo <ppajuel at gmail.com>
2017-04-01 17:16 GMT+02:00 Ladislav Michl <ladis at linux-mips.org>:
>
> nand_spl_load_image implementation was copied over into three
> different drivers and now with nand_spl_read_block used for
> ubispl situation gets even worse. For now use least intrusive
> solution and #include the same implementation to nand drivers.
>
> Signed-off-by: Ladislav Michl <ladis at linux-mips.org>
> ---
> drivers/mtd/nand/am335x_spl_bch.c | 49 +----------------
> drivers/mtd/nand/atmel_nand.c | 30 +---------
> drivers/mtd/nand/nand_spl_loaders.c | 106 ++++++++++++++++++++++++++++++++++++
> drivers/mtd/nand/nand_spl_simple.c | 98 +--------------------------------
> 4 files changed, 112 insertions(+), 171 deletions(-)
>
> diff --git a/drivers/mtd/nand/am335x_spl_bch.c b/drivers/mtd/nand/am335x_spl_bch.c
> index a8a7a66a18..c433caa365 100644
> --- a/drivers/mtd/nand/am335x_spl_bch.c
> +++ b/drivers/mtd/nand/am335x_spl_bch.c
> @@ -170,53 +170,6 @@ static int nand_read_page(int block, int page, void *dst)
> return 0;
> }
>
> -int nand_spl_load_image(uint32_t offs, unsigned int size, void *dst)
> -{
> - unsigned int block, lastblock;
> - unsigned int page, page_offset;
> -
> - /*
> - * offs has to be aligned to a page address!
> - */
> - block = offs / CONFIG_SYS_NAND_BLOCK_SIZE;
> - lastblock = (offs + size - 1) / CONFIG_SYS_NAND_BLOCK_SIZE;
> - page = (offs % CONFIG_SYS_NAND_BLOCK_SIZE) / CONFIG_SYS_NAND_PAGE_SIZE;
> - page_offset = offs % CONFIG_SYS_NAND_PAGE_SIZE;
> -
> - while (block <= lastblock) {
> - if (!nand_is_bad_block(block)) {
> - /*
> - * Skip bad blocks
> - */
> - while (page < CONFIG_SYS_NAND_PAGE_COUNT) {
> - nand_read_page(block, page, dst);
> - /*
> - * When offs is not aligned to page address the
> - * extra offset is copied to dst as well. Copy
> - * the image such that its first byte will be
> - * at the dst.
> - */
> - if (unlikely(page_offset)) {
> - memmove(dst, dst + page_offset,
> - CONFIG_SYS_NAND_PAGE_SIZE);
> - dst = (void *)((int)dst - page_offset);
> - page_offset = 0;
> - }
> - dst += CONFIG_SYS_NAND_PAGE_SIZE;
> - page++;
> - }
> -
> - page = 0;
> - } else {
> - lastblock++;
> - }
> -
> - block++;
> - }
> -
> - return 0;
> -}
> -
> /* nand_init() - initialize data to make nand usable by SPL */
> void nand_init(void)
> {
> @@ -241,3 +194,5 @@ void nand_deselect(void)
> if (nand_chip.select_chip)
> nand_chip.select_chip(mtd, -1);
> }
> +
> +#include "nand_spl_loaders.c"
> diff --git a/drivers/mtd/nand/atmel_nand.c b/drivers/mtd/nand/atmel_nand.c
> index 8669432deb..00c8bc5f12 100644
> --- a/drivers/mtd/nand/atmel_nand.c
> +++ b/drivers/mtd/nand/atmel_nand.c
> @@ -1379,34 +1379,6 @@ static int nand_read_page(int block, int page, void *dst)
> }
> #endif /* CONFIG_SPL_NAND_ECC */
>
> -int nand_spl_load_image(uint32_t offs, unsigned int size, void *dst)
> -{
> - unsigned int block, lastblock;
> - unsigned int page;
> -
> - block = offs / CONFIG_SYS_NAND_BLOCK_SIZE;
> - lastblock = (offs + size - 1) / CONFIG_SYS_NAND_BLOCK_SIZE;
> - page = (offs % CONFIG_SYS_NAND_BLOCK_SIZE) / CONFIG_SYS_NAND_PAGE_SIZE;
> -
> - while (block <= lastblock) {
> - if (!nand_is_bad_block(block)) {
> - while (page < CONFIG_SYS_NAND_PAGE_COUNT) {
> - nand_read_page(block, page, dst);
> - dst += CONFIG_SYS_NAND_PAGE_SIZE;
> - page++;
> - }
> -
> - page = 0;
> - } else {
> - lastblock++;
> - }
> -
> - block++;
> - }
> -
> - return 0;
> -}
> -
> int at91_nand_wait_ready(struct mtd_info *mtd)
> {
> struct nand_chip *this = mtd_to_nand(mtd);
> @@ -1473,6 +1445,8 @@ void nand_deselect(void)
> nand_chip.select_chip(mtd, -1);
> }
>
> +#include "nand_spl_loaders.c"
> +
> #else
>
> #ifndef CONFIG_SYS_NAND_BASE_LIST
> diff --git a/drivers/mtd/nand/nand_spl_loaders.c b/drivers/mtd/nand/nand_spl_loaders.c
> new file mode 100644
> index 0000000000..2a4b104954
> --- /dev/null
> +++ b/drivers/mtd/nand/nand_spl_loaders.c
> @@ -0,0 +1,106 @@
> +#ifdef CONFIG_SPL_NAND_LOAD
> +int nand_spl_load_image(uint32_t offs, unsigned int size, void *dst)
> +{
> + unsigned int block, lastblock;
> + unsigned int page, page_offset;
> +
> + /* offs has to be aligned to a page address! */
> + block = offs / CONFIG_SYS_NAND_BLOCK_SIZE;
> + lastblock = (offs + size - 1) / CONFIG_SYS_NAND_BLOCK_SIZE;
> + page = (offs % CONFIG_SYS_NAND_BLOCK_SIZE) / CONFIG_SYS_NAND_PAGE_SIZE;
> + page_offset = offs % CONFIG_SYS_NAND_PAGE_SIZE;
> +
> + while (block <= lastblock) {
> + if (!nand_is_bad_block(block)) {
> + /* Skip bad blocks */
> + while (page < CONFIG_SYS_NAND_PAGE_COUNT) {
> + nand_read_page(block, page, dst);
> + /*
> + * When offs is not aligned to page address the
> + * extra offset is copied to dst as well. Copy
> + * the image such that its first byte will be
> + * at the dst.
> + */
> + if (unlikely(page_offset)) {
> + memmove(dst, dst + page_offset,
> + CONFIG_SYS_NAND_PAGE_SIZE);
> + dst = (void *)((int)dst - page_offset);
> + page_offset = 0;
> + }
> + dst += CONFIG_SYS_NAND_PAGE_SIZE;
> + page++;
> + }
> +
> + page = 0;
> + } else {
> + lastblock++;
> + }
> +
> + block++;
> + }
> +
> + return 0;
> +}
> +#endif
> +
> +#ifdef CONFIG_SPL_UBI
> +/*
> + * Temporary storage for non NAND page aligned and non NAND page sized
> + * reads. Note: This does not support runtime detected FLASH yet, but
> + * that should be reasonably easy to fix by making the buffer large
> + * enough :)
> + */
> +static u8 scratch_buf[CONFIG_SYS_NAND_PAGE_SIZE];
> +
> +/**
> + * nand_spl_read_block - Read data from physical eraseblock into a buffer
> + * @block: Number of the physical eraseblock
> + * @offset: Data offset from the start of @peb
> + * @len: Data size to read
> + * @dst: Address of the destination buffer
> + *
> + * This could be further optimized if we'd have a subpage read
> + * function in the simple code. On NAND which allows subpage reads
> + * this would spare quite some time to readout e.g. the VID header of
> + * UBI.
> + *
> + * Notes:
> + * @offset + @len are not allowed to be larger than a physical
> + * erase block. No sanity check done for simplicity reasons.
> + *
> + * To support runtime detected flash this needs to be extended by
> + * information about the actual flash geometry, but thats beyond the
> + * scope of this effort and for most applications where fast boot is
> + * required it is not an issue anyway.
> + */
> +int nand_spl_read_block(int block, int offset, int len, void *dst)
> +{
> + int page, read;
> +
> + /* Calculate the page number */
> + page = offset / CONFIG_SYS_NAND_PAGE_SIZE;
> +
> + /* Offset to the start of a flash page */
> + offset = offset % CONFIG_SYS_NAND_PAGE_SIZE;
> +
> + while (len) {
> + /*
> + * Non page aligned reads go to the scratch buffer.
> + * Page aligned reads go directly to the destination.
> + */
> + if (offset || len < CONFIG_SYS_NAND_PAGE_SIZE) {
> + nand_read_page(block, page, scratch_buf);
> + read = min(len, CONFIG_SYS_NAND_PAGE_SIZE - offset);
> + memcpy(dst, scratch_buf + offset, read);
> + offset = 0;
> + } else {
> + nand_read_page(block, page, dst);
> + read = CONFIG_SYS_NAND_PAGE_SIZE;
> + }
> + page++;
> + len -= read;
> + dst += read;
> + }
> + return 0;
> +}
> +#endif
> diff --git a/drivers/mtd/nand/nand_spl_simple.c b/drivers/mtd/nand/nand_spl_simple.c
> index 55f48d3a14..56e86d1760 100644
> --- a/drivers/mtd/nand/nand_spl_simple.c
> +++ b/drivers/mtd/nand/nand_spl_simple.c
> @@ -209,102 +209,6 @@ static int nand_read_page(int block, int page, void *dst)
> }
> #endif
>
> -#ifdef CONFIG_SPL_UBI
> -/*
> - * Temporary storage for non NAND page aligned and non NAND page sized
> - * reads. Note: This does not support runtime detected FLASH yet, but
> - * that should be reasonably easy to fix by making the buffer large
> - * enough :)
> - */
> -static u8 scratch_buf[CONFIG_SYS_NAND_PAGE_SIZE];
> -
> -/**
> - * nand_spl_read_block - Read data from physical eraseblock into a buffer
> - * @block: Number of the physical eraseblock
> - * @offset: Data offset from the start of @peb
> - * @len: Data size to read
> - * @dst: Address of the destination buffer
> - *
> - * This could be further optimized if we'd have a subpage read
> - * function in the simple code. On NAND which allows subpage reads
> - * this would spare quite some time to readout e.g. the VID header of
> - * UBI.
> - *
> - * Notes:
> - * @offset + @len are not allowed to be larger than a physical
> - * erase block. No sanity check done for simplicity reasons.
> - *
> - * To support runtime detected flash this needs to be extended by
> - * information about the actual flash geometry, but thats beyond the
> - * scope of this effort and for most applications where fast boot is
> - * required it is not an issue anyway.
> - */
> -int nand_spl_read_block(int block, int offset, int len, void *dst)
> -{
> - int page, read;
> -
> - /* Calculate the page number */
> - page = offset / CONFIG_SYS_NAND_PAGE_SIZE;
> -
> - /* Offset to the start of a flash page */
> - offset = offset % CONFIG_SYS_NAND_PAGE_SIZE;
> -
> - while (len) {
> - /*
> - * Non page aligned reads go to the scratch buffer.
> - * Page aligned reads go directly to the destination.
> - */
> - if (offset || len < CONFIG_SYS_NAND_PAGE_SIZE) {
> - nand_read_page(block, page, scratch_buf);
> - read = min(len, CONFIG_SYS_NAND_PAGE_SIZE - offset);
> - memcpy(dst, scratch_buf + offset, read);
> - offset = 0;
> - } else {
> - nand_read_page(block, page, dst);
> - read = CONFIG_SYS_NAND_PAGE_SIZE;
> - }
> - page++;
> - len -= read;
> - dst += read;
> - }
> - return 0;
> -}
> -#endif
> -
> -int nand_spl_load_image(uint32_t offs, unsigned int size, void *dst)
> -{
> - unsigned int block, lastblock;
> - unsigned int page;
> -
> - /*
> - * offs has to be aligned to a page address!
> - */
> - block = offs / CONFIG_SYS_NAND_BLOCK_SIZE;
> - lastblock = (offs + size - 1) / CONFIG_SYS_NAND_BLOCK_SIZE;
> - page = (offs % CONFIG_SYS_NAND_BLOCK_SIZE) / CONFIG_SYS_NAND_PAGE_SIZE;
> -
> - while (block <= lastblock) {
> - if (!nand_is_bad_block(block)) {
> - /*
> - * Skip bad blocks
> - */
> - while (page < CONFIG_SYS_NAND_PAGE_COUNT) {
> - nand_read_page(block, page, dst);
> - dst += CONFIG_SYS_NAND_PAGE_SIZE;
> - page++;
> - }
> -
> - page = 0;
> - } else {
> - lastblock++;
> - }
> -
> - block++;
> - }
> -
> - return 0;
> -}
> -
> /* nand_init() - initialize data to make nand usable by SPL */
> void nand_init(void)
> {
> @@ -333,3 +237,5 @@ void nand_deselect(void)
> if (nand_chip.select_chip)
> nand_chip.select_chip(mtd, -1);
> }
> +
> +#include "nand_spl_loaders.c"
> --
> 2.11.0
>
More information about the U-Boot
mailing list