diff options
Diffstat (limited to '')
-rwxr-xr-x | .bin/xx.c | 71 |
1 files changed, 45 insertions, 26 deletions
diff --git a/.bin/xx.c b/.bin/xx.c index 6af0d6a7..e92d12d3 100755 --- a/.bin/xx.c +++ b/.bin/xx.c @@ -23,34 +23,10 @@ enum { FLAG_ASCII = 1, FLAG_OFFSET = 2, FLAG_SKIP = 4, + FLAG_UNDUMP = 8, }; -int main(int argc, char *argv[]) { - size_t cols = 16; - size_t group = 8; - uint8_t flags = FLAG_ASCII | FLAG_OFFSET; - char *path = NULL; - - int opt; - while ((opt = getopt(argc, argv, "ac:fg:hk")) > 0) { - switch (opt) { - case 'a': flags ^= FLAG_ASCII; break; - case 'f': flags ^= FLAG_OFFSET; break; - case 'k': flags ^= FLAG_SKIP; break; - case 'c': cols = strtoul(optarg, NULL, 10); break; - case 'g': group = strtoul(optarg, NULL, 10); break; - default: - fprintf(stderr, "usage: xx [-afk] [-c cols] [-g group] [file]\n"); - return (opt == 'h') ? EX_OK : EX_USAGE; - } - } - if (!cols) return EX_USAGE; - if (argc > optind) - path = argv[optind]; - - FILE *file = path ? fopen(path, "r") : stdin; - if (!file) err(EX_NOINPUT, "%s", path); - +void dump(size_t cols, size_t group, uint8_t flags, FILE *file) { uint8_t buf[cols]; size_t offset = 0, len = 0; for (;;) { @@ -87,6 +63,49 @@ int main(int argc, char *argv[]) { printf("\n"); if (len < sizeof(buf)) break; } +} + +void undump(FILE *file) { + uint8_t byte; + int match; + while (1 == (match = fscanf(file, " %hhx", &byte))) { + printf("%c", byte); + } + if (match == 0) errx(EX_DATAERR, "invalid input"); +} + +int main(int argc, char *argv[]) { + size_t cols = 16; + size_t group = 8; + uint8_t flags = FLAG_ASCII | FLAG_OFFSET; + char *path = NULL; + + int opt; + while ((opt = getopt(argc, argv, "ac:fg:hku")) > 0) { + switch (opt) { + case 'a': flags ^= FLAG_ASCII; break; + case 'f': flags ^= FLAG_OFFSET; break; + case 'k': flags ^= FLAG_SKIP; break; + case 'u': flags ^= FLAG_UNDUMP; break; + case 'c': cols = strtoul(optarg, NULL, 10); break; + case 'g': group = strtoul(optarg, NULL, 10); break; + default: + fprintf(stderr, "usage: xx [-afku] [-c cols] [-g group] [file]\n"); + return (opt == 'h') ? EX_OK : EX_USAGE; + } + } + if (!cols) return EX_USAGE; + if (argc > optind) + path = argv[optind]; + + FILE *file = path ? fopen(path, "r") : stdin; + if (!file) err(EX_NOINPUT, "%s", path); + + if (flags & FLAG_UNDUMP) { + undump(file); + } else { + dump(cols, group, flags, file); + } if (ferror(file)) err(EX_IOERR, "%s", path); return EX_OK; |