FuzzerInternal.h 5.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178
  1. //===- FuzzerInternal.h - Internal header for the Fuzzer --------*- C++ -* ===//
  2. //
  3. // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
  4. // See https://llvm.org/LICENSE.txt for license information.
  5. // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
  6. //
  7. //===----------------------------------------------------------------------===//
  8. // Define the main class fuzzer::Fuzzer and most functions.
  9. //===----------------------------------------------------------------------===//
  10. #ifndef LLVM_FUZZER_INTERNAL_H
  11. #define LLVM_FUZZER_INTERNAL_H
  12. #include "FuzzerDataFlowTrace.h"
  13. #include "FuzzerDefs.h"
  14. #include "FuzzerExtFunctions.h"
  15. #include "FuzzerInterface.h"
  16. #include "FuzzerOptions.h"
  17. #include "FuzzerSHA1.h"
  18. #include "FuzzerValueBitMap.h"
  19. #include <algorithm>
  20. #include <atomic>
  21. #include <chrono>
  22. #include <climits>
  23. #include <cstdlib>
  24. #include <string.h>
  25. namespace fuzzer {
  26. using namespace std::chrono;
  27. class Fuzzer final {
  28. public:
  29. Fuzzer(UserCallback CB, InputCorpus &Corpus, MutationDispatcher &MD,
  30. const FuzzingOptions &Options);
  31. ~Fuzzer() = delete;
  32. void Loop(std::vector<SizedFile> &CorporaFiles);
  33. void ReadAndExecuteSeedCorpora(std::vector<SizedFile> &CorporaFiles);
  34. void MinimizeCrashLoop(const Unit &U);
  35. void RereadOutputCorpus(size_t MaxSize);
  36. size_t secondsSinceProcessStartUp() {
  37. return duration_cast<seconds>(system_clock::now() - ProcessStartTime)
  38. .count();
  39. }
  40. bool TimedOut() {
  41. return Options.MaxTotalTimeSec > 0 &&
  42. secondsSinceProcessStartUp() >
  43. static_cast<size_t>(Options.MaxTotalTimeSec);
  44. }
  45. size_t execPerSec() {
  46. size_t Seconds = secondsSinceProcessStartUp();
  47. return Seconds ? TotalNumberOfRuns / Seconds : 0;
  48. }
  49. size_t getTotalNumberOfRuns() { return TotalNumberOfRuns; }
  50. static void StaticAlarmCallback();
  51. static void StaticCrashSignalCallback();
  52. static void StaticExitCallback();
  53. static void StaticInterruptCallback();
  54. static void StaticFileSizeExceedCallback();
  55. static void StaticGracefulExitCallback();
  56. // Executes the target callback on {Data, Size} once.
  57. // Returns false if the input was rejected by the target (target returned -1),
  58. // and true otherwise.
  59. bool ExecuteCallback(const uint8_t *Data, size_t Size);
  60. bool RunOne(const uint8_t *Data, size_t Size, bool MayDeleteFile = false,
  61. InputInfo *II = nullptr, bool ForceAddToCorpus = false,
  62. bool *FoundUniqFeatures = nullptr);
  63. void TPCUpdateObservedPCs();
  64. // Merge Corpora[1:] into Corpora[0].
  65. void Merge(const std::vector<std::string> &Corpora);
  66. void CrashResistantMergeInternalStep(const std::string &ControlFilePath,
  67. bool IsSetCoverMerge);
  68. MutationDispatcher &GetMD() { return MD; }
  69. void PrintFinalStats();
  70. void SetMaxInputLen(size_t MaxInputLen);
  71. void SetMaxMutationLen(size_t MaxMutationLen);
  72. void RssLimitCallback();
  73. bool InFuzzingThread() const { return IsMyThread; }
  74. size_t GetCurrentUnitInFuzzingThead(const uint8_t **Data) const;
  75. void TryDetectingAMemoryLeak(const uint8_t *Data, size_t Size,
  76. bool DuringInitialCorpusExecution);
  77. void HandleMalloc(size_t Size);
  78. static void MaybeExitGracefully();
  79. static int InterruptExitCode();
  80. std::string WriteToOutputCorpus(const Unit &U);
  81. private:
  82. void AlarmCallback();
  83. void CrashCallback();
  84. void ExitCallback();
  85. void CrashOnOverwrittenData();
  86. void InterruptCallback();
  87. void MutateAndTestOne();
  88. void PurgeAllocator();
  89. void ReportNewCoverage(InputInfo *II, const Unit &U);
  90. void PrintPulseAndReportSlowInput(const uint8_t *Data, size_t Size);
  91. void WriteUnitToFileWithPrefix(const Unit &U, const char *Prefix);
  92. void PrintStats(const char *Where, const char *End = "\n", size_t Units = 0,
  93. size_t Features = 0);
  94. void PrintStatusForNewUnit(const Unit &U, const char *Text);
  95. void CheckExitOnSrcPosOrItem();
  96. static void StaticDeathCallback();
  97. void DumpCurrentUnit(const char *Prefix);
  98. void DeathCallback();
  99. void AllocateCurrentUnitData();
  100. uint8_t *CurrentUnitData = nullptr;
  101. std::atomic<size_t> CurrentUnitSize;
  102. uint8_t BaseSha1[kSHA1NumBytes]; // Checksum of the base unit.
  103. bool GracefulExitRequested = false;
  104. size_t TotalNumberOfRuns = 0;
  105. size_t NumberOfNewUnitsAdded = 0;
  106. size_t LastCorpusUpdateRun = 0;
  107. bool HasMoreMallocsThanFrees = false;
  108. size_t NumberOfLeakDetectionAttempts = 0;
  109. system_clock::time_point LastAllocatorPurgeAttemptTime = system_clock::now();
  110. UserCallback CB;
  111. InputCorpus &Corpus;
  112. MutationDispatcher &MD;
  113. FuzzingOptions Options;
  114. DataFlowTrace DFT;
  115. system_clock::time_point ProcessStartTime = system_clock::now();
  116. system_clock::time_point UnitStartTime, UnitStopTime;
  117. long TimeOfLongestUnitInSeconds = 0;
  118. long EpochOfLastReadOfOutputCorpus = 0;
  119. size_t MaxInputLen = 0;
  120. size_t MaxMutationLen = 0;
  121. size_t TmpMaxMutationLen = 0;
  122. std::vector<uint32_t> UniqFeatureSetTmp;
  123. // Need to know our own thread.
  124. static thread_local bool IsMyThread;
  125. };
  126. struct ScopedEnableMsanInterceptorChecks {
  127. ScopedEnableMsanInterceptorChecks() {
  128. if (EF->__msan_scoped_enable_interceptor_checks)
  129. EF->__msan_scoped_enable_interceptor_checks();
  130. }
  131. ~ScopedEnableMsanInterceptorChecks() {
  132. if (EF->__msan_scoped_disable_interceptor_checks)
  133. EF->__msan_scoped_disable_interceptor_checks();
  134. }
  135. };
  136. struct ScopedDisableMsanInterceptorChecks {
  137. ScopedDisableMsanInterceptorChecks() {
  138. if (EF->__msan_scoped_disable_interceptor_checks)
  139. EF->__msan_scoped_disable_interceptor_checks();
  140. }
  141. ~ScopedDisableMsanInterceptorChecks() {
  142. if (EF->__msan_scoped_enable_interceptor_checks)
  143. EF->__msan_scoped_enable_interceptor_checks();
  144. }
  145. };
  146. } // namespace fuzzer
  147. #endif // LLVM_FUZZER_INTERNAL_H