Fixed and refactored profiler options handling

- extracted profiler options in a separate class
- switched from system property reading to command line arguments
- added profile based compilation options to CompilerOptions
- removed no longer used kProfile compilation filter
- optimize dex files only if the profiler is enabled
- clean up unused arguments

Bug: 12877748
Bug: 15275634
Change-Id: I37ff68e7694370950ce8db2360562e9058ecebb7
diff --git a/compiler/dex/frontend.cc b/compiler/dex/frontend.cc
index 3d22774..7848b06 100644
--- a/compiler/dex/frontend.cc
+++ b/compiler/dex/frontend.cc
@@ -903,7 +903,7 @@
     cu.mir_graph->EnableOpcodeCounting();
   }
 
-  // Check early if we should skip this compilation if using the profiled filter.
+  // Check early if we should skip this compilation if the profiler is enabled.
   if (cu.compiler_driver->ProfilePresent()) {
     std::string methodname = PrettyMethod(method_idx, dex_file);
     if (cu.mir_graph->SkipCompilation(methodname)) {
diff --git a/compiler/dex/mir_analysis.cc b/compiler/dex/mir_analysis.cc
index 7129f8a..2ec17de 100644
--- a/compiler/dex/mir_analysis.cc
+++ b/compiler/dex/mir_analysis.cc
@@ -1015,7 +1015,7 @@
     return true;
   }
 
-  if (!compiler_options.IsCompilationEnabled() || compiler_filter == CompilerOptions::kProfiled) {
+  if (!compiler_options.IsCompilationEnabled()) {
     return true;
   }
 
diff --git a/compiler/driver/compiler_driver.cc b/compiler/driver/compiler_driver.cc
index 15a086b..1cfd194 100644
--- a/compiler/driver/compiler_driver.cc
+++ b/compiler/driver/compiler_driver.cc
@@ -55,7 +55,6 @@
 #include "thread_pool.h"
 #include "trampolines/trampoline_compiler.h"
 #include "transaction.h"
-#include "utils.h"
 #include "verifier/method_verifier.h"
 #include "verifier/method_verifier-inl.h"
 
@@ -331,7 +330,7 @@
                                bool image, DescriptorSet* image_classes, size_t thread_count,
                                bool dump_stats, bool dump_passes, CumulativeLogger* timer,
                                std::string profile_file)
-    : profile_ok_(false), compiler_options_(compiler_options),
+    : profile_present_(false), compiler_options_(compiler_options),
       verification_results_(verification_results),
       method_inliner_map_(method_inliner_map),
       compiler_(Compiler::Create(this, compiler_kind)),
@@ -365,11 +364,6 @@
 
   CHECK_PTHREAD_CALL(pthread_key_create, (&tls_key_, NULL), "compiler tls key");
 
-  // Read the profile file if one is provided.
-  if (profile_file != "") {
-    profile_ok_ = profile_file_.LoadFile(profile_file);
-  }
-
   dex_to_dex_compiler_ = reinterpret_cast<DexToDexCompilerFn>(ArtCompileDEX);
 
   compiler_->Init();
@@ -385,6 +379,16 @@
   if (compiler_options->GetGenerateGDBInformation()) {
     cfi_info_.reset(compiler_->GetCallFrameInformationInitialization(*this));
   }
+
+  // Read the profile file if one is provided.
+  if (!profile_file.empty()) {
+    profile_present_ = profile_file_.LoadFile(profile_file);
+    if (profile_present_) {
+      LOG(INFO) << "Using profile data form file " << profile_file;
+    } else {
+      LOG(INFO) << "Failed to load profile file " << profile_file;
+    }
+  }
 }
 
 std::vector<uint8_t>* CompilerDriver::DeduplicateCode(const std::vector<uint8_t>& code) {
@@ -2044,7 +2048,7 @@
   }
 
 bool CompilerDriver::SkipCompilation(const std::string& method_name) {
-  if (!profile_ok_) {
+  if (!profile_present_) {
     return false;
   }
   // First find the method in the profile file.
@@ -2056,18 +2060,17 @@
   }
 
   // Methods that comprise top_k_threshold % of the total samples will be compiled.
-  double top_k_threshold = GetDoubleProperty("dalvik.vm.profiler.compile_thr", 10.0, 90.0, 90.0);
-
   // Compare against the start of the topK percentage bucket just in case the threshold
   // falls inside a bucket.
-  bool compile = data.GetTopKUsedPercentage() - data.GetUsedPercent() <= top_k_threshold;
+  bool compile = data.GetTopKUsedPercentage() - data.GetUsedPercent()
+                 <= compiler_options_->GetTopKProfileThreshold();
   if (compile) {
     LOG(INFO) << "compiling method " << method_name << " because its usage is part of top "
         << data.GetTopKUsedPercentage() << "% with a percent of " << data.GetUsedPercent() << "%"
-        << " (topKThreshold=" << top_k_threshold << ")";
+        << " (topKThreshold=" << compiler_options_->GetTopKProfileThreshold() << ")";
   } else {
     VLOG(compiler) << "not compiling method " << method_name << " because it's not part of leading "
-        << top_k_threshold << "% samples)";
+        << compiler_options_->GetTopKProfileThreshold() << "% samples)";
   }
   return !compile;
 }
diff --git a/compiler/driver/compiler_driver.h b/compiler/driver/compiler_driver.h
index e952f63..fad6798 100644
--- a/compiler/driver/compiler_driver.h
+++ b/compiler/driver/compiler_driver.h
@@ -143,7 +143,7 @@
   }
 
   bool ProfilePresent() const {
-    return profile_ok_;
+    return profile_present_;
   }
 
   // Are we compiling and creating an image file?
@@ -596,7 +596,7 @@
   }
 
   ProfileFile profile_file_;
-  bool profile_ok_;
+  bool profile_present_;
 
   // Should the compiler run on this method given profile information?
   bool SkipCompilation(const std::string& method_name);
diff --git a/compiler/driver/compiler_options.h b/compiler/driver/compiler_options.h
index 20c6bc8..05a9ac7 100644
--- a/compiler/driver/compiler_options.h
+++ b/compiler/driver/compiler_options.h
@@ -24,7 +24,6 @@
   enum CompilerFilter {
     kVerifyNone,          // Skip verification and compile nothing except JNI stubs.
     kInterpretOnly,       // Compile nothing except JNI stubs.
-    kProfiled,            // Compile based on profile.
     kSpace,               // Maximize space savings.
     kBalanced,            // Try to get the best performance return on compilation investment.
     kSpeed,               // Maximize runtime performance.
@@ -33,7 +32,7 @@
 
   // Guide heuristics to determine whether to compile method if profile data not available.
 #if ART_SMALL_MODE
-  static const CompilerFilter kDefaultCompilerFilter = kProfiled;
+  static const CompilerFilter kDefaultCompilerFilter = kInterpretOnly;
 #else
   static const CompilerFilter kDefaultCompilerFilter = kSpeed;
 #endif
@@ -42,6 +41,7 @@
   static const size_t kDefaultSmallMethodThreshold = 60;
   static const size_t kDefaultTinyMethodThreshold = 20;
   static const size_t kDefaultNumDexMethodsThreshold = 900;
+  static constexpr double kDefaultTopKProfileThreshold = 90.0;
 
   CompilerOptions() :
     compiler_filter_(kDefaultCompilerFilter),
@@ -50,7 +50,8 @@
     small_method_threshold_(kDefaultSmallMethodThreshold),
     tiny_method_threshold_(kDefaultTinyMethodThreshold),
     num_dex_methods_threshold_(kDefaultNumDexMethodsThreshold),
-    generate_gdb_information_(false)
+    generate_gdb_information_(false),
+    top_k_profile_threshold_(kDefaultTopKProfileThreshold)
 #ifdef ART_SEA_IR_MODE
     , sea_ir_mode_(false)
 #endif
@@ -62,7 +63,8 @@
                   size_t small_method_threshold,
                   size_t tiny_method_threshold,
                   size_t num_dex_methods_threshold,
-                  bool generate_gdb_information
+                  bool generate_gdb_information,
+                  double top_k_profile_threshold
 #ifdef ART_SEA_IR_MODE
                   , bool sea_ir_mode
 #endif
@@ -73,7 +75,8 @@
     small_method_threshold_(small_method_threshold),
     tiny_method_threshold_(tiny_method_threshold),
     num_dex_methods_threshold_(num_dex_methods_threshold),
-    generate_gdb_information_(generate_gdb_information)
+    generate_gdb_information_(generate_gdb_information),
+    top_k_profile_threshold_(top_k_profile_threshold)
 #ifdef ART_SEA_IR_MODE
     , sea_ir_mode_(sea_ir_mode)
 #endif
@@ -132,6 +135,10 @@
     return num_dex_methods_threshold_;
   }
 
+  double GetTopKProfileThreshold() const {
+    return top_k_profile_threshold_;
+  }
+
 #ifdef ART_SEA_IR_MODE
   bool GetSeaIrMode();
 #endif
@@ -148,7 +155,8 @@
   size_t tiny_method_threshold_;
   size_t num_dex_methods_threshold_;
   bool generate_gdb_information_;
-
+  // When using a profile file only the top K% of the profiled samples will be compiled.
+  double top_k_profile_threshold_;
 #ifdef ART_SEA_IR_MODE
   bool sea_ir_mode_;
 #endif