summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorLouis Burda <quent.burda@gmail.com>2022-09-16 02:36:24 +0200
committerLouis Burda <quent.burda@gmail.com>2023-02-23 00:55:51 +0100
commit8a8e88fc843e8b5f9ee57c542f3c512ca78286a6 (patch)
treebfb5f93097da3b52a30fb42ebb305bff443f1a06
parentdb101f60ec24a988a10c0d8cf68a921fa0907e25 (diff)
downloadbin-8a8e88fc843e8b5f9ee57c542f3c512ca78286a6.tar.gz
bin-8a8e88fc843e8b5f9ee57c542f3c512ca78286a6.zip
Utilities for converting from and to binary
-rw-r--r--.gitignore4
-rw-r--r--Makefile21
-rw-r--r--bin.c88
-rw-r--r--unbin.c (renamed from bitcat.c)54
4 files changed, 136 insertions, 31 deletions
diff --git a/.gitignore b/.gitignore
index 94a873d..e385933 100644
--- a/.gitignore
+++ b/.gitignore
@@ -1,2 +1,2 @@
-vgcore*
-bitcat
+bin
+unbin
diff --git a/Makefile b/Makefile
index 476bd96..a725a37 100644
--- a/Makefile
+++ b/Makefile
@@ -1,8 +1,19 @@
-CFLAGS ?=
-LDFLAGS ?=
+DESTDIR ?=
+BINDIR ?= /usr/local/bin
-all: bitcat
+all: bin unbin
-%: %.c
- $(CC) -o $@ $< $(CFLAGS) $(LDFLAGS)
+clean:
+ rm -f bin
+bin: bin.c
+
+unbin: unbin.c
+
+install: bin unbin
+ install -m755 $^ $(DESTDIR)$(BINDIR)
+
+uninstall:
+ rm -f $(DESTDIR)$(BINDIR)/{bin,unbin}
+
+.PHONY: all clean install uninstall
diff --git a/bin.c b/bin.c
new file mode 100644
index 0000000..ede1819
--- /dev/null
+++ b/bin.c
@@ -0,0 +1,88 @@
+#include <stdlib.h>
+#include <stdio.h>
+#include <string.h>
+#include <stdarg.h>
+
+#define ISFLAG(str, fshort, flong) (!strcmp(str, fshort) || !strcmp(str, flong))
+
+const char *usage = "USAGE: bin [-r] [-s SKIP] [-n COUNT] [FILE]\n";
+
+void
+die(const char *fmtstr, ...)
+{
+ va_list ap;
+
+ va_start(ap, fmtstr);
+ vfprintf(stderr, fmtstr, ap);
+ va_end(ap);
+
+ exit(EXIT_FAILURE);
+}
+
+int
+main(int argc, const char **argv)
+{
+ unsigned char byte, bit;
+ size_t skip, cnt, pos;
+ const char *filepath;
+ int i, revbyte, cntset;
+ char *end;
+ FILE *f;
+
+ filepath = NULL;
+ cnt = skip = 0;
+ revbyte = 0;
+ cntset = 0;
+
+ for (i = 1; i < argc; i++) {
+ if (ISFLAG(argv[i], "-s", "--skip")) {
+ if (i++ >= argc - 1) goto missing_arg;
+ skip = strtoul(argv[i], &end, 0);
+ if (end && *end) goto bad_arg;
+ } else if (ISFLAG(argv[i], "-n", "--count")) {
+ if (i++ >= argc - 1) goto missing_arg;
+ cnt = strtoul(argv[i], &end, 0);
+ cntset = 1;
+ if (end && *end) goto bad_arg;
+ } else if (ISFLAG(argv[i], "-r", "--revb")) {
+ revbyte = 1;
+ } else if (ISFLAG(argv[i], "-h", "--help")) {
+ die(usage);
+ } else if (*argv[i] == '-') {
+ die("Unknown flag: %s\n", argv[i]);
+ } else if (filepath) {
+ die("Too many files specified\n");
+ } else {
+ filepath = argv[i];
+ }
+ }
+
+ if (!filepath)
+ f = stdin;
+ else if (!(f = fopen(filepath, "r")))
+ die("Failed to open file\n");
+
+ pos = 0;
+ while (!cntset || pos < skip + cnt) {
+ if (pos % 8 == 0) byte = fgetc(f);
+ if (feof(f)) break;
+ if (pos >= skip) {
+ if (revbyte)
+ bit = (byte >> (pos % 8)) & 1;
+ else
+ bit = (byte >> (7 - pos % 8)) & 1;
+ putchar(bit ? '1' : '0');
+ }
+ pos += 1;
+ }
+
+ fclose(f);
+
+ return EXIT_SUCCESS;
+
+missing_arg:
+ die("Flag %s expects an argument\n", argv[i]);
+
+bad_arg:
+ die("Argument has unexpected value: %s\n", argv[i]);
+}
diff --git a/bitcat.c b/unbin.c
index d27df14..e808076 100644
--- a/bitcat.c
+++ b/unbin.c
@@ -5,7 +5,7 @@
#define ISFLAG(str, fshort, flong) (!strcmp(str, fshort) || !strcmp(str, flong))
-const char *usage = "USAGE: bitcat [-r] [-s SKIP] [-n COUNT] FILE\n";
+const char *usage = "USAGE: unbin [-r] [-s SKIP] [-n COUNT] [FILE]\n";
void
die(const char *fmtstr, ...)
@@ -23,24 +23,25 @@ int
main(int argc, const char **argv)
{
unsigned char byte, bit;
- size_t skip, size, pos;
+ size_t skip, cnt, pos;
const char *filepath;
- int i, revbyte;
+ int i, revbyte, cntset;
char *end;
FILE *f;
- if (argc <= 1) die(usage);
-
filepath = NULL;
- revbyte = size = skip = 0;
+ cnt = skip = 0;
+ revbyte = cntset = 0;
+
for (i = 1; i < argc; i++) {
if (ISFLAG(argv[i], "-s", "--skip")) {
if (i++ == argc - 1) goto missing_arg;
- skip = strtol(argv[i], &end, 0);
+ skip = strtoul(argv[i], &end, 0);
if (end && *end) goto bad_arg;
} else if (ISFLAG(argv[i], "-n", "--count")) {
if (i++ == argc - 1) goto missing_arg;
- size = strtol(argv[i], &end, 0);
+ cnt = strtoul(argv[i], &end, 0);
+ cntset = 1;
if (end && *end) goto bad_arg;
} else if (ISFLAG(argv[i], "-r", "--revb")) {
revbyte = 1;
@@ -56,25 +57,30 @@ main(int argc, const char **argv)
}
if (!filepath)
- die("No file specified\n");
-
- if (!(f = fopen(filepath, "r")))
+ f = stdin;
+ else if (!(f = fopen(filepath, "r")))
die("Failed to open file\n");
- if (!size) {
- fseek(f, 0, SEEK_END);
- size = ftell(f) * 8;
- fseek(f, 0, SEEK_SET);
- }
-
- for (pos = 0; pos < size + skip && !feof(f); pos++) {
- if (pos % 8 == 0) byte = fgetc(f);
- if (revbyte)
- bit = (byte >> (7 - pos % 8)) & 1;
- else
- bit = (byte >> (pos % 8)) & 1;
- if (pos >= skip) putchar(bit ? '1' : '0');
+ pos = 0;
+ while (!cntset || pos < cnt + skip) {
+ if (pos % 8 == 0) byte = 0;
+ bit = fgetc(f);
+ if (feof(f)) break;
+ if (bit != '1' && bit != '0')
+ continue;
+ bit = (bit == '1');
+ if (pos >= 0) {
+ if (revbyte)
+ byte |= bit << (pos % 8);
+ else
+ byte |= bit << (7 - pos % 8);
+ if (pos % 8 == 7)
+ putchar(byte);
+ }
+ pos += 1;
}
+ if (pos % 8 != 0)
+ putchar(byte);
fclose(f);