aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorB. Watson <urchlay@slackware.uk>2025-11-29 04:12:07 -0500
committerB. Watson <urchlay@slackware.uk>2025-11-29 04:12:07 -0500
commit25380d9b6846574b1bad03708226f7bf346b8391 (patch)
tree6d5865c224c4a155f193e51ecd880572b6fefd7b
parent8b4a168475a005d7fc4a298321688fccdb2f8ba3 (diff)
downloadalftools-25380d9b6846574b1bad03708226f7bf346b8391.tar.gz
alf: Sanity-check generated Atari filenames.
-rw-r--r--src/Makefile6
-rw-r--r--src/alf.c2
-rw-r--r--src/extract.c65
-rw-r--r--src/sanity.c72
-rw-r--r--src/sanity.h2
5 files changed, 82 insertions, 65 deletions
diff --git a/src/Makefile b/src/Makefile
index da19876..6e0100c 100644
--- a/src/Makefile
+++ b/src/Makefile
@@ -43,9 +43,9 @@ CFLAGS=-DVERSION='"$(VERSION)"' -Wall -I../f65 $(COPT)
BINS=alf alfsum unalf
MANS=alf.1 alfsum.1 unalf.1
-UNALF_OBJS=unalf.o io.o listalf.o extract.o f65.o glob.o opts.o usage.o self.o asmcode.o
+UNALF_OBJS=unalf.o io.o listalf.o extract.o f65.o glob.o opts.o usage.o self.o asmcode.o sanity.o
ALFSUM_OBJS=alfsum.o self.o
-ALF_OBJS=alf.o self.o alfusage.o
+ALF_OBJS=alf.o self.o alfusage.o sanity.o
.PHONY: all clean install crosswin windows windows-upload realclean
@@ -88,6 +88,8 @@ listalf.o: listalf.c addrs.h unalf.h ../f65/f65.h
extract.o: extract.c addrs.h unalf.h ../f65/f65.h
+sanity.o: sanity.c sanity.h
+
ver.rst:
echo '.. |version| replace:: $(VERSION)' > ver.rst
diff --git a/src/alf.c b/src/alf.c
index 916958d..7559eae 100644
--- a/src/alf.c
+++ b/src/alf.c
@@ -7,6 +7,7 @@
#include <sys/stat.h>
#include <time.h>
+#include "sanity.h"
#include "self.h"
#ifndef u8
@@ -155,6 +156,7 @@ void create_header(void) {
atarify_filename(hdr_filename);
printf("Crunching %s\n", hdr_filename);
+ sanity_check_filename(hdr_filename);
if(opt_alftime)
time = 0x03130588;
diff --git a/src/extract.c b/src/extract.c
index 6d940a2..f6b36e7 100644
--- a/src/extract.c
+++ b/src/extract.c
@@ -1,5 +1,6 @@
#include "unalf.h"
#include "addrs.h"
+#include "sanity.h"
#include <time.h>
#include <utime.h>
@@ -17,68 +18,6 @@ u16 dpeek(int addr) {
return mem[addr] | (mem[addr + 1] << 8);
}
-static void bad_atari_filename(const char *msg) {
- char fn[50] = "";
- char xbuf[5];
- int i;
- u8 c;
-
- for(i = 0; (c = (u8)out_filename[i]) && i < 12; i++) {
- if(c < ' ' || c > '|') {
- /* not printable, insert a hex escape */
- sprintf(xbuf, "$%02X", c);
- strcat(fn, xbuf);
- } else {
- strncat(fn, (char *)&c, 1);
- }
- }
-
- fprintf(stderr, "%s: bad Atari filename \"%s\": %s\n", self, fn, msg);
-}
-
-/* note to self: it's tempting to use isalpha(), isprint(), etc
- from ctype.h... but those are locale-aware. we want ASCII-only
- versions. */
-static void sanity_check_filename(void) {
- u8 c;
- unsigned int i, bad = 0, dots = 0, uscore = 0;
-
- c = out_filename[0];
- if(!c) {
- bad_atari_filename("empty! corrupt ALF file?");
- return;
- } else if(c < 'A' || c > 'Z') {
- bad_atari_filename("does not begin with A-Z");
- }
-
- for(i = 0; (c = out_filename[i]) && i < 12; i++) {
- if(c >= 'A' && c <= 'Z')
- continue;
- if(c >= '0' && c <= '9')
- continue;
- if(c == '_') {
- uscore++;
- continue;
- }
- if(c == '.') {
- dots++;
- continue;
- }
- bad++;
- }
-
- if(!dots) {
- bad_atari_filename("no \".\"");
- } else if(dots > 1) {
- bad_atari_filename("more than one \".\"");
- }
-
- if(bad)
- bad_atari_filename("invalid characters. corrupt ALF file?");
- else if(uscore)
- fprintf(stderr, "%s: filename has underscore, OK on Sparta/MyDOS, not Atari DOS 2.x\n", self);
-}
-
void fix_filename(void) {
char *p;
@@ -89,7 +28,7 @@ void fix_filename(void) {
out_filename[12] = '\0';
}
- sanity_check_filename();
+ sanity_check_filename(out_filename);
if(opts.lowercase) {
for(p = out_filename; *p; p++)
diff --git a/src/sanity.c b/src/sanity.c
new file mode 100644
index 0000000..ccbcae1
--- /dev/null
+++ b/src/sanity.c
@@ -0,0 +1,72 @@
+#include <stdio.h>
+#include <string.h>
+
+#ifndef u8
+#define u8 unsigned char
+#endif
+
+extern const char *self;
+
+void bad_atari_filename(const char *fname, const char *msg) {
+ char fn[50] = "";
+ char xbuf[5];
+ int i;
+ u8 c;
+
+ for(i = 0; (c = (u8)fname[i]) && i < 12; i++) {
+ if(c < ' ' || c > '|') {
+ /* not printable, insert a hex escape */
+ sprintf(xbuf, "$%02X", c);
+ strcat(fn, xbuf);
+ } else {
+ strncat(fn, (char *)&c, 1);
+ }
+ }
+
+ fprintf(stderr, "%s: warning: bad Atari filename \"%s\": %s\n", self, fn, msg);
+}
+
+/* note to self: it's tempting to use isalpha(), isprint(), etc
+ from ctype.h... but those are locale-aware. we want ASCII-only
+ versions. */
+void sanity_check_filename(const char *fname) {
+ u8 c;
+ unsigned int i, bad = 0, dots = 0, uscore = 0;
+
+ c = fname[0];
+ if(!c) {
+ bad_atari_filename(fname, "empty!");
+ return;
+ } else if(c < 'A' || c > 'Z') {
+ bad_atari_filename(fname, "does not begin with A-Z");
+ }
+
+ for(i = 0; (c = fname[i]) && i < 12; i++) {
+ if(c >= 'A' && c <= 'Z')
+ continue;
+ if(c >= '0' && c <= '9')
+ continue;
+ if(c == '_') {
+ uscore++;
+ continue;
+ }
+ if(c == '.') {
+ dots++;
+ continue;
+ }
+ bad++;
+ }
+
+ if(!dots) {
+ bad_atari_filename(fname, "no \".\"");
+ } else if(dots > 1) {
+ bad_atari_filename(fname, "more than one \".\"");
+ }
+
+ if(bad)
+ bad_atari_filename(fname, "invalid characters.");
+ else if(uscore)
+ fprintf(stderr, "%s: filename has underscore, OK on Sparta/MyDOS, not Atari DOS 2.x\n", self);
+}
+
+
diff --git a/src/sanity.h b/src/sanity.h
new file mode 100644
index 0000000..b1f3821
--- /dev/null
+++ b/src/sanity.h
@@ -0,0 +1,2 @@
+void bad_atari_filename(const char *msg);
+void sanity_check_filename(const char *fname);