1 #include "hb-fuzzer.hh"
10 // Only allow ~5,000 set values between the two input sets.
11 // Arbitrarily long input sets do not trigger any meaningful
12 // differences in behaviour so there's no benefit from allowing
13 // the fuzzer to create super large sets.
14 #define MAX_INPUT_SIZE 20000
16 enum set_operation_t : uint8_t
21 SYMMETRIC_DIFFERENCE = 3
26 set_operation_t operation;
27 uint32_t first_set_size;
30 static hb_set_t *create_set (const uint32_t *value_array, int count)
32 hb_set_t *set = hb_set_create ();
33 for (int i = 0; i < count; i++)
34 hb_set_add (set, value_array[i]);
39 extern "C" int LLVMFuzzerTestOneInput (const uint8_t *data, size_t size)
41 alloc_state = _fuzzing_alloc_state (data, size);
43 if (size < sizeof (instructions_t))
46 if (size > MAX_INPUT_SIZE)
49 #pragma GCC diagnostic push
50 #pragma GCC diagnostic ignored "-Wstrict-aliasing"
51 const instructions_t &instructions = reinterpret_cast<const instructions_t &> (data);
52 #pragma GCC diagnostic pop
53 data += sizeof (instructions_t);
54 size -= sizeof (instructions_t);
56 const uint32_t *values = reinterpret_cast<const uint32_t *> (data);
57 size = size / sizeof (uint32_t);
59 if (size < instructions.first_set_size)
62 hb_set_t *set_a = create_set (values, instructions.first_set_size);
64 values += instructions.first_set_size;
65 size -= instructions.first_set_size;
66 hb_set_t *set_b = create_set (values, size);
68 switch (instructions.operation)
71 hb_set_intersect (set_a, set_b);
74 hb_set_union (set_a, set_b);
77 hb_set_subtract (set_a, set_b);
79 case SYMMETRIC_DIFFERENCE:
80 hb_set_symmetric_difference (set_a, set_b);
86 hb_set_destroy (set_a);
87 hb_set_destroy (set_b);