Merge "libmemtrack: Remove libpagemap dependency."
diff --git a/base/include/android-base/unique_fd.h b/base/include/android-base/unique_fd.h
index c8d12cf..2c890b4 100644
--- a/base/include/android-base/unique_fd.h
+++ b/base/include/android-base/unique_fd.h
@@ -161,22 +161,35 @@
// Inline functions, so that they can be used header-only.
template <typename Closer>
-inline bool Pipe(unique_fd_impl<Closer>* read, unique_fd_impl<Closer>* write) {
+inline bool Pipe(unique_fd_impl<Closer>* read, unique_fd_impl<Closer>* write,
+ int flags = O_CLOEXEC) {
int pipefd[2];
#if defined(__linux__)
- if (pipe2(pipefd, O_CLOEXEC) != 0) {
+ if (pipe2(pipefd, flags) != 0) {
return false;
}
#else // defined(__APPLE__)
+ if (flags & ~(O_CLOEXEC | O_NONBLOCK)) {
+ return false;
+ }
if (pipe(pipefd) != 0) {
return false;
}
- if (fcntl(pipefd[0], F_SETFD, FD_CLOEXEC) != 0 || fcntl(pipefd[1], F_SETFD, FD_CLOEXEC) != 0) {
- close(pipefd[0]);
- close(pipefd[1]);
- return false;
+ if (flags & O_CLOEXEC) {
+ if (fcntl(pipefd[0], F_SETFD, FD_CLOEXEC) != 0 || fcntl(pipefd[1], F_SETFD, FD_CLOEXEC) != 0) {
+ close(pipefd[0]);
+ close(pipefd[1]);
+ return false;
+ }
+ }
+ if (flags & O_NONBLOCK) {
+ if (fcntl(pipefd[0], F_SETFL, O_NONBLOCK) != 0 || fcntl(pipefd[1], F_SETFL, O_NONBLOCK) != 0) {
+ close(pipefd[0]);
+ close(pipefd[1]);
+ return false;
+ }
}
#endif
diff --git a/fs_mgr/OWNERS b/fs_mgr/OWNERS
index 817a0b8..cbbd3bc 100644
--- a/fs_mgr/OWNERS
+++ b/fs_mgr/OWNERS
@@ -1,2 +1,3 @@
bowgotsai@google.com
+dvander@google.com
tomcherry@google.com
diff --git a/fs_mgr/fs_mgr.cpp b/fs_mgr/fs_mgr.cpp
index 70a1045..ded3678 100644
--- a/fs_mgr/fs_mgr.cpp
+++ b/fs_mgr/fs_mgr.cpp
@@ -81,6 +81,8 @@
#define ZRAM_CONF_MCS "/sys/block/zram0/max_comp_streams"
#define ZRAM_BACK_DEV "/sys/block/zram0/backing_dev"
+#define SYSFS_EXT4_VERITY "/sys/fs/ext4/features/verity"
+
#define ARRAY_SIZE(a) (sizeof(a) / sizeof(*(a)))
using android::base::Realpath;
@@ -110,6 +112,7 @@
FS_STAT_TOGGLE_QUOTAS_FAILED = 0x10000,
FS_STAT_SET_RESERVED_BLOCKS_FAILED = 0x20000,
FS_STAT_ENABLE_ENCRYPTION_FAILED = 0x40000,
+ FS_STAT_ENABLE_VERITY_FAILED = 0x80000,
};
// TODO: switch to inotify()
@@ -440,6 +443,43 @@
}
}
+// Enable fs-verity if needed.
+static void tune_verity(const std::string& blk_device, const FstabEntry& entry,
+ const struct ext4_super_block* sb, int* fs_stat) {
+ bool has_verity = (sb->s_feature_ro_compat & cpu_to_le32(EXT4_FEATURE_RO_COMPAT_VERITY)) != 0;
+ bool want_verity = entry.fs_mgr_flags.fs_verity;
+
+ if (has_verity || !want_verity) {
+ return;
+ }
+
+ std::string verity_support;
+ if (!android::base::ReadFileToString(SYSFS_EXT4_VERITY, &verity_support)) {
+ LERROR << "Failed to open " << SYSFS_EXT4_VERITY;
+ return;
+ }
+
+ if (!(android::base::Trim(verity_support) == "supported")) {
+ LERROR << "Current ext4 verity not supported by kernel";
+ return;
+ }
+
+ if (!tune2fs_available()) {
+ LERROR << "Unable to enable ext4 verity on " << blk_device
+ << " because " TUNE2FS_BIN " is missing";
+ return;
+ }
+
+ LINFO << "Enabling ext4 verity on " << blk_device;
+
+ const char* argv[] = {TUNE2FS_BIN, "-O", "verity", blk_device.c_str()};
+ if (!run_tune2fs(argv, ARRAY_SIZE(argv))) {
+ LERROR << "Failed to run " TUNE2FS_BIN " to enable "
+ << "ext4 verity on " << blk_device;
+ *fs_stat |= FS_STAT_ENABLE_VERITY_FAILED;
+ }
+}
+
// Read the primary superblock from an f2fs filesystem. On failure return
// false. If it's not an f2fs filesystem, also set FS_STAT_INVALID_MAGIC.
#define F2FS_BLKSIZE 4096
@@ -511,12 +551,14 @@
}
if (is_extfs(entry.fs_type) &&
- (entry.fs_mgr_flags.reserved_size || entry.fs_mgr_flags.file_encryption)) {
+ (entry.fs_mgr_flags.reserved_size || entry.fs_mgr_flags.file_encryption ||
+ entry.fs_mgr_flags.fs_verity)) {
struct ext4_super_block sb;
if (read_ext4_superblock(blk_device, &sb, &fs_stat)) {
tune_reserved_size(blk_device, entry, &sb, &fs_stat);
tune_encrypt(blk_device, entry, &sb, &fs_stat);
+ tune_verity(blk_device, entry, &sb, &fs_stat);
}
}
diff --git a/fs_mgr/fs_mgr_fstab.cpp b/fs_mgr/fs_mgr_fstab.cpp
index c9f34a7..9d4f280 100644
--- a/fs_mgr/fs_mgr_fstab.cpp
+++ b/fs_mgr/fs_mgr_fstab.cpp
@@ -125,6 +125,7 @@
{"zram_loopback_path=", MF_ZRAM_LOOPBACK_PATH},
{"zram_loopback_size=", MF_ZRAM_LOOPBACK_SIZE},
{"zram_backing_dev_path=", MF_ZRAM_BACKING_DEV_PATH},
+ {"fsverity", MF_FS_VERITY},
{0, 0},
};
@@ -1087,6 +1088,10 @@
return fstab->fs_mgr_flags & MF_CHECKPOINT_BLK;
}
+int fs_mgr_is_fs_verity(const struct fstab_rec* fstab) {
+ return fstab->fs_mgr_flags & MF_FS_VERITY;
+}
+
FstabEntry BuildGsiSystemFstabEntry() {
FstabEntry system = {
.blk_device = "system_gsi",
diff --git a/fs_mgr/fs_mgr_priv.h b/fs_mgr/fs_mgr_priv.h
index 39ceff7..3b9ddee 100644
--- a/fs_mgr/fs_mgr_priv.h
+++ b/fs_mgr/fs_mgr_priv.h
@@ -128,6 +128,8 @@
0x400000000
#define MF_ZRAM_BACKING_DEV_PATH \
0x800000000
+#define MF_FS_VERITY \
+ 0x1000000000
// clang-format on
#define DM_BUF_SIZE 4096
diff --git a/fs_mgr/include_fstab/fstab/fstab.h b/fs_mgr/include_fstab/fstab/fstab.h
index 5d8496d..4a05949 100644
--- a/fs_mgr/include_fstab/fstab/fstab.h
+++ b/fs_mgr/include_fstab/fstab/fstab.h
@@ -95,6 +95,7 @@
int fs_mgr_is_checkpoint_fs(const struct fstab_rec* fstab);
int fs_mgr_is_checkpoint_blk(const struct fstab_rec* fstab);
int fs_mgr_has_sysfs_path(const struct fstab_rec* fstab);
+int fs_mgr_is_fs_verity(const struct fstab_rec* fstab);
std::string fs_mgr_get_slot_suffix();
std::set<std::string> fs_mgr_get_boot_devices();
@@ -174,6 +175,10 @@
// bit 32
bool slot_select_other : 1;
+ bool zram_loopback_path : 1;
+ bool zram_loopback_size : 1;
+ bool zram_backing_dev_path : 1;
+ bool fs_verity : 1;
};
} fs_mgr_flags;
diff --git a/fs_mgr/liblp/builder.cpp b/fs_mgr/liblp/builder.cpp
index b99ff8f..110d56e 100644
--- a/fs_mgr/liblp/builder.cpp
+++ b/fs_mgr/liblp/builder.cpp
@@ -269,6 +269,11 @@
}
static bool VerifyDeviceProperties(const BlockDeviceInfo& device_info) {
+ if (device_info.logical_block_size == 0) {
+ LERROR << "Block device " << device_info.partition_name
+ << " logical block size must not be zero.";
+ return false;
+ }
if (device_info.logical_block_size % LP_SECTOR_SIZE != 0) {
LERROR << "Block device " << device_info.partition_name
<< " logical block size must be a multiple of 512.";
@@ -335,7 +340,7 @@
out.alignment = device_info.alignment;
out.alignment_offset = device_info.alignment_offset;
out.size = device_info.size;
- if (device_info.partition_name.size() >= sizeof(out.partition_name)) {
+ if (device_info.partition_name.size() > sizeof(out.partition_name)) {
LERROR << "Partition name " << device_info.partition_name << " exceeds maximum length.";
return false;
}
diff --git a/fs_mgr/liblp/include/liblp/metadata_format.h b/fs_mgr/liblp/include/liblp/metadata_format.h
index 9c5ec5c..8934aaf 100644
--- a/fs_mgr/liblp/include/liblp/metadata_format.h
+++ b/fs_mgr/liblp/include/liblp/metadata_format.h
@@ -127,7 +127,7 @@
* num_entries, and the result must not overflow a 32-bit signed integer.
*/
typedef struct LpMetadataTableDescriptor {
- /* 0: Location of the table, relative to the metadata header. */
+ /* 0: Location of the table, relative to end of the metadata header. */
uint32_t offset;
/* 4: Number of entries in the table. */
uint32_t num_entries;
@@ -272,7 +272,7 @@
/* 40: Maximum size in bytes. If 0, the group has no maximum size. */
uint64_t maximum_size;
-} LpMetadataPartitionGroup;
+} __attribute__((packed)) LpMetadataPartitionGroup;
/* This flag is only intended to be used with super_empty.img and super.img on
* retrofit devices. If set, the group needs a slot suffix to be interpreted
@@ -323,7 +323,7 @@
/* 60: Flags (see LP_BLOCK_DEVICE_* flags below). */
uint32_t flags;
-} LpMetadataBlockDevice;
+} __attribute__((packed)) LpMetadataBlockDevice;
/* This flag is only intended to be used with super_empty.img and super.img on
* retrofit devices. On these devices there are A and B super partitions, and
diff --git a/fs_mgr/liblp/reader.cpp b/fs_mgr/liblp/reader.cpp
index 24c6b2c..dcee6d2 100644
--- a/fs_mgr/liblp/reader.cpp
+++ b/fs_mgr/liblp/reader.cpp
@@ -256,6 +256,10 @@
LERROR << "Logical partition has invalid attribute set.";
return nullptr;
}
+ if (partition.first_extent_index + partition.num_extents < partition.first_extent_index) {
+ LERROR << "Logical partition first_extent_index + num_extents overflowed.";
+ return nullptr;
+ }
if (partition.first_extent_index + partition.num_extents > header.extents.num_entries) {
LERROR << "Logical partition has invalid extent list.";
return nullptr;
diff --git a/fs_mgr/liblp/writer.cpp b/fs_mgr/liblp/writer.cpp
index 54a1883..bffcb7e 100644
--- a/fs_mgr/liblp/writer.cpp
+++ b/fs_mgr/liblp/writer.cpp
@@ -373,11 +373,11 @@
// safety.
std::string old_blob;
if (!ValidateAndSerializeMetadata(opener, *backup.get(), slot_suffix, &old_blob)) {
- LERROR << "Error serializing primary metadata to repair corrupted backup";
+ LERROR << "Error serializing backup metadata to repair corrupted primary";
return false;
}
if (!WritePrimaryMetadata(fd, metadata, slot_number, old_blob, writer)) {
- LERROR << "Error writing primary metadata to repair corrupted backup";
+ LERROR << "Error writing backup metadata to repair corrupted primary";
return false;
}
}
diff --git a/init/reboot.cpp b/init/reboot.cpp
index 0aa7810..5b90969 100644
--- a/init/reboot.cpp
+++ b/init/reboot.cpp
@@ -57,6 +57,7 @@
#include "service.h"
#include "sigchld_handler.h"
+using android::base::GetBoolProperty;
using android::base::Split;
using android::base::StringPrintf;
using android::base::Timer;
@@ -398,9 +399,31 @@
Service* bootAnim = ServiceList::GetInstance().FindService("bootanim");
Service* surfaceFlinger = ServiceList::GetInstance().FindService("surfaceflinger");
if (bootAnim != nullptr && surfaceFlinger != nullptr && surfaceFlinger->IsRunning()) {
- // will not check animation class separately
+ bool do_shutdown_animation = GetBoolProperty("ro.init.shutdown_animation", false);
+
+ if (do_shutdown_animation) {
+ property_set("service.bootanim.exit", "0");
+ // Could be in the middle of animation. Stop and start so that it can pick
+ // up the right mode.
+ bootAnim->Stop();
+ }
+
for (const auto& service : ServiceList::GetInstance()) {
- if (service->classnames().count("animation")) service->SetShutdownCritical();
+ if (service->classnames().count("animation") == 0) {
+ continue;
+ }
+
+ // start all animation classes if stopped.
+ if (do_shutdown_animation) {
+ service->Start().IgnoreError();
+ }
+ service->SetShutdownCritical(); // will not check animation class separately
+ }
+
+ if (do_shutdown_animation) {
+ bootAnim->Start().IgnoreError();
+ surfaceFlinger->SetShutdownCritical();
+ bootAnim->SetShutdownCritical();
}
}
diff --git a/libmeminfo/tools/Android.bp b/libmeminfo/tools/Android.bp
index c852bbb..24054c6 100644
--- a/libmeminfo/tools/Android.bp
+++ b/libmeminfo/tools/Android.bp
@@ -13,7 +13,7 @@
// limitations under the License.
cc_binary {
- name: "librank2",
+ name: "librank",
cflags: [
"-Wall",
"-Werror",
@@ -27,7 +27,7 @@
}
cc_binary {
- name: "procmem2",
+ name: "procmem",
cflags: [
"-Wall",
"-Werror",
@@ -41,7 +41,7 @@
}
cc_binary {
- name: "procrank2",
+ name: "procrank",
cflags: [
"-Wall",
"-Werror",
@@ -55,7 +55,7 @@
}
cc_binary {
- name: "showmap2",
+ name: "showmap",
cflags: [
"-Wall",
"-Werror",
diff --git a/libnativeloader/include/nativeloader/dlext_namespaces.h b/libnativeloader/include/nativeloader/dlext_namespaces.h
index ca026b3..2d6ce85 100644
--- a/libnativeloader/include/nativeloader/dlext_namespaces.h
+++ b/libnativeloader/include/nativeloader/dlext_namespaces.h
@@ -109,19 +109,6 @@
struct android_namespace_t* to,
const char* shared_libs_sonames);
-/*
- * Get the default library search path.
- * The path will be copied into buffer, which must have space for at least
- * buffer_size chars. Elements are separated with ':', and the path will always
- * be null-terminated.
- *
- * If buffer_size is too small to hold the entire default search path and the
- * null terminator, this function will abort. There is currently no way to find
- * out what the required buffer size is. At the time of this writing, PATH_MAX
- * is sufficient and used by all callers of this function.
- */
-extern void android_get_LD_LIBRARY_PATH(char* buffer, size_t buffer_size);
-
extern struct android_namespace_t* android_get_exported_namespace(const char* name);
__END_DECLS
diff --git a/libnativeloader/include/nativeloader/native_loader.h b/libnativeloader/include/nativeloader/native_loader.h
index af53dc5..260f655 100644
--- a/libnativeloader/include/nativeloader/native_loader.h
+++ b/libnativeloader/include/nativeloader/native_loader.h
@@ -47,7 +47,7 @@
__attribute__((visibility("default"))) void* OpenNativeLibrary(
JNIEnv* env, int32_t target_sdk_version, const char* path, jobject class_loader,
- jstring library_path, bool* needs_native_bridge, char** error_msg);
+ const char* caller_location, jstring library_path, bool* needs_native_bridge, char** error_msg);
__attribute__((visibility("default"))) bool CloseNativeLibrary(void* handle,
const bool needs_native_bridge,
diff --git a/libnativeloader/native_loader.cpp b/libnativeloader/native_loader.cpp
index af7df72..ab17b29 100644
--- a/libnativeloader/native_loader.cpp
+++ b/libnativeloader/native_loader.cpp
@@ -43,6 +43,10 @@
#include <android-base/properties.h>
#endif
+extern "C" {
+struct android_namespace_t* android_get_exported_namespace(const char*);
+}
+
#define CHECK(predicate) LOG_ALWAYS_FATAL_IF(!(predicate),\
"%s:%d: %s CHECK '" #predicate "' failed.",\
__FILE__, __LINE__, __FUNCTION__)
@@ -119,6 +123,8 @@
// This list includes all directories app is allowed to access this way.
static constexpr const char* kWhitelistedDirectories = "/data:/mnt/expand";
+static constexpr const char* kApexPath = "/apex/";
+
static bool is_debuggable() {
char debuggable[PROP_VALUE_MAX];
property_get("ro.debuggable", debuggable, "0");
@@ -623,13 +629,51 @@
return nullptr;
}
+#if defined(__ANDROID__)
+static android_namespace_t* FindExportedNamespace(const char* caller_location) {
+ std::string location = caller_location;
+ // Lots of implicit assumptions here: we expect `caller_location` to be of the form:
+ // /apex/com.android...modulename/...
+ //
+ // And we extract from it 'modulename', which is the name of the linker namespace.
+ if (android::base::StartsWith(location, kApexPath)) {
+ size_t slash_index = location.find_first_of('/', strlen(kApexPath));
+ LOG_ALWAYS_FATAL_IF((slash_index == std::string::npos),
+ "Error finding namespace of apex: no slash in path %s", caller_location);
+ size_t dot_index = location.find_last_of('.', slash_index);
+ LOG_ALWAYS_FATAL_IF((dot_index == std::string::npos),
+ "Error finding namespace of apex: no dot in apex name %s", caller_location);
+ std::string name = location.substr(dot_index + 1, slash_index - dot_index - 1);
+ android_namespace_t* boot_namespace = android_get_exported_namespace(name.c_str());
+ LOG_ALWAYS_FATAL_IF((boot_namespace == nullptr),
+ "Error finding namespace of apex: no namespace called %s", name.c_str());
+ return boot_namespace;
+ }
+ return nullptr;
+}
+#endif
+
void* OpenNativeLibrary(JNIEnv* env, int32_t target_sdk_version, const char* path,
- jobject class_loader, jstring library_path, bool* needs_native_bridge,
- char** error_msg) {
+ jobject class_loader, const char* caller_location, jstring library_path,
+ bool* needs_native_bridge, char** error_msg) {
#if defined(__ANDROID__)
UNUSED(target_sdk_version);
if (class_loader == nullptr) {
*needs_native_bridge = false;
+ if (caller_location != nullptr) {
+ android_namespace_t* boot_namespace = FindExportedNamespace(caller_location);
+ if (boot_namespace != nullptr) {
+ const android_dlextinfo dlextinfo = {
+ .flags = ANDROID_DLEXT_USE_NAMESPACE,
+ .library_namespace = boot_namespace,
+ };
+ void* handle = android_dlopen_ext(path, RTLD_NOW, &dlextinfo);
+ if (handle == nullptr) {
+ *error_msg = strdup(dlerror());
+ }
+ return handle;
+ }
+ }
void* handle = dlopen(path, RTLD_NOW);
if (handle == nullptr) {
*error_msg = strdup(dlerror());
@@ -654,7 +698,7 @@
return OpenNativeLibraryInNamespace(ns, path, needs_native_bridge, error_msg);
#else
- UNUSED(env, target_sdk_version, class_loader);
+ UNUSED(env, target_sdk_version, class_loader, caller_location);
// Do some best effort to emulate library-path support. It will not
// work for dependencies.
diff --git a/rootdir/etc/ld.config.txt b/rootdir/etc/ld.config.txt
index 2dda648..3804c86 100644
--- a/rootdir/etc/ld.config.txt
+++ b/rootdir/etc/ld.config.txt
@@ -28,7 +28,7 @@
dir.postinstall = /postinstall
[system]
-additional.namespaces = runtime,sphal,vndk,rs
+additional.namespaces = runtime,conscrypt,media,sphal,vndk,rs
###############################################################################
# "default" namespace
@@ -129,6 +129,36 @@
namespace.runtime.link.default.allow_all_shared_libs = true
###############################################################################
+# "media" APEX namespace
+#
+# This namespace is for libraries within the media APEX.
+###############################################################################
+namespace.media.isolated = true
+namespace.media.visible = true
+
+namespace.media.search.paths = /apex/com.android.media/${LIB}
+
+namespace.media.links = default
+namespace.media.link.default.shared_libs = %LLNDK_LIBRARIES%
+namespace.media.link.default.shared_libs += libandroid.so
+namespace.media.link.default.shared_libs += libbinder_ndk.so
+namespace.media.link.default.shared_libs += %SANITIZER_RUNTIME_LIBRARIES%
+
+###############################################################################
+# "conscrypt" APEX namespace
+#
+# This namespace is for libraries within the conscrypt APEX.
+###############################################################################
+namespace.conscrypt.isolated = true
+namespace.conscrypt.visible = true
+
+namespace.conscrypt.search.paths = /apex/com.android.conscrypt/${LIB}
+namespace.conscrypt.links = default
+# TODO(b/119867084): Restrict to Bionic dlopen dependencies and PALette library
+# when it exists.
+namespace.conscrypt.link.default.allow_all_shared_libs = true
+
+###############################################################################
# "sphal" namespace
#
# SP-HAL(Sameprocess-HAL)s are the only vendor libraries that are allowed to be
diff --git a/rootdir/etc/ld.config.vndk_lite.txt b/rootdir/etc/ld.config.vndk_lite.txt
index 33b4698..2ce25b5 100644
--- a/rootdir/etc/ld.config.vndk_lite.txt
+++ b/rootdir/etc/ld.config.vndk_lite.txt
@@ -28,7 +28,7 @@
dir.postinstall = /postinstall
[system]
-additional.namespaces = runtime,sphal,vndk,rs
+additional.namespaces = runtime,conscrypt,media,sphal,vndk,rs
###############################################################################
# "default" namespace
@@ -76,6 +76,36 @@
namespace.runtime.link.default.allow_all_shared_libs = true
###############################################################################
+# "media" APEX namespace
+#
+# This namespace is for libraries within the media APEX.
+###############################################################################
+namespace.media.isolated = true
+namespace.media.visible = true
+
+namespace.media.search.paths = /apex/com.android.media/${LIB}
+
+namespace.media.links = default
+namespace.media.link.default.shared_libs = %LLNDK_LIBRARIES%
+namespace.media.link.default.shared_libs += libandroid.so
+namespace.media.link.default.shared_libs += libbinder_ndk.so
+namespace.media.link.default.shared_libs += %SANITIZER_RUNTIME_LIBRARIES%
+
+###############################################################################
+# "conscrypt" APEX namespace
+#
+# This namespace is for libraries within the conscrypt APEX.
+###############################################################################
+namespace.conscrypt.isolated = true
+namespace.conscrypt.visible = true
+
+namespace.conscrypt.search.paths = /apex/com.android.conscrypt/${LIB}
+namespace.conscrypt.links = default
+# TODO(b/119867084): Restrict to Bionic dlopen dependencies and PALette library
+# when it exists.
+namespace.conscrypt.link.default.allow_all_shared_libs = true
+
+###############################################################################
# "sphal" namespace
#
# SP-HAL(Sameprocess-HAL)s are the only vendor libraries that are allowed to be
diff --git a/rootdir/init.zygote32.rc b/rootdir/init.zygote32.rc
index ac87979..2e95687 100644
--- a/rootdir/init.zygote32.rc
+++ b/rootdir/init.zygote32.rc
@@ -4,6 +4,7 @@
user root
group root readproc reserved_disk
socket zygote stream 660 root system
+ updatable
onrestart write /sys/android_power/request_state wake
onrestart write /sys/power/state on
onrestart restart audioserver
diff --git a/rootdir/init.zygote32_64.rc b/rootdir/init.zygote32_64.rc
index a535846..1cfc3d6 100644
--- a/rootdir/init.zygote32_64.rc
+++ b/rootdir/init.zygote32_64.rc
@@ -4,6 +4,7 @@
user root
group root readproc reserved_disk
socket zygote stream 660 root system
+ updatable
onrestart write /sys/android_power/request_state wake
onrestart write /sys/power/state on
onrestart restart audioserver
@@ -19,5 +20,6 @@
user root
group root readproc reserved_disk
socket zygote_secondary stream 660 root system
+ updatable
onrestart restart zygote
writepid /dev/cpuset/foreground/tasks
diff --git a/rootdir/init.zygote64.rc b/rootdir/init.zygote64.rc
index 6fc810b..8ab012d 100644
--- a/rootdir/init.zygote64.rc
+++ b/rootdir/init.zygote64.rc
@@ -4,6 +4,7 @@
user root
group root readproc reserved_disk
socket zygote stream 660 root system
+ updatable
onrestart write /sys/android_power/request_state wake
onrestart write /sys/power/state on
onrestart restart audioserver
diff --git a/rootdir/init.zygote64_32.rc b/rootdir/init.zygote64_32.rc
index 7ddd52e..5abf149 100644
--- a/rootdir/init.zygote64_32.rc
+++ b/rootdir/init.zygote64_32.rc
@@ -4,6 +4,7 @@
user root
group root readproc reserved_disk
socket zygote stream 660 root system
+ updatable
onrestart write /sys/android_power/request_state wake
onrestart write /sys/power/state on
onrestart restart audioserver
@@ -19,5 +20,6 @@
user root
group root readproc reserved_disk
socket zygote_secondary stream 660 root system
+ updatable
onrestart restart zygote
writepid /dev/cpuset/foreground/tasks