We already have --length (aka --limit) for limiting how far the dump
goes; the obvious counterpart is --offset (aka --skip) for controlling
where to start the dump.
I did not bother to try and print an unaligned partial first line so
that subsequent lines can be nicely aligned, but rather the dump
always starts with a full line even when it displays with unusual
offsets.
Signed-off-by: Eric Blake <eblake(a)redhat.com>
---
dump/nbddump.pod | 8 +++++++-
dump/dump.c | 19 ++++++++++++++++---
2 files changed, 23 insertions(+), 4 deletions(-)
diff --git a/dump/nbddump.pod b/dump/nbddump.pod
index b05472fe..6acac426 100644
--- a/dump/nbddump.pod
+++ b/dump/nbddump.pod
@@ -4,7 +4,7 @@ nbddump - hexdump the content of a disk over NBD
=head1 SYNOPSIS
- nbddump [-n N|--length N] NBD
+ nbddump [-n N|--length N] [-o N|--offset N] NBD
C<NBD> is an NBD URI or subprocess:
@@ -103,6 +103,12 @@ if the output seems to be a terminal, and disable them if not.
Dump up to I<N> bytes and then stop.
+=item B<--offset=>N
+
+=item B<-o> N
+
+Start the dump at offset I<N> bytes.
+
=item B<-V>
=item B<--version>
diff --git a/dump/dump.c b/dump/dump.c
index 71bedf6a..7a475196 100644
--- a/dump/dump.c
+++ b/dump/dump.c
@@ -44,6 +44,7 @@ static const char *progname;
static struct nbd_handle *nbd;
bool colour;
static uint64_t limit = UINT64_MAX; /* --length (unlimited by default) */
+static uint64_t skip; /* --offset (0 by default) */
static int64_t size; /* actual size */
static bool can_meta_context; /* did we get extent data? */
@@ -72,6 +73,7 @@ usage (FILE *fp, int exitcode)
" --no-color, --no-colour\n"
" Suppress ANSI color even on output to terminal\n"
" -n LEN, --length=LEN Truncate output after LEN bytes dumped\n"
+" -o OFF, --offset=OFF Skip to offset OFF bytes before dumping\n"
"\n"
"Other options:\n"
"\n"
@@ -99,7 +101,7 @@ main (int argc, char *argv[])
COLOUR_OPTION,
NO_COLOUR_OPTION,
};
- const char *short_options = "n:V";
+ const char *short_options = "n:o:V";
const struct option long_options[] = {
{ "help", no_argument, NULL, HELP_OPTION },
{ "long-options", no_argument, NULL, LONG_OPTIONS },
@@ -116,6 +118,8 @@ main (int argc, char *argv[])
{ "no-colours", no_argument, NULL, NO_COLOUR_OPTION },
{ "length", required_argument, NULL, 'n' },
{ "limit", required_argument, NULL, 'n' },
+ { "offset", required_argument, NULL, 'o' },
+ { "skip", required_argument, NULL, 'o' },
{ NULL }
};
int c;
@@ -165,6 +169,15 @@ main (int argc, char *argv[])
}
break;
+ case 'o':
+ /* XXX Allow human sizes here. */
+ if (sscanf (optarg, "%" SCNu64, &skip) != 1) {
+ fprintf (stderr, "%s: could not parse --offset option: %s\n",
+ progname, optarg);
+ exit (EXIT_FAILURE);
+ }
+ break;
+
case 'V':
display_version ("nbddump");
exit (EXIT_SUCCESS);
@@ -342,8 +355,8 @@ do_dump (void)
const char *splat = colour ? "☆" : "*";
const char *pipe = colour ? "│" : "|";
const char *dot = colour ? "·" : ".";
- uint64_t offset = 0;
- uint64_t count = size > limit ? limit : size;
+ uint64_t offset = skip;
+ uint64_t count = size - offset > limit ? limit : size - offset;
size_t i, j;
char last[16];
bool printed_splat = false, same;
--
2.48.1