ref: 100cfd2e994fe870af1bd247097dfc105291c1bd
parent: ec4335e07f4819e82ec2cc95fba36764e5bcf8f2
author: Ben Harris <[email protected]>
date: Thu Feb 16 17:57:23 EST 2023
Separate fuzzing and harness in fuzzpuzz There's now a function, fuzz_one(), that processes a single save file, and main() arranges to call this a suitable number of times depending on whether we're in AFL persistent mode or not. This makes things a bit cleaner, and will probably make adding good support for other fuzzers, or just switching entirely to the horrible but popular libFuzzer interface, simpler.
--- a/fuzzpuzz.c
+++ b/fuzzpuzz.c
@@ -23,6 +23,44 @@
__AFL_FUZZ_INIT();
#endif
+static const char *fuzz_one(bool (*readfn)(void *, void *, int), void *rctx,
+ void (*rewindfn)(void *),
+ void (*writefn)(void *, const void *, int),
+ void *wctx)
+{
+ const char *err;
+ char *gamename;
+ int i, w, h;
+ const game *ourgame = NULL;
+ static const drawing_api drapi = { NULL };
+ midend *me;
+
+ err = identify_game(&gamename, readfn, rctx);
+ if (err != NULL) return err;
+
+ for (i = 0; i < gamecount; i++)
+ if (strcmp(gamename, gamelist[i]->name) == 0)
+ ourgame = gamelist[i];
+ sfree(gamename);
+ if (ourgame == NULL)
+ return "Game not recognised";
+
+ me = midend_new(NULL, ourgame, &drapi, NULL);
+
+ rewindfn(rctx);
+ err = midend_deserialise(me, readfn, rctx);
+ if (err != NULL) {
+ midend_free(me);
+ return err;
+ }
+ w = h = INT_MAX;
+ midend_size(me, &w, &h, false, 1);
+ midend_redraw(me);
+ midend_serialise(me, writefn, wctx);
+ midend_free(me);
+ return NULL;
+}
+
static bool savefile_read(void *wctx, void *buf, int len)
{
FILE *fp = (FILE *)wctx;
@@ -32,6 +70,13 @@
return (ret == len);
}
+static void savefile_rewind(void *wctx)
+{
+ FILE *fp = (FILE *)wctx;
+
+ rewind(fp);
+}
+
static void savefile_write(void *wctx, const void *buf, int len)
{
FILE *fp = (FILE *)wctx;
@@ -39,17 +84,11 @@
fwrite(buf, 1, len, fp);
}
-static drawing_api drapi = { NULL };
-
int main(int argc, char **argv)
{
const char *err;
- char *gamename;
- int i, ret = -1;
- const game *ourgame = NULL;
- midend *me;
+ int ret = -1;
FILE *in = NULL;
- int w, h;
if (argc != 1) {
fprintf(stderr, "usage: %s\n", argv[0]);
@@ -79,39 +118,14 @@
in = stdin;
while (ret == -1) {
#endif
- err = identify_game(&gamename, savefile_read, in);
- if (err != NULL) {
+ err = fuzz_one(savefile_read, in, savefile_rewind,
+ savefile_write, stdout);
+ if (err == NULL) {
+ ret = 0;
+ } else {
fprintf(stderr, "%s\n", err);
ret = 1;
- continue;
}
-
- for (i = 0; i < gamecount; i++)
- if (strcmp(gamename, gamelist[i]->name) == 0)
- ourgame = gamelist[i];
- sfree(gamename);
- if (ourgame == NULL) {
- fprintf(stderr, "Game not recognised\n");
- ret = 1;
- continue;
- }
-
- me = midend_new(NULL, ourgame, &drapi, NULL);
-
- rewind(in);
- err = midend_deserialise(me, savefile_read, in);
- if (err != NULL) {
- fprintf(stderr, "%s\n", err);
- ret = 1;
- midend_free(me);
- continue;
- }
- w = h = INT_MAX;
- midend_size(me, &w, &h, false, 1);
- midend_redraw(me);
- midend_serialise(me, savefile_write, stdout);
- midend_free(me);
- ret = 0;
}
return ret;
}