1 // Copyright 2017 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #include "base/android/jni_array.h"
6 #include "base/android/jni_string.h"
7 #include "base/android/library_loader/library_loader_hooks.h"
8 #include "base/file_descriptor_store.h"
9 #include "base/logging.h"
10 #include "base/macros.h"
11 #include "base/optional.h"
12 #include "base/posix/global_descriptors.h"
13 #include "jni/ChildProcessService_jni.h"
14
15 using base::android::JavaIntArrayToIntVector;
16 using base::android::JavaParamRef;
17
18 namespace base {
19 namespace android {
20
JNI_ChildProcessService_RegisterFileDescriptors(JNIEnv * env,const JavaParamRef<jclass> & clazz,const JavaParamRef<jobjectArray> & j_keys,const JavaParamRef<jintArray> & j_ids,const JavaParamRef<jintArray> & j_fds,const JavaParamRef<jlongArray> & j_offsets,const JavaParamRef<jlongArray> & j_sizes)21 void JNI_ChildProcessService_RegisterFileDescriptors(
22 JNIEnv* env,
23 const JavaParamRef<jclass>& clazz,
24 const JavaParamRef<jobjectArray>& j_keys,
25 const JavaParamRef<jintArray>& j_ids,
26 const JavaParamRef<jintArray>& j_fds,
27 const JavaParamRef<jlongArray>& j_offsets,
28 const JavaParamRef<jlongArray>& j_sizes) {
29 std::vector<base::Optional<std::string>> keys;
30 jsize keys_size = env->GetArrayLength(j_keys);
31 keys.reserve(keys_size);
32 for (jsize i = 0; i < keys_size; i++) {
33 base::android::ScopedJavaLocalRef<jstring> str(
34 env, static_cast<jstring>(env->GetObjectArrayElement(j_keys, i)));
35 base::Optional<std::string> key;
36 if (!str.is_null()) {
37 key = base::android::ConvertJavaStringToUTF8(env, str);
38 }
39 keys.push_back(std::move(key));
40 }
41
42 std::vector<int> ids;
43 base::android::JavaIntArrayToIntVector(env, j_ids, &ids);
44 std::vector<int> fds;
45 base::android::JavaIntArrayToIntVector(env, j_fds, &fds);
46 std::vector<int64_t> offsets;
47 base::android::JavaLongArrayToInt64Vector(env, j_offsets, &offsets);
48 std::vector<int64_t> sizes;
49 base::android::JavaLongArrayToInt64Vector(env, j_sizes, &sizes);
50
51 DCHECK_EQ(keys.size(), ids.size());
52 DCHECK_EQ(ids.size(), fds.size());
53 DCHECK_EQ(fds.size(), offsets.size());
54 DCHECK_EQ(offsets.size(), sizes.size());
55
56 for (size_t i = 0; i < ids.size(); i++) {
57 base::MemoryMappedFile::Region region = {offsets.at(i), sizes.at(i)};
58 const base::Optional<std::string>& key = keys.at(i);
59 int id = ids.at(i);
60 int fd = fds.at(i);
61 if (key) {
62 base::FileDescriptorStore::GetInstance().Set(*key, base::ScopedFD(fd),
63 region);
64 } else {
65 base::GlobalDescriptors::GetInstance()->Set(id, fd, region);
66 }
67 }
68 }
69
JNI_ChildProcessService_ExitChildProcess(JNIEnv * env,const JavaParamRef<jclass> & clazz)70 void JNI_ChildProcessService_ExitChildProcess(
71 JNIEnv* env,
72 const JavaParamRef<jclass>& clazz) {
73 VLOG(0) << "ChildProcessService: Exiting child process.";
74 base::android::LibraryLoaderExitHook();
75 _exit(0);
76 }
77
78 } // namespace android
79 } // namespace base
80