• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2011 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 #ifndef ART_RUNTIME_INSTRUMENTATION_H_
18 #define ART_RUNTIME_INSTRUMENTATION_H_
19 
20 #include <stdint.h>
21 #include <list>
22 #include <memory>
23 #include <unordered_set>
24 
25 #include "arch/instruction_set.h"
26 #include "base/enums.h"
27 #include "base/locks.h"
28 #include "base/macros.h"
29 #include "base/safe_map.h"
30 #include "gc_root.h"
31 
32 namespace art {
33 namespace mirror {
34 class Class;
35 class Object;
36 class Throwable;
37 }  // namespace mirror
38 class ArtField;
39 class ArtMethod;
40 template <typename T> class Handle;
41 template <typename T> class MutableHandle;
42 union JValue;
43 class SHARED_LOCKABLE ReaderWriterMutex;
44 class ShadowFrame;
45 class Thread;
46 enum class DeoptimizationMethodType;
47 
48 namespace instrumentation {
49 
50 // Interpreter handler tables.
51 enum InterpreterHandlerTable {
52   kMainHandlerTable = 0,          // Main handler table: no suspend check, no instrumentation.
53   kAlternativeHandlerTable = 1,   // Alternative handler table: suspend check and/or instrumentation
54                                   // enabled.
55   kNumHandlerTables
56 };
57 
58 // Do we want to deoptimize for method entry and exit listeners or just try to intercept
59 // invocations? Deoptimization forces all code to run in the interpreter and considerably hurts the
60 // application's performance.
61 static constexpr bool kDeoptimizeForAccurateMethodEntryExitListeners = true;
62 
63 // Instrumentation event listener API. Registered listeners will get the appropriate call back for
64 // the events they are listening for. The call backs supply the thread, method and dex_pc the event
65 // occurred upon. The thread may or may not be Thread::Current().
66 struct InstrumentationListener {
InstrumentationListenerInstrumentationListener67   InstrumentationListener() {}
~InstrumentationListenerInstrumentationListener68   virtual ~InstrumentationListener() {}
69 
70   // Call-back for when a method is entered.
71   virtual void MethodEntered(Thread* thread,
72                              Handle<mirror::Object> this_object,
73                              ArtMethod* method,
74                              uint32_t dex_pc) REQUIRES_SHARED(Locks::mutator_lock_) = 0;
75 
76   virtual void MethodExited(Thread* thread,
77                             Handle<mirror::Object> this_object,
78                             ArtMethod* method,
79                             uint32_t dex_pc,
80                             Handle<mirror::Object> return_value)
81       REQUIRES_SHARED(Locks::mutator_lock_);
82 
83   // Call-back for when a method is exited. The implementor should either handler-ize the return
84   // value (if appropriate) or use the alternate MethodExited callback instead if they need to
85   // go through a suspend point.
86   virtual void MethodExited(Thread* thread,
87                             Handle<mirror::Object> this_object,
88                             ArtMethod* method,
89                             uint32_t dex_pc,
90                             const JValue& return_value)
91       REQUIRES_SHARED(Locks::mutator_lock_) = 0;
92 
93   // Call-back for when a method is popped due to an exception throw. A method will either cause a
94   // MethodExited call-back or a MethodUnwind call-back when its activation is removed.
95   virtual void MethodUnwind(Thread* thread,
96                             Handle<mirror::Object> this_object,
97                             ArtMethod* method,
98                             uint32_t dex_pc)
99       REQUIRES_SHARED(Locks::mutator_lock_) = 0;
100 
101   // Call-back for when the dex pc moves in a method.
102   virtual void DexPcMoved(Thread* thread,
103                           Handle<mirror::Object> this_object,
104                           ArtMethod* method,
105                           uint32_t new_dex_pc)
106       REQUIRES_SHARED(Locks::mutator_lock_) = 0;
107 
108   // Call-back for when we read from a field.
109   virtual void FieldRead(Thread* thread,
110                          Handle<mirror::Object> this_object,
111                          ArtMethod* method,
112                          uint32_t dex_pc,
113                          ArtField* field) = 0;
114 
115   virtual void FieldWritten(Thread* thread,
116                             Handle<mirror::Object> this_object,
117                             ArtMethod* method,
118                             uint32_t dex_pc,
119                             ArtField* field,
120                             Handle<mirror::Object> field_value)
121       REQUIRES_SHARED(Locks::mutator_lock_);
122 
123   // Call-back for when we write into a field.
124   virtual void FieldWritten(Thread* thread,
125                             Handle<mirror::Object> this_object,
126                             ArtMethod* method,
127                             uint32_t dex_pc,
128                             ArtField* field,
129                             const JValue& field_value)
130       REQUIRES_SHARED(Locks::mutator_lock_) = 0;
131 
132   // Call-back when an exception is thrown.
133   virtual void ExceptionThrown(Thread* thread,
134                                Handle<mirror::Throwable> exception_object)
135       REQUIRES_SHARED(Locks::mutator_lock_) = 0;
136 
137   // Call-back when an exception is caught/handled by java code.
138   virtual void ExceptionHandled(Thread* thread, Handle<mirror::Throwable> exception_object)
139       REQUIRES_SHARED(Locks::mutator_lock_) = 0;
140 
141   // Call-back for when we execute a branch.
142   virtual void Branch(Thread* thread,
143                       ArtMethod* method,
144                       uint32_t dex_pc,
145                       int32_t dex_pc_offset)
146       REQUIRES_SHARED(Locks::mutator_lock_) = 0;
147 
148   // Call-back when a shadow_frame with the needs_notify_pop_ boolean set is popped off the stack by
149   // either return or exceptions. Normally instrumentation listeners should ensure that there are
150   // shadow-frames by deoptimizing stacks.
151   virtual void WatchedFramePop(Thread* thread ATTRIBUTE_UNUSED,
152                                const ShadowFrame& frame ATTRIBUTE_UNUSED)
153       REQUIRES_SHARED(Locks::mutator_lock_) = 0;
154 };
155 
156 class Instrumentation;
157 // A helper to send instrumentation events while popping the stack in a safe way.
158 class InstrumentationStackPopper {
159  public:
160   explicit InstrumentationStackPopper(Thread* self);
161   ~InstrumentationStackPopper() REQUIRES_SHARED(Locks::mutator_lock_);
162 
163   // Increase the number of frames being popped to 'desired_pops' return true if the frames were
164   // popped without any exceptions, false otherwise. The exception that caused the pop is
165   // 'exception'.
166   bool PopFramesTo(uint32_t desired_pops, /*in-out*/MutableHandle<mirror::Throwable>& exception)
167       REQUIRES_SHARED(Locks::mutator_lock_);
168 
169  private:
170   Thread* self_;
171   Instrumentation* instrumentation_;
172   uint32_t frames_to_remove_;
173 };
174 
175 // Instrumentation is a catch-all for when extra information is required from the runtime. The
176 // typical use for instrumentation is for profiling and debugging. Instrumentation may add stubs
177 // to method entry and exit, it may also force execution to be switched to the interpreter and
178 // trigger deoptimization.
179 class Instrumentation {
180  public:
181   enum InstrumentationEvent {
182     kMethodEntered = 0x1,
183     kMethodExited = 0x2,
184     kMethodUnwind = 0x4,
185     kDexPcMoved = 0x8,
186     kFieldRead = 0x10,
187     kFieldWritten = 0x20,
188     kExceptionThrown = 0x40,
189     kBranch = 0x80,
190     kWatchedFramePop = 0x200,
191     kExceptionHandled = 0x400,
192   };
193 
194   enum class InstrumentationLevel {
195     kInstrumentNothing,                   // execute without instrumentation
196     kInstrumentWithInstrumentationStubs,  // execute with instrumentation entry/exit stubs
197     kInstrumentWithInterpreter            // execute with interpreter
198   };
199 
200   Instrumentation();
201 
202   // Add a listener to be notified of the masked together sent of instrumentation events. This
203   // suspend the runtime to install stubs. You are expected to hold the mutator lock as a proxy
204   // for saying you should have suspended all threads (installing stubs while threads are running
205   // will break).
206   void AddListener(InstrumentationListener* listener, uint32_t events)
207       REQUIRES(Locks::mutator_lock_, !Locks::thread_list_lock_, !Locks::classlinker_classes_lock_);
208 
209   // Removes a listener possibly removing instrumentation stubs.
210   void RemoveListener(InstrumentationListener* listener, uint32_t events)
211       REQUIRES(Locks::mutator_lock_, !Locks::thread_list_lock_, !Locks::classlinker_classes_lock_);
212 
213   // Deoptimization.
214   void EnableDeoptimization()
215       REQUIRES(Locks::mutator_lock_)
216       REQUIRES(!GetDeoptimizedMethodsLock());
217   // Calls UndeoptimizeEverything which may visit class linker classes through ConfigureStubs.
218   void DisableDeoptimization(const char* key)
219       REQUIRES(Locks::mutator_lock_, Roles::uninterruptible_)
220       REQUIRES(!GetDeoptimizedMethodsLock());
221 
AreAllMethodsDeoptimized()222   bool AreAllMethodsDeoptimized() const {
223     return interpreter_stubs_installed_;
224   }
225   bool ShouldNotifyMethodEnterExitEvents() const REQUIRES_SHARED(Locks::mutator_lock_);
226 
CanDeoptimize()227   bool CanDeoptimize() {
228     return deoptimization_enabled_;
229   }
230 
231   // Executes everything with interpreter.
232   void DeoptimizeEverything(const char* key)
233       REQUIRES(Locks::mutator_lock_, Roles::uninterruptible_)
234       REQUIRES(!Locks::thread_list_lock_,
235                !Locks::classlinker_classes_lock_,
236                !GetDeoptimizedMethodsLock());
237 
238   // Executes everything with compiled code (or interpreter if there is no code). May visit class
239   // linker classes through ConfigureStubs.
240   void UndeoptimizeEverything(const char* key)
241       REQUIRES(Locks::mutator_lock_, Roles::uninterruptible_)
242       REQUIRES(!Locks::thread_list_lock_,
243                !Locks::classlinker_classes_lock_,
244                !GetDeoptimizedMethodsLock());
245 
246   // Deoptimize a method by forcing its execution with the interpreter. Nevertheless, a static
247   // method (except a class initializer) set to the resolution trampoline will be deoptimized only
248   // once its declaring class is initialized.
249   void Deoptimize(ArtMethod* method)
250       REQUIRES(Locks::mutator_lock_, !Locks::thread_list_lock_, !GetDeoptimizedMethodsLock());
251 
252   // Undeoptimze the method by restoring its entrypoints. Nevertheless, a static method
253   // (except a class initializer) set to the resolution trampoline will be updated only once its
254   // declaring class is initialized.
255   void Undeoptimize(ArtMethod* method)
256       REQUIRES(Locks::mutator_lock_, !Locks::thread_list_lock_, !GetDeoptimizedMethodsLock());
257 
258   // Indicates whether the method has been deoptimized so it is executed with the interpreter.
259   bool IsDeoptimized(ArtMethod* method)
260       REQUIRES(!GetDeoptimizedMethodsLock()) REQUIRES_SHARED(Locks::mutator_lock_);
261 
262   // Enable method tracing by installing instrumentation entry/exit stubs or interpreter.
263   void EnableMethodTracing(const char* key,
264                            bool needs_interpreter = kDeoptimizeForAccurateMethodEntryExitListeners)
265       REQUIRES(Locks::mutator_lock_, Roles::uninterruptible_)
266       REQUIRES(!Locks::thread_list_lock_,
267                !Locks::classlinker_classes_lock_,
268                !GetDeoptimizedMethodsLock());
269 
270   // Disable method tracing by uninstalling instrumentation entry/exit stubs or interpreter.
271   void DisableMethodTracing(const char* key)
272       REQUIRES(Locks::mutator_lock_, Roles::uninterruptible_)
273       REQUIRES(!Locks::thread_list_lock_,
274                !Locks::classlinker_classes_lock_,
275                !GetDeoptimizedMethodsLock());
276 
GetInterpreterHandlerTable()277   InterpreterHandlerTable GetInterpreterHandlerTable() const
278       REQUIRES_SHARED(Locks::mutator_lock_) {
279     return interpreter_handler_table_;
280   }
281 
282   void InstrumentQuickAllocEntryPoints() REQUIRES(!Locks::instrument_entrypoints_lock_);
283   void UninstrumentQuickAllocEntryPoints() REQUIRES(!Locks::instrument_entrypoints_lock_);
284   void InstrumentQuickAllocEntryPointsLocked()
285       REQUIRES(Locks::instrument_entrypoints_lock_, !Locks::thread_list_lock_,
286                !Locks::runtime_shutdown_lock_);
287   void UninstrumentQuickAllocEntryPointsLocked()
288       REQUIRES(Locks::instrument_entrypoints_lock_, !Locks::thread_list_lock_,
289                !Locks::runtime_shutdown_lock_);
290   void ResetQuickAllocEntryPoints() REQUIRES(Locks::runtime_shutdown_lock_);
291 
292   // Update the code of a method respecting any installed stubs.
293   void UpdateMethodsCode(ArtMethod* method, const void* quick_code)
294       REQUIRES_SHARED(Locks::mutator_lock_) REQUIRES(!GetDeoptimizedMethodsLock());
295 
296   // Update the code of a native method to a JITed stub.
297   void UpdateNativeMethodsCodeToJitCode(ArtMethod* method, const void* quick_code)
298       REQUIRES_SHARED(Locks::mutator_lock_) REQUIRES(!GetDeoptimizedMethodsLock());
299 
300   // Update the code of a method to the interpreter respecting any installed stubs from debugger.
301   void UpdateMethodsCodeToInterpreterEntryPoint(ArtMethod* method)
302       REQUIRES_SHARED(Locks::mutator_lock_) REQUIRES(!GetDeoptimizedMethodsLock());
303 
304   // Update the code of a method respecting any installed stubs from debugger.
305   void UpdateMethodsCodeForJavaDebuggable(ArtMethod* method, const void* quick_code)
306       REQUIRES_SHARED(Locks::mutator_lock_) REQUIRES(!GetDeoptimizedMethodsLock());
307 
308   // Return the code that we can execute for an invoke including from the JIT.
309   const void* GetCodeForInvoke(ArtMethod* method) const
310       REQUIRES_SHARED(Locks::mutator_lock_);
311 
312   // Get the quick code for the given method. More efficient than asking the class linker as it
313   // will short-cut to GetCode if instrumentation and static method resolution stubs aren't
314   // installed.
315   const void* GetQuickCodeFor(ArtMethod* method, PointerSize pointer_size) const
316       REQUIRES_SHARED(Locks::mutator_lock_);
317 
ForceInterpretOnly()318   void ForceInterpretOnly() {
319     interpret_only_ = true;
320     forced_interpret_only_ = true;
321   }
322 
323   // Called by ArtMethod::Invoke to determine dispatch mechanism.
InterpretOnly()324   bool InterpretOnly() const {
325     return interpret_only_;
326   }
327 
IsForcedInterpretOnly()328   bool IsForcedInterpretOnly() const {
329     return forced_interpret_only_;
330   }
331 
332   // Code is in boot image oat file which isn't compiled as debuggable.
333   // Need debug version (interpreter or jitted) if that's the case.
334   bool NeedDebugVersionFor(ArtMethod* method) const
335       REQUIRES_SHARED(Locks::mutator_lock_);
336 
AreExitStubsInstalled()337   bool AreExitStubsInstalled() const {
338     return instrumentation_stubs_installed_;
339   }
340 
HasMethodEntryListeners()341   bool HasMethodEntryListeners() const REQUIRES_SHARED(Locks::mutator_lock_) {
342     return have_method_entry_listeners_;
343   }
344 
HasMethodExitListeners()345   bool HasMethodExitListeners() const REQUIRES_SHARED(Locks::mutator_lock_) {
346     return have_method_exit_listeners_;
347   }
348 
HasMethodUnwindListeners()349   bool HasMethodUnwindListeners() const REQUIRES_SHARED(Locks::mutator_lock_) {
350     return have_method_unwind_listeners_;
351   }
352 
HasDexPcListeners()353   bool HasDexPcListeners() const REQUIRES_SHARED(Locks::mutator_lock_) {
354     return have_dex_pc_listeners_;
355   }
356 
HasFieldReadListeners()357   bool HasFieldReadListeners() const REQUIRES_SHARED(Locks::mutator_lock_) {
358     return have_field_read_listeners_;
359   }
360 
HasFieldWriteListeners()361   bool HasFieldWriteListeners() const REQUIRES_SHARED(Locks::mutator_lock_) {
362     return have_field_write_listeners_;
363   }
364 
HasExceptionThrownListeners()365   bool HasExceptionThrownListeners() const REQUIRES_SHARED(Locks::mutator_lock_) {
366     return have_exception_thrown_listeners_;
367   }
368 
HasBranchListeners()369   bool HasBranchListeners() const REQUIRES_SHARED(Locks::mutator_lock_) {
370     return have_branch_listeners_;
371   }
372 
HasWatchedFramePopListeners()373   bool HasWatchedFramePopListeners() const REQUIRES_SHARED(Locks::mutator_lock_) {
374     return have_watched_frame_pop_listeners_;
375   }
376 
HasExceptionHandledListeners()377   bool HasExceptionHandledListeners() const REQUIRES_SHARED(Locks::mutator_lock_) {
378     return have_exception_handled_listeners_;
379   }
380 
IsActive()381   bool IsActive() const REQUIRES_SHARED(Locks::mutator_lock_) {
382     return have_dex_pc_listeners_ || have_method_entry_listeners_ || have_method_exit_listeners_ ||
383         have_field_read_listeners_ || have_field_write_listeners_ ||
384         have_exception_thrown_listeners_ || have_method_unwind_listeners_ ||
385         have_branch_listeners_ || have_watched_frame_pop_listeners_ ||
386         have_exception_handled_listeners_;
387   }
388 
389   // Inform listeners that a method has been entered. A dex PC is provided as we may install
390   // listeners into executing code and get method enter events for methods already on the stack.
MethodEnterEvent(Thread * thread,mirror::Object * this_object,ArtMethod * method,uint32_t dex_pc)391   void MethodEnterEvent(Thread* thread, mirror::Object* this_object,
392                         ArtMethod* method, uint32_t dex_pc) const
393       REQUIRES_SHARED(Locks::mutator_lock_) {
394     if (UNLIKELY(HasMethodEntryListeners())) {
395       MethodEnterEventImpl(thread, this_object, method, dex_pc);
396     }
397   }
398 
399   // Inform listeners that a method has been exited.
MethodExitEvent(Thread * thread,mirror::Object * this_object,ArtMethod * method,uint32_t dex_pc,const JValue & return_value)400   void MethodExitEvent(Thread* thread,
401                        mirror::Object* this_object,
402                        ArtMethod* method,
403                        uint32_t dex_pc,
404                        const JValue& return_value) const
405       REQUIRES_SHARED(Locks::mutator_lock_) {
406     if (UNLIKELY(HasMethodExitListeners())) {
407       MethodExitEventImpl(thread, this_object, method, dex_pc, return_value);
408     }
409   }
410 
411   // Inform listeners that a method has been exited due to an exception.
412   void MethodUnwindEvent(Thread* thread, mirror::Object* this_object,
413                          ArtMethod* method, uint32_t dex_pc) const
414       REQUIRES_SHARED(Locks::mutator_lock_);
415 
416   // Inform listeners that the dex pc has moved (only supported by the interpreter).
DexPcMovedEvent(Thread * thread,mirror::Object * this_object,ArtMethod * method,uint32_t dex_pc)417   void DexPcMovedEvent(Thread* thread, mirror::Object* this_object,
418                        ArtMethod* method, uint32_t dex_pc) const
419       REQUIRES_SHARED(Locks::mutator_lock_) {
420     if (UNLIKELY(HasDexPcListeners())) {
421       DexPcMovedEventImpl(thread, this_object, method, dex_pc);
422     }
423   }
424 
425   // Inform listeners that a branch has been taken (only supported by the interpreter).
Branch(Thread * thread,ArtMethod * method,uint32_t dex_pc,int32_t offset)426   void Branch(Thread* thread, ArtMethod* method, uint32_t dex_pc, int32_t offset) const
427       REQUIRES_SHARED(Locks::mutator_lock_) {
428     if (UNLIKELY(HasBranchListeners())) {
429       BranchImpl(thread, method, dex_pc, offset);
430     }
431   }
432 
433   // Inform listeners that we read a field (only supported by the interpreter).
FieldReadEvent(Thread * thread,mirror::Object * this_object,ArtMethod * method,uint32_t dex_pc,ArtField * field)434   void FieldReadEvent(Thread* thread, mirror::Object* this_object,
435                       ArtMethod* method, uint32_t dex_pc,
436                       ArtField* field) const
437       REQUIRES_SHARED(Locks::mutator_lock_) {
438     if (UNLIKELY(HasFieldReadListeners())) {
439       FieldReadEventImpl(thread, this_object, method, dex_pc, field);
440     }
441   }
442 
443   // Inform listeners that we write a field (only supported by the interpreter).
FieldWriteEvent(Thread * thread,mirror::Object * this_object,ArtMethod * method,uint32_t dex_pc,ArtField * field,const JValue & field_value)444   void FieldWriteEvent(Thread* thread, mirror::Object* this_object,
445                        ArtMethod* method, uint32_t dex_pc,
446                        ArtField* field, const JValue& field_value) const
447       REQUIRES_SHARED(Locks::mutator_lock_) {
448     if (UNLIKELY(HasFieldWriteListeners())) {
449       FieldWriteEventImpl(thread, this_object, method, dex_pc, field, field_value);
450     }
451   }
452 
453   // Inform listeners that a branch has been taken (only supported by the interpreter).
WatchedFramePopped(Thread * thread,const ShadowFrame & frame)454   void WatchedFramePopped(Thread* thread, const ShadowFrame& frame) const
455       REQUIRES_SHARED(Locks::mutator_lock_) {
456     if (UNLIKELY(HasWatchedFramePopListeners())) {
457       WatchedFramePopImpl(thread, frame);
458     }
459   }
460 
461   // Inform listeners that an exception was thrown.
462   void ExceptionThrownEvent(Thread* thread, mirror::Throwable* exception_object) const
463       REQUIRES_SHARED(Locks::mutator_lock_);
464 
465   // Inform listeners that an exception has been handled. This is not sent for native code or for
466   // exceptions which reach the end of the thread's stack.
467   void ExceptionHandledEvent(Thread* thread, mirror::Throwable* exception_object) const
468       REQUIRES_SHARED(Locks::mutator_lock_);
469 
470   // Called when an instrumented method is entered. The intended link register (lr) is saved so
471   // that returning causes a branch to the method exit stub. Generates method enter events.
472   void PushInstrumentationStackFrame(Thread* self, mirror::Object* this_object,
473                                      ArtMethod* method, uintptr_t lr,
474                                      bool interpreter_entry)
475       REQUIRES_SHARED(Locks::mutator_lock_);
476 
477   DeoptimizationMethodType GetDeoptimizationMethodType(ArtMethod* method)
478       REQUIRES_SHARED(Locks::mutator_lock_);
479 
480   // Called when an instrumented method is exited. Removes the pushed instrumentation frame
481   // returning the intended link register. Generates method exit events. The gpr_result and
482   // fpr_result pointers are pointers to the locations where the integer/pointer and floating point
483   // result values of the function are stored. Both pointers must always be valid but the values
484   // held there will only be meaningful if interpreted as the appropriate type given the function
485   // being returned from.
486   TwoWordReturn PopInstrumentationStackFrame(Thread* self, uintptr_t* return_pc,
487                                              uint64_t* gpr_result, uint64_t* fpr_result)
488       REQUIRES_SHARED(Locks::mutator_lock_) REQUIRES(!GetDeoptimizedMethodsLock());
489 
490   // Pops nframes instrumentation frames from the current thread. Returns the return pc for the last
491   // instrumentation frame that's popped.
492   uintptr_t PopFramesForDeoptimization(Thread* self, size_t nframes) const
493       REQUIRES_SHARED(Locks::mutator_lock_);
494 
495   // Call back for configure stubs.
496   void InstallStubsForClass(mirror::Class* klass) REQUIRES_SHARED(Locks::mutator_lock_)
497       REQUIRES(!GetDeoptimizedMethodsLock());
498 
499   void InstallStubsForMethod(ArtMethod* method)
500       REQUIRES_SHARED(Locks::mutator_lock_) REQUIRES(!GetDeoptimizedMethodsLock());
501 
502   // Sets up instrumentation to allow single thread deoptimization using ForceInterpreterCount.
503   void EnableSingleThreadDeopt()
504       REQUIRES(Locks::mutator_lock_, Roles::uninterruptible_)
505       REQUIRES(!Locks::thread_list_lock_,
506                !Locks::classlinker_classes_lock_,
507                !GetDeoptimizedMethodsLock());
508 
509   // Install instrumentation exit stub on every method of the stack of the given thread.
510   // This is used by the debugger to cause a deoptimization of the thread's stack after updating
511   // local variable(s).
512   void InstrumentThreadStack(Thread* thread)
513       REQUIRES_SHARED(Locks::mutator_lock_);
514 
515   static size_t ComputeFrameId(Thread* self,
516                                size_t frame_depth,
517                                size_t inlined_frames_before_frame)
518       REQUIRES_SHARED(Locks::mutator_lock_);
519 
520   // Does not hold lock, used to check if someone changed from not instrumented to instrumented
521   // during a GC suspend point.
AllocEntrypointsInstrumented()522   bool AllocEntrypointsInstrumented() const REQUIRES_SHARED(Locks::mutator_lock_) {
523     return alloc_entrypoints_instrumented_;
524   }
525 
526   InstrumentationLevel GetCurrentInstrumentationLevel() const;
527 
528  private:
529   // Returns true if moving to the given instrumentation level requires the installation of stubs.
530   // False otherwise.
531   bool RequiresInstrumentationInstallation(InstrumentationLevel new_level) const;
532 
533   // Does the job of installing or removing instrumentation code within methods.
534   // In order to support multiple clients using instrumentation at the same time,
535   // the caller must pass a unique key (a string) identifying it so we remind which
536   // instrumentation level it needs. Therefore the current instrumentation level
537   // becomes the highest instrumentation level required by a client.
538   void ConfigureStubs(const char* key, InstrumentationLevel desired_instrumentation_level)
539       REQUIRES(Locks::mutator_lock_, Roles::uninterruptible_)
540       REQUIRES(!GetDeoptimizedMethodsLock(),
541                !Locks::thread_list_lock_,
542                !Locks::classlinker_classes_lock_);
543   void UpdateStubs() REQUIRES(Locks::mutator_lock_, Roles::uninterruptible_)
544       REQUIRES(!GetDeoptimizedMethodsLock(),
545                !Locks::thread_list_lock_,
546                !Locks::classlinker_classes_lock_);
547   void UpdateInstrumentationLevels(InstrumentationLevel level)
548       REQUIRES(Locks::mutator_lock_, Roles::uninterruptible_)
549       REQUIRES(!GetDeoptimizedMethodsLock(),
550                !Locks::thread_list_lock_,
551                !Locks::classlinker_classes_lock_);
552 
UpdateInterpreterHandlerTable()553   void UpdateInterpreterHandlerTable() REQUIRES(Locks::mutator_lock_) {
554     /*
555      * TUNING: Dalvik's mterp stashes the actual current handler table base in a
556      * tls field.  For Arm, this enables all suspend, debug & tracing checks to be
557      * collapsed into a single conditionally-executed ldw instruction.
558      * Move to Dalvik-style handler-table management for both the goto interpreter and
559      * mterp.
560      */
561     interpreter_handler_table_ = IsActive() ? kAlternativeHandlerTable : kMainHandlerTable;
562   }
563 
564   // No thread safety analysis to get around SetQuickAllocEntryPointsInstrumented requiring
565   // exclusive access to mutator lock which you can't get if the runtime isn't started.
566   void SetEntrypointsInstrumented(bool instrumented) NO_THREAD_SAFETY_ANALYSIS;
567 
568   void MethodEnterEventImpl(Thread* thread,
569                             ObjPtr<mirror::Object> this_object,
570                             ArtMethod* method,
571                             uint32_t dex_pc) const
572       REQUIRES_SHARED(Locks::mutator_lock_);
573   void MethodExitEventImpl(Thread* thread,
574                            ObjPtr<mirror::Object> this_object,
575                            ArtMethod* method,
576                            uint32_t dex_pc,
577                            const JValue& return_value) const
578       REQUIRES_SHARED(Locks::mutator_lock_);
579   void DexPcMovedEventImpl(Thread* thread,
580                            ObjPtr<mirror::Object> this_object,
581                            ArtMethod* method,
582                            uint32_t dex_pc) const
583       REQUIRES_SHARED(Locks::mutator_lock_);
584   void BranchImpl(Thread* thread, ArtMethod* method, uint32_t dex_pc, int32_t offset) const
585       REQUIRES_SHARED(Locks::mutator_lock_);
586   void WatchedFramePopImpl(Thread* thread, const ShadowFrame& frame) const
587       REQUIRES_SHARED(Locks::mutator_lock_);
588   void FieldReadEventImpl(Thread* thread,
589                           ObjPtr<mirror::Object> this_object,
590                           ArtMethod* method,
591                           uint32_t dex_pc,
592                           ArtField* field) const
593       REQUIRES_SHARED(Locks::mutator_lock_);
594   void FieldWriteEventImpl(Thread* thread,
595                            ObjPtr<mirror::Object> this_object,
596                            ArtMethod* method,
597                            uint32_t dex_pc,
598                            ArtField* field,
599                            const JValue& field_value) const
600       REQUIRES_SHARED(Locks::mutator_lock_);
601 
602   // Read barrier-aware utility functions for accessing deoptimized_methods_
603   bool AddDeoptimizedMethod(ArtMethod* method)
604       REQUIRES_SHARED(Locks::mutator_lock_) REQUIRES(GetDeoptimizedMethodsLock());
605   bool IsDeoptimizedMethod(ArtMethod* method)
606       REQUIRES_SHARED(Locks::mutator_lock_, GetDeoptimizedMethodsLock());
607   bool RemoveDeoptimizedMethod(ArtMethod* method)
608       REQUIRES_SHARED(Locks::mutator_lock_) REQUIRES(GetDeoptimizedMethodsLock());
609   ArtMethod* BeginDeoptimizedMethod()
610       REQUIRES_SHARED(Locks::mutator_lock_, GetDeoptimizedMethodsLock());
611   bool IsDeoptimizedMethodsEmpty() const
612       REQUIRES_SHARED(Locks::mutator_lock_, GetDeoptimizedMethodsLock());
613   void UpdateMethodsCodeImpl(ArtMethod* method, const void* quick_code)
614       REQUIRES_SHARED(Locks::mutator_lock_) REQUIRES(!GetDeoptimizedMethodsLock());
615 
GetDeoptimizedMethodsLock()616   ReaderWriterMutex* GetDeoptimizedMethodsLock() const {
617     return deoptimized_methods_lock_.get();
618   }
619 
620   // Have we hijacked ArtMethod::code_ so that it calls instrumentation/interpreter code?
621   bool instrumentation_stubs_installed_;
622 
623   // Have we hijacked ArtMethod::code_ to reference the enter/exit stubs?
624   bool entry_exit_stubs_installed_;
625 
626   // Have we hijacked ArtMethod::code_ to reference the enter interpreter stub?
627   bool interpreter_stubs_installed_;
628 
629   // Do we need the fidelity of events that we only get from running within the interpreter?
630   bool interpret_only_;
631 
632   // Did the runtime request we only run in the interpreter? ie -Xint mode.
633   bool forced_interpret_only_;
634 
635   // Do we have any listeners for method entry events? Short-cut to avoid taking the
636   // instrumentation_lock_.
637   bool have_method_entry_listeners_ GUARDED_BY(Locks::mutator_lock_);
638 
639   // Do we have any listeners for method exit events? Short-cut to avoid taking the
640   // instrumentation_lock_.
641   bool have_method_exit_listeners_ GUARDED_BY(Locks::mutator_lock_);
642 
643   // Do we have any listeners for method unwind events? Short-cut to avoid taking the
644   // instrumentation_lock_.
645   bool have_method_unwind_listeners_ GUARDED_BY(Locks::mutator_lock_);
646 
647   // Do we have any listeners for dex move events? Short-cut to avoid taking the
648   // instrumentation_lock_.
649   bool have_dex_pc_listeners_ GUARDED_BY(Locks::mutator_lock_);
650 
651   // Do we have any listeners for field read events? Short-cut to avoid taking the
652   // instrumentation_lock_.
653   bool have_field_read_listeners_ GUARDED_BY(Locks::mutator_lock_);
654 
655   // Do we have any listeners for field write events? Short-cut to avoid taking the
656   // instrumentation_lock_.
657   bool have_field_write_listeners_ GUARDED_BY(Locks::mutator_lock_);
658 
659   // Do we have any exception thrown listeners? Short-cut to avoid taking the instrumentation_lock_.
660   bool have_exception_thrown_listeners_ GUARDED_BY(Locks::mutator_lock_);
661 
662   // Do we have any frame pop listeners? Short-cut to avoid taking the instrumentation_lock_.
663   bool have_watched_frame_pop_listeners_ GUARDED_BY(Locks::mutator_lock_);
664 
665   // Do we have any branch listeners? Short-cut to avoid taking the instrumentation_lock_.
666   bool have_branch_listeners_ GUARDED_BY(Locks::mutator_lock_);
667 
668   // Do we have any exception handled listeners? Short-cut to avoid taking the
669   // instrumentation_lock_.
670   bool have_exception_handled_listeners_ GUARDED_BY(Locks::mutator_lock_);
671 
672   // Contains the instrumentation level required by each client of the instrumentation identified
673   // by a string key.
674   typedef SafeMap<const char*, InstrumentationLevel> InstrumentationLevelTable;
675   InstrumentationLevelTable requested_instrumentation_levels_ GUARDED_BY(Locks::mutator_lock_);
676 
677   // The event listeners, written to with the mutator_lock_ exclusively held.
678   // Mutators must be able to iterate over these lists concurrently, that is, with listeners being
679   // added or removed while iterating. The modifying thread holds exclusive lock,
680   // so other threads cannot iterate (i.e. read the data of the list) at the same time but they
681   // do keep iterators that need to remain valid. This is the reason these listeners are std::list
682   // and not for example std::vector: the existing storage for a std::list does not move.
683   // Note that mutators cannot make a copy of these lists before iterating, as the instrumentation
684   // listeners can also be deleted concurrently.
685   // As a result, these lists are never trimmed. That's acceptable given the low number of
686   // listeners we have.
687   std::list<InstrumentationListener*> method_entry_listeners_ GUARDED_BY(Locks::mutator_lock_);
688   std::list<InstrumentationListener*> method_exit_listeners_ GUARDED_BY(Locks::mutator_lock_);
689   std::list<InstrumentationListener*> method_unwind_listeners_ GUARDED_BY(Locks::mutator_lock_);
690   std::list<InstrumentationListener*> branch_listeners_ GUARDED_BY(Locks::mutator_lock_);
691   std::list<InstrumentationListener*> dex_pc_listeners_ GUARDED_BY(Locks::mutator_lock_);
692   std::list<InstrumentationListener*> field_read_listeners_ GUARDED_BY(Locks::mutator_lock_);
693   std::list<InstrumentationListener*> field_write_listeners_ GUARDED_BY(Locks::mutator_lock_);
694   std::list<InstrumentationListener*> exception_thrown_listeners_ GUARDED_BY(Locks::mutator_lock_);
695   std::list<InstrumentationListener*> watched_frame_pop_listeners_ GUARDED_BY(Locks::mutator_lock_);
696   std::list<InstrumentationListener*> exception_handled_listeners_ GUARDED_BY(Locks::mutator_lock_);
697 
698   // The set of methods being deoptimized (by the debugger) which must be executed with interpreter
699   // only.
700   mutable std::unique_ptr<ReaderWriterMutex> deoptimized_methods_lock_ BOTTOM_MUTEX_ACQUIRED_AFTER;
701   std::unordered_set<ArtMethod*> deoptimized_methods_ GUARDED_BY(GetDeoptimizedMethodsLock());
702   bool deoptimization_enabled_;
703 
704   // Current interpreter handler table. This is updated each time the thread state flags are
705   // modified.
706   InterpreterHandlerTable interpreter_handler_table_ GUARDED_BY(Locks::mutator_lock_);
707 
708   // Greater than 0 if quick alloc entry points instrumented.
709   size_t quick_alloc_entry_points_instrumentation_counter_;
710 
711   // alloc_entrypoints_instrumented_ is only updated with all the threads suspended, this is done
712   // to prevent races with the GC where the GC relies on thread suspension only see
713   // alloc_entrypoints_instrumented_ change during suspend points.
714   bool alloc_entrypoints_instrumented_;
715 
716   // If we can use instrumentation trampolines. After the first time we instrument something with
717   // the interpreter we can no longer use trampolines because it can lead to stack corruption.
718   // TODO Figure out a way to remove the need for this.
719   bool can_use_instrumentation_trampolines_;
720 
721   friend class InstrumentationTest;  // For GetCurrentInstrumentationLevel and ConfigureStubs.
722   friend class InstrumentationStackPopper;  // For popping instrumentation frames.
723 
724   DISALLOW_COPY_AND_ASSIGN(Instrumentation);
725 };
726 std::ostream& operator<<(std::ostream& os, const Instrumentation::InstrumentationEvent& rhs);
727 std::ostream& operator<<(std::ostream& os, const Instrumentation::InstrumentationLevel& rhs);
728 
729 // An element in the instrumentation side stack maintained in art::Thread.
730 struct InstrumentationStackFrame {
InstrumentationStackFrameInstrumentationStackFrame731   InstrumentationStackFrame(mirror::Object* this_object,
732                             ArtMethod* method,
733                             uintptr_t return_pc,
734                             size_t frame_id,
735                             bool interpreter_entry)
736       : this_object_(this_object),
737         method_(method),
738         return_pc_(return_pc),
739         frame_id_(frame_id),
740         interpreter_entry_(interpreter_entry) {
741   }
742 
743   std::string Dump() const REQUIRES_SHARED(Locks::mutator_lock_);
744 
745   mirror::Object* this_object_;
746   ArtMethod* method_;
747   uintptr_t return_pc_;
748   size_t frame_id_;
749   bool interpreter_entry_;
750 };
751 
752 }  // namespace instrumentation
753 }  // namespace art
754 
755 #endif  // ART_RUNTIME_INSTRUMENTATION_H_
756