1 /*
2 * Copyright (C) 2015 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 <map>
18 #include <sstream>
19 #include <string>
20 #include <vector>
21
22 #include <unistd.h>
23
24 #include <binder/IInterface.h>
25 #include <binder/IPCThreadState.h>
26 #include <binder/IServiceManager.h>
27 #include <binder/ProcessState.h>
28 #include <binder/Status.h>
29 #include <nativehelper/ScopedFd.h>
30 #include <utils/Errors.h>
31 #include <utils/Log.h>
32 #include <utils/Looper.h>
33 #include <utils/StrongPointer.h>
34
35 #include "android/aidl/tests/BnTestService.h"
36 #include "android/aidl/tests/ITestService.h"
37
38 #include "android/aidl/tests/BnNamedCallback.h"
39 #include "android/aidl/tests/INamedCallback.h"
40
41 // Used implicitly.
42 #undef LOG_TAG
43 #define LOG_TAG "aidl_native_service"
44
45 // libutils:
46 using android::Looper;
47 using android::LooperCallback;
48 using android::OK;
49 using android::sp;
50 using android::String16;
51
52 // libbinder:
53 using android::BnInterface;
54 using android::defaultServiceManager;
55 using android::IInterface;
56 using android::IPCThreadState;
57 using android::Parcel;
58 using android::ProcessState;
59 using android::binder::Status;
60
61 // Generated code:
62 using android::aidl::tests::BnNamedCallback;
63 using android::aidl::tests::BnTestService;
64 using android::aidl::tests::INamedCallback;
65 using android::aidl::tests::SimpleParcelable;
66 using android::os::PersistableBundle;
67
68 // Standard library
69 using std::map;
70 using std::string;
71 using std::unique_ptr;
72 using std::vector;
73
74 namespace {
75
76 class BinderCallback : public LooperCallback {
77 public:
BinderCallback()78 BinderCallback() {}
~BinderCallback()79 ~BinderCallback() override {}
80
handleEvent(int,int,void *)81 int handleEvent(int /* fd */, int /* events */, void* /* data */) override {
82 IPCThreadState::self()->handlePolledCommands();
83 return 1; // Continue receiving callbacks.
84 }
85 };
86
87 class NamedCallback : public BnNamedCallback {
88 public:
NamedCallback(String16 name)89 NamedCallback(String16 name) : name_(name) {}
90
GetName(String16 * ret)91 Status GetName(String16* ret) {
92 *ret = name_;
93 return Status::ok();
94 }
95
96 private:
97 String16 name_;
98 };
99
100 class NativeService : public BnTestService {
101 public:
NativeService()102 NativeService() {}
103 virtual ~NativeService() = default;
104
LogRepeatedStringToken(const String16 & token)105 void LogRepeatedStringToken(const String16& token) {
106 ALOGI("Repeating '%s' of length=%zu", android::String8(token).string(),
107 token.size());
108 }
109
110 template <typename T>
LogRepeatedToken(const T & token)111 void LogRepeatedToken(const T& token) {
112 std::ostringstream token_str;
113 token_str << token;
114 ALOGI("Repeating token %s", token_str.str().c_str());
115 }
116
RepeatBoolean(bool token,bool * _aidl_return)117 Status RepeatBoolean(bool token, bool* _aidl_return) override {
118 LogRepeatedToken(token ? 1 : 0);
119 *_aidl_return = token;
120 return Status::ok();
121 }
RepeatByte(int8_t token,int8_t * _aidl_return)122 Status RepeatByte(int8_t token, int8_t* _aidl_return) override {
123 LogRepeatedToken(token);
124 *_aidl_return = token;
125 return Status::ok();
126 }
RepeatChar(char16_t token,char16_t * _aidl_return)127 Status RepeatChar(char16_t token, char16_t* _aidl_return) override {
128 LogRepeatedStringToken(String16(&token, 1));
129 *_aidl_return = token;
130 return Status::ok();
131 }
RepeatInt(int32_t token,int32_t * _aidl_return)132 Status RepeatInt(int32_t token, int32_t* _aidl_return) override {
133 LogRepeatedToken(token);
134 *_aidl_return = token;
135 return Status::ok();
136 }
RepeatLong(int64_t token,int64_t * _aidl_return)137 Status RepeatLong(int64_t token, int64_t* _aidl_return) override {
138 LogRepeatedToken(token);
139 *_aidl_return = token;
140 return Status::ok();
141 }
RepeatFloat(float token,float * _aidl_return)142 Status RepeatFloat(float token, float* _aidl_return) override {
143 LogRepeatedToken(token);
144 *_aidl_return = token;
145 return Status::ok();
146 }
RepeatDouble(double token,double * _aidl_return)147 Status RepeatDouble(double token, double* _aidl_return) override {
148 LogRepeatedToken(token);
149 *_aidl_return = token;
150 return Status::ok();
151 }
RepeatString(const String16 & token,String16 * _aidl_return)152 Status RepeatString(const String16& token, String16* _aidl_return) override {
153 LogRepeatedStringToken(token);
154 *_aidl_return = token;
155 return Status::ok();
156 }
157
RepeatSimpleParcelable(const SimpleParcelable & input,SimpleParcelable * repeat,SimpleParcelable * _aidl_return)158 Status RepeatSimpleParcelable(const SimpleParcelable& input,
159 SimpleParcelable* repeat,
160 SimpleParcelable* _aidl_return) override {
161 ALOGI("Repeated a SimpleParcelable %s", input.toString().c_str());
162 *repeat = input;
163 *_aidl_return = input;
164 return Status::ok();
165 }
166
RepeatPersistableBundle(const PersistableBundle & input,PersistableBundle * _aidl_return)167 Status RepeatPersistableBundle(const PersistableBundle& input,
168 PersistableBundle* _aidl_return) override {
169 ALOGI("Repeated a PersistableBundle");
170 *_aidl_return = input;
171 return Status::ok();
172 }
173
174 template <typename T>
ReverseArray(const vector<T> & input,vector<T> * repeated,vector<T> * _aidl_return)175 Status ReverseArray(const vector<T>& input, vector<T>* repeated,
176 vector<T>* _aidl_return) {
177 ALOGI("Reversing array of length %zu", input.size());
178 *repeated = input;
179 *_aidl_return = input;
180 std::reverse(_aidl_return->begin(), _aidl_return->end());
181 return Status::ok();
182 }
183
184 template<typename T>
RepeatNullable(const unique_ptr<T> & input,unique_ptr<T> * _aidl_return)185 Status RepeatNullable(const unique_ptr<T>& input,
186 unique_ptr<T>* _aidl_return) {
187 ALOGI("Repeating nullable value");
188
189 _aidl_return->reset();
190 if (input) {
191 _aidl_return->reset(new T(*input));
192 }
193
194 return Status::ok();
195 }
196
ReverseBoolean(const vector<bool> & input,vector<bool> * repeated,vector<bool> * _aidl_return)197 Status ReverseBoolean(const vector<bool>& input,
198 vector<bool>* repeated,
199 vector<bool>* _aidl_return) override {
200 return ReverseArray(input, repeated, _aidl_return);
201 }
ReverseByte(const vector<uint8_t> & input,vector<uint8_t> * repeated,vector<uint8_t> * _aidl_return)202 Status ReverseByte(const vector<uint8_t>& input,
203 vector<uint8_t>* repeated,
204 vector<uint8_t>* _aidl_return) override {
205 return ReverseArray(input, repeated, _aidl_return);
206 }
ReverseChar(const vector<char16_t> & input,vector<char16_t> * repeated,vector<char16_t> * _aidl_return)207 Status ReverseChar(const vector<char16_t>& input,
208 vector<char16_t>* repeated,
209 vector<char16_t>* _aidl_return) override {
210 return ReverseArray(input, repeated, _aidl_return);
211 }
ReverseInt(const vector<int32_t> & input,vector<int32_t> * repeated,vector<int32_t> * _aidl_return)212 Status ReverseInt(const vector<int32_t>& input,
213 vector<int32_t>* repeated,
214 vector<int32_t>* _aidl_return) override {
215 return ReverseArray(input, repeated, _aidl_return);
216 }
ReverseLong(const vector<int64_t> & input,vector<int64_t> * repeated,vector<int64_t> * _aidl_return)217 Status ReverseLong(const vector<int64_t>& input,
218 vector<int64_t>* repeated,
219 vector<int64_t>* _aidl_return) override {
220 return ReverseArray(input, repeated, _aidl_return);
221 }
ReverseFloat(const vector<float> & input,vector<float> * repeated,vector<float> * _aidl_return)222 Status ReverseFloat(const vector<float>& input,
223 vector<float>* repeated,
224 vector<float>* _aidl_return) override {
225 return ReverseArray(input, repeated, _aidl_return);
226 }
ReverseDouble(const vector<double> & input,vector<double> * repeated,vector<double> * _aidl_return)227 Status ReverseDouble(const vector<double>& input,
228 vector<double>* repeated,
229 vector<double>* _aidl_return) override {
230 return ReverseArray(input, repeated, _aidl_return);
231 }
ReverseString(const vector<String16> & input,vector<String16> * repeated,vector<String16> * _aidl_return)232 Status ReverseString(const vector<String16>& input,
233 vector<String16>* repeated,
234 vector<String16>* _aidl_return) override {
235 return ReverseArray(input, repeated, _aidl_return);
236 }
ReverseSimpleParcelables(const vector<SimpleParcelable> & input,vector<SimpleParcelable> * repeated,vector<SimpleParcelable> * _aidl_return)237 Status ReverseSimpleParcelables(
238 const vector<SimpleParcelable>& input,
239 vector<SimpleParcelable>* repeated,
240 vector<SimpleParcelable>* _aidl_return) override {
241 return ReverseArray(input, repeated, _aidl_return);
242 }
ReversePersistableBundles(const vector<PersistableBundle> & input,vector<PersistableBundle> * repeated,vector<PersistableBundle> * _aidl_return)243 Status ReversePersistableBundles(
244 const vector<PersistableBundle>& input,
245 vector<PersistableBundle>* repeated,
246 vector<PersistableBundle>* _aidl_return) override {
247 return ReverseArray(input, repeated, _aidl_return);
248 }
249
GetOtherTestService(const String16 & name,sp<INamedCallback> * returned_service)250 Status GetOtherTestService(const String16& name,
251 sp<INamedCallback>* returned_service) override {
252 if (service_map_.find(name) == service_map_.end()) {
253 sp<INamedCallback> new_item(new NamedCallback(name));
254 service_map_[name] = new_item;
255 }
256
257 *returned_service = service_map_[name];
258 return Status::ok();
259 }
260
VerifyName(const sp<INamedCallback> & service,const String16 & name,bool * returned_value)261 Status VerifyName(const sp<INamedCallback>& service, const String16& name,
262 bool* returned_value) override {
263 String16 foundName;
264 Status status = service->GetName(&foundName);
265
266 if (status.isOk()) {
267 *returned_value = foundName == name;
268 }
269
270 return status;
271 }
272
ReverseStringList(const vector<String16> & input,vector<String16> * repeated,vector<String16> * _aidl_return)273 Status ReverseStringList(const vector<String16>& input,
274 vector<String16>* repeated,
275 vector<String16>* _aidl_return) override {
276 return ReverseArray(input, repeated, _aidl_return);
277 }
278
ReverseNamedCallbackList(const vector<sp<IBinder>> & input,vector<sp<IBinder>> * repeated,vector<sp<IBinder>> * _aidl_return)279 Status ReverseNamedCallbackList(const vector<sp<IBinder>>& input,
280 vector<sp<IBinder>>* repeated,
281 vector<sp<IBinder>>* _aidl_return) override {
282 return ReverseArray(input, repeated, _aidl_return);
283 }
284
RepeatFileDescriptor(const ScopedFd & read,ScopedFd * _aidl_return)285 Status RepeatFileDescriptor(const ScopedFd& read,
286 ScopedFd* _aidl_return) override {
287 ALOGE("Repeating file descriptor");
288 *_aidl_return = ScopedFd(dup(read.get()));
289 return Status::ok();
290 }
291
ReverseFileDescriptorArray(const vector<ScopedFd> & input,vector<ScopedFd> * repeated,vector<ScopedFd> * _aidl_return)292 Status ReverseFileDescriptorArray(const vector<ScopedFd>& input,
293 vector<ScopedFd>* repeated,
294 vector<ScopedFd>* _aidl_return) override {
295 ALOGI("Reversing descriptor array of length %zu", input.size());
296 for (const auto& item : input) {
297 repeated->push_back(ScopedFd(dup(item.get())));
298 _aidl_return->push_back(ScopedFd(dup(item.get())));
299 }
300 std::reverse(_aidl_return->begin(), _aidl_return->end());
301 return Status::ok();
302 }
303
ThrowServiceException(int code)304 Status ThrowServiceException(int code) override {
305 return Status::fromServiceSpecificError(code);
306 }
307
RepeatNullableIntArray(const unique_ptr<vector<int32_t>> & input,unique_ptr<vector<int32_t>> * _aidl_return)308 Status RepeatNullableIntArray(const unique_ptr<vector<int32_t>>& input,
309 unique_ptr<vector<int32_t>>* _aidl_return) {
310 return RepeatNullable(input, _aidl_return);
311 }
312
RepeatNullableStringList(const unique_ptr<vector<unique_ptr<String16>>> & input,unique_ptr<vector<unique_ptr<String16>>> * _aidl_return)313 Status RepeatNullableStringList(
314 const unique_ptr<vector<unique_ptr<String16>>>& input,
315 unique_ptr<vector<unique_ptr<String16>>>* _aidl_return) {
316 ALOGI("Repeating nullable string list");
317 if (!input) {
318 _aidl_return->reset();
319 return Status::ok();
320 }
321
322 _aidl_return->reset(new vector<unique_ptr<String16>>);
323
324 for (const auto& item : *input) {
325 if (!item) {
326 (*_aidl_return)->emplace_back(nullptr);
327 } else {
328 (*_aidl_return)->emplace_back(new String16(*item));
329 }
330 }
331
332 return Status::ok();
333 }
334
RepeatNullableString(const unique_ptr<String16> & input,unique_ptr<String16> * _aidl_return)335 Status RepeatNullableString(const unique_ptr<String16>& input,
336 unique_ptr<String16>* _aidl_return) {
337 return RepeatNullable(input, _aidl_return);
338 }
339
RepeatNullableParcelable(const unique_ptr<SimpleParcelable> & input,unique_ptr<SimpleParcelable> * _aidl_return)340 Status RepeatNullableParcelable(const unique_ptr<SimpleParcelable>& input,
341 unique_ptr<SimpleParcelable>* _aidl_return) {
342 return RepeatNullable(input, _aidl_return);
343 }
344
RepeatUtf8CppString(const string & token,string * _aidl_return)345 Status RepeatUtf8CppString(const string& token,
346 string* _aidl_return) override {
347 ALOGI("Repeating utf8 string '%s' of length=%zu", token.c_str(), token.size());
348 *_aidl_return = token;
349 return Status::ok();
350 }
351
RepeatNullableUtf8CppString(const unique_ptr<string> & token,unique_ptr<string> * _aidl_return)352 Status RepeatNullableUtf8CppString(
353 const unique_ptr<string>& token,
354 unique_ptr<string>* _aidl_return) override {
355 if (!token) {
356 ALOGI("Received null @utf8InCpp string");
357 return Status::ok();
358 }
359 ALOGI("Repeating utf8 string '%s' of length=%zu",
360 token->c_str(), token->size());
361 _aidl_return->reset(new string(*token));
362 return Status::ok();
363 }
364
ReverseUtf8CppString(const vector<string> & input,vector<string> * repeated,vector<string> * _aidl_return)365 Status ReverseUtf8CppString(const vector<string>& input,
366 vector<string>* repeated,
367 vector<string>* _aidl_return) {
368 return ReverseArray(input, repeated, _aidl_return);
369 }
370
ReverseUtf8CppStringList(const unique_ptr<vector<unique_ptr<::string>>> & input,unique_ptr<vector<unique_ptr<string>>> * repeated,unique_ptr<vector<unique_ptr<string>>> * _aidl_return)371 Status ReverseUtf8CppStringList(
372 const unique_ptr<vector<unique_ptr<::string>>>& input,
373 unique_ptr<vector<unique_ptr<string>>>* repeated,
374 unique_ptr<vector<unique_ptr<string>>>* _aidl_return) {
375 if (!input) {
376 ALOGI("Received null list of utf8 strings");
377 return Status::ok();
378 }
379 _aidl_return->reset(new vector<unique_ptr<string>>);
380 repeated->reset(new vector<unique_ptr<string>>);
381
382 for (const auto& item : *input) {
383 (*repeated)->emplace_back(nullptr);
384 (*_aidl_return)->emplace_back(nullptr);
385 if (item) {
386 (*repeated)->back().reset(new string(*item));
387 (*_aidl_return)->back().reset(new string(*item));
388 }
389 }
390 std::reverse((*_aidl_return)->begin(), (*_aidl_return)->end());
391
392 return Status::ok();
393 }
394
395 private:
396 map<String16, sp<INamedCallback>> service_map_;
397 };
398
Run()399 int Run() {
400 android::sp<NativeService> service = new NativeService;
401 sp<Looper> looper(Looper::prepare(0 /* opts */));
402
403 int binder_fd = -1;
404 ProcessState::self()->setThreadPoolMaxThreadCount(0);
405 IPCThreadState::self()->disableBackgroundScheduling(true);
406 IPCThreadState::self()->setupPolling(&binder_fd);
407 ALOGI("Got binder FD %d", binder_fd);
408 if (binder_fd < 0) return -1;
409
410 sp<BinderCallback> cb(new BinderCallback);
411 if (looper->addFd(binder_fd, Looper::POLL_CALLBACK, Looper::EVENT_INPUT, cb,
412 nullptr) != 1) {
413 ALOGE("Failed to add binder FD to Looper");
414 return -1;
415 }
416
417 defaultServiceManager()->addService(service->getInterfaceDescriptor(),
418 service);
419
420 ALOGI("Entering loop");
421 while (true) {
422 const int result = looper->pollAll(-1 /* timeoutMillis */);
423 ALOGI("Looper returned %d", result);
424 }
425 return 0;
426 }
427
428 } // namespace
429
main(int,char * [])430 int main(int /* argc */, char* /* argv */ []) {
431 return Run();
432 }
433