xref: /freebsd/contrib/libder/tests/fuzz_write.c (revision 35c0a8c449fd2b7f75029ebed5e10852240f0865)
1 /*-
2  * Copyright (c) 2024 Kyle Evans <kevans@FreeBSD.org>
3  *
4  * SPDX-License-Identifier: BSD-2-Clause
5  */
6 
7 #include <sys/param.h>
8 #include <sys/socket.h>
9 
10 #include <assert.h>
11 #include <signal.h>
12 #include <stdbool.h>
13 #include <stdio.h>
14 #include <stdlib.h>
15 #include <unistd.h>
16 
17 #include <libder.h>
18 
19 #include "fuzzers.h"
20 
21 int
LLVMFuzzerTestOneInput(const uint8_t * data,size_t sz)22 LLVMFuzzerTestOneInput(const uint8_t *data, size_t sz)
23 {
24 	struct libder_ctx *ctx;
25 	struct libder_object *obj;
26 	size_t readsz;
27 	int ret;
28 	bool strict;
29 
30 	if (sz < 2)
31 		return (-1);
32 
33 	/*
34 	 * I worked this in originally by just using the high bit of the first
35 	 * byte, but then I realized that encoding it that way would make it
36 	 * impossible to get strict validation of universal and application
37 	 * tags.  The former is a bit more important than the latter.
38 	 */
39 	strict = !!data[0];
40 	data++;
41 	sz--;
42 
43 	ctx = libder_open();
44 	libder_set_strict(ctx, strict);
45 	ret = -1;
46 	readsz = sz;
47 	obj = libder_read(ctx, data, &readsz);
48 	if (obj == NULL || readsz != sz)
49 		goto out;
50 
51 	if (obj != NULL) {
52 		uint8_t *buf = NULL;
53 		size_t bufsz = 0;
54 
55 		/*
56 		 * If we successfully read it, then it shouldn't
57 		 * overflow.  We're letting libder allocate the buffer,
58 		 * so we shouldn't be able to hit the 'too small' bit.
59 		 *
60 		 * I can't imagine what other errors might happen, so
61 		 * we'll just assert on it.
62 		 */
63 		buf = libder_write(ctx, obj, buf, &bufsz);
64 		if (buf == NULL)
65 			goto out;
66 
67 		assert(bufsz != 0);
68 
69 		free(buf);
70 	}
71 
72 	ret = 0;
73 
74 out:
75 	libder_obj_free(obj);
76 	libder_close(ctx);
77 
78 	return (ret);
79 }
80