blob: 9e449a20a6f0706fc2255b4f69562ecebc541333 [file] [log] [blame]
Narayan Kamath973b4662014-03-31 13:41:26 +01001/*
2 * Copyright (C) 2008 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
Chris Waileseac7f4e2019-01-17 14:57:10 -080017/*
18 * Disable optimization of this file if we are compiling with the address
19 * sanitizer. This is a mitigation for b/122921367 and can be removed once the
20 * bug is fixed.
21 */
22#if __has_feature(address_sanitizer)
23#pragma clang optimize off
24#endif
25
Colin Cross18cd9f52014-06-13 12:58:55 -070026#define LOG_TAG "Zygote"
Narayan Kamath973b4662014-03-31 13:41:26 +010027
28// sys/mount.h has to come before linux/fs.h due to redefinition of MS_RDONLY, MS_BIND, etc
29#include <sys/mount.h>
30#include <linux/fs.h>
31
Chris Wailesaf594fc2018-11-02 11:00:07 -070032#include <functional>
Jeff Sharkeyfaf3f692015-06-30 15:56:33 -070033#include <list>
Chris Wailesaf594fc2018-11-02 11:00:07 -070034#include <optional>
Andreas Gampeb053cce2015-11-17 16:38:59 -080035#include <sstream>
Jeff Sharkeyfaf3f692015-06-30 15:56:33 -070036#include <string>
37
Josh Gaod7951102018-06-26 16:05:12 -070038#include <android/fdsan.h>
Colin Cross18cd9f52014-06-13 12:58:55 -070039#include <fcntl.h>
Dan Albert46d84442014-11-18 16:07:51 -080040#include <grp.h>
41#include <inttypes.h>
Christopher Ferrisab16dd12017-05-15 16:50:29 -070042#include <malloc.h>
Jeff Sharkeyfaf3f692015-06-30 15:56:33 -070043#include <mntent.h>
Narayan Kamath973b4662014-03-31 13:41:26 +010044#include <paths.h>
45#include <signal.h>
46#include <stdlib.h>
Colin Cross18cd9f52014-06-13 12:58:55 -070047#include <sys/capability.h>
Robert Seseke4f8d692016-09-13 19:13:01 -040048#include <sys/cdefs.h>
Colin Cross18cd9f52014-06-13 12:58:55 -070049#include <sys/personality.h>
50#include <sys/prctl.h>
51#include <sys/resource.h>
52#include <sys/stat.h>
Vitalii Tomkiv5cbce852016-05-18 17:43:02 -070053#include <sys/time.h>
Colin Cross18cd9f52014-06-13 12:58:55 -070054#include <sys/types.h>
55#include <sys/utsname.h>
56#include <sys/wait.h>
Dan Albert46d84442014-11-18 16:07:51 -080057#include <unistd.h>
Colin Cross18cd9f52014-06-13 12:58:55 -070058
Andreas Gampe8dfa1782017-01-05 12:45:58 -080059#include "android-base/logging.h"
Minchan Kim5fa8af22018-06-27 11:32:40 +090060#include <android-base/properties.h>
Carmen Jacksondd401252017-02-23 15:21:10 -080061#include <android-base/file.h>
62#include <android-base/stringprintf.h>
Colin Cross18cd9f52014-06-13 12:58:55 -070063#include <cutils/fs.h>
64#include <cutils/multiuser.h>
65#include <cutils/sched_policy.h>
Sharvil Nanavati4990e4f2014-06-29 17:06:52 -070066#include <private/android_filesystem_config.h>
Colin Cross18cd9f52014-06-13 12:58:55 -070067#include <utils/String8.h>
68#include <selinux/android.h>
Victor Hsiehc8176ef2018-01-08 12:43:00 -080069#include <seccomp_policy.h>
Howard Ro27330412018-10-02 12:08:28 -070070#include <stats_event_list.h>
Colin Cross0161bbc2014-06-03 13:26:58 -070071#include <processgroup/processgroup.h>
Colin Cross18cd9f52014-06-13 12:58:55 -070072
Andreas Gampeed6b9df2014-11-20 22:02:20 -080073#include "core_jni_helpers.h"
Steven Moreland2279b252017-07-19 09:50:45 -070074#include <nativehelper/JNIHelp.h>
75#include <nativehelper/ScopedLocalRef.h>
76#include <nativehelper/ScopedPrimitiveArray.h>
77#include <nativehelper/ScopedUtfChars.h>
Robert Sesek8225b7c2016-12-16 14:02:31 -050078#include "fd_utils.h"
Narayan Kamath973b4662014-03-31 13:41:26 +010079
jgu212eacd062014-09-10 06:55:07 -040080#include "nativebridge/native_bridge.h"
81
Narayan Kamath973b4662014-03-31 13:41:26 +010082namespace {
83
Chris Wailesaf594fc2018-11-02 11:00:07 -070084using namespace std::placeholders;
85
Narayan Kamath973b4662014-03-31 13:41:26 +010086using android::String8;
Sudheer Shanka663b1042018-07-30 17:34:21 -070087using android::base::StringAppendF;
Carmen Jacksondd401252017-02-23 15:21:10 -080088using android::base::StringPrintf;
89using android::base::WriteStringToFile;
Minchan Kim5fa8af22018-06-27 11:32:40 +090090using android::base::GetBoolProperty;
Narayan Kamath973b4662014-03-31 13:41:26 +010091
Andreas Gamped5758f62018-03-12 12:08:55 -070092#define CREATE_ERROR(...) StringPrintf("%s:%d: ", __FILE__, __LINE__). \
93 append(StringPrintf(__VA_ARGS__))
94
Narayan Kamath973b4662014-03-31 13:41:26 +010095static pid_t gSystemServerPid = 0;
96
Sudheer Shanka663b1042018-07-30 17:34:21 -070097static const char kIsolatedStorage[] = "persist.sys.isolated_storage";
Narayan Kamath973b4662014-03-31 13:41:26 +010098static const char kZygoteClassName[] = "com/android/internal/os/Zygote";
99static jclass gZygoteClass;
Orion Hodson46724e72018-10-19 13:05:33 +0100100static jmethodID gCallPostForkSystemServerHooks;
Narayan Kamath973b4662014-03-31 13:41:26 +0100101static jmethodID gCallPostForkChildHooks;
102
Victor Hsiehc8176ef2018-01-08 12:43:00 -0800103static bool g_is_security_enforced = true;
104
Narayan Kamath973b4662014-03-31 13:41:26 +0100105// Must match values in com.android.internal.os.Zygote.
106enum MountExternalKind {
107 MOUNT_EXTERNAL_NONE = 0,
Jeff Sharkey48877892015-03-18 11:27:19 -0700108 MOUNT_EXTERNAL_DEFAULT = 1,
Jeff Sharkey9527b222015-06-24 15:24:48 -0700109 MOUNT_EXTERNAL_READ = 2,
110 MOUNT_EXTERNAL_WRITE = 3,
Sudheer Shanka3a0df3b2018-12-12 12:43:43 -0800111 MOUNT_EXTERNAL_INSTALLER = 4,
112 MOUNT_EXTERNAL_FULL = 5,
Narayan Kamath973b4662014-03-31 13:41:26 +0100113};
114
Orion Hodson8d005a62018-12-05 12:28:53 +0000115// Must match values in com.android.internal.os.Zygote.
116enum RuntimeFlags : uint32_t {
117 DEBUG_ENABLE_JDWP = 1,
118};
119
Andreas Gampeb053cce2015-11-17 16:38:59 -0800120static void RuntimeAbort(JNIEnv* env, int line, const char* msg) {
121 std::ostringstream oss;
122 oss << __FILE__ << ":" << line << ": " << msg;
123 env->FatalError(oss.str().c_str());
Narayan Kamath973b4662014-03-31 13:41:26 +0100124}
125
126// This signal handler is for zygote mode, since the zygote must reap its children
127static void SigChldHandler(int /*signal_number*/) {
128 pid_t pid;
129 int status;
130
Christopher Ferrisa8a79542015-08-31 15:40:01 -0700131 // It's necessary to save and restore the errno during this function.
132 // Since errno is stored per thread, changing it here modifies the errno
133 // on the thread on which this signal handler executes. If a signal occurs
134 // between a call and an errno check, it's possible to get the errno set
135 // here.
136 // See b/23572286 for extra information.
137 int saved_errno = errno;
138
Narayan Kamath973b4662014-03-31 13:41:26 +0100139 while ((pid = waitpid(-1, &status, WNOHANG)) > 0) {
140 // Log process-death status that we care about. In general it is
141 // not safe to call LOG(...) from a signal handler because of
142 // possible reentrancy. However, we know a priori that the
143 // current implementation of LOG() is safe to call from a SIGCHLD
144 // handler in the zygote process. If the LOG() implementation
145 // changes its locking strategy or its use of syscalls within the
146 // lazy-init critical section, its use here may become unsafe.
147 if (WIFEXITED(status)) {
Josh Gao6d747ca2017-08-02 12:54:05 -0700148 ALOGI("Process %d exited cleanly (%d)", pid, WEXITSTATUS(status));
Narayan Kamath973b4662014-03-31 13:41:26 +0100149 } else if (WIFSIGNALED(status)) {
Josh Gao6d747ca2017-08-02 12:54:05 -0700150 ALOGI("Process %d exited due to signal (%d)", pid, WTERMSIG(status));
Narayan Kamath973b4662014-03-31 13:41:26 +0100151 if (WCOREDUMP(status)) {
152 ALOGI("Process %d dumped core.", pid);
153 }
Narayan Kamath973b4662014-03-31 13:41:26 +0100154 }
155
156 // If the just-crashed process is the system_server, bring down zygote
157 // so that it is restarted by init and system server will be restarted
158 // from there.
159 if (pid == gSystemServerPid) {
Dan Albert46d84442014-11-18 16:07:51 -0800160 ALOGE("Exit zygote because system server (%d) has terminated", pid);
Narayan Kamath973b4662014-03-31 13:41:26 +0100161 kill(getpid(), SIGKILL);
162 }
163 }
164
Narayan Kamath160992d2014-04-14 14:46:07 +0100165 // Note that we shouldn't consider ECHILD an error because
166 // the secondary zygote might have no children left to wait for.
167 if (pid < 0 && errno != ECHILD) {
168 ALOGW("Zygote SIGCHLD error in waitpid: %s", strerror(errno));
Narayan Kamath973b4662014-03-31 13:41:26 +0100169 }
Christopher Ferrisa8a79542015-08-31 15:40:01 -0700170
171 errno = saved_errno;
Narayan Kamath973b4662014-03-31 13:41:26 +0100172}
173
yuanhao435e84b2018-01-15 15:37:02 +0800174// Configures the SIGCHLD/SIGHUP handlers for the zygote process. This is
175// configured very late, because earlier in the runtime we may fork() and
176// exec() other processes, and we want to waitpid() for those rather than
Narayan Kamath973b4662014-03-31 13:41:26 +0100177// have them be harvested immediately.
178//
yuanhao435e84b2018-01-15 15:37:02 +0800179// Ignore SIGHUP because all processes forked by the zygote are in the same
180// process group as the zygote and we don't want to be notified if we become
181// an orphaned group and have one or more stopped processes. This is not a
182// theoretical concern :
183// - we can become an orphaned group if one of our direct descendants forks
184// and is subsequently killed before its children.
185// - crash_dump routinely STOPs the process it's tracing.
186//
187// See issues b/71965619 and b/25567761 for further details.
188//
Narayan Kamath973b4662014-03-31 13:41:26 +0100189// This ends up being called repeatedly before each fork(), but there's
190// no real harm in that.
yuanhao435e84b2018-01-15 15:37:02 +0800191static void SetSignalHandlers() {
192 struct sigaction sig_chld = {};
193 sig_chld.sa_handler = SigChldHandler;
Narayan Kamath973b4662014-03-31 13:41:26 +0100194
yuanhao435e84b2018-01-15 15:37:02 +0800195 if (sigaction(SIGCHLD, &sig_chld, NULL) < 0) {
Elliott Hughes960e8312014-09-30 08:49:01 -0700196 ALOGW("Error setting SIGCHLD handler: %s", strerror(errno));
Narayan Kamath973b4662014-03-31 13:41:26 +0100197 }
yuanhao435e84b2018-01-15 15:37:02 +0800198
199 struct sigaction sig_hup = {};
200 sig_hup.sa_handler = SIG_IGN;
201 if (sigaction(SIGHUP, &sig_hup, NULL) < 0) {
202 ALOGW("Error setting SIGHUP handler: %s", strerror(errno));
203 }
Narayan Kamath973b4662014-03-31 13:41:26 +0100204}
205
206// Sets the SIGCHLD handler back to default behavior in zygote children.
yuanhao435e84b2018-01-15 15:37:02 +0800207static void UnsetChldSignalHandler() {
Narayan Kamath973b4662014-03-31 13:41:26 +0100208 struct sigaction sa;
209 memset(&sa, 0, sizeof(sa));
210 sa.sa_handler = SIG_DFL;
211
yuanhao435e84b2018-01-15 15:37:02 +0800212 if (sigaction(SIGCHLD, &sa, NULL) < 0) {
Elliott Hughes960e8312014-09-30 08:49:01 -0700213 ALOGW("Error unsetting SIGCHLD handler: %s", strerror(errno));
Narayan Kamath973b4662014-03-31 13:41:26 +0100214 }
215}
216
217// Calls POSIX setgroups() using the int[] object as an argument.
218// A NULL argument is tolerated.
Andreas Gamped5758f62018-03-12 12:08:55 -0700219static bool SetGids(JNIEnv* env, jintArray javaGids, std::string* error_msg) {
Narayan Kamath973b4662014-03-31 13:41:26 +0100220 if (javaGids == NULL) {
Andreas Gamped5758f62018-03-12 12:08:55 -0700221 return true;
Narayan Kamath973b4662014-03-31 13:41:26 +0100222 }
223
224 ScopedIntArrayRO gids(env, javaGids);
225 if (gids.get() == NULL) {
Andreas Gamped5758f62018-03-12 12:08:55 -0700226 *error_msg = CREATE_ERROR("Getting gids int array failed");
227 return false;
Narayan Kamath973b4662014-03-31 13:41:26 +0100228 }
229 int rc = setgroups(gids.size(), reinterpret_cast<const gid_t*>(&gids[0]));
230 if (rc == -1) {
Andreas Gamped5758f62018-03-12 12:08:55 -0700231 *error_msg = CREATE_ERROR("setgroups failed: %s, gids.size=%zu", strerror(errno), gids.size());
232 return false;
Narayan Kamath973b4662014-03-31 13:41:26 +0100233 }
Andreas Gamped5758f62018-03-12 12:08:55 -0700234
235 return true;
Narayan Kamath973b4662014-03-31 13:41:26 +0100236}
237
238// Sets the resource limits via setrlimit(2) for the values in the
239// two-dimensional array of integers that's passed in. The second dimension
240// contains a tuple of length 3: (resource, rlim_cur, rlim_max). NULL is
241// treated as an empty array.
Andreas Gamped5758f62018-03-12 12:08:55 -0700242static bool SetRLimits(JNIEnv* env, jobjectArray javaRlimits, std::string* error_msg) {
Narayan Kamath973b4662014-03-31 13:41:26 +0100243 if (javaRlimits == NULL) {
Andreas Gamped5758f62018-03-12 12:08:55 -0700244 return true;
Narayan Kamath973b4662014-03-31 13:41:26 +0100245 }
246
247 rlimit rlim;
248 memset(&rlim, 0, sizeof(rlim));
249
250 for (int i = 0; i < env->GetArrayLength(javaRlimits); ++i) {
251 ScopedLocalRef<jobject> javaRlimitObject(env, env->GetObjectArrayElement(javaRlimits, i));
252 ScopedIntArrayRO javaRlimit(env, reinterpret_cast<jintArray>(javaRlimitObject.get()));
253 if (javaRlimit.size() != 3) {
Andreas Gamped5758f62018-03-12 12:08:55 -0700254 *error_msg = CREATE_ERROR("rlimits array must have a second dimension of size 3");
255 return false;
Narayan Kamath973b4662014-03-31 13:41:26 +0100256 }
257
258 rlim.rlim_cur = javaRlimit[1];
259 rlim.rlim_max = javaRlimit[2];
260
261 int rc = setrlimit(javaRlimit[0], &rlim);
262 if (rc == -1) {
Andreas Gamped5758f62018-03-12 12:08:55 -0700263 *error_msg = CREATE_ERROR("setrlimit(%d, {%ld, %ld}) failed", javaRlimit[0], rlim.rlim_cur,
Dan Albert46d84442014-11-18 16:07:51 -0800264 rlim.rlim_max);
Andreas Gamped5758f62018-03-12 12:08:55 -0700265 return false;
Narayan Kamath973b4662014-03-31 13:41:26 +0100266 }
267 }
Andreas Gamped5758f62018-03-12 12:08:55 -0700268
269 return true;
Narayan Kamath973b4662014-03-31 13:41:26 +0100270}
271
Orion Hodson8d005a62018-12-05 12:28:53 +0000272static void EnableDebugger() {
273 // To let a non-privileged gdbserver attach to this
274 // process, we must set our dumpable flag.
275 if (prctl(PR_SET_DUMPABLE, 1, 0, 0, 0) == -1) {
276 ALOGE("prctl(PR_SET_DUMPABLE) failed");
277 }
278
279 // A non-privileged native debugger should be able to attach to the debuggable app, even if Yama
280 // is enabled (see kernel/Documentation/security/Yama.txt).
281 if (prctl(PR_SET_PTRACER, PR_SET_PTRACER_ANY, 0, 0, 0) == -1) {
282 // if Yama is off prctl(PR_SET_PTRACER) returns EINVAL - don't log in this
283 // case since it's expected behaviour.
284 if (errno != EINVAL) {
285 ALOGE("prctl(PR_SET_PTRACER, PR_SET_PTRACER_ANY) failed");
286 }
287 }
288
Orion Hodson2b71ad02018-12-07 16:44:33 +0000289 // Set the core dump size to zero unless wanted (see also coredump_setup in build/envsetup.sh).
290 if (!GetBoolProperty("persist.zygote.core_dump", false)) {
291 // Set the soft limit on core dump size to 0 without changing the hard limit.
292 rlimit rl;
293 if (getrlimit(RLIMIT_CORE, &rl) == -1) {
294 ALOGE("getrlimit(RLIMIT_CORE) failed");
295 } else {
296 rl.rlim_cur = 0;
297 if (setrlimit(RLIMIT_CORE, &rl) == -1) {
298 ALOGE("setrlimit(RLIMIT_CORE) failed");
299 }
Orion Hodson8d005a62018-12-05 12:28:53 +0000300 }
301 }
302}
303
Narayan Kamath973b4662014-03-31 13:41:26 +0100304// The debug malloc library needs to know whether it's the zygote or a child.
305extern "C" int gMallocLeakZygoteChild;
306
Christopher Ferris76de39e2017-06-20 16:13:40 -0700307static void PreApplicationInit() {
308 // The child process sets this to indicate it's not the zygote.
309 gMallocLeakZygoteChild = 1;
310
311 // Set the jemalloc decay time to 1.
312 mallopt(M_DECAY_TIME, 1);
313}
314
Victor Hsiehc8176ef2018-01-08 12:43:00 -0800315static void SetUpSeccompFilter(uid_t uid) {
316 if (!g_is_security_enforced) {
317 ALOGI("seccomp disabled by setenforce 0");
318 return;
319 }
320
321 // Apply system or app filter based on uid.
Victor Hsiehfa046a12018-03-28 16:26:28 -0700322 if (uid >= AID_APP_START) {
Victor Hsiehc8176ef2018-01-08 12:43:00 -0800323 set_app_seccomp_filter();
324 } else {
325 set_system_seccomp_filter();
326 }
327}
328
Andreas Gamped5758f62018-03-12 12:08:55 -0700329static bool EnableKeepCapabilities(std::string* error_msg) {
Narayan Kamath973b4662014-03-31 13:41:26 +0100330 int rc = prctl(PR_SET_KEEPCAPS, 1, 0, 0, 0);
331 if (rc == -1) {
Andreas Gamped5758f62018-03-12 12:08:55 -0700332 *error_msg = CREATE_ERROR("prctl(PR_SET_KEEPCAPS) failed: %s", strerror(errno));
333 return false;
Narayan Kamath973b4662014-03-31 13:41:26 +0100334 }
Andreas Gamped5758f62018-03-12 12:08:55 -0700335 return true;
Narayan Kamath973b4662014-03-31 13:41:26 +0100336}
337
Andreas Gamped5758f62018-03-12 12:08:55 -0700338static bool DropCapabilitiesBoundingSet(std::string* error_msg) {
Narayan Kamath973b4662014-03-31 13:41:26 +0100339 for (int i = 0; prctl(PR_CAPBSET_READ, i, 0, 0, 0) >= 0; i++) {
340 int rc = prctl(PR_CAPBSET_DROP, i, 0, 0, 0);
341 if (rc == -1) {
342 if (errno == EINVAL) {
343 ALOGE("prctl(PR_CAPBSET_DROP) failed with EINVAL. Please verify "
344 "your kernel is compiled with file capabilities support");
345 } else {
Andreas Gamped5758f62018-03-12 12:08:55 -0700346 *error_msg = CREATE_ERROR("prctl(PR_CAPBSET_DROP, %d) failed: %s", i, strerror(errno));
347 return false;
Narayan Kamath973b4662014-03-31 13:41:26 +0100348 }
349 }
350 }
Andreas Gamped5758f62018-03-12 12:08:55 -0700351 return true;
Narayan Kamath973b4662014-03-31 13:41:26 +0100352}
353
Andreas Gamped5758f62018-03-12 12:08:55 -0700354static bool SetInheritable(uint64_t inheritable, std::string* error_msg) {
Josh Gao45dab782017-02-01 14:56:09 -0800355 __user_cap_header_struct capheader;
356 memset(&capheader, 0, sizeof(capheader));
357 capheader.version = _LINUX_CAPABILITY_VERSION_3;
358 capheader.pid = 0;
359
360 __user_cap_data_struct capdata[2];
361 if (capget(&capheader, &capdata[0]) == -1) {
Andreas Gamped5758f62018-03-12 12:08:55 -0700362 *error_msg = CREATE_ERROR("capget failed: %s", strerror(errno));
363 return false;
Josh Gao45dab782017-02-01 14:56:09 -0800364 }
365
366 capdata[0].inheritable = inheritable;
367 capdata[1].inheritable = inheritable >> 32;
368
369 if (capset(&capheader, &capdata[0]) == -1) {
Andreas Gamped5758f62018-03-12 12:08:55 -0700370 *error_msg = CREATE_ERROR("capset(inh=%" PRIx64 ") failed: %s", inheritable, strerror(errno));
371 return false;
Josh Gao45dab782017-02-01 14:56:09 -0800372 }
Andreas Gamped5758f62018-03-12 12:08:55 -0700373
374 return true;
Josh Gao45dab782017-02-01 14:56:09 -0800375}
376
Andreas Gamped5758f62018-03-12 12:08:55 -0700377static bool SetCapabilities(uint64_t permitted, uint64_t effective, uint64_t inheritable,
378 std::string* error_msg) {
Narayan Kamath973b4662014-03-31 13:41:26 +0100379 __user_cap_header_struct capheader;
380 memset(&capheader, 0, sizeof(capheader));
381 capheader.version = _LINUX_CAPABILITY_VERSION_3;
382 capheader.pid = 0;
383
384 __user_cap_data_struct capdata[2];
385 memset(&capdata, 0, sizeof(capdata));
386 capdata[0].effective = effective;
387 capdata[1].effective = effective >> 32;
388 capdata[0].permitted = permitted;
389 capdata[1].permitted = permitted >> 32;
Josh Gao45dab782017-02-01 14:56:09 -0800390 capdata[0].inheritable = inheritable;
391 capdata[1].inheritable = inheritable >> 32;
Narayan Kamath973b4662014-03-31 13:41:26 +0100392
393 if (capset(&capheader, &capdata[0]) == -1) {
Andreas Gamped5758f62018-03-12 12:08:55 -0700394 *error_msg = CREATE_ERROR("capset(perm=%" PRIx64 ", eff=%" PRIx64 ", inh=%" PRIx64 ") "
395 "failed: %s", permitted, effective, inheritable, strerror(errno));
396 return false;
Narayan Kamath973b4662014-03-31 13:41:26 +0100397 }
Andreas Gamped5758f62018-03-12 12:08:55 -0700398 return true;
Narayan Kamath973b4662014-03-31 13:41:26 +0100399}
400
Andreas Gamped5758f62018-03-12 12:08:55 -0700401static bool SetSchedulerPolicy(std::string* error_msg) {
Narayan Kamath973b4662014-03-31 13:41:26 +0100402 errno = -set_sched_policy(0, SP_DEFAULT);
403 if (errno != 0) {
Andreas Gamped5758f62018-03-12 12:08:55 -0700404 *error_msg = CREATE_ERROR("set_sched_policy(0, SP_DEFAULT) failed: %s", strerror(errno));
405 return false;
Narayan Kamath973b4662014-03-31 13:41:26 +0100406 }
Andreas Gamped5758f62018-03-12 12:08:55 -0700407 return true;
Narayan Kamath973b4662014-03-31 13:41:26 +0100408}
409
Jeff Sharkeyfaf3f692015-06-30 15:56:33 -0700410static int UnmountTree(const char* path) {
411 size_t path_len = strlen(path);
412
413 FILE* fp = setmntent("/proc/mounts", "r");
414 if (fp == NULL) {
415 ALOGE("Error opening /proc/mounts: %s", strerror(errno));
416 return -errno;
417 }
418
419 // Some volumes can be stacked on each other, so force unmount in
420 // reverse order to give us the best chance of success.
421 std::list<std::string> toUnmount;
422 mntent* mentry;
423 while ((mentry = getmntent(fp)) != NULL) {
424 if (strncmp(mentry->mnt_dir, path, path_len) == 0) {
425 toUnmount.push_front(std::string(mentry->mnt_dir));
426 }
427 }
428 endmntent(fp);
429
Chih-Hung Hsieha1b644e2018-12-11 11:09:20 -0800430 for (const auto& path : toUnmount) {
Jeff Sharkeyfaf3f692015-06-30 15:56:33 -0700431 if (umount2(path.c_str(), MNT_DETACH)) {
432 ALOGW("Failed to unmount %s: %s", path.c_str(), strerror(errno));
433 }
434 }
435 return 0;
436}
437
Sudheer Shanka3f0645b2018-09-18 13:07:59 -0700438static bool createPkgSandbox(uid_t uid, const std::string& package_name, std::string* error_msg) {
Sudheer Shanka663b1042018-07-30 17:34:21 -0700439 // Create /mnt/user/0/package/<package-name>
440 userid_t user_id = multiuser_get_user_id(uid);
Sudheer Shanka3f0645b2018-09-18 13:07:59 -0700441 std::string pkg_sandbox_dir = StringPrintf("/mnt/user/%d", user_id);
Sudheer Shanka8d8223e2018-08-03 18:18:21 -0700442 if (fs_prepare_dir(pkg_sandbox_dir.c_str(), 0751, AID_ROOT, AID_ROOT) != 0) {
Sudheer Shanka663b1042018-07-30 17:34:21 -0700443 *error_msg = CREATE_ERROR("fs_prepare_dir failed on %s", pkg_sandbox_dir.c_str());
444 return false;
445 }
446 StringAppendF(&pkg_sandbox_dir, "/package");
447 if (fs_prepare_dir(pkg_sandbox_dir.c_str(), 0700, AID_ROOT, AID_ROOT) != 0) {
448 *error_msg = CREATE_ERROR("fs_prepare_dir failed on %s", pkg_sandbox_dir.c_str());
449 return false;
450 }
Sudheer Shanka3f0645b2018-09-18 13:07:59 -0700451 StringAppendF(&pkg_sandbox_dir, "/%s", package_name.c_str());
Sudheer Shanka663b1042018-07-30 17:34:21 -0700452 if (fs_prepare_dir(pkg_sandbox_dir.c_str(), 0755, uid, uid) != 0) {
453 *error_msg = CREATE_ERROR("fs_prepare_dir failed on %s", pkg_sandbox_dir.c_str());
454 return false;
455 }
456 return true;
457}
458
Sudheer Shanka3a0df3b2018-12-12 12:43:43 -0800459static bool bindMount(const std::string& sourceDir, const std::string& targetDir,
460 std::string* error_msg) {
461 if (TEMP_FAILURE_RETRY(mount(sourceDir.c_str(), targetDir.c_str(),
462 nullptr, MS_BIND | MS_REC, nullptr)) == -1) {
463 *error_msg = CREATE_ERROR("Failed to mount %s to %s: %s",
464 sourceDir.c_str(), targetDir.c_str(), strerror(errno));
465 return false;
466 }
467 if (TEMP_FAILURE_RETRY(mount(nullptr, targetDir.c_str(),
468 nullptr, MS_SLAVE | MS_REC, nullptr)) == -1) {
469 *error_msg = CREATE_ERROR("Failed to set MS_SLAVE for %s", targetDir.c_str());
470 return false;
471 }
472 return true;
473}
474
Sudheer Shanka3f0645b2018-09-18 13:07:59 -0700475static bool mountPkgSpecificDir(const std::string& mntSourceRoot,
476 const std::string& mntTargetRoot, const std::string& packageName,
477 const char* dirName, std::string* error_msg) {
478 std::string mntSourceDir = StringPrintf("%s/Android/%s/%s",
479 mntSourceRoot.c_str(), dirName, packageName.c_str());
480 std::string mntTargetDir = StringPrintf("%s/Android/%s/%s",
481 mntTargetRoot.c_str(), dirName, packageName.c_str());
Sudheer Shanka3a0df3b2018-12-12 12:43:43 -0800482 return bindMount(mntSourceDir, mntTargetDir, error_msg);
Sudheer Shanka3f0645b2018-09-18 13:07:59 -0700483}
484
485static bool preparePkgSpecificDirs(const std::vector<std::string>& packageNames,
Sudheer Shanka3a0df3b2018-12-12 12:43:43 -0800486 const std::vector<std::string>& volumeLabels, bool mountAllObbs,
487 userid_t userId, std::string* error_msg) {
Sudheer Shanka3f0645b2018-09-18 13:07:59 -0700488 for (auto& label : volumeLabels) {
489 std::string mntSource = StringPrintf("/mnt/runtime/write/%s", label.c_str());
490 std::string mntTarget = StringPrintf("/storage/%s", label.c_str());
491 if (label == "emulated") {
492 StringAppendF(&mntSource, "/%d", userId);
493 StringAppendF(&mntTarget, "/%d", userId);
494 }
495 for (auto& package : packageNames) {
496 mountPkgSpecificDir(mntSource, mntTarget, package, "data", error_msg);
497 mountPkgSpecificDir(mntSource, mntTarget, package, "media", error_msg);
Sudheer Shanka3a0df3b2018-12-12 12:43:43 -0800498 if (!mountAllObbs) {
499 mountPkgSpecificDir(mntSource, mntTarget, package, "obb", error_msg);
500 }
501 }
502 if (mountAllObbs) {
503 StringAppendF(&mntSource, "/Android/obb");
504 StringAppendF(&mntTarget, "/Android/obb");
505 bindMount(mntSource, mntTarget, error_msg);
Sudheer Shanka3f0645b2018-09-18 13:07:59 -0700506 }
507 }
508 return true;
509}
510
Narayan Kamath973b4662014-03-31 13:41:26 +0100511// Create a private mount namespace and bind mount appropriate emulated
512// storage for the given user.
Jeff Sharkey9527b222015-06-24 15:24:48 -0700513static bool MountEmulatedStorage(uid_t uid, jint mount_mode,
Sudheer Shanka3f0645b2018-09-18 13:07:59 -0700514 bool force_mount_namespace, std::string* error_msg, const std::string& package_name,
515 const std::vector<std::string>& packages_for_uid,
516 const std::vector<std::string>& visible_vol_ids) {
Jeff Sharkey9527b222015-06-24 15:24:48 -0700517 // See storage config details at http://source.android.com/tech/storage/
518
Jeff Sharkey9527b222015-06-24 15:24:48 -0700519 String8 storageSource;
520 if (mount_mode == MOUNT_EXTERNAL_DEFAULT) {
Jeff Sharkey928e1ec2015-08-06 11:40:21 -0700521 storageSource = "/mnt/runtime/default";
Jeff Sharkey9527b222015-06-24 15:24:48 -0700522 } else if (mount_mode == MOUNT_EXTERNAL_READ) {
Jeff Sharkey928e1ec2015-08-06 11:40:21 -0700523 storageSource = "/mnt/runtime/read";
Jeff Sharkey9527b222015-06-24 15:24:48 -0700524 } else if (mount_mode == MOUNT_EXTERNAL_WRITE) {
Jeff Sharkey928e1ec2015-08-06 11:40:21 -0700525 storageSource = "/mnt/runtime/write";
Sudheer Shanka3a0df3b2018-12-12 12:43:43 -0800526 } else if (mount_mode == MOUNT_EXTERNAL_NONE && !force_mount_namespace) {
Jeff Sharkey9527b222015-06-24 15:24:48 -0700527 // Sane default of no storage visible
528 return true;
529 }
Robert Sesek8a3a6ff2016-10-31 11:25:10 -0400530
531 // Create a second private mount namespace for our process
532 if (unshare(CLONE_NEWNS) == -1) {
Andreas Gamped5758f62018-03-12 12:08:55 -0700533 *error_msg = CREATE_ERROR("Failed to unshare(): %s", strerror(errno));
Robert Sesek8a3a6ff2016-10-31 11:25:10 -0400534 return false;
535 }
536
Robert Sesek06f39302017-03-20 17:30:05 -0400537 // Handle force_mount_namespace with MOUNT_EXTERNAL_NONE.
538 if (mount_mode == MOUNT_EXTERNAL_NONE) {
539 return true;
540 }
541
Sudheer Shanka663b1042018-07-30 17:34:21 -0700542 if (GetBoolProperty(kIsolatedStorage, false)) {
Sudheer Shanka98cb3f02018-08-17 16:10:29 -0700543 if (mount_mode == MOUNT_EXTERNAL_FULL) {
544 storageSource = "/mnt/runtime/write";
545 if (TEMP_FAILURE_RETRY(mount(storageSource.string(), "/storage",
546 NULL, MS_BIND | MS_REC | MS_SLAVE, NULL)) == -1) {
547 *error_msg = CREATE_ERROR("Failed to mount %s to /storage: %s",
548 storageSource.string(),
549 strerror(errno));
550 return false;
551 }
Jeff Sharkey9527b222015-06-24 15:24:48 -0700552
Sudheer Shanka98cb3f02018-08-17 16:10:29 -0700553 // Mount user-specific symlink helper into place
554 userid_t user_id = multiuser_get_user_id(uid);
555 const String8 userSource(String8::format("/mnt/user/%d", user_id));
556 if (fs_prepare_dir(userSource.string(), 0751, 0, 0) == -1) {
557 *error_msg = CREATE_ERROR("fs_prepare_dir failed on %s", userSource.string());
558 return false;
559 }
560 if (TEMP_FAILURE_RETRY(mount(userSource.string(), "/storage/self",
561 NULL, MS_BIND, NULL)) == -1) {
562 *error_msg = CREATE_ERROR("Failed to mount %s to /storage/self: %s",
563 userSource.string(),
564 strerror(errno));
565 return false;
566 }
567 } else {
Sudheer Shanka3f0645b2018-09-18 13:07:59 -0700568 if (package_name.empty()) {
Sudheer Shanka98cb3f02018-08-17 16:10:29 -0700569 return true;
570 }
Sudheer Shanka3f0645b2018-09-18 13:07:59 -0700571 userid_t user_id = multiuser_get_user_id(uid);
572 std::string pkgSandboxDir = StringPrintf("/mnt/user/%d/package/%s",
573 user_id, package_name.c_str());
574 struct stat sb;
575 bool sandboxAlreadyCreated = true;
576 if (TEMP_FAILURE_RETRY(lstat(pkgSandboxDir.c_str(), &sb)) == -1) {
577 if (errno == ENOENT) {
578 ALOGD("Sandbox not yet created for %s", pkgSandboxDir.c_str());
579 sandboxAlreadyCreated = false;
580 if (!createPkgSandbox(uid, package_name, error_msg)) {
581 return false;
582 }
583 } else {
584 ALOGE("Failed to lstat %s", pkgSandboxDir.c_str());
585 return false;
586 }
Sudheer Shanka98cb3f02018-08-17 16:10:29 -0700587 }
588 if (TEMP_FAILURE_RETRY(mount(pkgSandboxDir.c_str(), "/storage",
589 nullptr, MS_BIND | MS_REC | MS_SLAVE, nullptr)) == -1) {
590 *error_msg = CREATE_ERROR("Failed to mount %s to /storage: %s",
591 pkgSandboxDir.c_str(), strerror(errno));
592 return false;
593 }
Sudheer Shanka3a0df3b2018-12-12 12:43:43 -0800594 if (access("/storage/obb_mount", F_OK) == 0) {
595 if (mount_mode != MOUNT_EXTERNAL_INSTALLER) {
596 remove("/storage/obb_mount");
597 }
598 } else {
599 if (mount_mode == MOUNT_EXTERNAL_INSTALLER) {
600 int fd = TEMP_FAILURE_RETRY(open("/storage/obb_mount",
601 O_RDWR | O_CREAT, 0660));
602 if (fd == -1) {
603 *error_msg = CREATE_ERROR("Couldn't create /storage/obb_mount: %s",
604 strerror(errno));
605 return false;
606 }
607 close(fd);
608 }
609 }
Sudheer Shanka3f0645b2018-09-18 13:07:59 -0700610 // If the sandbox was already created by vold, only then set up the bind mounts for
611 // pkg specific directories. Otherwise, leave as is and bind mounts will be taken
612 // care of by vold later.
613 if (sandboxAlreadyCreated) {
614 if (!preparePkgSpecificDirs(packages_for_uid, visible_vol_ids,
Sudheer Shanka3a0df3b2018-12-12 12:43:43 -0800615 mount_mode == MOUNT_EXTERNAL_INSTALLER, user_id, error_msg)) {
Sudheer Shanka3f0645b2018-09-18 13:07:59 -0700616 return false;
617 }
618 }
Sudheer Shanka663b1042018-07-30 17:34:21 -0700619 }
620 } else {
621 if (TEMP_FAILURE_RETRY(mount(storageSource.string(), "/storage",
622 NULL, MS_BIND | MS_REC | MS_SLAVE, NULL)) == -1) {
623 *error_msg = CREATE_ERROR("Failed to mount %s to /storage: %s",
624 storageSource.string(),
625 strerror(errno));
626 return false;
627 }
628
629 // Mount user-specific symlink helper into place
630 userid_t user_id = multiuser_get_user_id(uid);
631 const String8 userSource(String8::format("/mnt/user/%d", user_id));
632 if (fs_prepare_dir(userSource.string(), 0751, 0, 0) == -1) {
633 *error_msg = CREATE_ERROR("fs_prepare_dir failed on %s", userSource.string());
634 return false;
635 }
636 if (TEMP_FAILURE_RETRY(mount(userSource.string(), "/storage/self",
637 NULL, MS_BIND, NULL)) == -1) {
638 *error_msg = CREATE_ERROR("Failed to mount %s to /storage/self: %s",
639 userSource.string(),
640 strerror(errno));
641 return false;
642 }
Jeff Sharkey9527b222015-06-24 15:24:48 -0700643 }
644
Narayan Kamath973b4662014-03-31 13:41:26 +0100645 return true;
Narayan Kamath973b4662014-03-31 13:41:26 +0100646}
647
Narayan Kamath973b4662014-03-31 13:41:26 +0100648static bool NeedsNoRandomizeWorkaround() {
649#if !defined(__arm__)
650 return false;
651#else
652 int major;
653 int minor;
654 struct utsname uts;
655 if (uname(&uts) == -1) {
656 return false;
657 }
658
659 if (sscanf(uts.release, "%d.%d", &major, &minor) != 2) {
660 return false;
661 }
662
663 // Kernels before 3.4.* need the workaround.
664 return (major < 3) || ((major == 3) && (minor < 4));
665#endif
666}
Narayan Kamath973b4662014-03-31 13:41:26 +0100667
668// Utility to close down the Zygote socket file descriptors while
669// the child is still running as root with Zygote's privileges. Each
670// descriptor (if any) is closed via dup2(), replacing it with a valid
671// (open) descriptor to /dev/null.
672
Andreas Gamped5758f62018-03-12 12:08:55 -0700673static bool DetachDescriptors(JNIEnv* env, jintArray fdsToClose, std::string* error_msg) {
Narayan Kamath973b4662014-03-31 13:41:26 +0100674 if (!fdsToClose) {
Andreas Gamped5758f62018-03-12 12:08:55 -0700675 return true;
Narayan Kamath973b4662014-03-31 13:41:26 +0100676 }
677 jsize count = env->GetArrayLength(fdsToClose);
Mykola Kondratenko1ca062f2015-07-31 17:22:26 +0200678 ScopedIntArrayRO ar(env, fdsToClose);
679 if (ar.get() == NULL) {
Andreas Gamped5758f62018-03-12 12:08:55 -0700680 *error_msg = "Bad fd array";
681 return false;
Narayan Kamath973b4662014-03-31 13:41:26 +0100682 }
683 jsize i;
684 int devnull;
685 for (i = 0; i < count; i++) {
686 devnull = open("/dev/null", O_RDWR);
687 if (devnull < 0) {
Andreas Gamped5758f62018-03-12 12:08:55 -0700688 *error_msg = std::string("Failed to open /dev/null: ").append(strerror(errno));
689 return false;
Narayan Kamath973b4662014-03-31 13:41:26 +0100690 }
Elliott Hughes960e8312014-09-30 08:49:01 -0700691 ALOGV("Switching descriptor %d to /dev/null: %s", ar[i], strerror(errno));
Narayan Kamath973b4662014-03-31 13:41:26 +0100692 if (dup2(devnull, ar[i]) < 0) {
Andreas Gamped5758f62018-03-12 12:08:55 -0700693 *error_msg = StringPrintf("Failed dup2() on descriptor %d: %s", ar[i], strerror(errno));
694 return false;
Narayan Kamath973b4662014-03-31 13:41:26 +0100695 }
696 close(devnull);
697 }
Andreas Gamped5758f62018-03-12 12:08:55 -0700698 return true;
Narayan Kamath973b4662014-03-31 13:41:26 +0100699}
700
701void SetThreadName(const char* thread_name) {
702 bool hasAt = false;
703 bool hasDot = false;
704 const char* s = thread_name;
705 while (*s) {
706 if (*s == '.') {
707 hasDot = true;
708 } else if (*s == '@') {
709 hasAt = true;
710 }
711 s++;
712 }
713 const int len = s - thread_name;
714 if (len < 15 || hasAt || !hasDot) {
715 s = thread_name;
716 } else {
717 s = thread_name + len - 15;
718 }
719 // pthread_setname_np fails rather than truncating long strings.
720 char buf[16]; // MAX_TASK_COMM_LEN=16 is hard-coded into bionic
721 strlcpy(buf, s, sizeof(buf)-1);
722 errno = pthread_setname_np(pthread_self(), buf);
723 if (errno != 0) {
Elliott Hughes960e8312014-09-30 08:49:01 -0700724 ALOGW("Unable to set the name of current thread to '%s': %s", buf, strerror(errno));
Narayan Kamath973b4662014-03-31 13:41:26 +0100725 }
Andreas Gampe041483a2018-03-05 13:00:42 -0800726 // Update base::logging default tag.
727 android::base::SetDefaultTag(buf);
Narayan Kamath973b4662014-03-31 13:41:26 +0100728}
729
Narayan Kamathc5f27a72016-08-19 13:45:24 +0100730// The list of open zygote file descriptors.
731static FileDescriptorTable* gOpenFdTable = NULL;
732
Andreas Gamped5758f62018-03-12 12:08:55 -0700733static bool FillFileDescriptorVector(JNIEnv* env,
Chris Wailesaf594fc2018-11-02 11:00:07 -0700734 jintArray managed_fds,
Andreas Gamped5758f62018-03-12 12:08:55 -0700735 std::vector<int>* fds,
736 std::string* error_msg) {
Andreas Gampe8dfa1782017-01-05 12:45:58 -0800737 CHECK(fds != nullptr);
Chris Wailesaf594fc2018-11-02 11:00:07 -0700738 if (managed_fds != nullptr) {
739 ScopedIntArrayRO ar(env, managed_fds);
Andreas Gampe8dfa1782017-01-05 12:45:58 -0800740 if (ar.get() == nullptr) {
Andreas Gamped5758f62018-03-12 12:08:55 -0700741 *error_msg = "Bad fd array";
742 return false;
Andreas Gampe8dfa1782017-01-05 12:45:58 -0800743 }
744 fds->reserve(ar.size());
745 for (size_t i = 0; i < ar.size(); ++i) {
746 fds->push_back(ar[i]);
747 }
748 }
Andreas Gamped5758f62018-03-12 12:08:55 -0700749 return true;
Andreas Gampe8dfa1782017-01-05 12:45:58 -0800750}
751
Chris Wailesaf594fc2018-11-02 11:00:07 -0700752[[noreturn]]
753static void ZygoteFailure(JNIEnv* env,
754 const char* process_name,
755 jstring managed_process_name,
756 const std::string& msg) {
757 std::unique_ptr<ScopedUtfChars> scoped_managed_process_name_ptr = nullptr;
758 if (managed_process_name != nullptr) {
759 scoped_managed_process_name_ptr.reset(new ScopedUtfChars(env, managed_process_name));
760 if (scoped_managed_process_name_ptr->c_str() != nullptr) {
761 process_name = scoped_managed_process_name_ptr->c_str();
David Sehrde8d0bd2018-06-22 10:45:36 -0700762 }
763 }
764
Chris Wailesaf594fc2018-11-02 11:00:07 -0700765 const std::string& error_msg =
766 (process_name == nullptr) ? msg : StringPrintf("(%s) %s", process_name, msg.c_str());
David Sehrde8d0bd2018-06-22 10:45:36 -0700767
Chris Wailesaf594fc2018-11-02 11:00:07 -0700768 env->FatalError(error_msg.c_str());
769 __builtin_unreachable();
770}
David Sehrde8d0bd2018-06-22 10:45:36 -0700771
Chris Wailesaf594fc2018-11-02 11:00:07 -0700772static std::optional<std::string> ExtractJString(JNIEnv* env,
773 const char* process_name,
774 jstring managed_process_name,
775 jstring managed_string) {
776 if (managed_string == nullptr) {
777 return std::optional<std::string>();
778 } else {
779 ScopedUtfChars scoped_string_chars(env, managed_string);
780
781 if (scoped_string_chars.c_str() != nullptr) {
782 return std::optional<std::string>(scoped_string_chars.c_str());
David Sehrde8d0bd2018-06-22 10:45:36 -0700783 } else {
Chris Wailesaf594fc2018-11-02 11:00:07 -0700784 ZygoteFailure(env, process_name, managed_process_name, "Failed to extract JString.");
David Sehrde8d0bd2018-06-22 10:45:36 -0700785 }
786 }
David Sehrde8d0bd2018-06-22 10:45:36 -0700787}
788
Chris Wailesaf594fc2018-11-02 11:00:07 -0700789// Utility routine to fork a zygote.
790static pid_t ForkCommon(JNIEnv* env, bool is_system_server,
791 jintArray managed_fds_to_close, jintArray managed_fds_to_ignore) {
yuanhao435e84b2018-01-15 15:37:02 +0800792 SetSignalHandlers();
Narayan Kamath973b4662014-03-31 13:41:26 +0100793
David Sehrde8d0bd2018-06-22 10:45:36 -0700794 // Block SIGCHLD prior to fork.
Narayan Kamathdfcc79e2016-11-07 16:22:48 +0000795 sigset_t sigchld;
796 sigemptyset(&sigchld);
797 sigaddset(&sigchld, SIGCHLD);
798
Chris Wailesaf594fc2018-11-02 11:00:07 -0700799 // Curry a failure function.
800 auto fail_fn = std::bind(ZygoteFailure, env, is_system_server ? "system_server" : "zygote",
801 nullptr, _1);
Andreas Gamped5758f62018-03-12 12:08:55 -0700802
Narayan Kamathdfcc79e2016-11-07 16:22:48 +0000803 // Temporarily block SIGCHLD during forks. The SIGCHLD handler might
804 // log, which would result in the logging FDs we close being reopened.
805 // This would cause failures because the FDs are not whitelisted.
806 //
807 // Note that the zygote process is single threaded at this point.
808 if (sigprocmask(SIG_BLOCK, &sigchld, nullptr) == -1) {
Andreas Gamped5758f62018-03-12 12:08:55 -0700809 fail_fn(CREATE_ERROR("sigprocmask(SIG_SETMASK, { SIGCHLD }) failed: %s", strerror(errno)));
Narayan Kamathdfcc79e2016-11-07 16:22:48 +0000810 }
811
Narayan Kamath3764a262016-08-30 15:36:19 +0100812 // Close any logging related FDs before we start evaluating the list of
813 // file descriptors.
814 __android_log_close();
Howard Ro27330412018-10-02 12:08:28 -0700815 stats_log_close();
Narayan Kamath3764a262016-08-30 15:36:19 +0100816
Chris Wailesaf594fc2018-11-02 11:00:07 -0700817 // If this is the first fork for this zygote, create the open FD table. If
818 // it isn't, we just need to check whether the list of open files has changed
819 // (and it shouldn't in the normal case).
Andreas Gamped5758f62018-03-12 12:08:55 -0700820 std::string error_msg;
Andreas Gampe8dfa1782017-01-05 12:45:58 -0800821 std::vector<int> fds_to_ignore;
Chris Wailesaf594fc2018-11-02 11:00:07 -0700822 if (!FillFileDescriptorVector(env, managed_fds_to_ignore, &fds_to_ignore, &error_msg)) {
Andreas Gamped5758f62018-03-12 12:08:55 -0700823 fail_fn(error_msg);
824 }
Chris Wailesaf594fc2018-11-02 11:00:07 -0700825
826 if (gOpenFdTable == nullptr) {
Andreas Gampec362a442018-03-12 14:53:34 -0700827 gOpenFdTable = FileDescriptorTable::Create(fds_to_ignore, &error_msg);
Chris Wailesaf594fc2018-11-02 11:00:07 -0700828 if (gOpenFdTable == nullptr) {
Andreas Gampec362a442018-03-12 14:53:34 -0700829 fail_fn(error_msg);
Narayan Kamathc5f27a72016-08-19 13:45:24 +0100830 }
Andreas Gampec362a442018-03-12 14:53:34 -0700831 } else if (!gOpenFdTable->Restat(fds_to_ignore, &error_msg)) {
832 fail_fn(error_msg);
Narayan Kamathc5f27a72016-08-19 13:45:24 +0100833 }
834
Josh Gaod7951102018-06-26 16:05:12 -0700835 android_fdsan_error_level fdsan_error_level = android_fdsan_get_error_level();
836
Narayan Kamath973b4662014-03-31 13:41:26 +0100837 pid_t pid = fork();
838
839 if (pid == 0) {
David Sehrde8d0bd2018-06-22 10:45:36 -0700840 // The child process.
Christopher Ferris76de39e2017-06-20 16:13:40 -0700841 PreApplicationInit();
Christopher Ferrisab16dd12017-05-15 16:50:29 -0700842
Narayan Kamath973b4662014-03-31 13:41:26 +0100843 // Clean up any descriptors which must be closed immediately
Chris Wailesaf594fc2018-11-02 11:00:07 -0700844 if (!DetachDescriptors(env, managed_fds_to_close, &error_msg)) {
Andreas Gamped5758f62018-03-12 12:08:55 -0700845 fail_fn(error_msg);
846 }
Narayan Kamath973b4662014-03-31 13:41:26 +0100847
Narayan Kamathc5f27a72016-08-19 13:45:24 +0100848 // Re-open all remaining open file descriptors so that they aren't shared
849 // with the zygote across a fork.
Andreas Gampec362a442018-03-12 14:53:34 -0700850 if (!gOpenFdTable->ReopenOrDetach(&error_msg)) {
851 fail_fn(error_msg);
Narayan Kamathc5f27a72016-08-19 13:45:24 +0100852 }
Josh Gaod7951102018-06-26 16:05:12 -0700853
854 // Turn fdsan back on.
855 android_fdsan_set_error_level(fdsan_error_level);
David Sehrde8d0bd2018-06-22 10:45:36 -0700856 }
Narayan Kamathc5f27a72016-08-19 13:45:24 +0100857
David Sehrde8d0bd2018-06-22 10:45:36 -0700858 // We blocked SIGCHLD prior to a fork, we unblock it here.
859 if (sigprocmask(SIG_UNBLOCK, &sigchld, nullptr) == -1) {
860 fail_fn(CREATE_ERROR("sigprocmask(SIG_SETMASK, { SIGCHLD }) failed: %s", strerror(errno)));
Narayan Kamath973b4662014-03-31 13:41:26 +0100861 }
Chris Wailesaf594fc2018-11-02 11:00:07 -0700862
Narayan Kamath973b4662014-03-31 13:41:26 +0100863 return pid;
864}
Luis Hector Chavez72042c92017-07-12 10:03:30 -0700865
Chris Wailesaf594fc2018-11-02 11:00:07 -0700866// Utility routine to specialize a zygote child process.
867static void SpecializeCommon(JNIEnv* env, uid_t uid, gid_t gid, jintArray gids,
868 jint runtime_flags, jobjectArray rlimits,
869 jlong permitted_capabilities, jlong effective_capabilities,
870 jint mount_external, jstring managed_se_info,
871 jstring managed_nice_name, bool is_system_server,
872 bool is_child_zygote, jstring managed_instruction_set,
873 jstring managed_app_data_dir, jstring managed_package_name,
874 jobjectArray managed_pacakges_for_uid,
875 jobjectArray managed_visible_vol_ids) {
876 auto fail_fn = std::bind(ZygoteFailure, env, is_system_server ? "system_server" : "zygote",
877 managed_nice_name, _1);
878 auto extract_fn = std::bind(ExtractJString, env, is_system_server ? "system_server" : "zygote",
879 managed_nice_name, _1);
880
881 auto se_info = extract_fn(managed_se_info);
882 auto nice_name = extract_fn(managed_nice_name);
883 auto instruction_set = extract_fn(managed_instruction_set);
884 auto app_data_dir = extract_fn(managed_app_data_dir);
885 auto package_name = extract_fn(managed_package_name);
886
887 std::string error_msg;
888
889 // Keep capabilities across UID change, unless we're staying root.
890 if (uid != 0) {
891 if (!EnableKeepCapabilities(&error_msg)) {
892 fail_fn(error_msg);
893 }
894 }
895
896 if (!SetInheritable(permitted_capabilities, &error_msg)) {
897 fail_fn(error_msg);
898 }
899
900 if (!DropCapabilitiesBoundingSet(&error_msg)) {
901 fail_fn(error_msg);
902 }
903
904 bool use_native_bridge = !is_system_server &&
905 instruction_set.has_value() &&
906 android::NativeBridgeAvailable() &&
907 android::NeedsNativeBridge(instruction_set.value().c_str());
908
909 if (use_native_bridge && !app_data_dir.has_value()) {
910 // The app_data_dir variable should never be empty if we need to use a
911 // native bridge. In general, app_data_dir will never be empty for normal
912 // applications. It can only happen in special cases (for isolated
913 // processes which are not associated with any app). These are launched by
914 // the framework and should not be emulated anyway.
915 use_native_bridge = false;
916 ALOGW("Native bridge will not be used because managed_app_data_dir == nullptr.");
917 }
918
919 if (!package_name.has_value()) {
920 if (is_system_server) {
921 package_name.emplace("android");
922 } else {
923 package_name.emplace("");
924 }
925 }
926
927 std::vector<std::string> packages_for_uid;
928 if (managed_pacakges_for_uid != nullptr) {
929 jsize count = env->GetArrayLength(managed_pacakges_for_uid);
930 for (jsize package_index = 0; package_index < count; ++package_index) {
931 jstring managed_package_for_uid =
932 (jstring) env->GetObjectArrayElement(managed_pacakges_for_uid, package_index);
933
934 auto package_for_uid = extract_fn(managed_package_for_uid);
935 if (LIKELY(package_for_uid.has_value())) {
936 packages_for_uid.emplace_back(std::move(package_for_uid.value()));
937 } else {
938 fail_fn("Null string found in managed packages_for_uid.");
939 }
940 }
941 }
942
943 std::vector<std::string> visible_vol_ids;
944 if (managed_visible_vol_ids != nullptr) {
945 jsize count = env->GetArrayLength(managed_visible_vol_ids);
946 for (jsize vol_id_index = 0; vol_id_index < count; ++vol_id_index) {
947 jstring managed_visible_vol_id =
948 (jstring) env->GetObjectArrayElement(managed_visible_vol_ids, vol_id_index);
949
950 auto visible_vol_id = extract_fn(managed_visible_vol_id);
951 if (LIKELY(visible_vol_id.has_value())) {
952 visible_vol_ids.emplace_back(std::move(visible_vol_id.value()));
953 } else {
954 fail_fn("Null string found in managed visible_vol_ids.");
955 }
956 }
957 }
958
959 if (!MountEmulatedStorage(uid, mount_external, use_native_bridge, &error_msg,
960 package_name.value(), packages_for_uid, visible_vol_ids)) {
961 ALOGW("Failed to mount emulated storage: %s (%s)", error_msg.c_str(), strerror(errno));
962 if (errno == ENOTCONN || errno == EROFS) {
963 // When device is actively encrypting, we get ENOTCONN here
964 // since FUSE was mounted before the framework restarted.
965 // When encrypted device is booting, we get EROFS since
966 // FUSE hasn't been created yet by init.
967 // In either case, continue without external storage.
968 } else {
969 fail_fn(error_msg);
970 }
971 }
972
973 // If this zygote isn't root, it won't be able to create a process group,
974 // since the directory is owned by root.
975 if (!is_system_server && getuid() == 0) {
976 int rc = createProcessGroup(uid, getpid());
977 if (rc == -EROFS) {
978 ALOGW("createProcessGroup failed, kernel missing CONFIG_CGROUP_CPUACCT?");
979 } else if (rc != 0) {
980 ALOGE("createProcessGroup(%d, %d) failed: %s", uid, /* pid= */ 0, strerror(-rc));
981 }
982 }
983
984 if (!SetGids(env, gids, &error_msg)) {
985 fail_fn(error_msg);
986 }
987
988 if (!SetRLimits(env, rlimits, &error_msg)) {
989 fail_fn(error_msg);
990 }
991
992 if (use_native_bridge) {
993 // Due to the logic behind use_native_bridge we know that both app_data_dir
994 // and instruction_set contain values.
995 android::PreInitializeNativeBridge(app_data_dir.value().c_str(),
996 instruction_set.value().c_str());
997 }
998
999 if (setresgid(gid, gid, gid) == -1) {
1000 fail_fn(CREATE_ERROR("setresgid(%d) failed: %s", gid, strerror(errno)));
1001 }
1002
1003 // Must be called when the new process still has CAP_SYS_ADMIN, in this case,
1004 // before changing uid from 0, which clears capabilities. The other
1005 // alternative is to call prctl(PR_SET_NO_NEW_PRIVS, 1) afterward, but that
1006 // breaks SELinux domain transition (see b/71859146). As the result,
1007 // privileged syscalls used below still need to be accessible in app process.
1008 SetUpSeccompFilter(uid);
1009
1010 if (setresuid(uid, uid, uid) == -1) {
1011 fail_fn(CREATE_ERROR("setresuid(%d) failed: %s", uid, strerror(errno)));
1012 }
1013
1014 // The "dumpable" flag of a process, which controls core dump generation, is
1015 // overwritten by the value in /proc/sys/fs/suid_dumpable when the effective
1016 // user or group ID changes. See proc(5) for possible values. In most cases,
1017 // the value is 0, so core dumps are disabled for zygote children. However,
1018 // when running in a Chrome OS container, the value is already set to 2,
1019 // which allows the external crash reporter to collect all core dumps. Since
1020 // only system crashes are interested, core dump is disabled for app
1021 // processes. This also ensures compliance with CTS.
1022 int dumpable = prctl(PR_GET_DUMPABLE);
1023 if (dumpable == -1) {
1024 ALOGE("prctl(PR_GET_DUMPABLE) failed: %s", strerror(errno));
1025 RuntimeAbort(env, __LINE__, "prctl(PR_GET_DUMPABLE) failed");
1026 }
1027
1028 if (dumpable == 2 && uid >= AID_APP) {
1029 if (prctl(PR_SET_DUMPABLE, 0, 0, 0, 0) == -1) {
1030 ALOGE("prctl(PR_SET_DUMPABLE, 0) failed: %s", strerror(errno));
1031 RuntimeAbort(env, __LINE__, "prctl(PR_SET_DUMPABLE, 0) failed");
1032 }
1033 }
1034
Orion Hodson8d005a62018-12-05 12:28:53 +00001035 // Set process properties to enable debugging if required.
1036 if ((runtime_flags & RuntimeFlags::DEBUG_ENABLE_JDWP) != 0) {
1037 EnableDebugger();
1038 }
1039
Chris Wailesaf594fc2018-11-02 11:00:07 -07001040 if (NeedsNoRandomizeWorkaround()) {
1041 // Work around ARM kernel ASLR lossage (http://b/5817320).
1042 int old_personality = personality(0xffffffff);
1043 int new_personality = personality(old_personality | ADDR_NO_RANDOMIZE);
1044 if (new_personality == -1) {
1045 ALOGW("personality(%d) failed: %s", new_personality, strerror(errno));
1046 }
1047 }
1048
1049 if (!SetCapabilities(permitted_capabilities, effective_capabilities, permitted_capabilities,
1050 &error_msg)) {
1051 fail_fn(error_msg);
1052 }
1053
1054 if (!SetSchedulerPolicy(&error_msg)) {
1055 fail_fn(error_msg);
1056 }
1057
1058 const char* se_info_ptr = se_info.has_value() ? se_info.value().c_str() : nullptr;
1059 const char* nice_name_ptr = nice_name.has_value() ? nice_name.value().c_str() : nullptr;
1060
1061 if (selinux_android_setcontext(uid, is_system_server, se_info_ptr, nice_name_ptr) == -1) {
1062 fail_fn(CREATE_ERROR("selinux_android_setcontext(%d, %d, \"%s\", \"%s\") failed",
1063 uid, is_system_server, se_info_ptr, nice_name_ptr));
1064 }
1065
1066 // Make it easier to debug audit logs by setting the main thread's name to the
1067 // nice name rather than "app_process".
1068 if (nice_name.has_value()) {
1069 SetThreadName(nice_name.value().c_str());
1070 } else if (is_system_server) {
1071 SetThreadName("system_server");
1072 }
1073
1074 // Unset the SIGCHLD handler, but keep ignoring SIGHUP (rationale in SetSignalHandlers).
1075 UnsetChldSignalHandler();
1076
1077 if (is_system_server) {
1078 env->CallStaticVoidMethod(gZygoteClass, gCallPostForkSystemServerHooks);
1079 if (env->ExceptionCheck()) {
1080 fail_fn("Error calling post fork system server hooks.");
1081 }
1082 // TODO(oth): Remove hardcoded label here (b/117874058).
1083 static const char* kSystemServerLabel = "u:r:system_server:s0";
1084 if (selinux_android_setcon(kSystemServerLabel) != 0) {
1085 fail_fn(CREATE_ERROR("selinux_android_setcon(%s)", kSystemServerLabel));
1086 }
1087 }
1088
1089 env->CallStaticVoidMethod(gZygoteClass, gCallPostForkChildHooks, runtime_flags,
1090 is_system_server, is_child_zygote, managed_instruction_set);
1091
1092 if (env->ExceptionCheck()) {
1093 fail_fn("Error calling post fork hooks.");
1094 }
1095}
1096
Luis Hector Chavez72042c92017-07-12 10:03:30 -07001097static uint64_t GetEffectiveCapabilityMask(JNIEnv* env) {
1098 __user_cap_header_struct capheader;
1099 memset(&capheader, 0, sizeof(capheader));
1100 capheader.version = _LINUX_CAPABILITY_VERSION_3;
1101 capheader.pid = 0;
1102
1103 __user_cap_data_struct capdata[2];
1104 if (capget(&capheader, &capdata[0]) == -1) {
1105 ALOGE("capget failed: %s", strerror(errno));
1106 RuntimeAbort(env, __LINE__, "capget failed");
1107 }
1108
Chris Wailesaf594fc2018-11-02 11:00:07 -07001109 return capdata[0].effective | (static_cast<uint64_t>(capdata[1].effective) << 32);
1110}
1111
1112static jlong CalculateCapabilities(JNIEnv* env, jint uid, jint gid, jintArray gids,
1113 bool is_child_zygote) {
1114 jlong capabilities = 0;
1115
1116 /*
1117 * Grant the following capabilities to the Bluetooth user:
1118 * - CAP_WAKE_ALARM
1119 * - CAP_NET_RAW
1120 * - CAP_NET_BIND_SERVICE (for DHCP client functionality)
1121 * - CAP_SYS_NICE (for setting RT priority for audio-related threads)
1122 */
1123
1124 if (multiuser_get_app_id(uid) == AID_BLUETOOTH) {
1125 capabilities |= (1LL << CAP_WAKE_ALARM);
1126 capabilities |= (1LL << CAP_NET_RAW);
1127 capabilities |= (1LL << CAP_NET_BIND_SERVICE);
1128 capabilities |= (1LL << CAP_SYS_NICE);
1129 }
1130
Remi NGUYEN VANc094a542018-12-07 16:52:24 +09001131 if (multiuser_get_app_id(uid) == AID_NETWORK_STACK) {
1132 capabilities |= (1LL << CAP_NET_ADMIN);
1133 capabilities |= (1LL << CAP_NET_BROADCAST);
1134 capabilities |= (1LL << CAP_NET_BIND_SERVICE);
1135 capabilities |= (1LL << CAP_NET_RAW);
1136 }
1137
Chris Wailesaf594fc2018-11-02 11:00:07 -07001138 /*
1139 * Grant CAP_BLOCK_SUSPEND to processes that belong to GID "wakelock"
1140 */
1141
1142 bool gid_wakelock_found = false;
1143 if (gid == AID_WAKELOCK) {
1144 gid_wakelock_found = true;
1145 } else if (gids != nullptr) {
1146 jsize gids_num = env->GetArrayLength(gids);
1147 ScopedIntArrayRO native_gid_proxy(env, gids);
1148
1149 if (native_gid_proxy.get() == nullptr) {
1150 RuntimeAbort(env, __LINE__, "Bad gids array");
1151 }
1152
1153 for (int gid_index = gids_num; --gids_num >= 0;) {
1154 if (native_gid_proxy[gid_index] == AID_WAKELOCK) {
1155 gid_wakelock_found = true;
1156 break;
1157 }
1158 }
1159 }
1160
1161 if (gid_wakelock_found) {
1162 capabilities |= (1LL << CAP_BLOCK_SUSPEND);
1163 }
1164
1165 /*
1166 * Grant child Zygote processes the following capabilities:
1167 * - CAP_SETUID (change UID of child processes)
1168 * - CAP_SETGID (change GID of child processes)
1169 * - CAP_SETPCAP (change capabilities of child processes)
1170 */
1171
1172 if (is_child_zygote) {
1173 capabilities |= (1LL << CAP_SETUID);
1174 capabilities |= (1LL << CAP_SETGID);
1175 capabilities |= (1LL << CAP_SETPCAP);
1176 }
1177
1178 /*
1179 * Containers run without some capabilities, so drop any caps that are not
1180 * available.
1181 */
1182
1183 return capabilities & GetEffectiveCapabilityMask(env);
Luis Hector Chavez72042c92017-07-12 10:03:30 -07001184}
Narayan Kamath973b4662014-03-31 13:41:26 +01001185} // anonymous namespace
1186
1187namespace android {
1188
Victor Hsiehc8176ef2018-01-08 12:43:00 -08001189static void com_android_internal_os_Zygote_nativeSecurityInit(JNIEnv*, jclass) {
Chris Wailesaf594fc2018-11-02 11:00:07 -07001190 // security_getenforce is not allowed on app process. Initialize and cache
1191 // the value before zygote forks.
Victor Hsiehc8176ef2018-01-08 12:43:00 -08001192 g_is_security_enforced = security_getenforce();
1193}
1194
Christopher Ferris76de39e2017-06-20 16:13:40 -07001195static void com_android_internal_os_Zygote_nativePreApplicationInit(JNIEnv*, jclass) {
1196 PreApplicationInit();
1197}
1198
Narayan Kamath973b4662014-03-31 13:41:26 +01001199static jint com_android_internal_os_Zygote_nativeForkAndSpecialize(
1200 JNIEnv* env, jclass, jint uid, jint gid, jintArray gids,
Nicolas Geoffray81edac42017-09-07 14:13:29 +01001201 jint runtime_flags, jobjectArray rlimits,
Chris Wailesaf594fc2018-11-02 11:00:07 -07001202 jint mount_external, jstring se_info, jstring nice_name,
1203 jintArray fds_to_close, jintArray fds_to_ignore, jboolean is_child_zygote,
1204 jstring instruction_set, jstring app_data_dir, jstring package_name,
1205 jobjectArray packages_for_uid, jobjectArray visible_vol_ids) {
1206 jlong capabilities = CalculateCapabilities(env, uid, gid, gids, is_child_zygote);
Pavlin Radoslavovfbd59042015-11-23 17:13:25 -08001207
Chris Wailesaf594fc2018-11-02 11:00:07 -07001208 pid_t pid = ForkCommon(env, false, fds_to_close, fds_to_ignore);
David Sehrde8d0bd2018-06-22 10:45:36 -07001209 if (pid == 0) {
1210 SpecializeCommon(env, uid, gid, gids, runtime_flags, rlimits,
1211 capabilities, capabilities,
Chris Wailesaf594fc2018-11-02 11:00:07 -07001212 mount_external, se_info, nice_name, false,
1213 is_child_zygote == JNI_TRUE, instruction_set, app_data_dir,
1214 package_name, packages_for_uid, visible_vol_ids);
David Sehrde8d0bd2018-06-22 10:45:36 -07001215 }
1216 return pid;
Narayan Kamath973b4662014-03-31 13:41:26 +01001217}
1218
1219static jint com_android_internal_os_Zygote_nativeForkSystemServer(
1220 JNIEnv* env, jclass, uid_t uid, gid_t gid, jintArray gids,
Chris Wailesaf594fc2018-11-02 11:00:07 -07001221 jint runtime_flags, jobjectArray rlimits, jlong permitted_capabilities,
1222 jlong effective_capabilities) {
1223 pid_t pid = ForkCommon(env, true,
1224 /* managed_fds_to_close= */ nullptr,
1225 /* managed_fds_to_ignore= */ nullptr);
David Sehrde8d0bd2018-06-22 10:45:36 -07001226 if (pid == 0) {
1227 SpecializeCommon(env, uid, gid, gids, runtime_flags, rlimits,
Chris Wailesaf594fc2018-11-02 11:00:07 -07001228 permitted_capabilities, effective_capabilities,
1229 MOUNT_EXTERNAL_DEFAULT, nullptr, nullptr, true,
1230 false, nullptr, nullptr, nullptr, nullptr, nullptr);
David Sehrde8d0bd2018-06-22 10:45:36 -07001231 } else if (pid > 0) {
Narayan Kamath973b4662014-03-31 13:41:26 +01001232 // The zygote process checks whether the child process has died or not.
1233 ALOGI("System server process %d has been created", pid);
1234 gSystemServerPid = pid;
1235 // There is a slight window that the system server process has crashed
1236 // but it went unnoticed because we haven't published its pid yet. So
1237 // we recheck here just to make sure that all is well.
1238 int status;
1239 if (waitpid(pid, &status, WNOHANG) == pid) {
1240 ALOGE("System server process %d has died. Restarting Zygote!", pid);
Andreas Gampeb053cce2015-11-17 16:38:59 -08001241 RuntimeAbort(env, __LINE__, "System server process has died. Restarting Zygote!");
Narayan Kamath973b4662014-03-31 13:41:26 +01001242 }
Carmen Jacksondd401252017-02-23 15:21:10 -08001243
Minchan Kim5fa8af22018-06-27 11:32:40 +09001244 bool low_ram_device = GetBoolProperty("ro.config.low_ram", false);
1245 bool per_app_memcg = GetBoolProperty("ro.config.per_app_memcg", low_ram_device);
1246 if (per_app_memcg) {
1247 // Assign system_server to the correct memory cgroup.
1248 // Not all devices mount /dev/memcg so check for the file first
1249 // to avoid unnecessarily printing errors and denials in the logs.
1250 if (!access("/dev/memcg/system/tasks", F_OK) &&
Jeff Vander Stoep6bdc3a22017-11-22 23:09:23 -08001251 !WriteStringToFile(StringPrintf("%d", pid), "/dev/memcg/system/tasks")) {
Minchan Kim5fa8af22018-06-27 11:32:40 +09001252 ALOGE("couldn't write %d to /dev/memcg/system/tasks", pid);
1253 }
Carmen Jacksondd401252017-02-23 15:21:10 -08001254 }
Narayan Kamath973b4662014-03-31 13:41:26 +01001255 }
1256 return pid;
1257}
1258
Robert Sesek54e387d2016-12-02 17:27:50 -05001259static void com_android_internal_os_Zygote_nativeAllowFileAcrossFork(
1260 JNIEnv* env, jclass, jstring path) {
1261 ScopedUtfChars path_native(env, path);
1262 const char* path_cstr = path_native.c_str();
1263 if (!path_cstr) {
Chris Wailesaf594fc2018-11-02 11:00:07 -07001264 RuntimeAbort(env, __LINE__, "path_cstr == nullptr");
Robert Sesek54e387d2016-12-02 17:27:50 -05001265 }
1266 FileDescriptorWhitelist::Get()->Allow(path_cstr);
1267}
1268
doheon1.lee885b7422016-01-20 13:07:27 +09001269static void com_android_internal_os_Zygote_nativeUnmountStorageOnInit(JNIEnv* env, jclass) {
1270 // Zygote process unmount root storage space initially before every child processes are forked.
1271 // Every forked child processes (include SystemServer) only mount their own root storage space
Robert Seseke4f8d692016-09-13 19:13:01 -04001272 // and no need unmount storage operation in MountEmulatedStorage method.
1273 // Zygote process does not utilize root storage spaces and unshares its mount namespace below.
1274
1275 // See storage config details at http://source.android.com/tech/storage/
1276 // Create private mount namespace shared by all children
1277 if (unshare(CLONE_NEWNS) == -1) {
1278 RuntimeAbort(env, __LINE__, "Failed to unshare()");
1279 return;
1280 }
1281
1282 // Mark rootfs as being a slave so that changes from default
1283 // namespace only flow into our children.
1284 if (mount("rootfs", "/", nullptr, (MS_SLAVE | MS_REC), nullptr) == -1) {
1285 RuntimeAbort(env, __LINE__, "Failed to mount() rootfs as MS_SLAVE");
1286 return;
1287 }
1288
1289 // Create a staging tmpfs that is shared by our children; they will
1290 // bind mount storage into their respective private namespaces, which
1291 // are isolated from each other.
1292 const char* target_base = getenv("EMULATED_STORAGE_TARGET");
1293 if (target_base != nullptr) {
1294#define STRINGIFY_UID(x) __STRING(x)
1295 if (mount("tmpfs", target_base, "tmpfs", MS_NOSUID | MS_NODEV,
1296 "uid=0,gid=" STRINGIFY_UID(AID_SDCARD_R) ",mode=0751") == -1) {
1297 ALOGE("Failed to mount tmpfs to %s", target_base);
1298 RuntimeAbort(env, __LINE__, "Failed to mount tmpfs");
1299 return;
1300 }
1301#undef STRINGIFY_UID
1302 }
doheon1.lee885b7422016-01-20 13:07:27 +09001303
1304 UnmountTree("/storage");
doheon1.lee885b7422016-01-20 13:07:27 +09001305}
1306
Daniel Micay76f6a862015-09-19 17:31:01 -04001307static const JNINativeMethod gMethods[] = {
Victor Hsiehc8176ef2018-01-08 12:43:00 -08001308 { "nativeSecurityInit", "()V",
1309 (void *) com_android_internal_os_Zygote_nativeSecurityInit },
Andreas Gampeaec67dc2014-09-02 21:23:06 -07001310 { "nativeForkAndSpecialize",
Sudheer Shanka3f0645b2018-09-18 13:07:59 -07001311 "(II[II[[IILjava/lang/String;Ljava/lang/String;[I[IZLjava/lang/String;Ljava/lang/String;Ljava/lang/String;[Ljava/lang/String;[Ljava/lang/String;)I",
Narayan Kamath973b4662014-03-31 13:41:26 +01001312 (void *) com_android_internal_os_Zygote_nativeForkAndSpecialize },
1313 { "nativeForkSystemServer", "(II[II[[IJJ)I",
doheon1.lee885b7422016-01-20 13:07:27 +09001314 (void *) com_android_internal_os_Zygote_nativeForkSystemServer },
Robert Sesek54e387d2016-12-02 17:27:50 -05001315 { "nativeAllowFileAcrossFork", "(Ljava/lang/String;)V",
1316 (void *) com_android_internal_os_Zygote_nativeAllowFileAcrossFork },
doheon1.lee885b7422016-01-20 13:07:27 +09001317 { "nativeUnmountStorageOnInit", "()V",
Christopher Ferris76de39e2017-06-20 16:13:40 -07001318 (void *) com_android_internal_os_Zygote_nativeUnmountStorageOnInit },
1319 { "nativePreApplicationInit", "()V",
1320 (void *) com_android_internal_os_Zygote_nativePreApplicationInit }
Narayan Kamath973b4662014-03-31 13:41:26 +01001321};
1322
1323int register_com_android_internal_os_Zygote(JNIEnv* env) {
Andreas Gampeed6b9df2014-11-20 22:02:20 -08001324 gZygoteClass = MakeGlobalRefOrDie(env, FindClassOrDie(env, kZygoteClassName));
Orion Hodson46724e72018-10-19 13:05:33 +01001325 gCallPostForkSystemServerHooks = GetStaticMethodIDOrDie(env, gZygoteClass,
1326 "callPostForkSystemServerHooks",
1327 "()V");
Andreas Gampeed6b9df2014-11-20 22:02:20 -08001328 gCallPostForkChildHooks = GetStaticMethodIDOrDie(env, gZygoteClass, "callPostForkChildHooks",
Robert Sesekd0a190df2018-02-12 18:46:01 -05001329 "(IZZLjava/lang/String;)V");
Narayan Kamath973b4662014-03-31 13:41:26 +01001330
Andreas Gampeed6b9df2014-11-20 22:02:20 -08001331 return RegisterMethodsOrDie(env, "com/android/internal/os/Zygote", gMethods, NELEM(gMethods));
Narayan Kamath973b4662014-03-31 13:41:26 +01001332}
1333} // namespace android