From a1ca60f4e5b2694af6145ba52ca7709438c42766 Mon Sep 17 00:00:00 2001 From: Jim Meyering Date: Sun, 3 Dec 2000 08:44:12 +0000 Subject: [PATCH] Make od print valid addresses for offsets of 2^32 and larger. (format_address): Use off_t, not long unsigned_int as the parameter type. (format_address_none): Likewise. Mark parameter as unused. (format_address_std): Likewise. (format_address_label): Likewise. (print_ascii): Mark format string parameter as unused. (write_block): Use off_t, not long unsigned_int as offset type. (expand_address_fmt): New function. (main): Use it to expand each address format string template. Reported by Mark Nudelman, via Andreas Jaeger. --- src/od.c | 44 ++++++++++++++++++++++++++++++++------------ 1 file changed, 32 insertions(+), 12 deletions(-) diff --git a/src/od.c b/src/od.c index 2b8ba2f..7f7cec6 100644 --- a/src/od.c +++ b/src/od.c @@ -178,7 +178,7 @@ static long int pseudo_offset; /* Function to format an address and optionally an additional parenthesized pseudo-address; it returns the formatted string. */ -static const char *(*format_address) PARAMS ((long unsigned int)); +static const char *(*format_address) PARAMS ((off_t)); /* The number of input bytes to skip before formatting and writing. */ static off_t n_bytes_to_skip = 0; @@ -516,7 +516,7 @@ dump_hexl_mode_trailer (long unsigned int n_bytes, const char *block) static void print_named_ascii (long unsigned int n_bytes, const char *block, - const char *unused_fmt_string) + const char *unused_fmt_string ATTRIBUTE_UNUSED) { int i; for (i = n_bytes; i > 0; i--) @@ -543,7 +543,7 @@ print_named_ascii (long unsigned int n_bytes, const char *block, static void print_ascii (long unsigned int n_bytes, const char *block, - const char *unused_fmt_string) + const char *unused_fmt_string ATTRIBUTE_UNUSED) { int i; for (i = n_bytes; i > 0; i--) @@ -1052,13 +1052,13 @@ skip (off_t n_skip) } static const char * -format_address_none (long unsigned int address) +format_address_none (off_t address ATTRIBUTE_UNUSED) { return ""; } static const char * -format_address_std (long unsigned int address) +format_address_std (off_t address) { const char *address_string; @@ -1068,7 +1068,7 @@ format_address_std (long unsigned int address) } static const char * -format_address_label (long unsigned int address) +format_address_label (off_t address) { const char *address_string; assert (output_address_fmt_string != NULL); @@ -1091,7 +1091,7 @@ format_address_label (long unsigned int address) only when it has not been padded to length BYTES_PER_BLOCK. */ static void -write_block (long unsigned int current_offset, long unsigned int n_bytes, +write_block (off_t current_offset, long unsigned int n_bytes, const char *prev_block, const char *curr_block) { static int first = 1; @@ -1582,6 +1582,26 @@ dump_strings (void) return err; } +/* There must be exactly one %s format specifier in FORMAT_TEMPLATE. + Return the just-malloc'd result of using sprintf to insert + OFF_T_PRINTF_FORMAT_STRING into FORMAT_TEMPLATE. + Technically, the caller should free this memory, but IMHO it's not + worth it in this case. */ +static char * +expand_address_fmt (char const *format_template) +{ + size_t len = strlen (format_template); + char *fmt = xmalloc (len + 1); + /* Ensure that the literal we're inserting is no longer than the two-byte + string `%s' it's replacing. There's also the %%, so technically we don't + even need the `+ 1' above. */ + assert (OFF_T_PRINTF_FORMAT_STRING[0] == 0 + || OFF_T_PRINTF_FORMAT_STRING[1] == 0 + || OFF_T_PRINTF_FORMAT_STRING[2] == 0); + sprintf (fmt, format_template, OFF_T_PRINTF_FORMAT_STRING); + return fmt; +} + int main (int argc, char **argv) { @@ -1633,7 +1653,7 @@ main (int argc, char **argv) n_specs_allocated = 5; spec = (struct tspec *) xmalloc (n_specs_allocated * sizeof (struct tspec)); - output_address_fmt_string = "%07o"; + output_address_fmt_string = expand_address_fmt ("%%07%so"); format_address = format_address_std; address_pad_len = 7; flag_dump_strings = 0; @@ -1653,17 +1673,17 @@ main (int argc, char **argv) switch (optarg[0]) { case 'd': - output_address_fmt_string = "%07d"; + output_address_fmt_string = expand_address_fmt ("%%07%sd"); format_address = format_address_std; address_pad_len = 7; break; case 'o': - output_address_fmt_string = "%07o"; + output_address_fmt_string = expand_address_fmt ("%%07%so"); format_address = format_address_std; address_pad_len = 7; break; case 'x': - output_address_fmt_string = "%06x"; + output_address_fmt_string = expand_address_fmt ("%%06%sx"); format_address = format_address_std; address_pad_len = 6; break; @@ -1867,7 +1887,7 @@ the maximum\nrepresentable value of type `long'"), optarg); if (output_address_fmt_string == NULL) { - output_address_fmt_string = "(%07o)"; + output_address_fmt_string = expand_address_fmt ("(%%07%so)"); format_address = format_address_std; } else -- 2.7.4