about summary refs log tree commit diff
path: root/custom_mutators/honggfuzz/mangle.c
diff options
context:
space:
mode:
Diffstat (limited to 'custom_mutators/honggfuzz/mangle.c')
-rw-r--r--custom_mutators/honggfuzz/mangle.c1039
1 files changed, 1039 insertions, 0 deletions
diff --git a/custom_mutators/honggfuzz/mangle.c b/custom_mutators/honggfuzz/mangle.c
new file mode 100644
index 00000000..05e0dcfa
--- /dev/null
+++ b/custom_mutators/honggfuzz/mangle.c
@@ -0,0 +1,1039 @@
+/*
+ *
+ * honggfuzz - run->dynfile->datafer mangling routines
+ * -----------------------------------------
+ *
+ * Author:
+ * Robert Swiecki <swiecki@google.com>
+ *
+ * Copyright 2010-2018 by Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may
+ * not use this file except in compliance with the License. You may obtain
+ * a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+ * implied. See the License for the specific language governing
+ * permissions and limitations under the License.
+ *
+ */
+
+#include "mangle.h"
+
+#include <ctype.h>
+#include <inttypes.h>
+#include <stdbool.h>
+#include <stdint.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <sys/types.h>
+#include <time.h>
+
+#include "input.h"
+#include "libhfcommon/common.h"
+#include "libhfcommon/log.h"
+#include "libhfcommon/util.h"
+
+static inline size_t mangle_LenLeft(run_t *run, size_t off) {
+
+  if (off >= run->dynfile->size) {
+
+    LOG_F("Offset is too large: off:%zu >= len:%zu", off, run->dynfile->size);
+
+  }
+
+  return (run->dynfile->size - off - 1);
+
+}
+
+/* Get a random value between <1:max> with x^2 distribution */
+static inline size_t mangle_getLen(size_t max) {
+
+  if (max > _HF_INPUT_MAX_SIZE) {
+
+    LOG_F("max (%zu) > _HF_INPUT_MAX_SIZE (%zu)", max,
+          (size_t)_HF_INPUT_MAX_SIZE);
+
+  }
+
+  if (max == 0) { LOG_F("max == 0"); }
+  if (max == 1) { return 1; }
+
+  const uint64_t max2 = (uint64_t)max * max;
+  const uint64_t max3 = (uint64_t)max * max * max;
+  const uint64_t rnd = util_rndGet(1, max2 - 1);
+
+  uint64_t ret = rnd * rnd;
+  ret /= max3;
+  ret += 1;
+
+  if (ret < 1) {
+
+    LOG_F("ret (%" PRIu64 ") < 1, max:%zu, rnd:%" PRIu64, ret, max, rnd);
+
+  }
+
+  if (ret > max) {
+
+    LOG_F("ret (%" PRIu64 ") > max (%zu), rnd:%" PRIu64, ret, max, rnd);
+
+  }
+
+  return (size_t)ret;
+
+}
+
+/* Prefer smaller values here, so use mangle_getLen() */
+static inline size_t mangle_getOffSet(run_t *run) {
+
+  return mangle_getLen(run->dynfile->size) - 1;
+
+}
+
+/* Offset which can be equal to the file size */
+static inline size_t mangle_getOffSetPlus1(run_t *run) {
+
+  size_t reqlen = HF_MIN(run->dynfile->size + 1, _HF_INPUT_MAX_SIZE);
+  return mangle_getLen(reqlen) - 1;
+
+}
+
+static inline void mangle_Move(run_t *run, size_t off_from, size_t off_to,
+                               size_t len) {
+
+  if (off_from >= run->dynfile->size) { return; }
+  if (off_to >= run->dynfile->size) { return; }
+  if (off_from == off_to) { return; }
+
+  size_t len_from = run->dynfile->size - off_from;
+  len = HF_MIN(len, len_from);
+
+  size_t len_to = run->dynfile->size - off_to;
+  len = HF_MIN(len, len_to);
+
+  memmove(&run->dynfile->data[off_to], &run->dynfile->data[off_from], len);
+
+}
+
+static inline void mangle_Overwrite(run_t *run, size_t off, const uint8_t *src,
+                                    size_t len, bool printable) {
+
+  if (len == 0) { return; }
+  size_t maxToCopy = run->dynfile->size - off;
+  if (len > maxToCopy) { len = maxToCopy; }
+
+  memmove(&run->dynfile->data[off], src, len);
+  if (printable) { util_turnToPrintable(&run->dynfile->data[off], len); }
+
+}
+
+static inline size_t mangle_Inflate(run_t *run, size_t off, size_t len,
+                                    bool printable) {
+
+  if (run->dynfile->size >= run->global->mutate.maxInputSz) { return 0; }
+  if (len > (run->global->mutate.maxInputSz - run->dynfile->size)) {
+
+    len = run->global->mutate.maxInputSz - run->dynfile->size;
+
+  }
+
+  input_setSize(run, run->dynfile->size + len);
+  mangle_Move(run, off, off + len, run->dynfile->size);
+  if (printable) { memset(&run->dynfile->data[off], ' ', len); }
+
+  return len;
+
+}
+
+static inline void mangle_Insert(run_t *run, size_t off, const uint8_t *val,
+                                 size_t len, bool printable) {
+
+  len = mangle_Inflate(run, off, len, printable);
+  mangle_Overwrite(run, off, val, len, printable);
+
+}
+
+static inline void mangle_UseValue(run_t *run, const uint8_t *val, size_t len,
+                                   bool printable) {
+
+  if (util_rnd64() % 2) {
+
+    mangle_Insert(run, mangle_getOffSetPlus1(run), val, len, printable);
+
+  } else {
+
+    mangle_Overwrite(run, mangle_getOffSet(run), val, len, printable);
+
+  }
+
+}
+
+static void mangle_MemSwap(run_t *run, bool printable HF_ATTR_UNUSED) {
+
+  size_t off1 = mangle_getOffSet(run);
+  size_t maxlen1 = run->dynfile->size - off1;
+
+  size_t off2 = mangle_getOffSet(run);
+  size_t maxlen2 = run->dynfile->size - off2;
+
+  size_t   len = mangle_getLen(HF_MIN(maxlen1, maxlen2));
+  uint8_t *tmpbuf = (uint8_t *)util_Malloc(len);
+  defer {
+
+    free(tmpbuf);
+
+  };
+
+  memcpy(tmpbuf, &run->dynfile->data[off1], len);
+  memmove(&run->dynfile->data[off1], &run->dynfile->data[off2], len);
+  memcpy(&run->dynfile->data[off2], tmpbuf, len);
+
+}
+
+static void mangle_MemCopy(run_t *run, bool printable HF_ATTR_UNUSED) {
+
+  size_t off = mangle_getOffSet(run);
+  size_t len = mangle_getLen(run->dynfile->size - off);
+
+  /* Use a temp buf, as Insert/Inflate can change source bytes */
+  uint8_t *tmpbuf = (uint8_t *)util_Malloc(len);
+  defer {
+
+    free(tmpbuf);
+
+  };
+
+  memcpy(tmpbuf, &run->dynfile->data[off], len);
+
+  mangle_UseValue(run, tmpbuf, len, printable);
+
+}
+
+static void mangle_Bytes(run_t *run, bool printable) {
+
+  uint16_t buf;
+  if (printable) {
+
+    util_rndBufPrintable((uint8_t *)&buf, sizeof(buf));
+
+  } else {
+
+    buf = util_rnd64();
+
+  }
+
+  /* Overwrite with random 1-2-byte values */
+  size_t toCopy = util_rndGet(1, 2);
+  mangle_UseValue(run, (const uint8_t *)&buf, toCopy, printable);
+
+}
+
+static void mangle_ByteRepeatOverwrite(run_t *run, bool printable) {
+
+  size_t off = mangle_getOffSet(run);
+  size_t destOff = off + 1;
+  size_t maxSz = run->dynfile->size - destOff;
+
+  /* No space to repeat */
+  if (!maxSz) {
+
+    mangle_Bytes(run, printable);
+    return;
+
+  }
+
+  size_t len = mangle_getLen(maxSz);
+  memset(&run->dynfile->data[destOff], run->dynfile->data[off], len);
+
+}
+
+static void mangle_ByteRepeatInsert(run_t *run, bool printable) {
+
+  size_t off = mangle_getOffSet(run);
+  size_t destOff = off + 1;
+  size_t maxSz = run->dynfile->size - destOff;
+
+  /* No space to repeat */
+  if (!maxSz) {
+
+    mangle_Bytes(run, printable);
+    return;
+
+  }
+
+  size_t len = mangle_getLen(maxSz);
+  len = mangle_Inflate(run, destOff, len, printable);
+  memset(&run->dynfile->data[destOff], run->dynfile->data[off], len);
+
+}
+
+static void mangle_Bit(run_t *run, bool printable) {
+
+  size_t off = mangle_getOffSet(run);
+  run->dynfile->data[off] ^= (uint8_t)(1U << util_rndGet(0, 7));
+  if (printable) { util_turnToPrintable(&(run->dynfile->data[off]), 1); }
+
+}
+
+static const struct {
+
+  const uint8_t val[8];
+  const size_t  size;
+
+} mangleMagicVals[] = {
+
+    /* 1B - No endianness */
+    {"\x00\x00\x00\x00\x00\x00\x00\x00", 1},
+    {"\x01\x00\x00\x00\x00\x00\x00\x00", 1},
+    {"\x02\x00\x00\x00\x00\x00\x00\x00", 1},
+    {"\x03\x00\x00\x00\x00\x00\x00\x00", 1},
+    {"\x04\x00\x00\x00\x00\x00\x00\x00", 1},
+    {"\x05\x00\x00\x00\x00\x00\x00\x00", 1},
+    {"\x06\x00\x00\x00\x00\x00\x00\x00", 1},
+    {"\x07\x00\x00\x00\x00\x00\x00\x00", 1},
+    {"\x08\x00\x00\x00\x00\x00\x00\x00", 1},
+    {"\x09\x00\x00\x00\x00\x00\x00\x00", 1},
+    {"\x0A\x00\x00\x00\x00\x00\x00\x00", 1},
+    {"\x0B\x00\x00\x00\x00\x00\x00\x00", 1},
+    {"\x0C\x00\x00\x00\x00\x00\x00\x00", 1},
+    {"\x0D\x00\x00\x00\x00\x00\x00\x00", 1},
+    {"\x0E\x00\x00\x00\x00\x00\x00\x00", 1},
+    {"\x0F\x00\x00\x00\x00\x00\x00\x00", 1},
+    {"\x10\x00\x00\x00\x00\x00\x00\x00", 1},
+    {"\x20\x00\x00\x00\x00\x00\x00\x00", 1},
+    {"\x40\x00\x00\x00\x00\x00\x00\x00", 1},
+    {"\x7E\x00\x00\x00\x00\x00\x00\x00", 1},
+    {"\x7F\x00\x00\x00\x00\x00\x00\x00", 1},
+    {"\x80\x00\x00\x00\x00\x00\x00\x00", 1},
+    {"\x81\x00\x00\x00\x00\x00\x00\x00", 1},
+    {"\xC0\x00\x00\x00\x00\x00\x00\x00", 1},
+    {"\xFE\x00\x00\x00\x00\x00\x00\x00", 1},
+    {"\xFF\x00\x00\x00\x00\x00\x00\x00", 1},
+    /* 2B - NE */
+    {"\x00\x00\x00\x00\x00\x00\x00\x00", 2},
+    {"\x01\x01\x00\x00\x00\x00\x00\x00", 2},
+    {"\x80\x80\x00\x00\x00\x00\x00\x00", 2},
+    {"\xFF\xFF\x00\x00\x00\x00\x00\x00", 2},
+    /* 2B - BE */
+    {"\x00\x01\x00\x00\x00\x00\x00\x00", 2},
+    {"\x00\x02\x00\x00\x00\x00\x00\x00", 2},
+    {"\x00\x03\x00\x00\x00\x00\x00\x00", 2},
+    {"\x00\x04\x00\x00\x00\x00\x00\x00", 2},
+    {"\x00\x05\x00\x00\x00\x00\x00\x00", 2},
+    {"\x00\x06\x00\x00\x00\x00\x00\x00", 2},
+    {"\x00\x07\x00\x00\x00\x00\x00\x00", 2},
+    {"\x00\x08\x00\x00\x00\x00\x00\x00", 2},
+    {"\x00\x09\x00\x00\x00\x00\x00\x00", 2},
+    {"\x00\x0A\x00\x00\x00\x00\x00\x00", 2},
+    {"\x00\x0B\x00\x00\x00\x00\x00\x00", 2},
+    {"\x00\x0C\x00\x00\x00\x00\x00\x00", 2},
+    {"\x00\x0D\x00\x00\x00\x00\x00\x00", 2},
+    {"\x00\x0E\x00\x00\x00\x00\x00\x00", 2},
+    {"\x00\x0F\x00\x00\x00\x00\x00\x00", 2},
+    {"\x00\x10\x00\x00\x00\x00\x00\x00", 2},
+    {"\x00\x20\x00\x00\x00\x00\x00\x00", 2},
+    {"\x00\x40\x00\x00\x00\x00\x00\x00", 2},
+    {"\x00\x7E\x00\x00\x00\x00\x00\x00", 2},
+    {"\x00\x7F\x00\x00\x00\x00\x00\x00", 2},
+    {"\x00\x80\x00\x00\x00\x00\x00\x00", 2},
+    {"\x00\x81\x00\x00\x00\x00\x00\x00", 2},
+    {"\x00\xC0\x00\x00\x00\x00\x00\x00", 2},
+    {"\x00\xFE\x00\x00\x00\x00\x00\x00", 2},
+    {"\x00\xFF\x00\x00\x00\x00\x00\x00", 2},
+    {"\x7E\xFF\x00\x00\x00\x00\x00\x00", 2},
+    {"\x7F\xFF\x00\x00\x00\x00\x00\x00", 2},
+    {"\x80\x00\x00\x00\x00\x00\x00\x00", 2},
+    {"\x80\x01\x00\x00\x00\x00\x00\x00", 2},
+    {"\xFF\xFE\x00\x00\x00\x00\x00\x00", 2},
+    /* 2B - LE */
+    {"\x00\x00\x00\x00\x00\x00\x00\x00", 2},
+    {"\x01\x00\x00\x00\x00\x00\x00\x00", 2},
+    {"\x02\x00\x00\x00\x00\x00\x00\x00", 2},
+    {"\x03\x00\x00\x00\x00\x00\x00\x00", 2},
+    {"\x04\x00\x00\x00\x00\x00\x00\x00", 2},
+    {"\x05\x00\x00\x00\x00\x00\x00\x00", 2},
+    {"\x06\x00\x00\x00\x00\x00\x00\x00", 2},
+    {"\x07\x00\x00\x00\x00\x00\x00\x00", 2},
+    {"\x08\x00\x00\x00\x00\x00\x00\x00", 2},
+    {"\x09\x00\x00\x00\x00\x00\x00\x00", 2},
+    {"\x0A\x00\x00\x00\x00\x00\x00\x00", 2},
+    {"\x0B\x00\x00\x00\x00\x00\x00\x00", 2},
+    {"\x0C\x00\x00\x00\x00\x00\x00\x00", 2},
+    {"\x0D\x00\x00\x00\x00\x00\x00\x00", 2},
+    {"\x0E\x00\x00\x00\x00\x00\x00\x00", 2},
+    {"\x0F\x00\x00\x00\x00\x00\x00\x00", 2},
+    {"\x10\x00\x00\x00\x00\x00\x00\x00", 2},
+    {"\x20\x00\x00\x00\x00\x00\x00\x00", 2},
+    {"\x40\x00\x00\x00\x00\x00\x00\x00", 2},
+    {"\x7E\x00\x00\x00\x00\x00\x00\x00", 2},
+    {"\x7F\x00\x00\x00\x00\x00\x00\x00", 2},
+    {"\x80\x00\x00\x00\x00\x00\x00\x00", 2},
+    {"\x81\x00\x00\x00\x00\x00\x00\x00", 2},
+    {"\xC0\x00\x00\x00\x00\x00\x00\x00", 2},
+    {"\xFE\x00\x00\x00\x00\x00\x00\x00", 2},
+    {"\xFF\x00\x00\x00\x00\x00\x00\x00", 2},
+    {"\xFF\x7E\x00\x00\x00\x00\x00\x00", 2},
+    {"\xFF\x7F\x00\x00\x00\x00\x00\x00", 2},
+    {"\x00\x80\x00\x00\x00\x00\x00\x00", 2},
+    {"\x01\x80\x00\x00\x00\x00\x00\x00", 2},
+    {"\xFE\xFF\x00\x00\x00\x00\x00\x00", 2},
+    /* 4B - NE */
+    {"\x00\x00\x00\x00\x00\x00\x00\x00", 4},
+    {"\x01\x01\x01\x01\x00\x00\x00\x00", 4},
+    {"\x80\x80\x80\x80\x00\x00\x00\x00", 4},
+    {"\xFF\xFF\xFF\xFF\x00\x00\x00\x00", 4},
+    /* 4B - BE */
+    {"\x00\x00\x00\x01\x00\x00\x00\x00", 4},
+    {"\x00\x00\x00\x02\x00\x00\x00\x00", 4},
+    {"\x00\x00\x00\x03\x00\x00\x00\x00", 4},
+    {"\x00\x00\x00\x04\x00\x00\x00\x00", 4},
+    {"\x00\x00\x00\x05\x00\x00\x00\x00", 4},
+    {"\x00\x00\x00\x06\x00\x00\x00\x00", 4},
+    {"\x00\x00\x00\x07\x00\x00\x00\x00", 4},
+    {"\x00\x00\x00\x08\x00\x00\x00\x00", 4},
+    {"\x00\x00\x00\x09\x00\x00\x00\x00", 4},
+    {"\x00\x00\x00\x0A\x00\x00\x00\x00", 4},
+    {"\x00\x00\x00\x0B\x00\x00\x00\x00", 4},
+    {"\x00\x00\x00\x0C\x00\x00\x00\x00", 4},
+    {"\x00\x00\x00\x0D\x00\x00\x00\x00", 4},
+    {"\x00\x00\x00\x0E\x00\x00\x00\x00", 4},
+    {"\x00\x00\x00\x0F\x00\x00\x00\x00", 4},
+    {"\x00\x00\x00\x10\x00\x00\x00\x00", 4},
+    {"\x00\x00\x00\x20\x00\x00\x00\x00", 4},
+    {"\x00\x00\x00\x40\x00\x00\x00\x00", 4},
+    {"\x00\x00\x00\x7E\x00\x00\x00\x00", 4},
+    {"\x00\x00\x00\x7F\x00\x00\x00\x00", 4},
+    {"\x00\x00\x00\x80\x00\x00\x00\x00", 4},
+    {"\x00\x00\x00\x81\x00\x00\x00\x00", 4},
+    {"\x00\x00\x00\xC0\x00\x00\x00\x00", 4},
+    {"\x00\x00\x00\xFE\x00\x00\x00\x00", 4},
+    {"\x00\x00\x00\xFF\x00\x00\x00\x00", 4},
+    {"\x7E\xFF\xFF\xFF\x00\x00\x00\x00", 4},
+    {"\x7F\xFF\xFF\xFF\x00\x00\x00\x00", 4},
+    {"\x80\x00\x00\x00\x00\x00\x00\x00", 4},
+    {"\x80\x00\x00\x01\x00\x00\x00\x00", 4},
+    {"\xFF\xFF\xFF\xFE\x00\x00\x00\x00", 4},
+    /* 4B - LE */
+    {"\x00\x00\x00\x00\x00\x00\x00\x00", 4},
+    {"\x01\x00\x00\x00\x00\x00\x00\x00", 4},
+    {"\x02\x00\x00\x00\x00\x00\x00\x00", 4},
+    {"\x03\x00\x00\x00\x00\x00\x00\x00", 4},
+    {"\x04\x00\x00\x00\x00\x00\x00\x00", 4},
+    {"\x05\x00\x00\x00\x00\x00\x00\x00", 4},
+    {"\x06\x00\x00\x00\x00\x00\x00\x00", 4},
+    {"\x07\x00\x00\x00\x00\x00\x00\x00", 4},
+    {"\x08\x00\x00\x00\x00\x00\x00\x00", 4},
+    {"\x09\x00\x00\x00\x00\x00\x00\x00", 4},
+    {"\x0A\x00\x00\x00\x00\x00\x00\x00", 4},
+    {"\x0B\x00\x00\x00\x00\x00\x00\x00", 4},
+    {"\x0C\x00\x00\x00\x00\x00\x00\x00", 4},
+    {"\x0D\x00\x00\x00\x00\x00\x00\x00", 4},
+    {"\x0E\x00\x00\x00\x00\x00\x00\x00", 4},
+    {"\x0F\x00\x00\x00\x00\x00\x00\x00", 4},
+    {"\x10\x00\x00\x00\x00\x00\x00\x00", 4},
+    {"\x20\x00\x00\x00\x00\x00\x00\x00", 4},
+    {"\x40\x00\x00\x00\x00\x00\x00\x00", 4},
+    {"\x7E\x00\x00\x00\x00\x00\x00\x00", 4},
+    {"\x7F\x00\x00\x00\x00\x00\x00\x00", 4},
+    {"\x80\x00\x00\x00\x00\x00\x00\x00", 4},
+    {"\x81\x00\x00\x00\x00\x00\x00\x00", 4},
+    {"\xC0\x00\x00\x00\x00\x00\x00\x00", 4},
+    {"\xFE\x00\x00\x00\x00\x00\x00\x00", 4},
+    {"\xFF\x00\x00\x00\x00\x00\x00\x00", 4},
+    {"\xFF\xFF\xFF\x7E\x00\x00\x00\x00", 4},
+    {"\xFF\xFF\xFF\x7F\x00\x00\x00\x00", 4},
+    {"\x00\x00\x00\x80\x00\x00\x00\x00", 4},
+    {"\x01\x00\x00\x80\x00\x00\x00\x00", 4},
+    {"\xFE\xFF\xFF\xFF\x00\x00\x00\x00", 4},
+    /* 8B - NE */
+    {"\x00\x00\x00\x00\x00\x00\x00\x00", 8},
+    {"\x01\x01\x01\x01\x01\x01\x01\x01", 8},
+    {"\x80\x80\x80\x80\x80\x80\x80\x80", 8},
+    {"\xFF\xFF\xFF\xFF\xFF\xFF\xFF\xFF", 8},
+    /* 8B - BE */
+    {"\x00\x00\x00\x00\x00\x00\x00\x01", 8},
+    {"\x00\x00\x00\x00\x00\x00\x00\x02", 8},
+    {"\x00\x00\x00\x00\x00\x00\x00\x03", 8},
+    {"\x00\x00\x00\x00\x00\x00\x00\x04", 8},
+    {"\x00\x00\x00\x00\x00\x00\x00\x05", 8},
+    {"\x00\x00\x00\x00\x00\x00\x00\x06", 8},
+    {"\x00\x00\x00\x00\x00\x00\x00\x07", 8},
+    {"\x00\x00\x00\x00\x00\x00\x00\x08", 8},
+    {"\x00\x00\x00\x00\x00\x00\x00\x09", 8},
+    {"\x00\x00\x00\x00\x00\x00\x00\x0A", 8},
+    {"\x00\x00\x00\x00\x00\x00\x00\x0B", 8},
+    {"\x00\x00\x00\x00\x00\x00\x00\x0C", 8},
+    {"\x00\x00\x00\x00\x00\x00\x00\x0D", 8},
+    {"\x00\x00\x00\x00\x00\x00\x00\x0E", 8},
+    {"\x00\x00\x00\x00\x00\x00\x00\x0F", 8},
+    {"\x00\x00\x00\x00\x00\x00\x00\x10", 8},
+    {"\x00\x00\x00\x00\x00\x00\x00\x20", 8},
+    {"\x00\x00\x00\x00\x00\x00\x00\x40", 8},
+    {"\x00\x00\x00\x00\x00\x00\x00\x7E", 8},
+    {"\x00\x00\x00\x00\x00\x00\x00\x7F", 8},
+    {"\x00\x00\x00\x00\x00\x00\x00\x80", 8},
+    {"\x00\x00\x00\x00\x00\x00\x00\x81", 8},
+    {"\x00\x00\x00\x00\x00\x00\x00\xC0", 8},
+    {"\x00\x00\x00\x00\x00\x00\x00\xFE", 8},
+    {"\x00\x00\x00\x00\x00\x00\x00\xFF", 8},
+    {"\x7E\xFF\xFF\xFF\xFF\xFF\xFF\xFF", 8},
+    {"\x7F\xFF\xFF\xFF\xFF\xFF\xFF\xFF", 8},
+    {"\x80\x00\x00\x00\x00\x00\x00\x00", 8},
+    {"\x80\x00\x00\x00\x00\x00\x00\x01", 8},
+    {"\xFF\xFF\xFF\xFF\xFF\xFF\xFF\xFE", 8},
+    /* 8B - LE */
+    {"\x00\x00\x00\x00\x00\x00\x00\x00", 8},
+    {"\x01\x00\x00\x00\x00\x00\x00\x00", 8},
+    {"\x02\x00\x00\x00\x00\x00\x00\x00", 8},
+    {"\x03\x00\x00\x00\x00\x00\x00\x00", 8},
+    {"\x04\x00\x00\x00\x00\x00\x00\x00", 8},
+    {"\x05\x00\x00\x00\x00\x00\x00\x00", 8},
+    {"\x06\x00\x00\x00\x00\x00\x00\x00", 8},
+    {"\x07\x00\x00\x00\x00\x00\x00\x00", 8},
+    {"\x08\x00\x00\x00\x00\x00\x00\x00", 8},
+    {"\x09\x00\x00\x00\x00\x00\x00\x00", 8},
+    {"\x0A\x00\x00\x00\x00\x00\x00\x00", 8},
+    {"\x0B\x00\x00\x00\x00\x00\x00\x00", 8},
+    {"\x0C\x00\x00\x00\x00\x00\x00\x00", 8},
+    {"\x0D\x00\x00\x00\x00\x00\x00\x00", 8},
+    {"\x0E\x00\x00\x00\x00\x00\x00\x00", 8},
+    {"\x0F\x00\x00\x00\x00\x00\x00\x00", 8},
+    {"\x10\x00\x00\x00\x00\x00\x00\x00", 8},
+    {"\x20\x00\x00\x00\x00\x00\x00\x00", 8},
+    {"\x40\x00\x00\x00\x00\x00\x00\x00", 8},
+    {"\x7E\x00\x00\x00\x00\x00\x00\x00", 8},
+    {"\x7F\x00\x00\x00\x00\x00\x00\x00", 8},
+    {"\x80\x00\x00\x00\x00\x00\x00\x00", 8},
+    {"\x81\x00\x00\x00\x00\x00\x00\x00", 8},
+    {"\xC0\x00\x00\x00\x00\x00\x00\x00", 8},
+    {"\xFE\x00\x00\x00\x00\x00\x00\x00", 8},
+    {"\xFF\x00\x00\x00\x00\x00\x00\x00", 8},
+    {"\xFF\xFF\xFF\xFF\xFF\xFF\xFF\x7E", 8},
+    {"\xFF\xFF\xFF\xFF\xFF\xFF\xFF\x7F", 8},
+    {"\x00\x00\x00\x00\x00\x00\x00\x80", 8},
+    {"\x01\x00\x00\x00\x00\x00\x00\x80", 8},
+    {"\xFE\xFF\xFF\xFF\xFF\xFF\xFF\xFF", 8},
+
+};
+
+static void mangle_Magic(run_t *run, bool printable) {
+
+  uint64_t choice = util_rndGet(0, ARRAYSIZE(mangleMagicVals) - 1);
+  mangle_UseValue(run, mangleMagicVals[choice].val,
+                  mangleMagicVals[choice].size, printable);
+
+}
+
+static void mangle_StaticDict(run_t *run, bool printable) {
+
+  if (run->global->mutate.dictionaryCnt == 0) {
+
+    mangle_Bytes(run, printable);
+    return;
+
+  }
+
+  uint64_t choice = util_rndGet(0, run->global->mutate.dictionaryCnt - 1);
+  mangle_UseValue(run, run->global->mutate.dictionary[choice].val,
+                  run->global->mutate.dictionary[choice].len, printable);
+
+}
+
+static inline const uint8_t *mangle_FeedbackDict(run_t *run, size_t *len) {
+
+  if (!run->global->feedback.cmpFeedback) { return NULL; }
+  cmpfeedback_t *cmpf = run->global->feedback.cmpFeedbackMap;
+  uint32_t       cnt = ATOMIC_GET(cmpf->cnt);
+  if (cnt == 0) { return NULL; }
+  if (cnt > ARRAYSIZE(cmpf->valArr)) { cnt = ARRAYSIZE(cmpf->valArr); }
+  uint32_t choice = util_rndGet(0, cnt - 1);
+  *len = (size_t)ATOMIC_GET(cmpf->valArr[choice].len);
+  if (*len == 0) { return NULL; }
+  return cmpf->valArr[choice].val;
+
+}
+
+static void mangle_ConstFeedbackDict(run_t *run, bool printable) {
+
+  size_t         len;
+  const uint8_t *val = mangle_FeedbackDict(run, &len);
+  if (val == NULL) {
+
+    mangle_Bytes(run, printable);
+    return;
+
+  }
+
+  mangle_UseValue(run, val, len, printable);
+
+}
+
+static void mangle_MemSet(run_t *run, bool printable) {
+
+  size_t off = mangle_getOffSet(run);
+  size_t len = mangle_getLen(run->dynfile->size - off);
+  int    val =
+      printable ? (int)util_rndPrintable() : (int)util_rndGet(0, UINT8_MAX);
+
+  memset(&run->dynfile->data[off], val, len);
+
+}
+
+static void mangle_RandomOverwrite(run_t *run, bool printable) {
+
+  size_t off = mangle_getOffSet(run);
+  size_t len = mangle_getLen(run->dynfile->size - off);
+  if (printable) {
+
+    util_rndBufPrintable(&run->dynfile->data[off], len);
+
+  } else {
+
+    util_rndBuf(&run->dynfile->data[off], len);
+
+  }
+
+}
+
+static void mangle_RandomInsert(run_t *run, bool printable) {
+
+  size_t off = mangle_getOffSet(run);
+  size_t len = mangle_getLen(run->dynfile->size - off);
+
+  len = mangle_Inflate(run, off, len, printable);
+
+  if (printable) {
+
+    util_rndBufPrintable(&run->dynfile->data[off], len);
+
+  } else {
+
+    util_rndBuf(&run->dynfile->data[off], len);
+
+  }
+
+}
+
+static inline void mangle_AddSubWithRange(run_t *run, size_t off, size_t varLen,
+                                          uint64_t range, bool printable) {
+
+  int64_t delta = (int64_t)util_rndGet(0, range * 2) - (int64_t)range;
+
+  switch (varLen) {
+
+    case 1: {
+
+      run->dynfile->data[off] += delta;
+      break;
+
+    }
+
+    case 2: {
+
+      int16_t val;
+      memcpy(&val, &run->dynfile->data[off], sizeof(val));
+      if (util_rnd64() & 0x1) {
+
+        val += delta;
+
+      } else {
+
+        /* Foreign endianess */
+        val = __builtin_bswap16(val);
+        val += delta;
+        val = __builtin_bswap16(val);
+
+      }
+
+      mangle_Overwrite(run, off, (uint8_t *)&val, varLen, printable);
+      break;
+
+    }
+
+    case 4: {
+
+      int32_t val;
+      memcpy(&val, &run->dynfile->data[off], sizeof(val));
+      if (util_rnd64() & 0x1) {
+
+        val += delta;
+
+      } else {
+
+        /* Foreign endianess */
+        val = __builtin_bswap32(val);
+        val += delta;
+        val = __builtin_bswap32(val);
+
+      }
+
+      mangle_Overwrite(run, off, (uint8_t *)&val, varLen, printable);
+      break;
+
+    }
+
+    case 8: {
+
+      int64_t val;
+      memcpy(&val, &run->dynfile->data[off], sizeof(val));
+      if (util_rnd64() & 0x1) {
+
+        val += delta;
+
+      } else {
+
+        /* Foreign endianess */
+        val = __builtin_bswap64(val);
+        val += delta;
+        val = __builtin_bswap64(val);
+
+      }
+
+      mangle_Overwrite(run, off, (uint8_t *)&val, varLen, printable);
+      break;
+
+    }
+
+    default: {
+
+      LOG_F("Unknown variable length size: %zu", varLen);
+
+    }
+
+  }
+
+}
+
+static void mangle_AddSub(run_t *run, bool printable) {
+
+  size_t off = mangle_getOffSet(run);
+
+  /* 1,2,4,8 */
+  size_t varLen = 1U << util_rndGet(0, 3);
+  if ((run->dynfile->size - off) < varLen) { varLen = 1; }
+
+  uint64_t range;
+  switch (varLen) {
+
+    case 1:
+      range = 16;
+      break;
+    case 2:
+      range = 4096;
+      break;
+    case 4:
+      range = 1048576;
+      break;
+    case 8:
+      range = 268435456;
+      break;
+    default:
+      LOG_F("Invalid operand size: %zu", varLen);
+
+  }
+
+  mangle_AddSubWithRange(run, off, varLen, range, printable);
+
+}
+
+static void mangle_IncByte(run_t *run, bool printable) {
+
+  size_t off = mangle_getOffSet(run);
+  if (printable) {
+
+    run->dynfile->data[off] = (run->dynfile->data[off] - 32 + 1) % 95 + 32;
+
+  } else {
+
+    run->dynfile->data[off] += (uint8_t)1UL;
+
+  }
+
+}
+
+static void mangle_DecByte(run_t *run, bool printable) {
+
+  size_t off = mangle_getOffSet(run);
+  if (printable) {
+
+    run->dynfile->data[off] = (run->dynfile->data[off] - 32 + 94) % 95 + 32;
+
+  } else {
+
+    run->dynfile->data[off] -= (uint8_t)1UL;
+
+  }
+
+}
+
+static void mangle_NegByte(run_t *run, bool printable) {
+
+  size_t off = mangle_getOffSet(run);
+  if (printable) {
+
+    run->dynfile->data[off] = 94 - (run->dynfile->data[off] - 32) + 32;
+
+  } else {
+
+    run->dynfile->data[off] = ~(run->dynfile->data[off]);
+
+  }
+
+}
+
+static void mangle_Expand(run_t *run, bool printable) {
+
+  size_t off = mangle_getOffSet(run);
+  size_t len;
+  if (util_rnd64() % 16) {
+
+    len = mangle_getLen(HF_MIN(16, run->global->mutate.maxInputSz - off));
+
+  } else {
+
+    len = mangle_getLen(run->global->mutate.maxInputSz - off);
+
+  }
+
+  mangle_Inflate(run, off, len, printable);
+
+}
+
+static void mangle_Shrink(run_t *run, bool printable HF_ATTR_UNUSED) {
+
+  if (run->dynfile->size <= 2U) { return; }
+
+  size_t off_start = mangle_getOffSet(run);
+  size_t len = mangle_LenLeft(run, off_start);
+  if (len == 0) { return; }
+  if (util_rnd64() % 16) {
+
+    len = mangle_getLen(HF_MIN(16, len));
+
+  } else {
+
+    len = mangle_getLen(len);
+
+  }
+
+  size_t off_end = off_start + len;
+  size_t len_to_move = run->dynfile->size - off_end;
+
+  mangle_Move(run, off_end, off_start, len_to_move);
+  input_setSize(run, run->dynfile->size - len);
+
+}
+
+static void mangle_ASCIINum(run_t *run, bool printable) {
+
+  size_t len = util_rndGet(2, 8);
+
+  char buf[20];
+  snprintf(buf, sizeof(buf), "%-19" PRId64, (int64_t)util_rnd64());
+
+  mangle_UseValue(run, (const uint8_t *)buf, len, printable);
+
+}
+
+static void mangle_ASCIINumChange(run_t *run, bool printable) {
+
+  size_t off = mangle_getOffSet(run);
+
+  /* Find a digit */
+  for (; off < run->dynfile->size; off++) {
+
+    if (isdigit(run->dynfile->data[off])) { break; }
+
+  }
+
+  if (off == run->dynfile->size) {
+
+    mangle_Bytes(run, printable);
+    return;
+
+  }
+
+  size_t len = HF_MIN(20, run->dynfile->size - off);
+  char   numbuf[21] = {};
+  strncpy(numbuf, (const char *)&run->dynfile->data[off], len);
+  uint64_t val = (uint64_t)strtoull(numbuf, NULL, 10);
+
+  switch (util_rndGet(0, 5)) {
+
+    case 0:
+      val += util_rndGet(1, 256);
+      break;
+    case 1:
+      val -= util_rndGet(1, 256);
+      break;
+    case 2:
+      val *= util_rndGet(1, 256);
+      break;
+    case 3:
+      val /= util_rndGet(1, 256);
+      break;
+    case 4:
+      val = ~(val);
+      break;
+    case 5:
+      val = util_rnd64();
+      break;
+    default:
+      LOG_F("Invalid choice");
+
+  };
+
+  len = HF_MIN((size_t)snprintf(numbuf, sizeof(numbuf), "%" PRIu64, val), len);
+  mangle_Overwrite(run, off, (const uint8_t *)numbuf, len, printable);
+
+}
+
+static void mangle_Splice(run_t *run, bool printable) {
+
+  const uint8_t *buf;
+  size_t         sz = input_getRandomInputAsBuf(run, &buf);
+  if (!sz) {
+
+    mangle_Bytes(run, printable);
+    return;
+
+  }
+
+  size_t remoteOff = mangle_getLen(sz) - 1;
+  size_t len = mangle_getLen(sz - remoteOff);
+  mangle_UseValue(run, &buf[remoteOff], len, printable);
+
+}
+
+static void mangle_Resize(run_t *run, bool printable) {
+
+  ssize_t oldsz = run->dynfile->size;
+  ssize_t newsz = 0;
+
+  uint64_t choice = util_rndGet(0, 32);
+  switch (choice) {
+
+    case 0:                                     /* Set new size arbitrarily */
+      newsz = (ssize_t)util_rndGet(1, run->global->mutate.maxInputSz);
+      break;
+    case 1 ... 4:                         /* Increase size by a small value */
+      newsz = oldsz + (ssize_t)util_rndGet(0, 8);
+      break;
+    case 5:                              /* Increase size by a larger value */
+      newsz = oldsz + (ssize_t)util_rndGet(9, 128);
+      break;
+    case 6 ... 9:                         /* Decrease size by a small value */
+      newsz = oldsz - (ssize_t)util_rndGet(0, 8);
+      break;
+    case 10:                             /* Decrease size by a larger value */
+      newsz = oldsz - (ssize_t)util_rndGet(9, 128);
+      break;
+    case 11 ... 32:                                           /* Do nothing */
+      newsz = oldsz;
+      break;
+    default:
+      LOG_F("Illegal value from util_rndGet: %" PRIu64, choice);
+      break;
+
+  }
+
+  if (newsz < 1) { newsz = 1; }
+  if (newsz > (ssize_t)run->global->mutate.maxInputSz) {
+
+    newsz = run->global->mutate.maxInputSz;
+
+  }
+
+  input_setSize(run, (size_t)newsz);
+  if (newsz > oldsz) {
+
+    if (printable) { memset(&run->dynfile->data[oldsz], ' ', newsz - oldsz); }
+
+  }
+
+}
+
+void mangle_mangleContent(run_t *run, int speed_factor) {
+
+  static void (*const mangleFuncs[])(run_t * run, bool printable) = {
+
+      /* Every *Insert or Expand expands file, so add more Shrink's */
+      mangle_Shrink,
+      mangle_Shrink,
+      mangle_Shrink,
+      mangle_Shrink,
+      mangle_Expand,
+      mangle_Bit,
+      mangle_IncByte,
+      mangle_DecByte,
+      mangle_NegByte,
+      mangle_AddSub,
+      mangle_MemSet,
+      mangle_MemSwap,
+      mangle_MemCopy,
+      mangle_Bytes,
+      mangle_ASCIINum,
+      mangle_ASCIINumChange,
+      mangle_ByteRepeatOverwrite,
+      mangle_ByteRepeatInsert,
+      mangle_Magic,
+      mangle_StaticDict,
+      mangle_ConstFeedbackDict,
+      mangle_RandomOverwrite,
+      mangle_RandomInsert,
+      mangle_Splice,
+
+  };
+
+  if (run->mutationsPerRun == 0U) { return; }
+  if (run->dynfile->size == 0U) {
+
+    mangle_Resize(run, /* printable= */ run->global->cfg.only_printable);
+
+  }
+
+  uint64_t changesCnt = run->global->mutate.mutationsPerRun;
+
+  if (speed_factor < 5) {
+
+    changesCnt = util_rndGet(1, run->global->mutate.mutationsPerRun);
+
+  } else if (speed_factor < 10) {
+
+    changesCnt = run->global->mutate.mutationsPerRun;
+
+  } else {
+
+    changesCnt = HF_MIN(speed_factor, 12);
+    changesCnt = HF_MAX(changesCnt, run->global->mutate.mutationsPerRun);
+
+  }
+
+  /* If last coverage acquisition was more than 5 secs ago, use splicing more
+   * frequently */
+  if ((time(NULL) - ATOMIC_GET(run->global->timing.lastCovUpdate)) > 5) {
+
+    if (util_rnd64() % 2) {
+
+      mangle_Splice(run, run->global->cfg.only_printable);
+
+    }
+
+  }
+
+  for (uint64_t x = 0; x < changesCnt; x++) {
+
+    uint64_t choice = util_rndGet(0, ARRAYSIZE(mangleFuncs) - 1);
+    mangleFuncs[choice](run, /* printable= */ run->global->cfg.only_printable);
+
+  }
+
+  wmb();
+
+}
+