JITEventListenerTest.cpp 7.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237
  1. //===- JITEventListenerTest.cpp - Unit tests for JITEventListeners --------===//
  2. //
  3. // The LLVM Compiler Infrastructure
  4. //
  5. // This file is distributed under the University of Illinois Open Source
  6. // License. See LICENSE.TXT for details.
  7. //
  8. //===----------------------------------------------------------------------===//
  9. #include "llvm/ExecutionEngine/JITEventListener.h"
  10. #include "llvm/ADT/OwningPtr.h"
  11. #include "llvm/CodeGen/MachineCodeInfo.h"
  12. #include "llvm/ExecutionEngine/JIT.h"
  13. #include "llvm/Instructions.h"
  14. #include "llvm/LLVMContext.h"
  15. #include "llvm/Module.h"
  16. #include "llvm/Support/TargetSelect.h"
  17. #include "llvm/TypeBuilder.h"
  18. #include "gtest/gtest.h"
  19. #include <vector>
  20. using namespace llvm;
  21. int dummy;
  22. namespace {
  23. struct FunctionEmittedEvent {
  24. // Indices are local to the RecordingJITEventListener, since the
  25. // JITEventListener interface makes no guarantees about the order of
  26. // calls between Listeners.
  27. unsigned Index;
  28. const Function *F;
  29. void *Code;
  30. size_t Size;
  31. JITEvent_EmittedFunctionDetails Details;
  32. };
  33. struct FunctionFreedEvent {
  34. unsigned Index;
  35. void *Code;
  36. };
  37. struct RecordingJITEventListener : public JITEventListener {
  38. std::vector<FunctionEmittedEvent> EmittedEvents;
  39. std::vector<FunctionFreedEvent> FreedEvents;
  40. unsigned NextIndex;
  41. RecordingJITEventListener() : NextIndex(0) {}
  42. virtual void NotifyFunctionEmitted(const Function &F,
  43. void *Code, size_t Size,
  44. const EmittedFunctionDetails &Details) {
  45. FunctionEmittedEvent Event = {NextIndex++, &F, Code, Size, Details};
  46. EmittedEvents.push_back(Event);
  47. }
  48. virtual void NotifyFreeingMachineCode(void *OldPtr) {
  49. FunctionFreedEvent Event = {NextIndex++, OldPtr};
  50. FreedEvents.push_back(Event);
  51. }
  52. };
  53. class JITEventListenerTest : public testing::Test {
  54. protected:
  55. JITEventListenerTest()
  56. : M(new Module("module", getGlobalContext())),
  57. EE(EngineBuilder(M)
  58. .setEngineKind(EngineKind::JIT)
  59. .create()) {
  60. }
  61. Module *M;
  62. const OwningPtr<ExecutionEngine> EE;
  63. };
  64. Function *buildFunction(Module *M) {
  65. Function *Result = Function::Create(
  66. TypeBuilder<int32_t(int32_t), false>::get(getGlobalContext()),
  67. GlobalValue::ExternalLinkage, "id", M);
  68. Value *Arg = Result->arg_begin();
  69. BasicBlock *BB = BasicBlock::Create(M->getContext(), "entry", Result);
  70. ReturnInst::Create(M->getContext(), Arg, BB);
  71. return Result;
  72. }
  73. // Tests that a single JITEventListener follows JIT events accurately.
  74. TEST_F(JITEventListenerTest, Simple) {
  75. RecordingJITEventListener Listener;
  76. EE->RegisterJITEventListener(&Listener);
  77. Function *F1 = buildFunction(M);
  78. Function *F2 = buildFunction(M);
  79. void *F1_addr = EE->getPointerToFunction(F1);
  80. void *F2_addr = EE->getPointerToFunction(F2);
  81. EE->getPointerToFunction(F1); // Should do nothing.
  82. EE->freeMachineCodeForFunction(F1);
  83. EE->freeMachineCodeForFunction(F2);
  84. ASSERT_EQ(2U, Listener.EmittedEvents.size());
  85. ASSERT_EQ(2U, Listener.FreedEvents.size());
  86. EXPECT_EQ(0U, Listener.EmittedEvents[0].Index);
  87. EXPECT_EQ(F1, Listener.EmittedEvents[0].F);
  88. EXPECT_EQ(F1_addr, Listener.EmittedEvents[0].Code);
  89. EXPECT_LT(0U, Listener.EmittedEvents[0].Size)
  90. << "We don't know how big the function will be, but it had better"
  91. << " contain some bytes.";
  92. EXPECT_EQ(1U, Listener.EmittedEvents[1].Index);
  93. EXPECT_EQ(F2, Listener.EmittedEvents[1].F);
  94. EXPECT_EQ(F2_addr, Listener.EmittedEvents[1].Code);
  95. EXPECT_LT(0U, Listener.EmittedEvents[1].Size)
  96. << "We don't know how big the function will be, but it had better"
  97. << " contain some bytes.";
  98. EXPECT_EQ(2U, Listener.FreedEvents[0].Index);
  99. EXPECT_EQ(F1_addr, Listener.FreedEvents[0].Code);
  100. EXPECT_EQ(3U, Listener.FreedEvents[1].Index);
  101. EXPECT_EQ(F2_addr, Listener.FreedEvents[1].Code);
  102. F1->eraseFromParent();
  103. F2->eraseFromParent();
  104. }
  105. // Tests that a single JITEventListener follows JIT events accurately.
  106. TEST_F(JITEventListenerTest, MultipleListenersDontInterfere) {
  107. RecordingJITEventListener Listener1;
  108. RecordingJITEventListener Listener2;
  109. RecordingJITEventListener Listener3;
  110. Function *F1 = buildFunction(M);
  111. Function *F2 = buildFunction(M);
  112. EE->RegisterJITEventListener(&Listener1);
  113. EE->RegisterJITEventListener(&Listener2);
  114. void *F1_addr = EE->getPointerToFunction(F1);
  115. EE->RegisterJITEventListener(&Listener3);
  116. EE->UnregisterJITEventListener(&Listener1);
  117. void *F2_addr = EE->getPointerToFunction(F2);
  118. EE->UnregisterJITEventListener(&Listener2);
  119. EE->UnregisterJITEventListener(&Listener3);
  120. EE->freeMachineCodeForFunction(F1);
  121. EE->RegisterJITEventListener(&Listener2);
  122. EE->RegisterJITEventListener(&Listener3);
  123. EE->RegisterJITEventListener(&Listener1);
  124. EE->freeMachineCodeForFunction(F2);
  125. EE->UnregisterJITEventListener(&Listener1);
  126. EE->UnregisterJITEventListener(&Listener2);
  127. EE->UnregisterJITEventListener(&Listener3);
  128. // Listener 1.
  129. ASSERT_EQ(1U, Listener1.EmittedEvents.size());
  130. ASSERT_EQ(1U, Listener1.FreedEvents.size());
  131. EXPECT_EQ(0U, Listener1.EmittedEvents[0].Index);
  132. EXPECT_EQ(F1, Listener1.EmittedEvents[0].F);
  133. EXPECT_EQ(F1_addr, Listener1.EmittedEvents[0].Code);
  134. EXPECT_LT(0U, Listener1.EmittedEvents[0].Size)
  135. << "We don't know how big the function will be, but it had better"
  136. << " contain some bytes.";
  137. EXPECT_EQ(1U, Listener1.FreedEvents[0].Index);
  138. EXPECT_EQ(F2_addr, Listener1.FreedEvents[0].Code);
  139. // Listener 2.
  140. ASSERT_EQ(2U, Listener2.EmittedEvents.size());
  141. ASSERT_EQ(1U, Listener2.FreedEvents.size());
  142. EXPECT_EQ(0U, Listener2.EmittedEvents[0].Index);
  143. EXPECT_EQ(F1, Listener2.EmittedEvents[0].F);
  144. EXPECT_EQ(F1_addr, Listener2.EmittedEvents[0].Code);
  145. EXPECT_LT(0U, Listener2.EmittedEvents[0].Size)
  146. << "We don't know how big the function will be, but it had better"
  147. << " contain some bytes.";
  148. EXPECT_EQ(1U, Listener2.EmittedEvents[1].Index);
  149. EXPECT_EQ(F2, Listener2.EmittedEvents[1].F);
  150. EXPECT_EQ(F2_addr, Listener2.EmittedEvents[1].Code);
  151. EXPECT_LT(0U, Listener2.EmittedEvents[1].Size)
  152. << "We don't know how big the function will be, but it had better"
  153. << " contain some bytes.";
  154. EXPECT_EQ(2U, Listener2.FreedEvents[0].Index);
  155. EXPECT_EQ(F2_addr, Listener2.FreedEvents[0].Code);
  156. // Listener 3.
  157. ASSERT_EQ(1U, Listener3.EmittedEvents.size());
  158. ASSERT_EQ(1U, Listener3.FreedEvents.size());
  159. EXPECT_EQ(0U, Listener3.EmittedEvents[0].Index);
  160. EXPECT_EQ(F2, Listener3.EmittedEvents[0].F);
  161. EXPECT_EQ(F2_addr, Listener3.EmittedEvents[0].Code);
  162. EXPECT_LT(0U, Listener3.EmittedEvents[0].Size)
  163. << "We don't know how big the function will be, but it had better"
  164. << " contain some bytes.";
  165. EXPECT_EQ(1U, Listener3.FreedEvents[0].Index);
  166. EXPECT_EQ(F2_addr, Listener3.FreedEvents[0].Code);
  167. F1->eraseFromParent();
  168. F2->eraseFromParent();
  169. }
  170. TEST_F(JITEventListenerTest, MatchesMachineCodeInfo) {
  171. RecordingJITEventListener Listener;
  172. MachineCodeInfo MCI;
  173. Function *F = buildFunction(M);
  174. EE->RegisterJITEventListener(&Listener);
  175. EE->runJITOnFunction(F, &MCI);
  176. void *F_addr = EE->getPointerToFunction(F);
  177. EE->freeMachineCodeForFunction(F);
  178. ASSERT_EQ(1U, Listener.EmittedEvents.size());
  179. ASSERT_EQ(1U, Listener.FreedEvents.size());
  180. EXPECT_EQ(0U, Listener.EmittedEvents[0].Index);
  181. EXPECT_EQ(F, Listener.EmittedEvents[0].F);
  182. EXPECT_EQ(F_addr, Listener.EmittedEvents[0].Code);
  183. EXPECT_EQ(MCI.address(), Listener.EmittedEvents[0].Code);
  184. EXPECT_EQ(MCI.size(), Listener.EmittedEvents[0].Size);
  185. EXPECT_EQ(1U, Listener.FreedEvents[0].Index);
  186. EXPECT_EQ(F_addr, Listener.FreedEvents[0].Code);
  187. }
  188. class JITEnvironment : public testing::Environment {
  189. virtual void SetUp() {
  190. // Required to create a JIT.
  191. InitializeNativeTarget();
  192. }
  193. };
  194. testing::Environment* const jit_env =
  195. testing::AddGlobalTestEnvironment(new JITEnvironment);
  196. } // anonymous namespace