summaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorAnwar Ghuloum <anwarg@google.com>2013-05-01 17:03:05 +0000
committerAndroid (Google) Code Review <android-gerrit@google.com>2013-05-01 17:03:06 +0000
commitcf9773a7adff883012dbd519a66e85f1f7aaaa11 (patch)
tree2202662f22597850bf03c5dbbb0305bfe46816a5 /src
parent654d91957edb4d1f7534ed5d743cf914db763448 (diff)
parent8447d84d847d4562d7a7bce62768c27e7d20a9aa (diff)
downloadart-cf9773a7adff883012dbd519a66e85f1f7aaaa11.tar.gz
art-cf9773a7adff883012dbd519a66e85f1f7aaaa11.tar.bz2
art-cf9773a7adff883012dbd519a66e85f1f7aaaa11.zip
Merge "Compile filter for small applications and methods" into dalvik-dev
Diffstat (limited to 'src')
-rw-r--r--src/common_test.h2
-rw-r--r--src/compiler/driver/compiler_driver.cc10
-rw-r--r--src/compiler/driver/compiler_driver.h7
-rw-r--r--src/dex2oat.cc49
-rw-r--r--src/oat_test.cc2
-rw-r--r--src/runtime.cc14
-rw-r--r--src/runtime.h27
-rw-r--r--src/runtime_support.cc2
8 files changed, 76 insertions, 37 deletions
diff --git a/src/common_test.h b/src/common_test.h
index 78d86d2f9..0aac36bfc 100644
--- a/src/common_test.h
+++ b/src/common_test.h
@@ -366,7 +366,7 @@ class CommonTest : public testing::Test {
}
class_linker_->FixupDexCaches(runtime_->GetResolutionMethod());
image_classes_.reset(new std::set<std::string>);
- compiler_driver_.reset(new CompilerDriver(compiler_backend, instruction_set, true, 2, false, false,
+ compiler_driver_.reset(new CompilerDriver(compiler_backend, instruction_set, true, 2, false,
image_classes_.get(), true, true));
// Create the heap thread pool so that the GC runs in parallel for tests. Normally, the thread
diff --git a/src/compiler/driver/compiler_driver.cc b/src/compiler/driver/compiler_driver.cc
index 301d255bb..bc3407302 100644
--- a/src/compiler/driver/compiler_driver.cc
+++ b/src/compiler/driver/compiler_driver.cc
@@ -283,7 +283,7 @@ static Fn FindFunction(const std::string& compiler_so_name, void* library, const
}
CompilerDriver::CompilerDriver(CompilerBackend compiler_backend, InstructionSet instruction_set,
- bool image, size_t thread_count, bool support_debugging, bool light_mode,
+ bool image, size_t thread_count, bool support_debugging,
const std::set<std::string>* image_classes,
bool dump_stats, bool dump_timings)
: compiler_backend_(compiler_backend),
@@ -294,7 +294,6 @@ CompilerDriver::CompilerDriver(CompilerBackend compiler_backend, InstructionSet
image_(image),
thread_count_(thread_count),
support_debugging_(support_debugging),
- light_mode_(light_mode),
start_ns_(0),
stats_(new AOTCompilationStats),
dump_stats_(dump_stats),
@@ -1566,12 +1565,15 @@ void CompilerDriver::CompileMethod(const DexFile::CodeItem* code_item, uint32_t
CHECK(compiled_method != NULL);
} else if ((access_flags & kAccAbstract) != 0) {
} else {
- // In light mode we only compile image classes.
- bool dont_compile = light_mode_ && ((image_classes_ == NULL) || (image_classes_->size() == 0));
+ // In small mode we only compile image classes.
+ bool dont_compile = Runtime::Current()->IsSmallMode() && ((image_classes_ == NULL) || (image_classes_->size() == 0));
// Don't compile class initializers, ever.
if (((access_flags & kAccConstructor) != 0) && ((access_flags & kAccStatic) != 0)) {
dont_compile = true;
+ } else if (code_item->insns_size_in_code_units_ < Runtime::Current()->GetSmallModeMethodDexSizeLimit()) {
+ // Do compile small methods.
+ dont_compile = false;
}
if (!dont_compile) {
diff --git a/src/compiler/driver/compiler_driver.h b/src/compiler/driver/compiler_driver.h
index a20e5ef58..7c37c6a08 100644
--- a/src/compiler/driver/compiler_driver.h
+++ b/src/compiler/driver/compiler_driver.h
@@ -67,7 +67,7 @@ class CompilerDriver {
// can assume will be in the image, with NULL implying all available
// classes.
explicit CompilerDriver(CompilerBackend compiler_backend, InstructionSet instruction_set, bool image,
- size_t thread_count, bool support_debugging, bool light_mode,
+ size_t thread_count, bool support_debugging,
const std::set<std::string>* image_classes,
bool dump_stats, bool dump_timings);
@@ -84,10 +84,6 @@ class CompilerDriver {
return support_debugging_;
}
- bool IsLightMode() const {
- return light_mode_;
- }
-
InstructionSet GetInstructionSet() const {
return instruction_set_;
}
@@ -331,7 +327,6 @@ class CompilerDriver {
bool image_;
size_t thread_count_;
bool support_debugging_;
- const bool light_mode_;
uint64_t start_ns_;
UniquePtr<AOTCompilationStats> stats_;
diff --git a/src/dex2oat.cc b/src/dex2oat.cc
index e41e537ee..37d29961a 100644
--- a/src/dex2oat.cc
+++ b/src/dex2oat.cc
@@ -137,8 +137,6 @@ static void Usage(const char* fmt, ...) {
UsageError(" Use a separate --runtime-arg switch for each argument.");
UsageError(" Example: --runtime-arg -Xms256m");
UsageError("");
- UsageError(" --light-mode: compile only if generating image file");
- UsageError("");
std::cerr << "See log for usage error information\n";
exit(EXIT_FAILURE);
}
@@ -146,15 +144,14 @@ static void Usage(const char* fmt, ...) {
class Dex2Oat {
public:
static bool Create(Dex2Oat** p_dex2oat, Runtime::Options& options, CompilerBackend compiler_backend,
- InstructionSet instruction_set, size_t thread_count, bool support_debugging,
- bool light_mode)
+ InstructionSet instruction_set, size_t thread_count, bool support_debugging)
SHARED_TRYLOCK_FUNCTION(true, Locks::mutator_lock_) {
if (!CreateRuntime(options, instruction_set)) {
*p_dex2oat = NULL;
return false;
}
*p_dex2oat = new Dex2Oat(Runtime::Current(), compiler_backend, instruction_set, thread_count,
- support_debugging, light_mode);
+ support_debugging);
return true;
}
@@ -265,7 +262,6 @@ class Dex2Oat {
image,
thread_count_,
support_debugging_,
- light_mode_,
image_classes,
dump_stats,
dump_timings));
@@ -274,6 +270,7 @@ class Dex2Oat {
driver->SetBitcodeFileName(bitcode_filename);
}
+
Thread::Current()->TransitionFromRunnableToSuspended(kNative);
driver->CompileAll(class_loader, dex_files);
@@ -344,23 +341,14 @@ class Dex2Oat {
return true;
}
- void SetLightMode(bool light_mode) {
- light_mode_ = light_mode;
- }
-
- bool GetLightMode() {
- return light_mode_;
- }
-
private:
explicit Dex2Oat(Runtime* runtime, CompilerBackend compiler_backend, InstructionSet instruction_set,
- size_t thread_count, bool support_debugging, bool light_mode)
+ size_t thread_count, bool support_debugging)
: compiler_backend_(compiler_backend),
instruction_set_(instruction_set),
runtime_(runtime),
thread_count_(thread_count),
support_debugging_(support_debugging),
- light_mode_(light_mode),
start_ns_(NanoTime()) {
}
@@ -486,7 +474,6 @@ class Dex2Oat {
Runtime* runtime_;
size_t thread_count_;
bool support_debugging_;
- bool light_mode_;
uint64_t start_ns_;
DISALLOW_IMPLICIT_CONSTRUCTORS(Dex2Oat);
@@ -674,7 +661,6 @@ static int dex2oat(int argc, char** argv) {
std::vector<const char*> runtime_args;
int thread_count = sysconf(_SC_NPROCESSORS_CONF);
bool support_debugging = false;
- bool light_mode = false;
#if defined(ART_USE_PORTABLE_COMPILER)
CompilerBackend compiler_backend = kPortable;
#else
@@ -694,9 +680,6 @@ static int dex2oat(int argc, char** argv) {
bool dump_timings = kIsDebugBuild;
bool watch_dog_enabled = !kIsTargetBuild;
-#if ART_LIGHT_MODE
- light_mode = true;
-#endif // ART_LIGHT_MODE
for (int i = 0; i < argc; i++) {
const StringPiece option(argv[i]);
@@ -726,8 +709,6 @@ static int dex2oat(int argc, char** argv) {
}
} else if (option == "-g") {
support_debugging = true;
- } else if (option == "--light-mode") {
- light_mode = true;
} else if (option == "--watch-dog") {
watch_dog_enabled = true;
} else if (option == "--no-watch-dog") {
@@ -932,8 +913,13 @@ static int dex2oat(int argc, char** argv) {
options.push_back(std::make_pair(runtime_args[i], reinterpret_cast<void*>(NULL)));
}
+#if ART_SMALL_MODE
+ options.push_back(std::make_pair("-small", reinterpret_cast<void*>(NULL)));
+#endif // ART_SMALL_MODE
+
Dex2Oat* p_dex2oat;
- if (!Dex2Oat::Create(&p_dex2oat, options, compiler_backend, instruction_set, thread_count, support_debugging, light_mode)) {
+ if (!Dex2Oat::Create(&p_dex2oat, options, compiler_backend, instruction_set, thread_count,
+ support_debugging)) {
LOG(ERROR) << "Failed to create dex2oat";
return EXIT_FAILURE;
}
@@ -980,6 +966,21 @@ static int dex2oat(int argc, char** argv) {
}
}
+ // If we're in small mode, but the program is small, turn off small mode.
+ // It doesn't make a difference for the boot image, so let's skip the check
+ // altogether.
+ if (Runtime::Current()->IsSmallMode() && !image) {
+ size_t num_methods = 0;
+ for (size_t i = 0; i != dex_files.size(); ++i) {
+ const DexFile* dex_file = dex_files[i];
+ CHECK(dex_file != NULL);
+ num_methods += dex_file->NumMethodIds();
+ }
+ if (num_methods <= Runtime::Current()->GetSmallModeMethodThreshold()) {
+ Runtime::Current()->SetSmallMode(false);
+ LOG(INFO) << "Below method threshold, compiling anyways";
+ }
+ }
UniquePtr<const CompilerDriver> compiler(dex2oat->CreateOatFile(boot_image_option,
host_prefix.get(),
diff --git a/src/oat_test.cc b/src/oat_test.cc
index a7fbaf14a..dd336d9a9 100644
--- a/src/oat_test.cc
+++ b/src/oat_test.cc
@@ -76,7 +76,7 @@ TEST_F(OatTest, WriteRead) {
#else
CompilerBackend compiler_backend = kQuick;
#endif
- compiler_driver_.reset(new CompilerDriver(compiler_backend, kThumb2, false, 2, false, false,
+ compiler_driver_.reset(new CompilerDriver(compiler_backend, kThumb2, false, 2, false,
NULL, true, true));
compiler_driver_->CompileAll(class_loader, class_linker->GetBootClassPath());
}
diff --git a/src/runtime.cc b/src/runtime.cc
index 3cb179357..0caf81d1e 100644
--- a/src/runtime.cc
+++ b/src/runtime.cc
@@ -364,6 +364,10 @@ Runtime::ParsedOptions* Runtime::ParsedOptions::Create(const Options& options, b
parsed->hook_exit_ = exit;
parsed->hook_abort_ = NULL; // We don't call abort(3) by default; see Runtime::Abort.
+ parsed->small_mode_ = true;
+ parsed->small_mode_method_threshold_ = Runtime::kDefaultSmallModeMethodThreshold;
+ parsed->small_mode_method_dex_size_limit_ = Runtime::kDefaultSmallModeMethodDexSizeLimit;
+
// gLogVerbosity.class_linker = true; // TODO: don't check this in!
// gLogVerbosity.compiler = true; // TODO: don't check this in!
// gLogVerbosity.heap = true; // TODO: don't check this in!
@@ -571,6 +575,12 @@ Runtime::ParsedOptions* Runtime::ParsedOptions::Create(const Options& options, b
Trace::SetDefaultClockSource(kProfilerClockSourceWall);
} else if (option == "-Xprofile:dualclock") {
Trace::SetDefaultClockSource(kProfilerClockSourceDual);
+ } else if (option == "-small") {
+ parsed->small_mode_ = true;
+ } else if (StartsWith(option, "-small-mode-methods-max:")) {
+ parsed->small_mode_method_threshold_ = ParseIntegerOrDie(option);
+ } else if (StartsWith(option, "-small-mode-methods-size-max:")) {
+ parsed->small_mode_method_dex_size_limit_ = ParseIntegerOrDie(option);
} else {
if (!ignore_unrecognized) {
// TODO: print usage via vfprintf
@@ -791,6 +801,10 @@ bool Runtime::Init(const Options& raw_options, bool ignore_unrecognized) {
is_zygote_ = options->is_zygote_;
is_concurrent_gc_enabled_ = options->is_concurrent_gc_enabled_;
+ small_mode_ = options->small_mode_;
+ small_mode_method_threshold_ = options->small_mode_method_threshold_;
+ small_mode_method_dex_size_limit_ = options->small_mode_method_dex_size_limit_;
+
vfprintf_ = options->hook_vfprintf_;
exit_ = options->hook_exit_;
abort_ = options->hook_abort_;
diff --git a/src/runtime.h b/src/runtime.h
index c7ccda187..ac9b50b27 100644
--- a/src/runtime.h
+++ b/src/runtime.h
@@ -61,6 +61,9 @@ class Runtime {
public:
typedef std::vector<std::pair<std::string, const void*> > Options;
+ static const size_t kDefaultSmallModeMethodThreshold = 10;
+ static const size_t kDefaultSmallModeMethodDexSizeLimit = 100;
+
class ParsedOptions {
public:
// returns null if problem parsing and ignore_unrecognized is false
@@ -95,6 +98,9 @@ class Runtime {
void (*hook_exit_)(jint status);
void (*hook_abort_)();
std::vector<std::string> properties_;
+ bool small_mode_;
+ size_t small_mode_method_threshold_;
+ size_t small_mode_method_dex_size_limit_;
private:
ParsedOptions() {}
@@ -116,6 +122,23 @@ class Runtime {
return is_concurrent_gc_enabled_;
}
+ bool IsSmallMode() const {
+ return small_mode_;
+ }
+
+
+ void SetSmallMode(bool small_mode) {
+ small_mode_ = small_mode;
+ }
+
+ size_t GetSmallModeMethodThreshold() const {
+ return small_mode_method_threshold_;
+ }
+
+ size_t GetSmallModeMethodDexSizeLimit() const {
+ return small_mode_method_dex_size_limit_;
+ }
+
const std::string& GetHostPrefix() const {
DCHECK(!IsStarted());
return host_prefix_;
@@ -339,6 +362,10 @@ class Runtime {
bool is_zygote_;
bool is_concurrent_gc_enabled_;
+ bool small_mode_;
+ size_t small_mode_method_threshold_;
+ size_t small_mode_method_dex_size_limit_;
+
// The host prefix is used during cross compilation. It is removed
// from the start of host paths such as:
// $ANDROID_PRODUCT_OUT/system/framework/boot.oat
diff --git a/src/runtime_support.cc b/src/runtime_support.cc
index 6ea05b48e..d9b369bac 100644
--- a/src/runtime_support.cc
+++ b/src/runtime_support.cc
@@ -211,7 +211,7 @@ mirror::Field* FindFieldFromCode(uint32_t field_idx, const mirror::AbstractMetho
if (fields_class->IsInitialized()) {
return resolved_field;
} else if (Runtime::Current()->GetClassLinker()->EnsureInitialized(fields_class, true, true)) {
- // otherwise let's ensure the class is initialized before resolving the field
+ // Otherwise let's ensure the class is initialized before resolving the field.
return resolved_field;
} else {
DCHECK(self->IsExceptionPending()); // Throw exception and unwind