From mboxrd@z Thu Jan 1 00:00:00 1970 From: Scott Wood Date: Mon, 17 Jun 2013 19:51:26 -0500 Subject: [U-Boot] [PATCH v2] dfu, nand: before write a buffer to nand, erase the nand sectors In-Reply-To: <1371445261-3785-1-git-send-email-hs@denx.de> (from hs@denx.de on Mon Jun 17 00:01:01 2013) Message-ID: <1371516686.9073.17@snotra> List-Id: MIME-Version: 1.0 Content-Type: text/plain; charset="us-ascii" Content-Transfer-Encoding: 7bit To: u-boot@lists.denx.de On 06/17/2013 12:01:01 AM, Heiko Schocher wrote: > before writing the received buffer to nand, erase the nand > sectors. If not doing this, nand write fails. See for > more info here: > > http://lists.denx.de/pipermail/u-boot/2013-June/156361.html > > Signed-off-by: Heiko Schocher > Cc: Scott Wood > Cc: Pantelis Antoniou > Cc: Lukasz Majewski > Cc: Kyungmin Park > Cc: Marek Vasut > Cc: Tom Rini > > --- > - changes for v2: > - use opts.spread as Scott Wood suggested > > drivers/dfu/dfu_nand.c | 17 +++++++++++++++-- > 1 Datei ge?ndert, 15 Zeilen hinzugef?gt(+), 2 Zeilen entfernt(-) > > diff --git a/drivers/dfu/dfu_nand.c b/drivers/dfu/dfu_nand.c > index 7dc89b2..93db9bd 100644 > --- a/drivers/dfu/dfu_nand.c > +++ b/drivers/dfu/dfu_nand.c > @@ -63,12 +63,25 @@ static int nand_block_op(enum dfu_nand_op op, > struct dfu_entity *dfu, > > nand = &nand_info[nand_curr_device]; > > - if (op == DFU_OP_READ) > + if (op == DFU_OP_READ) { > ret = nand_read_skip_bad(nand, start, &count, &actual, > lim, buf); > - else > + } else { > + nand_erase_options_t opts; > + > + memset(&opts, 0, sizeof(opts)); > + opts.offset = start; > + opts.length = count; > + opts.spread = 1; > + opts.quiet = 1; > + /* first erase */ > + ret = nand_erase_opts(nand, &opts); > + if (ret) > + return ret; > + /* then write */ > ret = nand_write_skip_bad(nand, start, &count, &actual, > lim, buf, 0); BTW, I notice you are currently using the limit functionality of nand_read/write_skip_bad... opts.spread currently does not have this support (as I noted before), which means that if there's an error you'd erase too much and then refuse to write. Maybe we need an opts.limit? adjust_size_for_badblocks, OTOH, is probably the opposite of what you wanted -- it subtracts from the size in order to get the number of good blocks within an interval, rather than adding the number of bad blocks to turn a data size into an interval. It's meant to produce an input to be used with skipping/spreading operations. Which makes me think we have a bug in cmd_nand.c -- we should be setting .spread in erase cases where we call adjust_size_for_badblocks. -Scott