Arrange to call close_stdout upon exit. Don't close stdout explicitly.
[platform/upstream/coreutils.git] / src / od.c
1 /* od -- dump files in octal and other formats
2    Copyright (C) 92, 1995-2000 Free Software Foundation, Inc.
3
4    This program is free software; you can redistribute it and/or modify
5    it under the terms of the GNU General Public License as published by
6    the Free Software Foundation; either version 2, or (at your option)
7    any later version.
8
9    This program is distributed in the hope that it will be useful,
10    but WITHOUT ANY WARRANTY; without even the implied warranty of
11    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12    GNU General Public License for more details.
13
14    You should have received a copy of the GNU General Public License
15    along with this program; if not, write to the Free Software Foundation,
16    Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.  */
17
18 /* Written by Jim Meyering.  */
19
20 #include <config.h>
21
22 #include <stdio.h>
23 #include <assert.h>
24 #include <getopt.h>
25 #include <sys/types.h>
26 #include "system.h"
27 #include "closeout.h"
28 #include "error.h"
29 #include "xstrtol.h"
30
31 /* The official name of this program (e.g., no `g' prefix).  */
32 #define PROGRAM_NAME "od"
33
34 #define AUTHORS "Jim Meyering"
35
36 #if defined(__GNUC__) || defined(STDC_HEADERS)
37 # include <float.h>
38 #endif
39
40 #ifdef HAVE_LONG_DOUBLE
41 typedef long double LONG_DOUBLE;
42 #else
43 typedef double LONG_DOUBLE;
44 #endif
45
46 #if HAVE_VALUES_H
47 # include <values.h>
48 #endif
49
50 /* The default number of input bytes per output line.  */
51 #define DEFAULT_BYTES_PER_BLOCK 16
52
53 /* The number of decimal digits of precision in a float.  */
54 #ifndef FLT_DIG
55 # define FLT_DIG 7
56 #endif
57
58 /* The number of decimal digits of precision in a double.  */
59 #ifndef DBL_DIG
60 # define DBL_DIG 15
61 #endif
62
63 /* The number of decimal digits of precision in a long double.  */
64 #ifndef LDBL_DIG
65 # define LDBL_DIG DBL_DIG
66 #endif
67
68 #if !HAVE_FSEEKO
69 # undef fseeko
70 # define fseeko(Stream, Offset, Whence) (-1)
71 #endif
72
73 enum size_spec
74   {
75     NO_SIZE,
76     CHAR,
77     SHORT,
78     INT,
79     LONG,
80     FLOAT_SINGLE,
81     FLOAT_DOUBLE,
82     FLOAT_LONG_DOUBLE
83   };
84
85 enum output_format
86   {
87     SIGNED_DECIMAL,
88     UNSIGNED_DECIMAL,
89     OCTAL,
90     HEXADECIMAL,
91     FLOATING_POINT,
92     NAMED_CHARACTER,
93     CHARACTER
94   };
95
96 /* Each output format specification (from POSIX `-t spec' or from
97    old-style options) is represented by one of these structures.  */
98 struct tspec
99   {
100     enum output_format fmt;
101     enum size_spec size;
102     void (*print_function) ();
103     char *fmt_string;
104     int hexl_mode_trailer;
105     int field_width;
106   };
107
108 /* The name this program was run with.  */
109 char *program_name;
110
111 /* Convert the number of 8-bit bytes of a binary representation to
112    the number of characters (digits + sign if the type is signed)
113    required to represent the same quantity in the specified base/type.
114    For example, a 32-bit (4-byte) quantity may require a field width
115    as wide as the following for these types:
116    11   unsigned octal
117    11   signed decimal
118    10   unsigned decimal
119    8    unsigned hexadecimal  */
120
121 static const unsigned int bytes_to_oct_digits[] =
122 {0, 3, 6, 8, 11, 14, 16, 19, 22, 25, 27, 30, 32, 35, 38, 41, 43};
123
124 static const unsigned int bytes_to_signed_dec_digits[] =
125 {1, 4, 6, 8, 11, 13, 16, 18, 20, 23, 25, 28, 30, 33, 35, 37, 40};
126
127 static const unsigned int bytes_to_unsigned_dec_digits[] =
128 {0, 3, 5, 8, 10, 13, 15, 17, 20, 22, 25, 27, 29, 32, 34, 37, 39};
129
130 static const unsigned int bytes_to_hex_digits[] =
131 {0, 2, 4, 6, 8, 10, 12, 14, 16, 18, 20, 22, 24, 26, 28, 30, 32};
132
133 /* Convert enum size_spec to the size of the named type.  */
134 static const int width_bytes[] =
135 {
136   -1,
137   sizeof (char),
138   sizeof (short int),
139   sizeof (int),
140   sizeof (long int),
141   sizeof (float),
142   sizeof (double),
143   sizeof (LONG_DOUBLE)
144 };
145
146 /* Names for some non-printing characters.  */
147 static const char *const charname[33] =
148 {
149   "nul", "soh", "stx", "etx", "eot", "enq", "ack", "bel",
150   "bs", "ht", "nl", "vt", "ff", "cr", "so", "si",
151   "dle", "dc1", "dc2", "dc3", "dc4", "nak", "syn", "etb",
152   "can", "em", "sub", "esc", "fs", "gs", "rs", "us",
153   "sp"
154 };
155
156 /* A printf control string for printing a file offset.  */
157 static const char *output_address_fmt_string;
158
159 /* FIXME: make this the number of octal digits in an unsigned long.  */
160 #define MAX_ADDRESS_LENGTH 13
161
162 /* Space for a normal address, a space, a pseudo address, parentheses
163    around the pseudo address, and a trailing zero byte. */
164 static char address_fmt_buffer[2 * MAX_ADDRESS_LENGTH + 4];
165 static char address_pad[MAX_ADDRESS_LENGTH + 1];
166
167 static unsigned long int string_min;
168 static unsigned long int flag_dump_strings;
169
170 /* Non-zero if we should recognize the pre-POSIX non-option arguments
171    that specified at most one file and optional arguments specifying
172    offset and pseudo-start address.  */
173 static int traditional;
174
175 /* Non-zero if an old-style `pseudo-address' was specified.  */
176 static long int flag_pseudo_start;
177
178 /* The difference between the old-style pseudo starting address and
179    the number of bytes to skip.  */
180 static long int pseudo_offset;
181
182 /* Function to format an address and optionally an additional parenthesized
183    pseudo-address; it returns the formatted string.  */
184 static const char *(*format_address) PARAMS ((long unsigned int));
185
186 /* The number of input bytes to skip before formatting and writing.  */
187 static off_t n_bytes_to_skip = 0;
188
189 /* When nonzero, MAX_BYTES_TO_FORMAT is the maximum number of bytes
190    to be read and formatted.  Otherwise all input is formatted.  */
191 static int limit_bytes_to_format = 0;
192
193 /* The maximum number of bytes that will be formatted.  This
194    value is used only when LIMIT_BYTES_TO_FORMAT is nonzero.  */
195 static off_t max_bytes_to_format;
196
197 /* When nonzero and two or more consecutive blocks are equal, format
198    only the first block and output an asterisk alone on the following
199    line to indicate that identical blocks have been elided.  */
200 static int abbreviate_duplicate_blocks = 1;
201
202 /* An array of specs describing how to format each input block.  */
203 static struct tspec *spec;
204
205 /* The number of format specs.  */
206 static unsigned int n_specs;
207
208 /* The allocated length of SPEC.  */
209 static unsigned int n_specs_allocated;
210
211 /* The number of input bytes formatted per output line.  It must be
212    a multiple of the least common multiple of the sizes associated with
213    the specified output types.  It should be as large as possible, but
214    no larger than 16 -- unless specified with the -w option.  */
215 static unsigned int bytes_per_block;
216
217 /* Human-readable representation of *file_list (for error messages).
218    It differs from *file_list only when *file_list is "-".  */
219 static char const *input_filename;
220
221 /* A NULL-terminated list of the file-arguments from the command line.
222    If no file-arguments were specified, this variable is initialized
223    to { "-", NULL }.  */
224 static char const *const *file_list;
225
226 /* The input stream associated with the current file.  */
227 static FILE *in_stream;
228
229 /* If nonzero, at least one of the files we read was standard input.  */
230 static int have_read_stdin;
231
232 #define LONGEST_INTEGRAL_TYPE long int
233
234 #define MAX_INTEGRAL_TYPE_SIZE sizeof(LONGEST_INTEGRAL_TYPE)
235 static enum size_spec integral_type_size[MAX_INTEGRAL_TYPE_SIZE + 1];
236
237 #define MAX_FP_TYPE_SIZE sizeof(LONG_DOUBLE)
238 static enum size_spec fp_type_size[MAX_FP_TYPE_SIZE + 1];
239
240 static struct option const long_options[] =
241 {
242   /* POSIX options.  */
243   {"skip-bytes", required_argument, NULL, 'j'},
244   {"address-radix", required_argument, NULL, 'A'},
245   {"read-bytes", required_argument, NULL, 'N'},
246   {"format", required_argument, NULL, 't'},
247   {"output-duplicates", no_argument, NULL, 'v'},
248
249   /* non-POSIX options.  */
250   {"strings", optional_argument, NULL, 's'},
251   {"traditional", no_argument, NULL, 'B'},
252   {"width", optional_argument, NULL, 'w'},
253
254   {GETOPT_HELP_OPTION_DECL},
255   {GETOPT_VERSION_OPTION_DECL},
256   {NULL, 0, NULL, 0}
257 };
258
259 void
260 usage (int status)
261 {
262   if (status != 0)
263     fprintf (stderr, _("Try `%s --help' for more information.\n"),
264              program_name);
265   else
266     {
267       printf (_("\
268 Usage: %s [OPTION]... [FILE]...\n\
269   or:  %s --traditional [FILE] [[+]OFFSET [[+]LABEL]]\n\
270 "),
271               program_name, program_name);
272       printf (_("\
273 Write an unambiguous representation, octal bytes by default, of FILE\n\
274 to standard output.  With no FILE, or when FILE is -, read standard input.\n\
275 \n\
276   -A, --address-radix=RADIX   decide how file offsets are printed\n\
277   -j, --skip-bytes=BYTES      skip BYTES input bytes first on each file\n\
278   -N, --read-bytes=BYTES      limit dump to BYTES input bytes per file\n\
279   -s, --strings[=BYTES]       output strings of at least BYTES graphic chars\n\
280   -t, --format=TYPE           select output format or formats\n\
281   -v, --output-duplicates     do not use * to mark line suppression\n\
282   -w, --width[=BYTES]         output BYTES bytes per output line\n\
283       --traditional           accept arguments in pre-POSIX form\n\
284       --help                  display this help and exit\n\
285       --version               output version information and exit\n\
286 \n\
287 Pre-POSIX format specifications may be intermixed, they accumulate:\n\
288   -a   same as -t a,  select named characters\n\
289   -b   same as -t oC, select octal bytes\n\
290   -c   same as -t c,  select ASCII characters or backslash escapes\n\
291   -d   same as -t u2, select unsigned decimal shorts\n\
292   -f   same as -t fF, select floats\n\
293   -h   same as -t x2, select hexadecimal shorts\n\
294   -i   same as -t d2, select decimal shorts\n\
295   -l   same as -t d4, select decimal longs\n\
296   -o   same as -t o2, select octal shorts\n\
297   -x   same as -t x2, select hexadecimal shorts\n\
298 "));
299       printf (_("\
300 \n\
301 For older syntax (second call format), OFFSET means -j OFFSET.  LABEL\n\
302 is the pseudo-address at first byte printed, incremented when dump is\n\
303 progressing.  For OFFSET and LABEL, a 0x or 0X prefix indicates\n\
304 hexadecimal, suffixes maybe . for octal and b multiply by 512.\n\
305 \n\
306 TYPE is made up of one or more of these specifications:\n\
307 \n\
308   a          named character\n\
309   c          ASCII character or backslash escape\n\
310   d[SIZE]    signed decimal, SIZE bytes per integer\n\
311   f[SIZE]    floating point, SIZE bytes per integer\n\
312   o[SIZE]    octal, SIZE bytes per integer\n\
313   u[SIZE]    unsigned decimal, SIZE bytes per integer\n\
314   x[SIZE]    hexadecimal, SIZE bytes per integer\n\
315 \n\
316 SIZE is a number.  For TYPE in doux, SIZE may also be C for\n\
317 sizeof(char), S for sizeof(short), I for sizeof(int) or L for\n\
318 sizeof(long).  If TYPE is f, SIZE may also be F for sizeof(float), D\n\
319 for sizeof(double) or L for sizeof(long double).\n\
320 \n\
321 RADIX is d for decimal, o for octal, x for hexadecimal or n for none.\n\
322 BYTES is hexadecimal with 0x or 0X prefix, it is multiplied by 512\n\
323 with b suffix, by 1024 with k and by 1048576 with m.  Adding a z suffix to\n\
324 any type adds a display of printable characters to the end of each line\n\
325 of output.  -s without a number implies 3.  -w without a number implies 32.\n\
326 By default, od uses -A o -t d2 -w 16.\n\
327 "));
328       puts (_("\nReport bugs to <bug-textutils@gnu.org>."));
329     }
330   exit (status == 0 ? EXIT_SUCCESS : EXIT_FAILURE);
331 }
332
333 /* Compute the greatest common denominator of U and V
334    using Euclid's algorithm.  */
335
336 static unsigned int
337 gcd (unsigned int u, unsigned int v)
338 {
339   unsigned int t;
340   while (v != 0)
341     {
342       t = u % v;
343       u = v;
344       v = t;
345     }
346   return u;
347 }
348
349 /* Compute the least common multiple of U and V.  */
350
351 static unsigned int
352 lcm (unsigned int u, unsigned int v)
353 {
354   unsigned int t = gcd (u, v);
355   if (t == 0)
356     return 0;
357   return u * v / t;
358 }
359
360 static void
361 print_s_char (long unsigned int n_bytes, const char *block,
362               const char *fmt_string)
363 {
364   int i;
365   for (i = n_bytes; i > 0; i--)
366     {
367       int tmp = (unsigned) *(const unsigned char *) block;
368       if (tmp > SCHAR_MAX)
369         tmp -= SCHAR_MAX - SCHAR_MIN + 1;
370       assert (tmp <= SCHAR_MAX);
371       printf (fmt_string, tmp);
372       block += sizeof (unsigned char);
373     }
374 }
375
376 static void
377 print_char (long unsigned int n_bytes, const char *block,
378             const char *fmt_string)
379 {
380   int i;
381   for (i = n_bytes; i > 0; i--)
382     {
383       unsigned int tmp = *(const unsigned char *) block;
384       printf (fmt_string, tmp);
385       block += sizeof (unsigned char);
386     }
387 }
388
389 static void
390 print_s_short (long unsigned int n_bytes, const char *block,
391                const char *fmt_string)
392 {
393   int i;
394   for (i = n_bytes / sizeof (unsigned short); i > 0; i--)
395     {
396       int tmp = (unsigned) *(const unsigned short *) block;
397       if (tmp > SHRT_MAX)
398         tmp -= SHRT_MAX - SHRT_MIN + 1;
399       assert (tmp <= SHRT_MAX);
400       printf (fmt_string, tmp);
401       block += sizeof (unsigned short);
402     }
403 }
404
405 static void
406 print_short (long unsigned int n_bytes, const char *block,
407              const char *fmt_string)
408 {
409   int i;
410   for (i = n_bytes / sizeof (unsigned short); i > 0; i--)
411     {
412       unsigned int tmp = *(const unsigned short *) block;
413       printf (fmt_string, tmp);
414       block += sizeof (unsigned short);
415     }
416 }
417
418 static void
419 print_int (long unsigned int n_bytes, const char *block,
420            const char *fmt_string)
421 {
422   int i;
423   for (i = n_bytes / sizeof (unsigned int); i > 0; i--)
424     {
425       unsigned int tmp = *(const unsigned int *) block;
426       printf (fmt_string, tmp);
427       block += sizeof (unsigned int);
428     }
429 }
430
431 static void
432 print_long (long unsigned int n_bytes, const char *block,
433             const char *fmt_string)
434 {
435   int i;
436   for (i = n_bytes / sizeof (unsigned long); i > 0; i--)
437     {
438       unsigned long tmp = *(const unsigned long *) block;
439       printf (fmt_string, tmp);
440       block += sizeof (unsigned long);
441     }
442 }
443
444 static void
445 print_float (long unsigned int n_bytes, const char *block,
446              const char *fmt_string)
447 {
448   int i;
449   for (i = n_bytes / sizeof (float); i > 0; i--)
450     {
451       float tmp = *(const float *) block;
452       printf (fmt_string, tmp);
453       block += sizeof (float);
454     }
455 }
456
457 static void
458 print_double (long unsigned int n_bytes, const char *block,
459               const char *fmt_string)
460 {
461   int i;
462   for (i = n_bytes / sizeof (double); i > 0; i--)
463     {
464       double tmp = *(const double *) block;
465       printf (fmt_string, tmp);
466       block += sizeof (double);
467     }
468 }
469
470 #ifdef HAVE_LONG_DOUBLE
471 static void
472 print_long_double (long unsigned int n_bytes, const char *block,
473                    const char *fmt_string)
474 {
475   int i;
476   for (i = n_bytes / sizeof (LONG_DOUBLE); i > 0; i--)
477     {
478       LONG_DOUBLE tmp = *(const LONG_DOUBLE *) block;
479       printf (fmt_string, tmp);
480       block += sizeof (LONG_DOUBLE);
481     }
482 }
483
484 #endif
485
486 static void
487 dump_hexl_mode_trailer (long unsigned int n_bytes, const char *block)
488 {
489   int i;
490   fputs ("  >", stdout);
491   for (i = n_bytes; i > 0; i--)
492     {
493       unsigned int c = *(const unsigned char *) block;
494       unsigned int c2 = (ISPRINT(c) ? c : '.');
495       putchar (c2);
496       block += sizeof (unsigned char);
497     }
498   putchar ('<');
499 }
500
501 static void
502 print_named_ascii (long unsigned int n_bytes, const char *block,
503                    const char *unused_fmt_string)
504 {
505   int i;
506   for (i = n_bytes; i > 0; i--)
507     {
508       unsigned int c = *(const unsigned char *) block;
509       unsigned int masked_c = (0x7f & c);
510       const char *s;
511       char buf[5];
512
513       if (masked_c == 127)
514         s = "del";
515       else if (masked_c <= 040)
516         s = charname[masked_c];
517       else
518         {
519           sprintf (buf, "  %c", masked_c);
520           s = buf;
521         }
522
523       printf (" %3s", s);
524       block += sizeof (unsigned char);
525     }
526 }
527
528 static void
529 print_ascii (long unsigned int n_bytes, const char *block,
530              const char *unused_fmt_string)
531 {
532   int i;
533   for (i = n_bytes; i > 0; i--)
534     {
535       unsigned int c = *(const unsigned char *) block;
536       const char *s;
537       char buf[5];
538
539       switch (c)
540         {
541         case '\0':
542           s = " \\0";
543           break;
544
545         case '\007':
546           s = " \\a";
547           break;
548
549         case '\b':
550           s = " \\b";
551           break;
552
553         case '\f':
554           s = " \\f";
555           break;
556
557         case '\n':
558           s = " \\n";
559           break;
560
561         case '\r':
562           s = " \\r";
563           break;
564
565         case '\t':
566           s = " \\t";
567           break;
568
569         case '\v':
570           s = " \\v";
571           break;
572
573         default:
574           sprintf (buf, (ISPRINT (c) ? "  %c" : "%03o"), c);
575           s = (const char *) buf;
576         }
577
578       printf (" %3s", s);
579       block += sizeof (unsigned char);
580     }
581 }
582
583 /* Convert a null-terminated (possibly zero-length) string S to an
584    unsigned long integer value.  If S points to a non-digit set *P to S,
585    *VAL to 0, and return 0.  Otherwise, accumulate the integer value of
586    the string of digits.  If the string of digits represents a value
587    larger than ULONG_MAX, don't modify *VAL or *P and return nonzero.
588    Otherwise, advance *P to the first non-digit after S, set *VAL to
589    the result of the conversion and return zero.  */
590
591 static int
592 simple_strtoul (const char *s, const char **p, long unsigned int *val)
593 {
594   unsigned long int sum;
595
596   sum = 0;
597   while (ISDIGIT (*s))
598     {
599       unsigned int c = *s++ - '0';
600       if (sum > (ULONG_MAX - c) / 10)
601         return 1;
602       sum = sum * 10 + c;
603     }
604   *p = s;
605   *val = sum;
606   return 0;
607 }
608
609 /* If S points to a single valid POSIX-style od format string, put
610    a description of that format in *TSPEC, make *NEXT point at the
611    character following the just-decoded format (if *NEXT is non-NULL),
612    and return zero.  If S is not valid, don't modify *NEXT or *TSPEC,
613    give a diagnostic, and return nonzero.  For example, if S were
614    "d4afL" *NEXT would be set to "afL" and *TSPEC would be
615      {
616        fmt = SIGNED_DECIMAL;
617        size = INT or LONG; (whichever integral_type_size[4] resolves to)
618        print_function = print_int; (assuming size == INT)
619        fmt_string = "%011d%c";
620       }
621    S_ORIG is solely for reporting errors.  It should be the full format
622    string argument.
623    */
624
625 static int
626 decode_one_format (const char *s_orig, const char *s, const char **next,
627                    struct tspec *tspec)
628 {
629   enum size_spec size_spec;
630   unsigned long int size;
631   enum output_format fmt;
632   const char *pre_fmt_string;
633   char *fmt_string;
634   void (*print_function) ();
635   const char *p;
636   unsigned int c;
637   unsigned int field_width = 0;
638
639   assert (tspec != NULL);
640
641   switch (*s)
642     {
643     case 'd':
644     case 'o':
645     case 'u':
646     case 'x':
647       c = *s;
648       ++s;
649       switch (*s)
650         {
651         case 'C':
652           ++s;
653           size = sizeof (char);
654           break;
655
656         case 'S':
657           ++s;
658           size = sizeof (short);
659           break;
660
661         case 'I':
662           ++s;
663           size = sizeof (int);
664           break;
665
666         case 'L':
667           ++s;
668           size = sizeof (long int);
669           break;
670
671         default:
672           if (simple_strtoul (s, &p, &size) != 0)
673             {
674               /* The integer at P in S would overflow an unsigned long.
675                  A digit string that long is sufficiently odd looking
676                  that the following diagnostic is sufficient.  */
677               error (0, 0, _("invalid type string `%s'"), s_orig);
678               return 1;
679             }
680           if (p == s)
681             size = sizeof (int);
682           else
683             {
684               if (size > MAX_INTEGRAL_TYPE_SIZE
685                   || integral_type_size[size] == NO_SIZE)
686                 {
687                   error (0, 0, _("invalid type string `%s';\n\
688 this system doesn't provide a %lu-byte integral type"), s_orig, size);
689                   return 1;
690                 }
691               s = p;
692             }
693           break;
694         }
695
696 #define FMT_BYTES_ALLOCATED 9
697       fmt_string = xmalloc (FMT_BYTES_ALLOCATED);
698
699       size_spec = integral_type_size[size];
700
701       switch (c)
702         {
703         case 'd':
704           fmt = SIGNED_DECIMAL;
705           sprintf (fmt_string, " %%%u%sd",
706                    (field_width = bytes_to_signed_dec_digits[size]),
707                    (size_spec == LONG ? "l" : ""));
708           break;
709
710         case 'o':
711           fmt = OCTAL;
712           sprintf (fmt_string, " %%0%u%so",
713                    (field_width = bytes_to_oct_digits[size]),
714                    (size_spec == LONG ? "l" : ""));
715           break;
716
717         case 'u':
718           fmt = UNSIGNED_DECIMAL;
719           sprintf (fmt_string, " %%%u%su",
720                    (field_width = bytes_to_unsigned_dec_digits[size]),
721                    (size_spec == LONG ? "l" : ""));
722           break;
723
724         case 'x':
725           fmt = HEXADECIMAL;
726           sprintf (fmt_string, " %%0%u%sx",
727                    (field_width = bytes_to_hex_digits[size]),
728                    (size_spec == LONG ? "l" : ""));
729           break;
730
731         default:
732           abort ();
733         }
734
735       assert (strlen (fmt_string) < FMT_BYTES_ALLOCATED);
736
737       switch (size_spec)
738         {
739         case CHAR:
740           print_function = (fmt == SIGNED_DECIMAL
741                             ? print_s_char
742                             : print_char);
743           break;
744
745         case SHORT:
746           print_function = (fmt == SIGNED_DECIMAL
747                             ? print_s_short
748                             : print_short);
749           break;
750
751         case INT:
752           print_function = print_int;
753           break;
754
755         case LONG:
756           print_function = print_long;
757           break;
758
759         default:
760           abort ();
761         }
762       break;
763
764     case 'f':
765       fmt = FLOATING_POINT;
766       ++s;
767       switch (*s)
768         {
769         case 'F':
770           ++s;
771           size = sizeof (float);
772           break;
773
774         case 'D':
775           ++s;
776           size = sizeof (double);
777           break;
778
779         case 'L':
780           ++s;
781           size = sizeof (LONG_DOUBLE);
782           break;
783
784         default:
785           if (simple_strtoul (s, &p, &size) != 0)
786             {
787               /* The integer at P in S would overflow an unsigned long.
788                  A digit string that long is sufficiently odd looking
789                  that the following diagnostic is sufficient.  */
790               error (0, 0, _("invalid type string `%s'"), s_orig);
791               return 1;
792             }
793           if (p == s)
794             size = sizeof (double);
795           else
796             {
797               if (size > MAX_FP_TYPE_SIZE
798                   || fp_type_size[size] == NO_SIZE)
799                 {
800                   error (0, 0, _("invalid type string `%s';\n\
801 this system doesn't provide a %lu-byte floating point type"), s_orig, size);
802                   return 1;
803                 }
804               s = p;
805             }
806           break;
807         }
808       size_spec = fp_type_size[size];
809
810       switch (size_spec)
811         {
812         case FLOAT_SINGLE:
813           print_function = print_float;
814           /* Don't use %#e; not all systems support it.  */
815           pre_fmt_string = " %%%d.%de";
816           fmt_string = xmalloc (strlen (pre_fmt_string));
817           sprintf (fmt_string, pre_fmt_string,
818                    (field_width = FLT_DIG + 8), FLT_DIG);
819           break;
820
821         case FLOAT_DOUBLE:
822           print_function = print_double;
823           pre_fmt_string = " %%%d.%de";
824           fmt_string = xmalloc (strlen (pre_fmt_string));
825           sprintf (fmt_string, pre_fmt_string,
826                    (field_width = DBL_DIG + 8), DBL_DIG);
827           break;
828
829 #ifdef HAVE_LONG_DOUBLE
830         case FLOAT_LONG_DOUBLE:
831           print_function = print_long_double;
832           pre_fmt_string = " %%%d.%dLe";
833           fmt_string = xmalloc (strlen (pre_fmt_string));
834           sprintf (fmt_string, pre_fmt_string,
835                    (field_width = LDBL_DIG + 8), LDBL_DIG);
836           break;
837 #endif
838
839         default:
840           abort ();
841         }
842       break;
843
844     case 'a':
845       ++s;
846       fmt = NAMED_CHARACTER;
847       size_spec = CHAR;
848       fmt_string = NULL;
849       print_function = print_named_ascii;
850       field_width = 3;
851       break;
852
853     case 'c':
854       ++s;
855       fmt = CHARACTER;
856       size_spec = CHAR;
857       fmt_string = NULL;
858       print_function = print_ascii;
859       field_width = 3;
860       break;
861
862     default:
863       error (0, 0, _("invalid character `%c' in type string `%s'"),
864              *s, s_orig);
865       return 1;
866     }
867
868   tspec->size = size_spec;
869   tspec->fmt = fmt;
870   tspec->print_function = print_function;
871   tspec->fmt_string = fmt_string;
872
873   tspec->field_width = field_width;
874   tspec->hexl_mode_trailer = (*s == 'z');
875   if (tspec->hexl_mode_trailer)
876     s++;
877
878   if (next != NULL)
879     *next = s;
880
881   return 0;
882 }
883
884 /* Decode the POSIX-style od format string S.  Append the decoded
885    representation to the global array SPEC, reallocating SPEC if
886    necessary.  Return zero if S is valid, nonzero otherwise.  */
887
888 static int
889 decode_format_string (const char *s)
890 {
891   const char *s_orig = s;
892   assert (s != NULL);
893
894   while (*s != '\0')
895     {
896       struct tspec tspec;
897       const char *next;
898
899       if (decode_one_format (s_orig, s, &next, &tspec))
900         return 1;
901
902       assert (s != next);
903       s = next;
904
905       if (n_specs >= n_specs_allocated)
906         {
907           n_specs_allocated = 1 + (3 * n_specs_allocated) / 2;
908           spec = (struct tspec *) xrealloc ((char *) spec,
909                                             (n_specs_allocated
910                                              * sizeof (struct tspec)));
911         }
912
913       memcpy ((char *) &spec[n_specs], (char *) &tspec,
914               sizeof (struct tspec));
915       ++n_specs;
916     }
917
918   return 0;
919 }
920
921 /* Given a list of one or more input filenames FILE_LIST, set the global
922    file pointer IN_STREAM to position N_SKIP in the concatenation of
923    those files.  If any file operation fails or if there are fewer than
924    N_SKIP bytes in the combined input, give an error message and return
925    nonzero.  When possible, use seek- rather than read operations to
926    advance IN_STREAM.  A file name of "-" is interpreted as standard
927    input.  */
928
929 static int
930 skip (off_t n_skip)
931 {
932   int err;
933
934   err = 0;
935   for ( /* empty */ ; *file_list != NULL; ++file_list)
936     {
937       struct stat file_stats;
938       int j;
939
940       if (STREQ (*file_list, "-"))
941         {
942           input_filename = _("standard input");
943           in_stream = stdin;
944           have_read_stdin = 1;
945         }
946       else
947         {
948           input_filename = *file_list;
949           in_stream = fopen (input_filename, "r");
950           if (in_stream == NULL)
951             {
952               error (0, errno, "%s", input_filename);
953               err = 1;
954               continue;
955             }
956         }
957       SET_BINARY (fileno (in_stream));
958
959       if (n_skip == 0)
960         break;
961
962       /* First try using fseek.  For large offsets, this extra work is
963          worthwhile.  If the offset is below some threshold it may be
964          more efficient to move the pointer by reading.  There are two
965          issues when trying to use fseek:
966            - the file must be seekable.
967            - before seeking to the specified position, make sure
968              that the new position is in the current file.
969              Try to do that by getting file's size using fstat().
970              But that will work only for regular files and dirs.  */
971
972       if (fstat (fileno (in_stream), &file_stats))
973         {
974           error (0, errno, "%s", input_filename);
975           err = 1;
976           continue;
977         }
978
979       /* The st_size field is valid only for regular files and
980          directories.  FIXME: is the preceding true?
981          If the number of bytes left to skip is at least as large as
982          the size of the current file, we can decrement
983          n_skip and go on to the next file.  */
984       if (S_ISREG (file_stats.st_mode) || S_ISDIR (file_stats.st_mode))
985         {
986           if (n_skip >= file_stats.st_size)
987             {
988               n_skip -= file_stats.st_size;
989               if (in_stream != stdin && fclose (in_stream) == EOF)
990                 {
991                   error (0, errno, "%s", input_filename);
992                   err = 1;
993                 }
994               continue;
995             }
996           else
997             {
998               /* Try fseeko if available, fseek otherwise.  */
999               if (fseeko (in_stream, n_skip, SEEK_SET) == 0
1000                   || (n_skip <= LONG_MAX
1001                       && fseek (in_stream, (long) n_skip, SEEK_SET) == 0))
1002                 {
1003                   n_skip = 0;
1004                   break;
1005                 }
1006             }
1007         }
1008
1009       /* Seek didn't work or wasn't attempted;  position the file pointer
1010          by reading.  */
1011
1012       for (j = n_skip / BUFSIZ; j >= 0; j--)
1013         {
1014           char buf[BUFSIZ];
1015           size_t n_bytes_to_read = (j > 0
1016                                     ? BUFSIZ
1017                                     : n_skip % BUFSIZ);
1018           size_t n_bytes_read;
1019           n_bytes_read = fread (buf, 1, n_bytes_to_read, in_stream);
1020           n_skip -= n_bytes_read;
1021           if (n_bytes_read != n_bytes_to_read)
1022             break;
1023         }
1024
1025       if (n_skip == 0)
1026         break;
1027     }
1028
1029   if (n_skip != 0)
1030     error (EXIT_FAILURE, 0, _("cannot skip past end of combined input"));
1031
1032   return err;
1033 }
1034
1035 static const char *
1036 format_address_none (long unsigned int address)
1037 {
1038   return "";
1039 }
1040
1041 static const char *
1042 format_address_std (long unsigned int address)
1043 {
1044   const char *address_string;
1045
1046   sprintf (address_fmt_buffer, output_address_fmt_string, address);
1047   address_string = address_fmt_buffer;
1048   return address_string;
1049 }
1050
1051 static const char *
1052 format_address_label (long unsigned int address)
1053 {
1054   const char *address_string;
1055   assert (output_address_fmt_string != NULL);
1056
1057   sprintf (address_fmt_buffer, output_address_fmt_string,
1058            address, address + pseudo_offset);
1059   address_string = address_fmt_buffer;
1060   return address_string;
1061 }
1062
1063 /* Write N_BYTES bytes from CURR_BLOCK to standard output once for each
1064    of the N_SPEC format specs.  CURRENT_OFFSET is the byte address of
1065    CURR_BLOCK in the concatenation of input files, and it is printed
1066    (optionally) only before the output line associated with the first
1067    format spec.  When duplicate blocks are being abbreviated, the output
1068    for a sequence of identical input blocks is the output for the first
1069    block followed by an asterisk alone on a line.  It is valid to compare
1070    the blocks PREV_BLOCK and CURR_BLOCK only when N_BYTES == BYTES_PER_BLOCK.
1071    That condition may be false only for the last input block -- and then
1072    only when it has not been padded to length BYTES_PER_BLOCK.  */
1073
1074 static void
1075 write_block (long unsigned int current_offset, long unsigned int n_bytes,
1076              const char *prev_block, const char *curr_block)
1077 {
1078   static int first = 1;
1079   static int prev_pair_equal = 0;
1080
1081 #define EQUAL_BLOCKS(b1, b2) (memcmp ((b1), (b2), bytes_per_block) == 0)
1082
1083   if (abbreviate_duplicate_blocks
1084       && !first && n_bytes == bytes_per_block
1085       && EQUAL_BLOCKS (prev_block, curr_block))
1086     {
1087       if (prev_pair_equal)
1088         {
1089           /* The two preceding blocks were equal, and the current
1090              block is the same as the last one, so print nothing.  */
1091         }
1092       else
1093         {
1094           printf ("*\n");
1095           prev_pair_equal = 1;
1096         }
1097     }
1098   else
1099     {
1100       unsigned int i;
1101
1102       prev_pair_equal = 0;
1103       for (i = 0; i < n_specs; i++)
1104         {
1105           const char *addr_or_pad = (i == 0
1106                                      ? format_address (current_offset)
1107                                      : address_pad);
1108
1109           fputs (addr_or_pad, stdout);
1110           (*spec[i].print_function) (n_bytes, curr_block, spec[i].fmt_string);
1111           if (spec[i].hexl_mode_trailer)
1112             {
1113               /* space-pad out to full line width, then dump the trailer */
1114               int datum_width = width_bytes[spec[i].size];
1115               int blank_fields = (bytes_per_block - n_bytes) / datum_width;
1116               int field_width = spec[i].field_width + 1;
1117               printf ("%*s", blank_fields * field_width, "");
1118               dump_hexl_mode_trailer (n_bytes, curr_block);
1119             }
1120           putchar ('\n');
1121         }
1122     }
1123   first = 0;
1124 }
1125
1126 /* Test whether there have been errors on in_stream, and close it if
1127    it is not standard input.  Return nonzero if there has been an error
1128    on in_stream or stdout; return zero otherwise.  This function will
1129    report more than one error only if both a read and a write error
1130    have occurred.  */
1131
1132 static int
1133 check_and_close (void)
1134 {
1135   int err;
1136
1137   err = 0;
1138   if (ferror (in_stream))
1139     {
1140       error (0, errno, "%s", input_filename);
1141       if (in_stream != stdin)
1142         fclose (in_stream);
1143       err = 1;
1144     }
1145   else if (in_stream != stdin && fclose (in_stream) == EOF)
1146     {
1147       error (0, errno, "%s", input_filename);
1148       err = 1;
1149     }
1150
1151   if (ferror (stdout))
1152     {
1153       error (0, errno, _("standard output"));
1154       err = 1;
1155     }
1156
1157   return err;
1158 }
1159
1160 /* Read a single byte into *C from the concatenation of the input files
1161    named in the global array FILE_LIST.  On the first call to this
1162    function, the global variable IN_STREAM is expected to be an open
1163    stream associated with the input file *FILE_LIST.  If IN_STREAM is
1164    at end-of-file, close it and update the global variables IN_STREAM,
1165    FILE_LIST, and INPUT_FILENAME so they correspond to the next file in
1166    the list.  Then try to read a byte from the newly opened file.
1167    Repeat if necessary until *FILE_LIST is NULL.  When EOF is reached
1168    for the last file in FILE_LIST, set *C to EOF and return.  Subsequent
1169    calls do likewise.  The return value is nonzero if any errors
1170    occured, zero otherwise.  */
1171
1172 static int
1173 read_char (int *c)
1174 {
1175   int err;
1176
1177   if (*file_list == NULL)
1178     {
1179       *c = EOF;
1180       return 0;
1181     }
1182
1183   err = 0;
1184   while (1)
1185     {
1186       *c = fgetc (in_stream);
1187
1188       if (*c != EOF)
1189         return err;
1190
1191       err |= check_and_close ();
1192
1193       do
1194         {
1195           ++file_list;
1196           if (*file_list == NULL)
1197             return err;
1198
1199           if (STREQ (*file_list, "-"))
1200             {
1201               input_filename = _("standard input");
1202               in_stream = stdin;
1203               have_read_stdin = 1;
1204             }
1205           else
1206             {
1207               input_filename = *file_list;
1208               in_stream = fopen (input_filename, "r");
1209               if (in_stream == NULL)
1210                 {
1211                   error (0, errno, "%s", input_filename);
1212                   err = 1;
1213                 }
1214             }
1215           SET_BINARY (fileno (in_stream));
1216         }
1217       while (in_stream == NULL);
1218     }
1219 }
1220
1221 /* Read N bytes into BLOCK from the concatenation of the input files
1222    named in the global array FILE_LIST.  On the first call to this
1223    function, the global variable IN_STREAM is expected to be an open
1224    stream associated with the input file *FILE_LIST.  On subsequent
1225    calls, if *FILE_LIST is NULL, don't modify BLOCK and return zero.
1226    If all N bytes cannot be read from IN_STREAM, close IN_STREAM and
1227    update the global variables IN_STREAM, FILE_LIST, and INPUT_FILENAME.
1228    Then try to read the remaining bytes from the newly opened file.
1229    Repeat if necessary until *FILE_LIST is NULL.  Set *N_BYTES_IN_BUFFER
1230    to the number of bytes read.  If an error occurs, it will be detected
1231    through ferror when the stream is about to be closed.  If there is an
1232    error, give a message but continue reading as usual and return nonzero.
1233    Otherwise return zero.  */
1234
1235 static int
1236 read_block (size_t n, char *block, size_t *n_bytes_in_buffer)
1237 {
1238   int err;
1239
1240   assert (n > 0 && n <= bytes_per_block);
1241
1242   *n_bytes_in_buffer = 0;
1243
1244   if (n == 0)
1245     return 0;
1246
1247   if (*file_list == NULL)
1248     return 0;                   /* EOF.  */
1249
1250   err = 0;
1251   while (1)
1252     {
1253       size_t n_needed;
1254       size_t n_read;
1255
1256       n_needed = n - *n_bytes_in_buffer;
1257       n_read = fread (block + *n_bytes_in_buffer, 1, n_needed, in_stream);
1258
1259       *n_bytes_in_buffer += n_read;
1260
1261       if (n_read == n_needed)
1262         return err;
1263
1264       err |= check_and_close ();
1265
1266       do
1267         {
1268           ++file_list;
1269           if (*file_list == NULL)
1270             return err;
1271
1272           if (STREQ (*file_list, "-"))
1273             {
1274               input_filename = _("standard input");
1275               in_stream = stdin;
1276               have_read_stdin = 1;
1277             }
1278           else
1279             {
1280               input_filename = *file_list;
1281               in_stream = fopen (input_filename, "r");
1282               if (in_stream == NULL)
1283                 {
1284                   error (0, errno, "%s", input_filename);
1285                   err = 1;
1286                 }
1287             }
1288           SET_BINARY (fileno (in_stream));
1289         }
1290       while (in_stream == NULL);
1291     }
1292 }
1293
1294 /* Return the least common multiple of the sizes associated
1295    with the format specs.  */
1296
1297 static int
1298 get_lcm (void)
1299 {
1300   unsigned int i;
1301   int l_c_m = 1;
1302
1303   for (i = 0; i < n_specs; i++)
1304     l_c_m = lcm (l_c_m, width_bytes[(int) spec[i].size]);
1305   return l_c_m;
1306 }
1307
1308 /* If S is a valid pre-POSIX offset specification with an optional leading '+'
1309    return the offset it denotes.  Otherwise, return -1.  */
1310
1311 off_t
1312 parse_old_offset (const char *s)
1313 {
1314   int radix;
1315   off_t offset;
1316   enum strtol_error s_err;
1317   long unsigned int tmp;
1318
1319   if (*s == '\0')
1320     return -1;
1321
1322   /* Skip over any leading '+'. */
1323   if (s[0] == '+')
1324     ++s;
1325
1326   /* Determine the radix we'll use to interpret S.  If there is a `.',
1327      it's decimal, otherwise, if the string begins with `0X'or `0x',
1328      it's hexadecimal, else octal.  */
1329   if (strchr (s, '.') != NULL)
1330     radix = 10;
1331   else
1332     {
1333       if (s[0] == '0' && (s[1] == 'x' || s[1] == 'X'))
1334         radix = 16;
1335       else
1336         radix = 8;
1337     }
1338
1339   s_err = xstrtoul (s, NULL, radix, &tmp, "Bb");
1340   if (s_err != LONGINT_OK)
1341     {
1342       STRTOL_FAIL_WARN (s, _("old-style offset"), s_err);
1343       return -1;
1344     }
1345   offset = tmp;
1346   return offset;
1347 }
1348
1349 /* Read a chunk of size BYTES_PER_BLOCK from the input files, write the
1350    formatted block to standard output, and repeat until the specified
1351    maximum number of bytes has been read or until all input has been
1352    processed.  If the last block read is smaller than BYTES_PER_BLOCK
1353    and its size is not a multiple of the size associated with a format
1354    spec, extend the input block with zero bytes until its length is a
1355    multiple of all format spec sizes.  Write the final block.  Finally,
1356    write on a line by itself the offset of the byte after the last byte
1357    read.  Accumulate return values from calls to read_block and
1358    check_and_close, and if any was nonzero, return nonzero.
1359    Otherwise, return zero.  */
1360
1361 static int
1362 dump (void)
1363 {
1364   char *block[2];
1365   off_t current_offset;
1366   off_t end_offset IF_LINT (= 0);
1367   int idx;
1368   int err;
1369   size_t n_bytes_read;
1370
1371   block[0] = (char *) alloca (bytes_per_block);
1372   block[1] = (char *) alloca (bytes_per_block);
1373
1374   current_offset = n_bytes_to_skip;
1375
1376   idx = 0;
1377   err = 0;
1378   if (limit_bytes_to_format)
1379     {
1380       end_offset = n_bytes_to_skip + max_bytes_to_format;
1381
1382       while (1)
1383         {
1384           size_t n_needed;
1385           if (current_offset >= end_offset)
1386             {
1387               n_bytes_read = 0;
1388               break;
1389             }
1390           n_needed = MIN (end_offset - current_offset,
1391                           (off_t) bytes_per_block);
1392           err |= read_block (n_needed, block[idx], &n_bytes_read);
1393           if (n_bytes_read < bytes_per_block)
1394             break;
1395           assert (n_bytes_read == bytes_per_block);
1396           write_block (current_offset, n_bytes_read,
1397                        block[!idx], block[idx]);
1398           current_offset += n_bytes_read;
1399           idx = !idx;
1400         }
1401     }
1402   else
1403     {
1404       while (1)
1405         {
1406           err |= read_block (bytes_per_block, block[idx], &n_bytes_read);
1407           if (n_bytes_read < bytes_per_block)
1408             break;
1409           assert (n_bytes_read == bytes_per_block);
1410           write_block (current_offset, n_bytes_read,
1411                        block[!idx], block[idx]);
1412           current_offset += n_bytes_read;
1413           idx = !idx;
1414         }
1415     }
1416
1417   if (n_bytes_read > 0)
1418     {
1419       int l_c_m;
1420       size_t bytes_to_write;
1421
1422       l_c_m = get_lcm ();
1423
1424       /* Make bytes_to_write the smallest multiple of l_c_m that
1425          is at least as large as n_bytes_read.  */
1426       bytes_to_write = l_c_m * (int) ((n_bytes_read + l_c_m - 1) / l_c_m);
1427
1428       memset (block[idx] + n_bytes_read, 0, bytes_to_write - n_bytes_read);
1429       write_block (current_offset, bytes_to_write,
1430                    block[!idx], block[idx]);
1431       current_offset += n_bytes_read;
1432     }
1433
1434   if (output_address_fmt_string != NULL)
1435     printf ("%s\n", format_address (current_offset));
1436
1437   if (limit_bytes_to_format && current_offset > end_offset)
1438     err |= check_and_close ();
1439
1440   return err;
1441 }
1442
1443 /* STRINGS mode.  Find each "string constant" in the input.
1444    A string constant is a run of at least `string_min' ASCII
1445    graphic (or formatting) characters terminated by a null.
1446    Based on a function written by Richard Stallman for a
1447    pre-POSIX version of od.  Return nonzero if an error
1448    occurs.  Otherwise, return zero.  */
1449
1450 static int
1451 dump_strings (void)
1452 {
1453   size_t bufsize = MAX (100, string_min);
1454   char *buf = xmalloc (bufsize);
1455   off_t address = n_bytes_to_skip;
1456   int err;
1457
1458   err = 0;
1459   while (1)
1460     {
1461       unsigned int i;
1462       int c;
1463
1464       /* See if the next `string_min' chars are all printing chars.  */
1465     tryline:
1466
1467       if (limit_bytes_to_format
1468           && address >= (n_bytes_to_skip + max_bytes_to_format -
1469                          (off_t) string_min))
1470         break;
1471
1472       for (i = 0; i < string_min; i++)
1473         {
1474           err |= read_char (&c);
1475           address++;
1476           if (c < 0)
1477             {
1478               free (buf);
1479               return err;
1480             }
1481           if (!ISPRINT (c))
1482             /* Found a non-printing.  Try again starting with next char.  */
1483             goto tryline;
1484           buf[i] = c;
1485         }
1486
1487       /* We found a run of `string_min' printable characters.
1488          Now see if it is terminated with a null byte.  */
1489       while (!limit_bytes_to_format
1490              || address < n_bytes_to_skip + max_bytes_to_format)
1491         {
1492           if (i == bufsize)
1493             {
1494               bufsize = 1 + 3 * bufsize / 2;
1495               buf = xrealloc (buf, bufsize);
1496             }
1497           err |= read_char (&c);
1498           address++;
1499           if (c < 0)
1500             {
1501               free (buf);
1502               return err;
1503             }
1504           if (c == '\0')
1505             break;              /* It is; print this string.  */
1506           if (!ISPRINT (c))
1507             goto tryline;       /* It isn't; give up on this string.  */
1508           buf[i++] = c;         /* String continues; store it all.  */
1509         }
1510
1511       /* If we get here, the string is all printable and null-terminated,
1512          so print it.  It is all in `buf' and `i' is its length.  */
1513       buf[i] = 0;
1514       if (output_address_fmt_string != NULL)
1515         {
1516           printf ("%s ", format_address (address - i - 1));
1517         }
1518       for (i = 0; (c = buf[i]); i++)
1519         {
1520           switch (c)
1521             {
1522             case '\007':
1523               fputs ("\\a", stdout);
1524               break;
1525
1526             case '\b':
1527               fputs ("\\b", stdout);
1528               break;
1529
1530             case '\f':
1531               fputs ("\\f", stdout);
1532               break;
1533
1534             case '\n':
1535               fputs ("\\n", stdout);
1536               break;
1537
1538             case '\r':
1539               fputs ("\\r", stdout);
1540               break;
1541
1542             case '\t':
1543               fputs ("\\t", stdout);
1544               break;
1545
1546             case '\v':
1547               fputs ("\\v", stdout);
1548               break;
1549
1550             default:
1551               putc (c, stdout);
1552             }
1553         }
1554       putchar ('\n');
1555     }
1556
1557   /* We reach this point only if we search through
1558      (max_bytes_to_format - string_min) bytes before reachine EOF.  */
1559
1560   free (buf);
1561
1562   err |= check_and_close ();
1563   return err;
1564 }
1565
1566 int
1567 main (int argc, char **argv)
1568 {
1569   int c;
1570   int n_files;
1571   unsigned int i;
1572   unsigned int l_c_m;
1573   unsigned int address_pad_len;
1574   unsigned long int desired_width;
1575   int width_specified = 0;
1576   int n_failed_decodes = 0;
1577   int err;
1578
1579   /* The old-style `pseudo starting address' to be printed in parentheses
1580      after any true address.  */
1581   long int pseudo_start IF_LINT (= 0);
1582
1583   program_name = argv[0];
1584   setlocale (LC_ALL, "");
1585   bindtextdomain (PACKAGE, LOCALEDIR);
1586   textdomain (PACKAGE);
1587
1588   atexit (close_stdout);
1589
1590   err = 0;
1591
1592   for (i = 0; i <= MAX_INTEGRAL_TYPE_SIZE; i++)
1593     integral_type_size[i] = NO_SIZE;
1594
1595   integral_type_size[sizeof (char)] = CHAR;
1596   integral_type_size[sizeof (short int)] = SHORT;
1597   integral_type_size[sizeof (int)] = INT;
1598   integral_type_size[sizeof (long int)] = LONG;
1599
1600   for (i = 0; i <= MAX_FP_TYPE_SIZE; i++)
1601     fp_type_size[i] = NO_SIZE;
1602
1603   fp_type_size[sizeof (float)] = FLOAT_SINGLE;
1604   /* The array entry for `double' is filled in after that for LONG_DOUBLE
1605      so that if `long double' is the same type or if long double isn't
1606      supported FLOAT_LONG_DOUBLE will never be used.  */
1607   fp_type_size[sizeof (LONG_DOUBLE)] = FLOAT_LONG_DOUBLE;
1608   fp_type_size[sizeof (double)] = FLOAT_DOUBLE;
1609
1610   n_specs = 0;
1611   n_specs_allocated = 5;
1612   spec = (struct tspec *) xmalloc (n_specs_allocated * sizeof (struct tspec));
1613
1614   output_address_fmt_string = "%07o";
1615   format_address = format_address_std;
1616   address_pad_len = 7;
1617   flag_dump_strings = 0;
1618
1619   while ((c = getopt_long (argc, argv, "abcdfhilos::xw::A:j:N:t:v",
1620                            long_options, NULL)) != -1)
1621     {
1622       unsigned long int tmp;
1623       enum strtol_error s_err;
1624
1625       switch (c)
1626         {
1627         case 0:
1628           break;
1629
1630         case 'A':
1631           switch (optarg[0])
1632             {
1633             case 'd':
1634               output_address_fmt_string = "%07d";
1635               format_address = format_address_std;
1636               address_pad_len = 7;
1637               break;
1638             case 'o':
1639               output_address_fmt_string = "%07o";
1640               format_address = format_address_std;
1641               address_pad_len = 7;
1642               break;
1643             case 'x':
1644               output_address_fmt_string = "%06x";
1645               format_address = format_address_std;
1646               address_pad_len = 6;
1647               break;
1648             case 'n':
1649               output_address_fmt_string = NULL;
1650               format_address = format_address_none;
1651               address_pad_len = 0;
1652               break;
1653             default:
1654               error (EXIT_FAILURE, 0,
1655                      _("invalid output address radix `%c'; \
1656 it must be one character from [doxn]"),
1657                      optarg[0]);
1658               break;
1659             }
1660           break;
1661
1662         case 'j':
1663           s_err = xstrtoul (optarg, NULL, 0, &tmp, "bkm");
1664           n_bytes_to_skip = tmp;
1665           if (s_err != LONGINT_OK)
1666             STRTOL_FATAL_ERROR (optarg, _("skip argument"), s_err);
1667           break;
1668
1669         case 'N':
1670           limit_bytes_to_format = 1;
1671
1672           /* FIXME: if off_t is long long and that's an 8-byte type,
1673              use xstrtouq here.  */
1674           s_err = xstrtoul (optarg, NULL, 0, &tmp, "bkm");
1675           max_bytes_to_format = tmp;
1676           if (s_err != LONGINT_OK)
1677             STRTOL_FATAL_ERROR (optarg, _("limit argument"), s_err);
1678
1679           if (tmp > LONG_MAX)
1680             error (EXIT_FAILURE, 0,
1681                    _("specified number of bytes `%s' is larger than \
1682 the maximum\nrepresentable value of type `long'"), optarg);
1683           break;
1684
1685         case 's':
1686           if (optarg == NULL)
1687             string_min = 3;
1688           else
1689             {
1690               s_err = xstrtoul (optarg, NULL, 0, &string_min, "bkm");
1691               if (s_err != LONGINT_OK)
1692                 STRTOL_FATAL_ERROR (optarg, _("minimum string length"), s_err);
1693             }
1694           ++flag_dump_strings;
1695           break;
1696
1697         case 't':
1698           if (decode_format_string (optarg))
1699             ++n_failed_decodes;
1700           break;
1701
1702         case 'v':
1703           abbreviate_duplicate_blocks = 0;
1704           break;
1705
1706         case 'B':
1707           traditional = 1;
1708           break;
1709
1710           /* The next several cases map the old, pre-POSIX format
1711              specification options to the corresponding POSIX format
1712              specs.  GNU od accepts any combination of old- and
1713              new-style options.  Format specification options accumulate.  */
1714
1715 #define CASE_OLD_ARG(old_char,new_string)               \
1716         case old_char:                                  \
1717           {                                             \
1718             if (decode_format_string (new_string))      \
1719               ++n_failed_decodes;                       \
1720           }                                             \
1721           break
1722
1723           CASE_OLD_ARG ('a', "a");
1724           CASE_OLD_ARG ('b', "oC");
1725           CASE_OLD_ARG ('c', "c");
1726           CASE_OLD_ARG ('d', "u2");
1727           CASE_OLD_ARG ('f', "fF");
1728           CASE_OLD_ARG ('h', "x2");
1729           CASE_OLD_ARG ('i', "d2");
1730           CASE_OLD_ARG ('l', "d4");
1731           CASE_OLD_ARG ('o', "o2");
1732           CASE_OLD_ARG ('x', "x2");
1733
1734 #undef CASE_OLD_ARG
1735
1736         case 'w':
1737           width_specified = 1;
1738           if (optarg == NULL)
1739             {
1740               desired_width = 32;
1741             }
1742           else
1743             {
1744               s_err = xstrtoul (optarg, NULL, 10, &desired_width, "");
1745               if (s_err != LONGINT_OK)
1746                 STRTOL_FATAL_ERROR (optarg, _("width specification"), s_err);
1747             }
1748           break;
1749
1750         case_GETOPT_HELP_CHAR;
1751
1752         case_GETOPT_VERSION_CHAR (PROGRAM_NAME, AUTHORS);
1753
1754         default:
1755           usage (1);
1756           break;
1757         }
1758     }
1759
1760   if (n_failed_decodes > 0)
1761     exit (EXIT_FAILURE);
1762
1763   if (flag_dump_strings && n_specs > 0)
1764     error (EXIT_FAILURE, 0,
1765            _("no type may be specified when dumping strings"));
1766
1767   n_files = argc - optind;
1768
1769   /* If the --backward-compatible option is used, there may be from
1770      0 to 3 remaining command line arguments;  handle each case
1771      separately.
1772         od [file] [[+]offset[.][b] [[+]label[.][b]]]
1773      The offset and pseudo_start have the same syntax.  */
1774
1775   if (traditional)
1776     {
1777       off_t offset;
1778
1779       if (n_files == 1)
1780         {
1781           if ((offset = parse_old_offset (argv[optind])) >= 0)
1782             {
1783               n_bytes_to_skip = offset;
1784               --n_files;
1785               ++argv;
1786             }
1787         }
1788       else if (n_files == 2)
1789         {
1790           off_t o1, o2;
1791           if ((o1 = parse_old_offset (argv[optind])) >= 0
1792               && (o2 = parse_old_offset (argv[optind + 1])) >= 0)
1793             {
1794               n_bytes_to_skip = o1;
1795               flag_pseudo_start = 1;
1796               pseudo_start = o2;
1797               argv += 2;
1798               n_files -= 2;
1799             }
1800           else if ((o2 = parse_old_offset (argv[optind + 1])) >= 0)
1801             {
1802               n_bytes_to_skip = o2;
1803               --n_files;
1804               argv[optind + 1] = argv[optind];
1805               ++argv;
1806             }
1807           else
1808             {
1809               error (0, 0,
1810                      _("invalid second operand in compatibility mode `%s'"),
1811                      argv[optind + 1]);
1812               usage (1);
1813             }
1814         }
1815       else if (n_files == 3)
1816         {
1817           off_t o1, o2;
1818           if ((o1 = parse_old_offset (argv[optind + 1])) >= 0
1819               && (o2 = parse_old_offset (argv[optind + 2])) >= 0)
1820             {
1821               n_bytes_to_skip = o1;
1822               flag_pseudo_start = 1;
1823               pseudo_start = o2;
1824               argv[optind + 2] = argv[optind];
1825               argv += 2;
1826               n_files -= 2;
1827             }
1828           else
1829             {
1830               error (0, 0,
1831             _("in compatibility mode, the last two arguments must be offsets"));
1832               usage (1);
1833             }
1834         }
1835       else if (n_files > 3)
1836         {
1837           error (0, 0,
1838                  _("compatibility mode supports at most three arguments"));
1839           usage (1);
1840         }
1841
1842       if (flag_pseudo_start)
1843         {
1844           static char buf[10];
1845
1846           if (output_address_fmt_string == NULL)
1847             {
1848               output_address_fmt_string = "(%07o)";
1849               format_address = format_address_std;
1850             }
1851           else
1852             {
1853               sprintf (buf, "%s (%s)",
1854                        output_address_fmt_string,
1855                        output_address_fmt_string);
1856               output_address_fmt_string = buf;
1857               format_address = format_address_label;
1858             }
1859         }
1860     }
1861
1862   assert (address_pad_len <= MAX_ADDRESS_LENGTH);
1863   for (i = 0; i < address_pad_len; i++)
1864     address_pad[i] = ' ';
1865   address_pad[address_pad_len] = '\0';
1866
1867   if (n_specs == 0)
1868     {
1869       if (decode_one_format ("o2", "o2", NULL, &(spec[0])))
1870         {
1871           /* This happens on Cray systems that don't have a 2-byte
1872              integral type.  */
1873           exit (EXIT_FAILURE);
1874         }
1875
1876       n_specs = 1;
1877     }
1878
1879   if (n_files > 0)
1880     file_list = (char const *const *) &argv[optind];
1881   else
1882     {
1883       /* If no files were listed on the command line, set up the
1884          global array FILE_LIST so that it contains the null-terminated
1885          list of one name: "-".  */
1886       static char const *const default_file_list[] = {"-", NULL};
1887
1888       file_list = default_file_list;
1889     }
1890
1891   err |= skip (n_bytes_to_skip);
1892   if (in_stream == NULL)
1893     goto cleanup;
1894
1895   pseudo_offset = (flag_pseudo_start ? pseudo_start - n_bytes_to_skip : 0);
1896
1897   /* Compute output block length.  */
1898   l_c_m = get_lcm ();
1899
1900   if (width_specified)
1901     {
1902       if (desired_width != 0 && desired_width % l_c_m == 0)
1903         bytes_per_block = desired_width;
1904       else
1905         {
1906           error (0, 0, _("warning: invalid width %lu; using %d instead"),
1907                  desired_width, l_c_m);
1908           bytes_per_block = l_c_m;
1909         }
1910     }
1911   else
1912     {
1913       if (l_c_m < DEFAULT_BYTES_PER_BLOCK)
1914         bytes_per_block = l_c_m * (int) (DEFAULT_BYTES_PER_BLOCK / l_c_m);
1915       else
1916         bytes_per_block = l_c_m;
1917     }
1918
1919 #ifdef DEBUG
1920   for (i = 0; i < n_specs; i++)
1921     {
1922       printf (_("%d: fmt=\"%s\" width=%d\n"),
1923               i, spec[i].fmt_string, width_bytes[spec[i].size]);
1924     }
1925 #endif
1926
1927   err |= (flag_dump_strings ? dump_strings () : dump ());
1928
1929 cleanup:;
1930
1931   if (have_read_stdin && fclose (stdin) == EOF)
1932     error (EXIT_FAILURE, errno, _("standard input"));
1933
1934   exit (err == 0 ? EXIT_SUCCESS : EXIT_FAILURE);
1935 }