[llvm] r278982 - [libFuzzer] one more mutation: ChangeBinaryInteger; also fix the breakage from r278970

Kostya Serebryany via llvm-commits llvm-commits at lists.llvm.org
Wed Aug 17 14:30:31 PDT 2016


Author: kcc
Date: Wed Aug 17 16:30:30 2016
New Revision: 278982

URL: http://llvm.org/viewvc/llvm-project?rev=278982&view=rev
Log:
[libFuzzer] one more mutation: ChangeBinaryInteger; also fix the breakage from r278970

Modified:
    llvm/trunk/lib/Fuzzer/FuzzerInternal.h
    llvm/trunk/lib/Fuzzer/FuzzerMutate.cpp
    llvm/trunk/lib/Fuzzer/test/FuzzerUnittest.cpp

Modified: llvm/trunk/lib/Fuzzer/FuzzerInternal.h
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Fuzzer/FuzzerInternal.h?rev=278982&r1=278981&r2=278982&view=diff
==============================================================================
--- llvm/trunk/lib/Fuzzer/FuzzerInternal.h (original)
+++ llvm/trunk/lib/Fuzzer/FuzzerInternal.h Wed Aug 17 16:30:30 2016
@@ -290,6 +290,8 @@ public:
 
   /// Tries to find an ASCII integer in Data, changes it to another ASCII int.
   size_t Mutate_ChangeASCIIInteger(uint8_t *Data, size_t Size, size_t MaxSize);
+  /// Change a 1-, 2-, 4-, or 8-byte integer in interesting ways.
+  size_t Mutate_ChangeBinaryInteger(uint8_t *Data, size_t Size, size_t MaxSize);
 
   /// CrossOver Data with some other element of the corpus.
   size_t Mutate_CrossOver(uint8_t *Data, size_t Size, size_t MaxSize);

Modified: llvm/trunk/lib/Fuzzer/FuzzerMutate.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Fuzzer/FuzzerMutate.cpp?rev=278982&r1=278981&r2=278982&view=diff
==============================================================================
--- llvm/trunk/lib/Fuzzer/FuzzerMutate.cpp (original)
+++ llvm/trunk/lib/Fuzzer/FuzzerMutate.cpp Wed Aug 17 16:30:30 2016
@@ -32,6 +32,7 @@ MutationDispatcher::MutationDispatcher(R
           {&MutationDispatcher::Mutate_ChangeBit, "ChangeBit"},
           {&MutationDispatcher::Mutate_ShuffleBytes, "ShuffleBytes"},
           {&MutationDispatcher::Mutate_ChangeASCIIInteger, "ChangeASCIIInt"},
+          {&MutationDispatcher::Mutate_ChangeBinaryInteger, "ChangeBinInt"},
           {&MutationDispatcher::Mutate_CopyPart, "CopyPart"},
           {&MutationDispatcher::Mutate_CrossOver, "CrossOver"},
           {&MutationDispatcher::Mutate_AddWordFromManualDictionary,
@@ -269,6 +270,42 @@ size_t MutationDispatcher::Mutate_Change
   return Size;
 }
 
+uint8_t  Bswap(uint8_t x)  { return x; }
+uint16_t Bswap(uint16_t x) { return __builtin_bswap16(x); }
+uint32_t Bswap(uint32_t x) { return __builtin_bswap32(x); }
+uint64_t Bswap(uint64_t x) { return __builtin_bswap64(x); }
+
+template<class T>
+size_t ChangeBinaryInteger(uint8_t *Data, size_t Size, Random &Rand) {
+  if (Size < sizeof(T)) return 0;
+  size_t Off = Rand(Size - sizeof(T) + 1);
+  assert(Off + sizeof(T) <= Size);
+  T Val;
+  memcpy(&Val, Data + Off, sizeof(Val));
+  T Add = Rand(21);
+  Add -= 10;
+  if (Rand.RandBool())
+    Val = Bswap(T(Bswap(Val) + Add));  // Add assuming different endiannes.
+  else
+    Val = Val + Add;                   // Add assuming current endiannes.
+  if (Add == 0 || Rand.RandBool())     // Maybe negate.
+    Val = -Val;
+  memcpy(Data + Off, &Val, sizeof(Val));
+  return Size;
+}
+
+size_t MutationDispatcher::Mutate_ChangeBinaryInteger(uint8_t *Data,
+                                                      size_t Size,
+                                                      size_t MaxSize) {
+  switch (Rand(4)) {
+    case 3: return ChangeBinaryInteger<uint64_t>(Data, Size, Rand);
+    case 2: return ChangeBinaryInteger<uint32_t>(Data, Size, Rand);
+    case 1: return ChangeBinaryInteger<uint16_t>(Data, Size, Rand);
+    case 0: return ChangeBinaryInteger<uint8_t>(Data, Size, Rand);
+    default: assert(0);
+  }
+}
+
 size_t MutationDispatcher::Mutate_CrossOver(uint8_t *Data, size_t Size,
                                             size_t MaxSize) {
   if (!Corpus || Corpus->size() < 2 || Size == 0) return 0;
@@ -286,7 +323,7 @@ size_t MutationDispatcher::Mutate_CrossO
       NewSize = InsertPartOf(O.data(), O.size(), U.data(), U.size(), MaxSize);
       if (NewSize)
         break;
-      LLVM_FALLTHROUGH;
+      // LLVM_FALLTHROUGH;
     case 2:
       NewSize = CopyPartOf(O.data(), O.size(), U.data(), U.size());
       break;

Modified: llvm/trunk/lib/Fuzzer/test/FuzzerUnittest.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Fuzzer/test/FuzzerUnittest.cpp?rev=278982&r1=278981&r2=278982&view=diff
==============================================================================
--- llvm/trunk/lib/Fuzzer/test/FuzzerUnittest.cpp (original)
+++ llvm/trunk/lib/Fuzzer/test/FuzzerUnittest.cpp Wed Aug 17 16:30:30 2016
@@ -219,7 +219,7 @@ TEST(FuzzerMutate, InsertRepeatedBytes1)
   TestInsertRepeatedBytes(&MutationDispatcher::Mutate_InsertRepeatedBytes, 10000);
 }
 TEST(FuzzerMutate, InsertRepeatedBytes2) {
-  TestInsertRepeatedBytes(&MutationDispatcher::Mutate, 200000);
+  TestInsertRepeatedBytes(&MutationDispatcher::Mutate, 300000);
 }
 
 void TestChangeByte(Mutator M, int NumIter) {
@@ -475,6 +475,42 @@ TEST(FuzzerMutate, ChangeASCIIInteger2)
   TestChangeASCIIInteger(&MutationDispatcher::Mutate, 1 << 15);
 }
 
+void TestChangeBinaryInteger(Mutator M, int NumIter) {
+  std::unique_ptr<ExternalFunctions> t(new ExternalFunctions());
+  fuzzer::EF = t.get();
+  Random Rand(0);
+  MutationDispatcher MD(Rand, {});
+
+  uint8_t CH0[8] = {0x00, 0x11, 0x22, 0x33, 0x44, 0x55, 0x66, 0x79};
+  uint8_t CH1[8] = {0x00, 0x11, 0x22, 0x31, 0x44, 0x55, 0x66, 0x77};
+  uint8_t CH2[8] = {0xff, 0x10, 0x22, 0x33, 0x44, 0x55, 0x66, 0x77};
+  uint8_t CH3[8] = {0x00, 0x11, 0x2a, 0x33, 0x44, 0x55, 0x66, 0x77};
+  uint8_t CH4[8] = {0x00, 0x11, 0x22, 0x33, 0x44, 0x4f, 0x66, 0x77};
+  uint8_t CH5[8] = {0xff, 0xee, 0xdd, 0xcc, 0xbb, 0xaa, 0x99, 0x88};
+
+  int FoundMask = 0;
+  for (int i = 0; i < NumIter; i++) {
+    uint8_t T[8] = {0x00, 0x11, 0x22, 0x33, 0x44, 0x55, 0x66, 0x77};
+    size_t NewSize = (MD.*M)(T, 8, 8);
+    /**/ if (NewSize == 8 && !memcmp(CH0, T, 8)) FoundMask |= 1 << 0;
+    else if (NewSize == 8 && !memcmp(CH1, T, 8)) FoundMask |= 1 << 1;
+    else if (NewSize == 8 && !memcmp(CH2, T, 8)) FoundMask |= 1 << 2;
+    else if (NewSize == 8 && !memcmp(CH3, T, 8)) FoundMask |= 1 << 3;
+    else if (NewSize == 8 && !memcmp(CH4, T, 8)) FoundMask |= 1 << 4;
+    else if (NewSize == 8 && !memcmp(CH5, T, 8)) FoundMask |= 1 << 5;
+  }
+  EXPECT_EQ(FoundMask, 63);
+}
+
+TEST(FuzzerMutate, ChangeBinaryInteger1) {
+  TestChangeBinaryInteger(&MutationDispatcher::Mutate_ChangeBinaryInteger,
+                         1 << 12);
+}
+
+TEST(FuzzerMutate, ChangeBinaryInteger2) {
+  TestChangeBinaryInteger(&MutationDispatcher::Mutate, 1 << 15);
+}
+
 
 TEST(FuzzerDictionary, ParseOneDictionaryEntry) {
   Unit U;




More information about the llvm-commits mailing list