just include fcntl.h not sys/fcntl.h
[oweals/busybox.git] / util-linux / hexdump.c
index 4510a5e66915a923e316e66bbe26c2b8d92c5ff3..e2cbcaf89bbcf1907323698d2667a3d95567fc50 100644 (file)
 #include <getopt.h>
 #include <stdlib.h>
 #include <string.h>
-#include "dump.h"
 #include "busybox.h"
+#include "dump.h"
 
-extern off_t skip;                      /* bytes to skip */
-
-extern FS *fshead;                             /* head of format strings */
-extern int blocksize;                          /* data block size */
-extern int length;                     /* max bytes to read */
-
-void addfile(char *name)
+static void bb_dump_addfile(char *name)
 {
        register char *p;
        FILE *fp;
-       int ch;
-       char buf[2048 + 1];
+       char *buf;
 
-       if (!(fp = fopen(name, "r"))) {
-               error_msg_and_die("hexdump: can't read %s.\n", name);
-       }
-       while (fgets(buf, sizeof(buf), fp)) {
-               if (!(p = index(buf, '\n'))) {
-                       error_msg("hexdump: line too long.\n");
-                       while ((ch = getchar()) != '\n' && ch != EOF);
-                       continue;
-               }
-               *p = '\0';
-               for (p = buf; *p && isspace(*p); ++p);
-               if (!*p || *p == '#') {
-                       continue;
+       fp = bb_xfopen(name, "r");
+
+       while ((buf = bb_get_chomped_line_from_file(fp)) != NULL) {
+               p = (char *) bb_skip_whitespace(buf);
+
+               if (*p && (*p != '#')) {
+                       bb_dump_add(p);
                }
-               add(p);
+               free(buf);
        }
-       (void)fclose(fp);
+       fclose(fp);
 }
 
+static const char * const add_strings[] = {
+                       "\"%07.7_ax \" 16/1 \"%03o \" \"\\n\"",         /* b */
+                       "\"%07.7_ax \" 16/1 \"%3_c \" \"\\n\"",         /* c */
+                       "\"%07.7_ax \" 8/2 \"  %05u \" \"\\n\"",        /* d */
+                       "\"%07.7_ax \" 8/2 \" %06o \" \"\\n\"",         /* o */
+                       "\"%07.7_ax \" 8/2 \"   %04x \" \"\\n\"",       /* x */
+};
+
+static const char add_first[] = "\"%07.7_Ax\n\"";
+
+static const char hexdump_opts[] = "bcdoxCe:f:n:s:v";
+
+static const struct suffix_mult suffixes[] = {
+       {"b",  512 },
+       {"k",  1024 },
+       {"m",  1024*1024 },
+       {NULL, 0 }
+};
+
 int hexdump_main(int argc, char **argv)
 {
 //     register FS *tfs;
-       char *p;
+       const char *p;
        int ch;
-       extern enum _vflag vflag;
-       vflag = FIRST;
-       length = -1;
 
-       while ((ch = getopt(argc, argv, "bcde:f:n:os:vx")) != EOF) {
-               switch (ch) {
-               case 'b':
-                       add("\"%07.7_Ax\n\"");
-                       add("\"%07.7_ax \" 16/1 \"%03o \" \"\\n\"");
-                       break;
-               case 'c':
-                       add("\"%07.7_Ax\n\"");
-                       add("\"%07.7_ax \" 16/1 \"%3_c \" \"\\n\"");
-                       break;
-               case 'd':
-                       add("\"%07.7_Ax\n\"");
-                       add("\"%07.7_ax \" 8/2 \"  %05u \" \"\\n\"");
-                       break;
-               case 'e':
-                       add(optarg);
-                       break;
-               case 'f':
-                       addfile(optarg);
-                       break;
-               case 'n':
-                       if ((length = atoi(optarg)) < 0) {
-                               error_msg_and_die("hexdump: bad length value.\n");
-                       }
-                       break;
-               case 'o':
-                       add("\"%07.7_Ax\n\"");
-                       add("\"%07.7_ax \" 8/2 \" %06o \" \"\\n\"");
-                       break;
-               case 's':
-                       if ((skip = strtol(optarg, &p, 0)) < 0) {
-                               error_msg_and_die("hexdump: bad skip value.\n");
-                       }
-                       switch(*p) {
-                               case 'b':
-                                       skip *= 512;
-                                       break;
-                               case 'k':
-                                       skip *= 1024;
-                                       break;
-                               case 'm':
-                                       skip *= 1048576;
-                                       break;
+       bb_dump_vflag = FIRST;
+       bb_dump_length = -1;
+
+       while ((ch = getopt(argc, argv, hexdump_opts)) > 0) {
+               if ((p = strchr(hexdump_opts, ch)) != NULL) {
+                       if ((p - hexdump_opts) < 5) {
+                               bb_dump_add(add_first);
+                               bb_dump_add(add_strings[(int)(p - hexdump_opts)]);
+                       } else if (ch == 'C') {
+                               bb_dump_add("\"%08.8_Ax\n\"");
+                               bb_dump_add("\"%08.8_ax  \" 8/1 \"%02x \" \"  \" 8/1 \"%02x \" ");
+                               bb_dump_add("\"  |\" 16/1 \"%_p\" \"|\\n\"");
+                       } else {
+                               /* Sae a little bit of space below by omitting the 'else's. */
+                               if (ch == 'e') {
+                                       bb_dump_add(optarg);
+                               } /* else */
+                               if (ch == 'f') {
+                                       bb_dump_addfile(optarg);
+                               } /* else */
+                               if (ch == 'n') {
+                                       bb_dump_length = bb_xgetularg10_bnd(optarg, 0, INT_MAX);
+                               } /* else */
+                               if (ch == 's') {
+                                       bb_dump_skip = bb_xgetularg_bnd_sfx(optarg, 10, 0, LONG_MAX, suffixes);
+                               } /* else */
+                               if (ch == 'v') {
+                                       bb_dump_vflag = ALL;
+                               }
                        }
-                       break;
-               case 'v':
-                       vflag = ALL;
-                       break;
-               case 'x':
-                       add("\"%07.7_Ax\n\"");
-                       add("\"%07.7_ax \" 8/2 \"   %04x \" \"\\n\"");
-                       break;
-               case '?':
-                       show_usage();
+               } else {
+                       bb_show_usage();
                }
        }
 
-       if (!fshead) {
-               add("\"%07.7_Ax\n\"");
-               add("\"%07.7_ax \" 8/2 \"%04x \" \"\\n\"");
+       if (!bb_dump_fshead) {
+               bb_dump_add(add_first);
+               bb_dump_add("\"%07.7_ax \" 8/2 \"%04x \" \"\\n\"");
        }
 
        argv += optind;
 
-       return(dump(argv));
+       return(bb_dump_dump(argv));
 }
 /*
  * Copyright (c) 1989 The Regents of the University of California.
@@ -147,11 +128,7 @@ int hexdump_main(int argc, char **argv)
  * 2. Redistributions in binary form must reproduce the above copyright
  *    notice, this list of conditions and the following disclaimer in the
  *    documentation and/or other materials provided with the distribution.
- * 3. All advertising materials mentioning features or use of this software
- *    must display the following acknowledgement:
- *     This product includes software developed by the University of
- *     California, Berkeley and its contributors.
- * 4. Neither the name of the University nor the names of its contributors
+ * 3. Neither the name of the University nor the names of its contributors
  *    may be used to endorse or promote products derived from this software
  *    without specific prior written permission.
  *