summaryrefslogtreecommitdiff
path: root/nanddump.c
diff options
context:
space:
mode:
authorBrian Norris <computersforpeace@gmail.com>2011-06-03 11:25:00 -0700
committerArtem Bityutskiy <Artem.Bityutskiy@nokia.com>2011-06-06 14:09:33 +0300
commit5dfb5a6adc731120e0c0bde63e0b8ee1b3922888 (patch)
tree02a16e8b1bd9a5708e9a1108c4464d4a0e4bd9e8 /nanddump.c
parent4f3c679db7415b4b0321848a4734abcec30dd9d8 (diff)
nanddump: add --skipbad option for bad blocks
This patch adds a new option "--skipbad" to nanddump. It is subtly different than "--omitbad". The following description was included in the help message to attempt to clarify the differences. Notes on --omitbad and --skipbad: With either option, we stop dumping data when we encounter a bad block and resume dumping at the next good block. However, with --omitbad, we count the bad block as part of the total dump length, whereas with --skipbad, the bad block is 'skipped,' that is, not counted toward the total dump length. Signed-off-by: Brian Norris <computersforpeace@gmail.com> Signed-off-by: Artem Bityutskiy <Artem.Bityutskiy@nokia.com>
Diffstat (limited to 'nanddump.c')
-rw-r--r--nanddump.c38
1 files changed, 36 insertions, 2 deletions
diff --git a/nanddump.c b/nanddump.c
index 214fb12..78ea22e 100644
--- a/nanddump.c
+++ b/nanddump.c
@@ -50,6 +50,7 @@ static void display_help(void)
"-a --forcebinary Force printing of binary data to tty\n"
"-c --canonicalprint Print canonical Hex+ASCII dump\n"
"-f file --file=file Dump to file\n"
+"-k --skipbad Skip over bad blocks (see below)\n"
"-l length --length=length Length\n"
"-n --noecc Read without error correction\n"
"-N --noskipbad Read without bad block skipping\n"
@@ -57,7 +58,14 @@ static void display_help(void)
"-b --omitbad Omit bad blocks from the dump\n"
"-p --prettyprint Print nice (hexdump)\n"
"-q --quiet Don't display progress and status messages\n"
-"-s addr --startaddress=addr Start address\n",
+"-s addr --startaddress=addr Start address\n"
+"\n"
+"Notes on --omitbad and --skipbad:\n"
+" With either option, we stop dumping data when we encounter a bad block\n"
+" and resume dumping at the next good block. However, with --omitbad, we\n"
+" count the bad block as part of the total dump length, whereas with\n"
+" --skipbad, the bad block is 'skipped,' that is, not counted toward the\n"
+" total dump length.\n",
PROGRAM_NAME);
exit(EXIT_SUCCESS);
}
@@ -90,6 +98,7 @@ static bool omitbad = false;
static bool quiet = false; // suppress diagnostic output
static bool canonical = false; // print nice + ascii
static bool forcebinary = false; // force printing binary to tty
+static bool skipbad = false; // skip over bad blocks
static void process_options(int argc, char * const argv[])
{
@@ -97,7 +106,7 @@ static void process_options(int argc, char * const argv[])
for (;;) {
int option_index = 0;
- static const char *short_options = "bs:f:l:opqnNca";
+ static const char *short_options = "bs:f:l:opqnNcak";
static const struct option long_options[] = {
{"help", no_argument, 0, 0},
{"version", no_argument, 0, 0},
@@ -111,6 +120,7 @@ static void process_options(int argc, char * const argv[])
{"length", required_argument, 0, 'l'},
{"noecc", no_argument, 0, 'n'},
{"noskipbad", no_argument, 0, 'N'},
+ {"skipbad", no_argument, 0, 'k'},
{"quiet", no_argument, 0, 'q'},
{0, 0, 0, 0},
};
@@ -167,6 +177,9 @@ static void process_options(int argc, char * const argv[])
case 'N':
noskipbad = true;
break;
+ case 'k':
+ skipbad = true;
+ break;
case '?':
error++;
break;
@@ -193,6 +206,19 @@ static void process_options(int argc, char * const argv[])
exit(EXIT_FAILURE);
}
+ if (noskipbad && skipbad) {
+ fprintf(stderr, "The noskipbad and skipbad options are "
+ "mutually-exclusive.\n"
+ "Choose one or the other.\n");
+ exit(EXIT_FAILURE);
+ }
+
+ if (omitbad && skipbad) {
+ fprintf(stderr, "The omitbad and skipbad options are mutually-"
+ "exclusive.\nChoose one or the other.\n");
+ exit(EXIT_FAILURE);
+ }
+
if ((argc - optind) != 1 || error)
display_help();
@@ -403,6 +429,14 @@ int main(int argc, char * const argv[])
}
if (badblock) {
+ /* skip bad block, increase end_addr */
+ if (skipbad) {
+ end_addr += mtd.eb_size;
+ ofs += mtd.eb_size - bs;
+ if (end_addr > mtd.size)
+ end_addr = mtd.size;
+ continue;
+ }
if (omitbad)
continue;
memset(readbuf, 0xff, bs);