• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright 2014 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_JIT_JIT_H_
18 #define ART_RUNTIME_JIT_JIT_H_
19 
20 #include <android-base/unique_fd.h>
21 
22 #include "base/histogram-inl.h"
23 #include "base/macros.h"
24 #include "base/mutex.h"
25 #include "base/runtime_debug.h"
26 #include "base/timing_logger.h"
27 #include "handle.h"
28 #include "offsets.h"
29 #include "interpreter/mterp/mterp.h"
30 #include "jit/debugger_interface.h"
31 #include "jit/profile_saver_options.h"
32 #include "obj_ptr.h"
33 #include "thread_pool.h"
34 
35 namespace art {
36 
37 class ArtMethod;
38 class ClassLinker;
39 class DexFile;
40 class OatDexFile;
41 struct RuntimeArgumentMap;
42 union JValue;
43 
44 namespace mirror {
45 class Object;
46 class Class;
47 class ClassLoader;
48 class DexCache;
49 class String;
50 }   // namespace mirror
51 
52 namespace jit {
53 
54 class JitCodeCache;
55 class JitMemoryRegion;
56 class JitOptions;
57 
58 static constexpr int16_t kJitCheckForOSR = -1;
59 static constexpr int16_t kJitHotnessDisabled = -2;
60 // At what priority to schedule jit threads. 9 is the lowest foreground priority on device.
61 // See android/os/Process.java.
62 static constexpr int kJitPoolThreadPthreadDefaultPriority = 9;
63 // We check whether to jit-compile the method every Nth invoke.
64 // The tests often use threshold of 1000 (and thus 500 to start profiling).
65 static constexpr uint32_t kJitSamplesBatchSize = 512;  // Must be power of 2.
66 
67 class JitOptions {
68  public:
69   static JitOptions* CreateFromRuntimeArguments(const RuntimeArgumentMap& options);
70 
GetCompileThreshold()71   uint16_t GetCompileThreshold() const {
72     return compile_threshold_;
73   }
74 
GetWarmupThreshold()75   uint16_t GetWarmupThreshold() const {
76     return warmup_threshold_;
77   }
78 
GetOsrThreshold()79   uint16_t GetOsrThreshold() const {
80     return osr_threshold_;
81   }
82 
GetPriorityThreadWeight()83   uint16_t GetPriorityThreadWeight() const {
84     return priority_thread_weight_;
85   }
86 
GetInvokeTransitionWeight()87   uint16_t GetInvokeTransitionWeight() const {
88     return invoke_transition_weight_;
89   }
90 
GetCodeCacheInitialCapacity()91   size_t GetCodeCacheInitialCapacity() const {
92     return code_cache_initial_capacity_;
93   }
94 
GetCodeCacheMaxCapacity()95   size_t GetCodeCacheMaxCapacity() const {
96     return code_cache_max_capacity_;
97   }
98 
DumpJitInfoOnShutdown()99   bool DumpJitInfoOnShutdown() const {
100     return dump_info_on_shutdown_;
101   }
102 
GetProfileSaverOptions()103   const ProfileSaverOptions& GetProfileSaverOptions() const {
104     return profile_saver_options_;
105   }
106 
GetSaveProfilingInfo()107   bool GetSaveProfilingInfo() const {
108     return profile_saver_options_.IsEnabled();
109   }
110 
GetThreadPoolPthreadPriority()111   int GetThreadPoolPthreadPriority() const {
112     return thread_pool_pthread_priority_;
113   }
114 
UseJitCompilation()115   bool UseJitCompilation() const {
116     return use_jit_compilation_;
117   }
118 
UseTieredJitCompilation()119   bool UseTieredJitCompilation() const {
120     return use_tiered_jit_compilation_;
121   }
122 
CanCompileBaseline()123   bool CanCompileBaseline() const {
124     return use_tiered_jit_compilation_ ||
125            use_baseline_compiler_ ||
126            interpreter::IsNterpSupported();
127   }
128 
SetUseJitCompilation(bool b)129   void SetUseJitCompilation(bool b) {
130     use_jit_compilation_ = b;
131   }
132 
SetSaveProfilingInfo(bool save_profiling_info)133   void SetSaveProfilingInfo(bool save_profiling_info) {
134     profile_saver_options_.SetEnabled(save_profiling_info);
135   }
136 
SetWaitForJitNotificationsToSaveProfile(bool value)137   void SetWaitForJitNotificationsToSaveProfile(bool value) {
138     profile_saver_options_.SetWaitForJitNotificationsToSave(value);
139   }
140 
SetJitAtFirstUse()141   void SetJitAtFirstUse() {
142     use_jit_compilation_ = true;
143     compile_threshold_ = 0;
144   }
145 
SetUseBaselineCompiler()146   void SetUseBaselineCompiler() {
147     use_baseline_compiler_ = true;
148   }
149 
UseBaselineCompiler()150   bool UseBaselineCompiler() const {
151     return use_baseline_compiler_;
152   }
153 
154  private:
155   // We add the sample in batches of size kJitSamplesBatchSize.
156   // This method rounds the threshold so that it is multiple of the batch size.
157   static uint32_t RoundUpThreshold(uint32_t threshold);
158 
159   bool use_jit_compilation_;
160   bool use_tiered_jit_compilation_;
161   bool use_baseline_compiler_;
162   size_t code_cache_initial_capacity_;
163   size_t code_cache_max_capacity_;
164   uint32_t compile_threshold_;
165   uint32_t warmup_threshold_;
166   uint32_t osr_threshold_;
167   uint16_t priority_thread_weight_;
168   uint16_t invoke_transition_weight_;
169   bool dump_info_on_shutdown_;
170   int thread_pool_pthread_priority_;
171   ProfileSaverOptions profile_saver_options_;
172 
JitOptions()173   JitOptions()
174       : use_jit_compilation_(false),
175         use_tiered_jit_compilation_(false),
176         use_baseline_compiler_(false),
177         code_cache_initial_capacity_(0),
178         code_cache_max_capacity_(0),
179         compile_threshold_(0),
180         warmup_threshold_(0),
181         osr_threshold_(0),
182         priority_thread_weight_(0),
183         invoke_transition_weight_(0),
184         dump_info_on_shutdown_(false),
185         thread_pool_pthread_priority_(kJitPoolThreadPthreadDefaultPriority) {}
186 
187   DISALLOW_COPY_AND_ASSIGN(JitOptions);
188 };
189 
190 // Implemented and provided by the compiler library.
191 class JitCompilerInterface {
192  public:
~JitCompilerInterface()193   virtual ~JitCompilerInterface() {}
194   virtual bool CompileMethod(
195       Thread* self, JitMemoryRegion* region, ArtMethod* method, bool baseline, bool osr)
196       REQUIRES_SHARED(Locks::mutator_lock_) = 0;
197   virtual void TypesLoaded(mirror::Class**, size_t count)
198       REQUIRES_SHARED(Locks::mutator_lock_) = 0;
199   virtual bool GenerateDebugInfo() = 0;
200   virtual void ParseCompilerOptions() = 0;
201 
202   virtual std::vector<uint8_t> PackElfFileForJIT(ArrayRef<const JITCodeEntry*> elf_files,
203                                                  ArrayRef<const void*> removed_symbols,
204                                                  bool compress,
205                                                  /*out*/ size_t* num_symbols) = 0;
206 };
207 
208 // Data structure holding information to perform an OSR.
209 struct OsrData {
210   // The native PC to jump to.
211   const uint8_t* native_pc;
212 
213   // The frame size of the compiled code to jump to.
214   size_t frame_size;
215 
216   // The dynamically allocated memory of size `frame_size` to copy to stack.
217   void* memory[0];
218 
NativePcOffsetOsrData219   static constexpr MemberOffset NativePcOffset() {
220     return MemberOffset(OFFSETOF_MEMBER(OsrData, native_pc));
221   }
222 
FrameSizeOffsetOsrData223   static constexpr MemberOffset FrameSizeOffset() {
224     return MemberOffset(OFFSETOF_MEMBER(OsrData, frame_size));
225   }
226 
MemoryOffsetOsrData227   static constexpr MemberOffset MemoryOffset() {
228     return MemberOffset(OFFSETOF_MEMBER(OsrData, memory));
229   }
230 };
231 
232 class Jit {
233  public:
234   static constexpr size_t kDefaultPriorityThreadWeightRatio = 1000;
235   static constexpr size_t kDefaultInvokeTransitionWeightRatio = 500;
236   // How frequently should the interpreter check to see if OSR compilation is ready.
237   static constexpr int16_t kJitRecheckOSRThreshold = 101;  // Prime number to avoid patterns.
238 
239   DECLARE_RUNTIME_DEBUG_FLAG(kSlowMode);
240 
241   virtual ~Jit();
242 
243   // Create JIT itself.
244   static Jit* Create(JitCodeCache* code_cache, JitOptions* options);
245 
246   bool CompileMethod(ArtMethod* method, Thread* self, bool baseline, bool osr, bool prejit)
247       REQUIRES_SHARED(Locks::mutator_lock_);
248 
GetCodeCache()249   const JitCodeCache* GetCodeCache() const {
250     return code_cache_;
251   }
252 
GetCodeCache()253   JitCodeCache* GetCodeCache() {
254     return code_cache_;
255   }
256 
GetJitCompiler()257   JitCompilerInterface* GetJitCompiler() const {
258     return jit_compiler_;
259   }
260 
261   void CreateThreadPool();
262   void DeleteThreadPool();
263   void WaitForWorkersToBeCreated();
264 
265   // Dump interesting info: #methods compiled, code vs data size, compile / verify cumulative
266   // loggers.
267   void DumpInfo(std::ostream& os) REQUIRES(!lock_);
268   // Add a timing logger to cumulative_timings_.
269   void AddTimingLogger(const TimingLogger& logger);
270 
271   void AddMemoryUsage(ArtMethod* method, size_t bytes)
272       REQUIRES(!lock_)
273       REQUIRES_SHARED(Locks::mutator_lock_);
274 
OSRMethodThreshold()275   uint16_t OSRMethodThreshold() const {
276     return options_->GetOsrThreshold();
277   }
278 
HotMethodThreshold()279   uint16_t HotMethodThreshold() const {
280     return options_->GetCompileThreshold();
281   }
282 
WarmMethodThreshold()283   uint16_t WarmMethodThreshold() const {
284     return options_->GetWarmupThreshold();
285   }
286 
PriorityThreadWeight()287   uint16_t PriorityThreadWeight() const {
288     return options_->GetPriorityThreadWeight();
289   }
290 
291   // Return whether we should do JIT compilation. Note this will returns false
292   // if we only need to save profile information and not compile methods.
UseJitCompilation()293   bool UseJitCompilation() const {
294     return options_->UseJitCompilation();
295   }
296 
GetSaveProfilingInfo()297   bool GetSaveProfilingInfo() const {
298     return options_->GetSaveProfilingInfo();
299   }
300 
301   // Wait until there is no more pending compilation tasks.
302   void WaitForCompilationToFinish(Thread* self);
303 
304   // Profiling methods.
305   void MethodEntered(Thread* thread, ArtMethod* method)
306       REQUIRES_SHARED(Locks::mutator_lock_);
307 
308   ALWAYS_INLINE void AddSamples(Thread* self,
309                                 ArtMethod* method,
310                                 uint16_t samples,
311                                 bool with_backedges)
312       REQUIRES_SHARED(Locks::mutator_lock_);
313 
314   void InvokeVirtualOrInterface(ObjPtr<mirror::Object> this_object,
315                                 ArtMethod* caller,
316                                 uint32_t dex_pc,
317                                 ArtMethod* callee)
318       REQUIRES_SHARED(Locks::mutator_lock_);
319 
NotifyInterpreterToCompiledCodeTransition(Thread * self,ArtMethod * caller)320   void NotifyInterpreterToCompiledCodeTransition(Thread* self, ArtMethod* caller)
321       REQUIRES_SHARED(Locks::mutator_lock_) {
322     AddSamples(self, caller, options_->GetInvokeTransitionWeight(), false);
323   }
324 
NotifyCompiledCodeToInterpreterTransition(Thread * self,ArtMethod * callee)325   void NotifyCompiledCodeToInterpreterTransition(Thread* self, ArtMethod* callee)
326       REQUIRES_SHARED(Locks::mutator_lock_) {
327     AddSamples(self, callee, options_->GetInvokeTransitionWeight(), false);
328   }
329 
330   // Starts the profile saver if the config options allow profile recording.
331   // The profile will be stored in the specified `filename` and will contain
332   // information collected from the given `code_paths` (a set of dex locations).
333   void StartProfileSaver(const std::string& filename,
334                          const std::vector<std::string>& code_paths);
335   void StopProfileSaver();
336 
337   void DumpForSigQuit(std::ostream& os) REQUIRES(!lock_);
338 
339   static void NewTypeLoadedIfUsingJit(mirror::Class* type)
340       REQUIRES_SHARED(Locks::mutator_lock_);
341 
342   // If debug info generation is turned on then write the type information for types already loaded
343   // into the specified class linker to the jit debug interface,
344   void DumpTypeInfoForLoadedTypes(ClassLinker* linker);
345 
346   // Return whether we should try to JIT compiled code as soon as an ArtMethod is invoked.
347   bool JitAtFirstUse();
348 
349   // Return whether we can invoke JIT code for `method`.
350   bool CanInvokeCompiledCode(ArtMethod* method);
351 
352   // Return whether the runtime should use a priority thread weight when sampling.
353   static bool ShouldUsePriorityThreadWeight(Thread* self);
354 
355   // Return the information required to do an OSR jump. Return null if the OSR
356   // cannot be done.
357   OsrData* PrepareForOsr(ArtMethod* method, uint32_t dex_pc, uint32_t* vregs)
358       REQUIRES_SHARED(Locks::mutator_lock_);
359 
360   // If an OSR compiled version is available for `method`,
361   // and `dex_pc + dex_pc_offset` is an entry point of that compiled
362   // version, this method will jump to the compiled code, let it run,
363   // and return true afterwards. Return false otherwise.
364   static bool MaybeDoOnStackReplacement(Thread* thread,
365                                         ArtMethod* method,
366                                         uint32_t dex_pc,
367                                         int32_t dex_pc_offset,
368                                         JValue* result)
369       REQUIRES_SHARED(Locks::mutator_lock_);
370 
371   // Load the compiler library.
372   static bool LoadCompilerLibrary(std::string* error_msg);
373 
GetThreadPool()374   ThreadPool* GetThreadPool() const {
375     return thread_pool_.get();
376   }
377 
378   // Stop the JIT by waiting for all current compilations and enqueued compilations to finish.
379   void Stop();
380 
381   // Start JIT threads.
382   void Start();
383 
384   // Transition to a child state.
385   void PostForkChildAction(bool is_system_server, bool is_zygote);
386 
387   // Prepare for forking.
388   void PreZygoteFork();
389 
390   // Adjust state after forking.
391   void PostZygoteFork();
392 
393   // Called when system finishes booting.
394   void BootCompleted();
395 
396   // Compile methods from the given profile (.prof extension). If `add_to_queue`
397   // is true, methods in the profile are added to the JIT queue. Otherwise they are compiled
398   // directly.
399   // Return the number of methods added to the queue.
400   uint32_t CompileMethodsFromProfile(Thread* self,
401                                      const std::vector<const DexFile*>& dex_files,
402                                      const std::string& profile_path,
403                                      Handle<mirror::ClassLoader> class_loader,
404                                      bool add_to_queue);
405 
406   // Compile methods from the given boot profile (.bprof extension). If `add_to_queue`
407   // is true, methods in the profile are added to the JIT queue. Otherwise they are compiled
408   // directly.
409   // Return the number of methods added to the queue.
410   uint32_t CompileMethodsFromBootProfile(Thread* self,
411                                          const std::vector<const DexFile*>& dex_files,
412                                          const std::string& profile_path,
413                                          Handle<mirror::ClassLoader> class_loader,
414                                          bool add_to_queue);
415 
416   // Register the dex files to the JIT. This is to perform any compilation/optimization
417   // at the point of loading the dex files.
418   void RegisterDexFiles(const std::vector<std::unique_ptr<const DexFile>>& dex_files,
419                         jobject class_loader);
420 
421   // Called by the compiler to know whether it can directly encode the
422   // method/class/string.
423   bool CanEncodeMethod(ArtMethod* method, bool is_for_shared_region) const
424       REQUIRES_SHARED(Locks::mutator_lock_);
425   bool CanEncodeClass(ObjPtr<mirror::Class> cls, bool is_for_shared_region) const
426       REQUIRES_SHARED(Locks::mutator_lock_);
427   bool CanEncodeString(ObjPtr<mirror::String> string, bool is_for_shared_region) const
428       REQUIRES_SHARED(Locks::mutator_lock_);
429   bool CanAssumeInitialized(ObjPtr<mirror::Class> cls, bool is_for_shared_region) const
430       REQUIRES_SHARED(Locks::mutator_lock_);
431 
432   // Map boot image methods after all compilation in zygote has been done.
433   void MapBootImageMethods() REQUIRES(Locks::mutator_lock_);
434 
435   // Notify to other processes that the zygote is done profile compiling boot
436   // class path methods.
437   void NotifyZygoteCompilationDone();
438 
439   void EnqueueOptimizedCompilation(ArtMethod* method, Thread* self);
440 
441   void EnqueueCompilationFromNterp(ArtMethod* method, Thread* self)
442       REQUIRES_SHARED(Locks::mutator_lock_);
443 
444  private:
445   Jit(JitCodeCache* code_cache, JitOptions* options);
446 
447   // Compile an individual method listed in a profile. If `add_to_queue` is
448   // true and the method was resolved, return true. Otherwise return false.
449   bool CompileMethodFromProfile(Thread* self,
450                                 ClassLinker* linker,
451                                 uint32_t method_idx,
452                                 Handle<mirror::DexCache> dex_cache,
453                                 Handle<mirror::ClassLoader> class_loader,
454                                 bool add_to_queue,
455                                 bool compile_after_boot)
456       REQUIRES_SHARED(Locks::mutator_lock_);
457 
458   // Compile the method if the number of samples passes a threshold.
459   // Returns false if we can not compile now - don't increment the counter and retry later.
460   bool MaybeCompileMethod(Thread* self,
461                           ArtMethod* method,
462                           uint32_t old_count,
463                           uint32_t new_count,
464                           bool with_backedges)
465       REQUIRES_SHARED(Locks::mutator_lock_);
466 
467   static bool BindCompilerMethods(std::string* error_msg);
468 
469   // JIT compiler
470   static void* jit_library_handle_;
471   static JitCompilerInterface* jit_compiler_;
472   static JitCompilerInterface* (*jit_load_)(void);
473   template <typename T> static bool LoadSymbol(T*, const char* symbol, std::string* error_msg);
474 
475   // JIT resources owned by runtime.
476   jit::JitCodeCache* const code_cache_;
477   const JitOptions* const options_;
478 
479   std::unique_ptr<ThreadPool> thread_pool_;
480   std::vector<std::unique_ptr<OatDexFile>> type_lookup_tables_;
481 
482   Mutex boot_completed_lock_;
483   bool boot_completed_ GUARDED_BY(boot_completed_lock_) = false;
484   std::deque<Task*> tasks_after_boot_ GUARDED_BY(boot_completed_lock_);
485 
486   // Performance monitoring.
487   CumulativeLogger cumulative_timings_;
488   Histogram<uint64_t> memory_use_ GUARDED_BY(lock_);
489   Mutex lock_ DEFAULT_MUTEX_ACQUIRED_AFTER;
490 
491   // In the JIT zygote configuration, after all compilation is done, the zygote
492   // will copy its contents of the boot image to the zygote_mapping_methods_,
493   // which will be picked up by processes that will map the memory
494   // in-place within the boot image mapping.
495   //
496   // zygote_mapping_methods_ is shared memory only usable by the zygote and not
497   // inherited by child processes. We create it eagerly to ensure other
498   // processes cannot seal writable the file.
499   MemMap zygote_mapping_methods_;
500 
501   // The file descriptor created through memfd_create pointing to memory holding
502   // boot image methods. Created by the zygote, and inherited by child
503   // processes. The descriptor will be closed in each process (including the
504   // zygote) once they don't need it.
505   android::base::unique_fd fd_methods_;
506 
507   // The size of the memory pointed by `fd_methods_`. Cached here to avoid
508   // recomputing it.
509   size_t fd_methods_size_;
510 
511   DISALLOW_COPY_AND_ASSIGN(Jit);
512 };
513 
514 // Helper class to stop the JIT for a given scope. This will wait for the JIT to quiesce.
515 class ScopedJitSuspend {
516  public:
517   ScopedJitSuspend();
518   ~ScopedJitSuspend();
519 
520  private:
521   bool was_on_;
522 };
523 
524 }  // namespace jit
525 }  // namespace art
526 
527 #endif  // ART_RUNTIME_JIT_JIT_H_
528