summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--runtime/Android.mk3
-rw-r--r--runtime/gc/heap.cc8
-rw-r--r--runtime/gc/heap.h18
-rw-r--r--runtime/native/dalvik_system_VMRuntime.cc14
-rw-r--r--runtime/native/dalvik_system_Zygote.cc50
-rw-r--r--runtime/utils.cc30
-rwxr-xr-xtools/cpplint.py2
-rwxr-xr-xtools/generate-operator-out.py2
8 files changed, 119 insertions, 8 deletions
diff --git a/runtime/Android.mk b/runtime/Android.mk
index a0ae4bffbc..24dfa3f699 100644
--- a/runtime/Android.mk
+++ b/runtime/Android.mk
@@ -307,6 +307,9 @@ $$(ENUM_OPERATOR_OUT_GEN): $$(GENERATED_SRC_DIR)/%_operator_out.cc : $(LOCAL_PAT
ifeq ($$(art_target_or_host),target)
LOCAL_CLANG := $(ART_TARGET_CLANG)
LOCAL_CFLAGS += $(ART_TARGET_CFLAGS)
+ ifneq ($(TARGET_BUILD_VARIANT),user)
+ LOCAL_CFLAGS += -DALLOW_DEXROOT_ON_CACHE
+ endif
else # host
LOCAL_CLANG := $(ART_HOST_CLANG)
LOCAL_CFLAGS += $(ART_HOST_CFLAGS)
diff --git a/runtime/gc/heap.cc b/runtime/gc/heap.cc
index 1b46257c08..a9b91333f3 100644
--- a/runtime/gc/heap.cc
+++ b/runtime/gc/heap.cc
@@ -940,6 +940,14 @@ void Heap::SetTargetHeapUtilization(float target) {
target_utilization_ = target;
}
+void Heap::SetTargetHeapMinFree(size_t bytes) {
+ min_free_ = bytes;
+}
+
+void Heap::SetTargetHeapConcurrentStart(size_t bytes) {
+ concurrent_start_bytes_ = bytes;
+}
+
size_t Heap::GetObjectsAllocated() const {
size_t total = 0;
typedef std::vector<space::ContinuousSpace*>::const_iterator It;
diff --git a/runtime/gc/heap.h b/runtime/gc/heap.h
index 0b64261fa1..530118bb23 100644
--- a/runtime/gc/heap.h
+++ b/runtime/gc/heap.h
@@ -203,6 +203,24 @@ class Heap {
// dalvik.system.VMRuntime.setTargetHeapUtilization.
void SetTargetHeapUtilization(float target);
+ // Sets HEAP_MIN_FREE, implements
+ // dalvik.system.VMRuntime.SetTargetHeapMinFree.
+ void SetTargetHeapMinFree(size_t bytes);
+
+ // Gets HEAP_MIN_FREE
+ int GetTargetHeapMinFree() const {
+ return min_free_;
+ }
+
+ // Sets HEAP_CONCURRENT_START, implements
+ // dalvik.system.VMRuntime.SetTargetHeapConcurrentStart.
+ void SetTargetHeapConcurrentStart(size_t bytes);
+
+ // Gets HEAP_CONCURRENT_START
+ int GetTargetHeapConcurrentStart() const {
+ return concurrent_start_bytes_;
+ }
+
// For the alloc space, sets the maximum number of bytes that the heap is allowed to allocate
// from the system. Doesn't allow the space to exceed its growth limit.
void SetIdealFootprint(size_t max_allowed_footprint);
diff --git a/runtime/native/dalvik_system_VMRuntime.cc b/runtime/native/dalvik_system_VMRuntime.cc
index 5fc8bd5a48..0a652b6d5f 100644
--- a/runtime/native/dalvik_system_VMRuntime.cc
+++ b/runtime/native/dalvik_system_VMRuntime.cc
@@ -43,6 +43,18 @@ static void VMRuntime_nativeSetTargetHeapUtilization(JNIEnv*, jobject, jfloat ta
Runtime::Current()->GetHeap()->SetTargetHeapUtilization(target);
}
+static jint VMRuntime_nativeSetTargetHeapMinFree(JNIEnv*, jobject, jint bytes) {
+ Runtime::Current()->GetHeap()->SetTargetHeapMinFree(bytes);
+
+ return Runtime::Current()->GetHeap()->GetTargetHeapMinFree();
+}
+
+static jint VMRuntime_nativeSetTargetHeapConcurrentStart(JNIEnv*, jobject, jint bytes) {
+ Runtime::Current()->GetHeap()->SetTargetHeapConcurrentStart(bytes);
+
+ return Runtime::Current()->GetHeap()->GetTargetHeapConcurrentStart();
+}
+
static void VMRuntime_startJitCompilation(JNIEnv*, jobject) {
}
@@ -206,6 +218,8 @@ static JNINativeMethod gMethods[] = {
NATIVE_METHOD(VMRuntime, getTargetHeapUtilization, "()F"),
NATIVE_METHOD(VMRuntime, isDebuggerActive, "()Z"),
NATIVE_METHOD(VMRuntime, nativeSetTargetHeapUtilization, "(F)V"),
+ NATIVE_METHOD(VMRuntime, nativeSetTargetHeapMinFree, "(I)I"),
+ NATIVE_METHOD(VMRuntime, nativeSetTargetHeapConcurrentStart, "(I)I"),
NATIVE_METHOD(VMRuntime, newNonMovableArray, "(Ljava/lang/Class;I)Ljava/lang/Object;"),
NATIVE_METHOD(VMRuntime, properties, "()[Ljava/lang/String;"),
NATIVE_METHOD(VMRuntime, setTargetSdkVersion, "(I)V"),
diff --git a/runtime/native/dalvik_system_Zygote.cc b/runtime/native/dalvik_system_Zygote.cc
index 2acacc9959..4b24192ab6 100644
--- a/runtime/native/dalvik_system_Zygote.cc
+++ b/runtime/native/dalvik_system_Zygote.cc
@@ -23,8 +23,10 @@
#include <signal.h>
#include <stdlib.h>
#include <sys/types.h>
+#include <sys/stat.h>
#include <sys/wait.h>
#include <unistd.h>
+#include <fcntl.h>
#include "cutils/fs.h"
#include "cutils/multiuser.h"
@@ -401,12 +403,43 @@ static bool NeedsNoRandomizeWorkaround() {
}
#endif
+// Utility to close down the Zygote socket file descriptors while
+// the child is still running as root with Zygote's privileges. Each
+// descriptor (if any) is closed via dup2(), replacing it with a valid
+// (open) descriptor to /dev/null.
+
+static void DetachDescriptors(JNIEnv* env, jintArray fdsToClose) {
+ if (!fdsToClose) {
+ return;
+ }
+ jsize count = env->GetArrayLength(fdsToClose);
+ jint *ar = env->GetIntArrayElements(fdsToClose, 0);
+ if (!ar) {
+ PLOG(FATAL) << "Bad fd array";
+ }
+ jsize i;
+ int devnull;
+ for (i = 0; i < count; i++) {
+ devnull = open("/dev/null", O_RDWR);
+ if (devnull < 0) {
+ PLOG(FATAL) << "Failed to open /dev/null";
+ continue;
+ }
+ PLOG(VERBOSE) << "Switching descriptor " << ar[i] << " to /dev/null";
+ if (dup2(devnull, ar[i]) < 0) {
+ PLOG(FATAL) << "Failed dup2() on descriptor " << ar[i];
+ }
+ close(devnull);
+ }
+}
+
// Utility routine to fork zygote and specialize the child process.
static pid_t ForkAndSpecializeCommon(JNIEnv* env, uid_t uid, gid_t gid, jintArray javaGids,
jint debug_flags, jobjectArray javaRlimits,
jlong permittedCapabilities, jlong effectiveCapabilities,
jint mount_external,
- jstring java_se_info, jstring java_se_name, bool is_system_server) {
+ jstring java_se_info, jstring java_se_name,
+ bool is_system_server, jintArray fdsToClose) {
Runtime* runtime = Runtime::Current();
CHECK(runtime->IsZygote()) << "runtime instance not started with -Xzygote";
if (!runtime->PreZygoteFork()) {
@@ -425,6 +458,9 @@ static pid_t ForkAndSpecializeCommon(JNIEnv* env, uid_t uid, gid_t gid, jintArra
// The child process.
gMallocLeakZygoteChild = 1;
+ // Clean up any descriptors which must be closed immediately
+ DetachDescriptors(env, fdsToClose);
+
// Keep capabilities across UID change, unless we're staying root.
if (uid != 0) {
EnableKeepCapabilities();
@@ -517,9 +553,11 @@ static pid_t ForkAndSpecializeCommon(JNIEnv* env, uid_t uid, gid_t gid, jintArra
}
static jint Zygote_nativeForkAndSpecialize(JNIEnv* env, jclass, jint uid, jint gid, jintArray gids,
- jint debug_flags, jobjectArray rlimits, jint mount_external,
- jstring se_info, jstring se_name) {
- return ForkAndSpecializeCommon(env, uid, gid, gids, debug_flags, rlimits, 0, 0, mount_external, se_info, se_name, false);
+ jint debug_flags, jobjectArray rlimits,
+ jint mount_external, jstring se_info, jstring se_name,
+ jintArray fdsToClose) {
+ return ForkAndSpecializeCommon(env, uid, gid, gids, debug_flags, rlimits, 0, 0, mount_external,
+ se_info, se_name, false, fdsToClose);
}
static jint Zygote_nativeForkSystemServer(JNIEnv* env, jclass, uid_t uid, gid_t gid, jintArray gids,
@@ -528,7 +566,7 @@ static jint Zygote_nativeForkSystemServer(JNIEnv* env, jclass, uid_t uid, gid_t
pid_t pid = ForkAndSpecializeCommon(env, uid, gid, gids,
debug_flags, rlimits,
permittedCapabilities, effectiveCapabilities,
- MOUNT_EXTERNAL_NONE, NULL, NULL, true);
+ MOUNT_EXTERNAL_NONE, NULL, NULL, true, NULL);
if (pid > 0) {
// The zygote process checks whether the child process has died or not.
LOG(INFO) << "System server process " << pid << " has been created";
@@ -545,7 +583,7 @@ static jint Zygote_nativeForkSystemServer(JNIEnv* env, jclass, uid_t uid, gid_t
}
static JNINativeMethod gMethods[] = {
- NATIVE_METHOD(Zygote, nativeForkAndSpecialize, "(II[II[[IILjava/lang/String;Ljava/lang/String;)I"),
+ NATIVE_METHOD(Zygote, nativeForkAndSpecialize, "(II[II[[IILjava/lang/String;Ljava/lang/String;[I)I"),
NATIVE_METHOD(Zygote, nativeForkSystemServer, "(II[II[[IJJ)I"),
};
diff --git a/runtime/utils.cc b/runtime/utils.cc
index bf36bf3e85..6cd5a9351a 100644
--- a/runtime/utils.cc
+++ b/runtime/utils.cc
@@ -56,6 +56,10 @@
#include <linux/unistd.h>
#endif
+#ifdef ALLOW_DEXROOT_ON_CACHE
+#include <cutils/properties.h>
+#endif
+
namespace art {
pid_t GetTid() {
@@ -1172,6 +1176,25 @@ const char* GetAndroidData() {
return android_data;
}
+#ifdef ALLOW_DEXROOT_ON_CACHE
+const char* GetAndroidCache() {
+ const char* android_cache = getenv("ANDROID_CACHE");
+ if (android_cache == NULL) {
+ if (OS::DirectoryExists("/cache")) {
+ android_cache = "/cache";
+ } else {
+ LOG(FATAL) << "ANDROID_CACHE not set and /cache does not exist";
+ return "";
+ }
+ }
+ if (!OS::DirectoryExists(android_cache)) {
+ LOG(FATAL) << "Failed to find ANDROID_CACHE directory " << android_cache;
+ return "";
+ }
+ return android_cache;
+}
+#endif
+
std::string GetDalvikCacheOrDie(const char* android_data) {
std::string dalvik_cache(StringPrintf("%s/dalvik-cache", android_data));
@@ -1192,6 +1215,13 @@ std::string GetDalvikCacheOrDie(const char* android_data) {
std::string GetDalvikCacheFilenameOrDie(const std::string& location) {
std::string dalvik_cache(GetDalvikCacheOrDie(GetAndroidData()));
+#ifdef ALLOW_DEXROOT_ON_CACHE
+ char dexoptDataOnly[PROPERTY_VALUE_MAX];
+ property_get("dalvik.vm.dexopt-data-only", dexoptDataOnly, "1");
+ if ((StartsWith(location, "/system")) && (strcmp(dexoptDataOnly, "1") != 0)) {
+ dalvik_cache = GetDalvikCacheOrDie(GetAndroidCache());
+ }
+#endif
if (location[0] != '/') {
LOG(FATAL) << "Expected path in location to be absolute: "<< location;
}
diff --git a/tools/cpplint.py b/tools/cpplint.py
index 30b5216b12..c2f6514c2b 100755
--- a/tools/cpplint.py
+++ b/tools/cpplint.py
@@ -1,4 +1,4 @@
-#!/usr/bin/python
+#!/usr/bin/env python
#
# Copyright (c) 2009 Google Inc. All rights reserved.
#
diff --git a/tools/generate-operator-out.py b/tools/generate-operator-out.py
index 0c085fbe93..19266b4f64 100755
--- a/tools/generate-operator-out.py
+++ b/tools/generate-operator-out.py
@@ -1,4 +1,4 @@
-#!/usr/bin/python
+#!/usr/bin/env python
#
# Copyright (C) 2012 The Android Open Source Project
#