1 /*
2 * Copyright (C) 2018 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
17 #include <android/binder_manager.h>
18 #include <binder/IServiceManager.h>
19 #include <binder/LazyServiceRegistrar.h>
20
21 #include "ibinder_internal.h"
22 #include "status_internal.h"
23
24 using ::android::defaultServiceManager;
25 using ::android::IBinder;
26 using ::android::IServiceManager;
27 using ::android::sp;
28 using ::android::status_t;
29 using ::android::statusToString;
30 using ::android::String16;
31 using ::android::String8;
32
AServiceManager_addService(AIBinder * binder,const char * instance)33 binder_exception_t AServiceManager_addService(AIBinder* binder, const char* instance) {
34 if (binder == nullptr || instance == nullptr) {
35 return EX_ILLEGAL_ARGUMENT;
36 }
37
38 sp<IServiceManager> sm = defaultServiceManager();
39 status_t exception = sm->addService(String16(instance), binder->getBinder());
40 return PruneException(exception);
41 }
42
AServiceManager_addServiceWithFlags(AIBinder * binder,const char * instance,const AServiceManager_AddServiceFlag flags)43 binder_exception_t AServiceManager_addServiceWithFlags(AIBinder* binder, const char* instance,
44 const AServiceManager_AddServiceFlag flags) {
45 if (binder == nullptr || instance == nullptr) {
46 return EX_ILLEGAL_ARGUMENT;
47 }
48
49 sp<IServiceManager> sm = defaultServiceManager();
50
51 bool allowIsolated = flags & AServiceManager_AddServiceFlag::ADD_SERVICE_ALLOW_ISOLATED;
52 int dumpFlags = 0;
53 if (flags & AServiceManager_AddServiceFlag::ADD_SERVICE_DUMP_FLAG_PRIORITY_CRITICAL) {
54 dumpFlags |= IServiceManager::DUMP_FLAG_PRIORITY_CRITICAL;
55 }
56 if (flags & AServiceManager_AddServiceFlag::ADD_SERVICE_DUMP_FLAG_PRIORITY_HIGH) {
57 dumpFlags |= IServiceManager::DUMP_FLAG_PRIORITY_HIGH;
58 }
59 if (flags & AServiceManager_AddServiceFlag::ADD_SERVICE_DUMP_FLAG_PRIORITY_NORMAL) {
60 dumpFlags |= IServiceManager::DUMP_FLAG_PRIORITY_NORMAL;
61 }
62 if (flags & AServiceManager_AddServiceFlag::ADD_SERVICE_DUMP_FLAG_PRIORITY_DEFAULT) {
63 dumpFlags |= IServiceManager::DUMP_FLAG_PRIORITY_DEFAULT;
64 }
65 if (dumpFlags == 0) {
66 dumpFlags = IServiceManager::DUMP_FLAG_PRIORITY_DEFAULT;
67 }
68 status_t exception =
69 sm->addService(String16(instance), binder->getBinder(), allowIsolated, dumpFlags);
70
71 return PruneException(exception);
72 }
73
AServiceManager_checkService(const char * instance)74 AIBinder* AServiceManager_checkService(const char* instance) {
75 if (instance == nullptr) {
76 return nullptr;
77 }
78
79 sp<IServiceManager> sm = defaultServiceManager();
80 sp<IBinder> binder = sm->checkService(String16(instance));
81
82 sp<AIBinder> ret = ABpBinder::lookupOrCreateFromBinder(binder);
83 AIBinder_incStrong(ret.get());
84 return ret.get();
85 }
AServiceManager_getService(const char * instance)86 AIBinder* AServiceManager_getService(const char* instance) {
87 if (instance == nullptr) {
88 return nullptr;
89 }
90
91 sp<IServiceManager> sm = defaultServiceManager();
92 sp<IBinder> binder = sm->getService(String16(instance));
93
94 sp<AIBinder> ret = ABpBinder::lookupOrCreateFromBinder(binder);
95 AIBinder_incStrong(ret.get());
96 return ret.get();
97 }
AServiceManager_registerLazyService(AIBinder * binder,const char * instance)98 binder_status_t AServiceManager_registerLazyService(AIBinder* binder, const char* instance) {
99 if (binder == nullptr || instance == nullptr) {
100 return STATUS_UNEXPECTED_NULL;
101 }
102
103 auto serviceRegistrar = android::binder::LazyServiceRegistrar::getInstance();
104 status_t status = serviceRegistrar.registerService(binder->getBinder(), instance);
105
106 return PruneStatusT(status);
107 }
AServiceManager_waitForService(const char * instance)108 AIBinder* AServiceManager_waitForService(const char* instance) {
109 if (instance == nullptr) {
110 return nullptr;
111 }
112
113 sp<IServiceManager> sm = defaultServiceManager();
114 sp<IBinder> binder = sm->waitForService(String16(instance));
115
116 sp<AIBinder> ret = ABpBinder::lookupOrCreateFromBinder(binder);
117 AIBinder_incStrong(ret.get());
118 return ret.get();
119 }
120 typedef void (*AServiceManager_onRegister)(const char* instance, AIBinder* registered,
121 void* cookie);
122
123 struct AServiceManager_NotificationRegistration
124 : public IServiceManager::LocalRegistrationCallback {
125 std::mutex m;
126 const char* instance = nullptr;
127 void* cookie = nullptr;
128 AServiceManager_onRegister onRegister = nullptr;
129
onServiceRegistrationAServiceManager_NotificationRegistration130 virtual void onServiceRegistration(const String16& smInstance, const sp<IBinder>& binder) {
131 std::lock_guard<std::mutex> l(m);
132 if (onRegister == nullptr) return;
133
134 LOG_ALWAYS_FATAL_IF(String8(smInstance) != instance, "onServiceRegistration: %s != %s",
135 String8(smInstance).c_str(), instance);
136
137 sp<AIBinder> ret = ABpBinder::lookupOrCreateFromBinder(binder);
138 AIBinder_incStrong(ret.get());
139
140 onRegister(instance, ret.get(), cookie);
141 }
142
clearAServiceManager_NotificationRegistration143 void clear() {
144 std::lock_guard<std::mutex> l(m);
145 instance = nullptr;
146 cookie = nullptr;
147 onRegister = nullptr;
148 }
149 };
150
151 __attribute__((warn_unused_result)) AServiceManager_NotificationRegistration*
AServiceManager_registerForServiceNotifications(const char * instance,AServiceManager_onRegister onRegister,void * cookie)152 AServiceManager_registerForServiceNotifications(const char* instance,
153 AServiceManager_onRegister onRegister,
154 void* cookie) {
155 LOG_ALWAYS_FATAL_IF(instance == nullptr, "instance == nullptr");
156 LOG_ALWAYS_FATAL_IF(onRegister == nullptr, "onRegister == nullptr for %s", instance);
157 // cookie can be nullptr
158
159 auto cb = sp<AServiceManager_NotificationRegistration>::make();
160 cb->instance = instance;
161 cb->onRegister = onRegister;
162 cb->cookie = cookie;
163
164 sp<IServiceManager> sm = defaultServiceManager();
165 if (status_t res = sm->registerForNotifications(String16(instance), cb); res != STATUS_OK) {
166 ALOGE("Failed to register for service notifications for %s: %s", instance,
167 statusToString(res).c_str());
168 return nullptr;
169 }
170
171 cb->incStrong(nullptr);
172 return cb.get();
173 }
174
AServiceManager_NotificationRegistration_delete(AServiceManager_NotificationRegistration * notification)175 void AServiceManager_NotificationRegistration_delete(
176 AServiceManager_NotificationRegistration* notification) {
177 LOG_ALWAYS_FATAL_IF(notification == nullptr, "notification == nullptr");
178 notification->clear();
179 notification->decStrong(nullptr);
180 }
181
AServiceManager_isDeclared(const char * instance)182 bool AServiceManager_isDeclared(const char* instance) {
183 if (instance == nullptr) {
184 return false;
185 }
186
187 sp<IServiceManager> sm = defaultServiceManager();
188 return sm->isDeclared(String16(instance));
189 }
AServiceManager_forEachDeclaredInstance(const char * interface,void * context,void (* callback)(const char *,void *))190 void AServiceManager_forEachDeclaredInstance(const char* interface, void* context,
191 void (*callback)(const char*, void*)) {
192 LOG_ALWAYS_FATAL_IF(interface == nullptr, "interface == nullptr");
193 // context may be nullptr
194 LOG_ALWAYS_FATAL_IF(callback == nullptr, "callback == nullptr");
195
196 sp<IServiceManager> sm = defaultServiceManager();
197 for (const String16& instance : sm->getDeclaredInstances(String16(interface))) {
198 callback(String8(instance).c_str(), context);
199 }
200 }
AServiceManager_isUpdatableViaApex(const char * instance)201 bool AServiceManager_isUpdatableViaApex(const char* instance) {
202 if (instance == nullptr) {
203 return false;
204 }
205
206 sp<IServiceManager> sm = defaultServiceManager();
207 return sm->updatableViaApex(String16(instance)) != std::nullopt;
208 }
AServiceManager_getUpdatableApexName(const char * instance,void * context,void (* callback)(const char *,void *))209 void AServiceManager_getUpdatableApexName(const char* instance, void* context,
210 void (*callback)(const char*, void*)) {
211 LOG_ALWAYS_FATAL_IF(instance == nullptr, "instance == nullptr");
212 // context may be nullptr
213 LOG_ALWAYS_FATAL_IF(callback == nullptr, "callback == nullptr");
214
215 sp<IServiceManager> sm = defaultServiceManager();
216 std::optional<String16> updatableViaApex = sm->updatableViaApex(String16(instance));
217 if (updatableViaApex.has_value()) {
218 callback(String8(updatableViaApex.value()).c_str(), context);
219 }
220 }
AServiceManager_openDeclaredPassthroughHal(const char * interface,const char * instance,int flag)221 void* AServiceManager_openDeclaredPassthroughHal(const char* interface, const char* instance,
222 int flag) {
223 LOG_ALWAYS_FATAL_IF(interface == nullptr, "interface == nullptr");
224 LOG_ALWAYS_FATAL_IF(instance == nullptr, "instance == nullptr");
225
226 return openDeclaredPassthroughHal(String16(interface), String16(instance), flag);
227 }
AServiceManager_forceLazyServicesPersist(bool persist)228 void AServiceManager_forceLazyServicesPersist(bool persist) {
229 auto serviceRegistrar = android::binder::LazyServiceRegistrar::getInstance();
230 serviceRegistrar.forcePersist(persist);
231 }
AServiceManager_setActiveServicesCallback(bool (* callback)(bool,void *),void * context)232 void AServiceManager_setActiveServicesCallback(bool (*callback)(bool, void*), void* context) {
233 auto serviceRegistrar = android::binder::LazyServiceRegistrar::getInstance();
234 std::function<bool(bool)> fn = [=](bool hasClients) -> bool {
235 return callback(hasClients, context);
236 };
237 serviceRegistrar.setActiveServicesCallback(fn);
238 }
AServiceManager_tryUnregister()239 bool AServiceManager_tryUnregister() {
240 auto serviceRegistrar = android::binder::LazyServiceRegistrar::getInstance();
241 return serviceRegistrar.tryUnregister();
242 }
AServiceManager_reRegister()243 void AServiceManager_reRegister() {
244 auto serviceRegistrar = android::binder::LazyServiceRegistrar::getInstance();
245 serviceRegistrar.reRegister();
246 }
247