summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorLouis Burda <quent.burda@gmail.com>2023-03-13 14:46:01 +0100
committerLouis Burda <quent.burda@gmail.com>2023-03-13 14:46:01 +0100
commit6da6771b247ef295105099dd62297bad82bfd502 (patch)
tree405fe7f88d8ad39356fe65a4571f62dfd2aad215
parent03ba9c7da68c3fadb64ca32dbc9258919b7ac19a (diff)
downloadsplice-6da6771b247ef295105099dd62297bad82bfd502.tar.gz
splice-6da6771b247ef295105099dd62297bad82bfd502.zip
Rename to splice
-rw-r--r--.gitignore2
-rw-r--r--Makefile17
-rw-r--r--binpatch.c54
-rw-r--r--splice.c60
4 files changed, 74 insertions, 59 deletions
diff --git a/.gitignore b/.gitignore
index 5e6ad6b..50dd627 100644
--- a/.gitignore
+++ b/.gitignore
@@ -1 +1 @@
-binpatch
+splice
diff --git a/Makefile b/Makefile
index 9eb7905..c051187 100644
--- a/Makefile
+++ b/Makefile
@@ -1,10 +1,19 @@
+PREFIX ?= /usr/local
+BINDIR ?= /bin
+
CFLAGS = -g
-all: binpatch
+all: splice
clean:
- rm -f binpatch
+ rm -f splice
+
+splice: splice.c
+
+install:
+ install -m 755 splice -t "$(DESTDIR)$(PREFIX)$(BINDIR)"
-binpatch: binpatch.c
+uninstall:
+ rm -f "$(DESTDIR)$(PREFIX)$(BINDIR)/splice"
-.PHONY: all clean
+.PHONY: all clean install uninstall
diff --git a/binpatch.c b/binpatch.c
deleted file mode 100644
index 9df9bc2..0000000
--- a/binpatch.c
+++ /dev/null
@@ -1,54 +0,0 @@
-#include <err.h>
-#include <stdio.h>
-#include <stdint.h>
-#include <stdlib.h>
-
-int
-main(int argc, const char **argv)
-{
- ssize_t addr, size;
- char *end, *data;
- FILE *file;
- int ret;
-
- if (argc != 4) {
- printf("USAGE: fwpatch TARGET OFFSET FILE\n");
- return 0;
- }
-
- addr = strtoull(argv[2], &end, 0);
- if (*end) err(1, "strtoull %s", argv[2]);
-
- file = fopen(argv[3], "rb");
- if (!file) err(1, "fopen %s", argv[3]);
-
- ret = fseek(file, 0, SEEK_END);
- if (ret < 0) err(1, "fseek %s", argv[3]);
-
- size = ftell(file);
- if (size < 0) err(1, "ftell %s", argv[3]);
-
- data = malloc(size);
- if (!data) err(1, "malloc %lu", size);
-
- ret = fseek(file, 0, SEEK_SET);
- if (ret < 0) err(1, "freek %s", argv[3]);
-
- if (fread(data, 1, size, file) != size)
- errx(1, "fread %lu", size);
-
- fclose(file);
-
- file = fopen(argv[1], "r+b");
- if (!file) err(1, "fopen %s", argv[1]);
-
- ret = fseek(file, addr, SEEK_SET);
- if (ret < 0) err(1, "fseek %s", argv[1]);
-
- if (fwrite(data, 1, size, file) != size)
- errx(1, "fwrite %lu", size);
-
- fclose(file);
-
- free(data);
-}
diff --git a/splice.c b/splice.c
new file mode 100644
index 0000000..2f11291
--- /dev/null
+++ b/splice.c
@@ -0,0 +1,60 @@
+#include <err.h>
+#include <stdio.h>
+#include <stdint.h>
+#include <stdlib.h>
+
+int
+main(int argc, const char **argv)
+{
+ char buf[BUFSIZ];
+ ssize_t start, end;
+ ssize_t pos, nread, nreq;
+ FILE *main_file;
+ char *endc;
+ int ret;
+
+ if (argc < 3 || argc > 4) {
+ printf("USAGE: fwpatch MAIN START [END]\n");
+ return 0;
+ }
+
+ main_file = fopen(argv[1], "rb");
+ if (!main_file) err(1, "fopen %s", argv[1]);
+
+ start = strtoll(argv[2], &endc, 0);
+ if (endc && *endc) err(1, "strtoll %s", argv[2]);
+ if (start < 0) errx(1, "negative start");
+
+ if (argc == 4) {
+ end = strtoll(argv[3], &endc, 0);
+ if (endc && *endc) err(1, "strtoll %s", argv[3]);
+ if (start >= end) errx(1, "invalid length");
+ } else {
+ end = -1;
+ }
+
+ pos = 0;
+ while (!feof(main_file) || !feof(stdin)) {
+ if (pos >= start && !feof(stdin)) {
+ nread = fread(buf, 1, BUFSIZ, stdin);
+ if (pos == start && end >= 0)
+ fseek(main_file, end, SEEK_CUR);
+ else if (end < 0)
+ fseek(main_file, nread, SEEK_CUR);
+ } else {
+ if (start > pos) {
+ nreq = start - pos;
+ if (nreq > BUFSIZ)
+ nreq = BUFSIZ;
+ } else {
+ nreq = BUFSIZ;
+ }
+ nread = fread(buf, 1, nreq, main_file);
+ }
+ if (fwrite(buf, 1, nread, stdout) != nread)
+ errx(1, "output truncated");
+ pos += nread;
+ }
+
+ fclose(main_file);
+}