blob: f21cb9c3494b53b9c081eb9a569dc1f45bd4586e [file] [log] [blame]
Iliyan Malchevb31e10c2016-08-13 23:03:25 -07001#define LOG_TAG "hidl_test"
Yifan Hong11992a62016-11-09 18:07:40 -08002
3#include "FooCallback.h"
4
Andreas Huber9cd48d02016-08-03 14:25:59 -07005#include <android-base/logging.h>
6
Steven Moreland01bcb772016-11-08 15:57:25 -08007#include <android/hidl/manager/1.0/IServiceManager.h>
Steven Moreland0693f312016-11-09 15:06:14 -08008#include <android/hidl/manager/1.0/IServiceNotification.h>
Steven Moreland01bcb772016-11-08 15:57:25 -08009
Martijn Coenen99e6beb2016-12-01 15:48:42 +010010#include <android/hidl/memory/1.0/IAllocator.h>
11#include <android/hidl/memory/1.0/IMemory.h>
12
Steven Morelandaa2b83a2016-12-21 15:52:11 -080013#include <android/hidl/token/1.0/ITokenManager.h>
14
Steven Morelandb48a7da2016-11-11 14:12:46 -080015#include <android/hardware/tests/foo/1.0/IFoo.h>
Yifan Hong01e7cde2017-01-09 17:45:45 -080016#include <android/hardware/tests/foo/1.0/BnHwSimple.h>
Yifan Hongdef2cfb2016-12-14 16:00:24 -080017#include <android/hardware/tests/foo/1.0/BsSimple.h>
Yifan Hong01e7cde2017-01-09 17:45:45 -080018#include <android/hardware/tests/foo/1.0/BpHwSimple.h>
Steven Morelandb48a7da2016-11-11 14:12:46 -080019#include <android/hardware/tests/bar/1.0/IBar.h>
Yifan Hong5749b2c2016-11-28 12:52:36 -080020#include <android/hardware/tests/bar/1.0/IComplicated.h>
Yifan Hong87ff8232017-01-09 12:07:05 -080021#include <android/hardware/tests/bar/1.0/IImportRules.h>
Steven Morelandb48a7da2016-11-11 14:12:46 -080022#include <android/hardware/tests/inheritance/1.0/IFetcher.h>
23#include <android/hardware/tests/inheritance/1.0/IGrandparent.h>
24#include <android/hardware/tests/inheritance/1.0/IParent.h>
25#include <android/hardware/tests/inheritance/1.0/IChild.h>
Martijn Coenen99e6beb2016-12-01 15:48:42 +010026#include <android/hardware/tests/memory/1.0/IMemoryTest.h>
Steven Morelandb48a7da2016-11-11 14:12:46 -080027#include <android/hardware/tests/pointer/1.0/IGraph.h>
28#include <android/hardware/tests/pointer/1.0/IPointer.h>
Andreas Huber9cd48d02016-08-03 14:25:59 -070029
Yifan Hong1dc87932016-08-19 09:51:01 -070030#include <gtest/gtest.h>
31#if GTEST_IS_THREADSAFE
32#include <sys/types.h>
Yifan Hongc70f0d82016-10-10 14:50:22 -070033#include <sys/wait.h>
Yifan Hong1dc87932016-08-19 09:51:01 -070034#include <signal.h>
35#include <errno.h>
36#include <pthread.h>
37#else
38#error "GTest did not detect pthread library."
39#endif
40
Steven Moreland01bcb772016-11-08 15:57:25 -080041#include <algorithm>
Steven Moreland0693f312016-11-09 15:06:14 -080042#include <condition_variable>
Yifan Hongd12398d2016-10-13 11:05:29 -070043#include <getopt.h>
44#include <inttypes.h>
Steven Moreland0693f312016-11-09 15:06:14 -080045#include <mutex>
Steven Moreland01bcb772016-11-08 15:57:25 -080046#include <set>
Yifan Hongbf459bc2016-08-23 16:50:37 -070047#include <sstream>
Yifan Hongccd782b2016-11-28 09:41:46 -080048#include <utility>
Yifan Hongd12398d2016-10-13 11:05:29 -070049#include <vector>
Yifan Hongbf459bc2016-08-23 16:50:37 -070050
Yifan Hong398e6fb2016-10-17 11:38:09 -070051#include <hidl-test/FooHelper.h>
52#include <hidl-test/PointerHelper.h>
53
Martijn Coenen93915102016-09-01 01:35:52 +020054#include <hidl/Status.h>
Martijn Coenen99e6beb2016-12-01 15:48:42 +010055#include <hidlmemory/mapping.h>
Martijn Coenenfa55d6e2016-12-20 06:08:31 +010056
Andreas Huber9cd48d02016-08-03 14:25:59 -070057#include <hwbinder/IPCThreadState.h>
Andreas Huber9cd48d02016-08-03 14:25:59 -070058
Iliyan Malchev0acf4192016-08-22 19:33:20 -070059#include <utils/Condition.h>
60#include <utils/Timers.h>
61
Yifan Hongbf459bc2016-08-23 16:50:37 -070062#define EXPECT_OK(__ret__) EXPECT_TRUE(isOk(__ret__))
Yifan Hong84465902016-09-27 15:52:17 -070063#define EXPECT_FAIL(__ret__) EXPECT_FALSE(isOk(__ret__))
Yifan Hong8c48ad72016-10-14 11:34:59 -070064#define EXPECT_ARRAYEQ(__a1__, __a2__, __size__) EXPECT_TRUE(isArrayEqual(__a1__, __a2__, __size__))
Yifan Hongbf459bc2016-08-23 16:50:37 -070065
66// TODO uncomment this when kernel is patched with pointer changes.
67//#define HIDL_RUN_POINTER_TESTS 1
68
Yifan Hongca890522016-10-12 10:03:41 -070069// forward declarations.
70class PassthroughEnvironment;
71class BinderizedEnvironment;
72
Yifan Hongc70f0d82016-10-10 14:50:22 -070073// static storage
74static enum TestMode {
75 BINDERIZED,
76 PASSTHROUGH
77} gMode;
Yifan Hongca890522016-10-12 10:03:41 -070078static PassthroughEnvironment *gPassthroughEnvironment = nullptr;
79static BinderizedEnvironment *gBinderizedEnvironment = nullptr;
Yifan Hong35d66002016-10-13 12:47:44 -070080// per process tag
81static std::string gServiceName;
Yifan Hongc70f0d82016-10-10 14:50:22 -070082// end static storage
83
Andreas Huber86a112b2016-10-19 14:25:16 -070084using ::android::hardware::tests::foo::V1_0::Abc;
Steven Moreland88ca4512016-08-11 11:24:10 -070085using ::android::hardware::tests::foo::V1_0::IFoo;
86using ::android::hardware::tests::foo::V1_0::IFooCallback;
Andreas Huber86a112b2016-10-19 14:25:16 -070087using ::android::hardware::tests::foo::V1_0::ISimple;
Yifan Hong11992a62016-11-09 18:07:40 -080088using ::android::hardware::tests::foo::V1_0::implementation::FooCallback;
Steven Moreland88ca4512016-08-11 11:24:10 -070089using ::android::hardware::tests::bar::V1_0::IBar;
Yifan Hong5749b2c2016-11-28 12:52:36 -080090using ::android::hardware::tests::bar::V1_0::IComplicated;
Yifan Hong1e81c532016-10-18 18:43:46 -070091using ::android::hardware::tests::inheritance::V1_0::IFetcher;
92using ::android::hardware::tests::inheritance::V1_0::IGrandparent;
93using ::android::hardware::tests::inheritance::V1_0::IParent;
94using ::android::hardware::tests::inheritance::V1_0::IChild;
Yifan Hongbf459bc2016-08-23 16:50:37 -070095using ::android::hardware::tests::pointer::V1_0::IGraph;
96using ::android::hardware::tests::pointer::V1_0::IPointer;
Martijn Coenen99e6beb2016-12-01 15:48:42 +010097using ::android::hardware::tests::memory::V1_0::IMemoryTest;
Yifan Hong35d66002016-10-13 12:47:44 -070098using ::android::hardware::IPCThreadState;
Iliyan Malchev2b6591b2016-08-18 19:15:19 -070099using ::android::hardware::Return;
Iliyan Malchevd57066f2016-09-08 13:59:38 -0700100using ::android::hardware::Void;
Martijn Coenenfa55d6e2016-12-20 06:08:31 +0100101using ::android::hardware::configureRpcThreadpool;
102using ::android::hardware::joinRpcThreadpool;
Andreas Huberf03332a2016-09-22 15:35:43 -0700103using ::android::hardware::hidl_array;
Martijn Coenen115d4282016-12-19 05:14:04 +0100104using ::android::hardware::hidl_death_recipient;
Martijn Coenen99e6beb2016-12-01 15:48:42 +0100105using ::android::hardware::hidl_memory;
Andreas Huber8a82ff72016-08-04 10:29:39 -0700106using ::android::hardware::hidl_string;
Martijn Coenen99e6beb2016-12-01 15:48:42 +0100107using ::android::hardware::hidl_vec;
Martijn Coenen115d4282016-12-19 05:14:04 +0100108using ::android::hidl::base::V1_0::IBase;
Steven Moreland01bcb772016-11-08 15:57:25 -0800109using ::android::hidl::manager::V1_0::IServiceManager;
Steven Moreland0693f312016-11-09 15:06:14 -0800110using ::android::hidl::manager::V1_0::IServiceNotification;
Martijn Coenen99e6beb2016-12-01 15:48:42 +0100111using ::android::hidl::memory::V1_0::IAllocator;
112using ::android::hidl::memory::V1_0::IMemory;
Steven Morelandaa2b83a2016-12-21 15:52:11 -0800113using ::android::hidl::token::V1_0::ITokenManager;
Andreas Huber9cd48d02016-08-03 14:25:59 -0700114using ::android::sp;
Martijn Coenen115d4282016-12-19 05:14:04 +0100115using ::android::wp;
Yifan Hong398e6fb2016-10-17 11:38:09 -0700116using ::android::to_string;
Iliyan Malchev0acf4192016-08-22 19:33:20 -0700117using ::android::Mutex;
Yifan Hong398e6fb2016-10-17 11:38:09 -0700118using ::android::MultiDimensionalToString;
Iliyan Malchev0acf4192016-08-22 19:33:20 -0700119using ::android::Condition;
Yifan Hong398e6fb2016-10-17 11:38:09 -0700120using ::android::DELAY_S;
121using ::android::DELAY_NS;
122using ::android::TOLERANCE_NS;
123using ::android::ONEWAY_TOLERANCE_NS;
124using std::to_string;
Andreas Huber9cd48d02016-08-03 14:25:59 -0700125
Yifan Hongbf459bc2016-08-23 16:50:37 -0700126template <typename T>
127static inline ::testing::AssertionResult isOk(::android::hardware::Return<T> ret) {
Steven Morelandcd00b9b2016-12-29 10:34:03 -0800128 return ret.isOk()
129 ? (::testing::AssertionSuccess() << ret.description())
130 : (::testing::AssertionFailure() << ret.description());
Yifan Hongbf459bc2016-08-23 16:50:37 -0700131}
132
133template<typename T, typename S>
134static inline bool isArrayEqual(const T arr1, const S arr2, size_t size) {
135 for(size_t i = 0; i < size; i++)
136 if(arr1[i] != arr2[i])
137 return false;
138 return true;
139}
140
Steven Moreland01bcb772016-11-08 15:57:25 -0800141template<typename T>
142std::string to_string(std::set<T> set) {
143 std::stringstream ss;
144 ss << "{";
145
146 bool first = true;
147 for (const T &item : set) {
148 if (first) {
149 first = false;
150 } else {
151 ss << ", ";
152 }
153
154 ss << to_string(item);
155 }
156
157 ss << "}";
158
159 return ss.str();
160}
161
Andreas Huber86a112b2016-10-19 14:25:16 -0700162struct Simple : public ISimple {
163 Simple(int32_t cookie)
164 : mCookie(cookie) {
165 }
166
167 Return<int32_t> getCookie() override {
168 return mCookie;
169 }
170
Yifan Hong5749b2c2016-11-28 12:52:36 -0800171 Return<void> customVecInt(customVecInt_cb _cb) override {
172 _cb(hidl_vec<int32_t>());
173 return Void();
174 }
175
176 Return<void> customVecStr(customVecStr_cb _cb) override {
177 hidl_vec<hidl_string> vec;
178 vec.resize(2);
179 _cb(vec);
180 return Void();
181 }
182
183 Return<void> mystr(mystr_cb _cb) override {
184 _cb(hidl_string());
185 return Void();
186 }
187
188 Return<void> myhandle(myhandle_cb _cb) override {
189 auto h = native_handle_create(0, 1);
190 _cb(h);
191 native_handle_delete(h);
192 return Void();
193 }
194
195private:
196 int32_t mCookie;
197};
198
199struct Complicated : public IComplicated {
200 Complicated(int32_t cookie)
201 : mCookie(cookie) {
202 }
203
204 Return<int32_t> getCookie() override {
205 return mCookie;
206 }
207
208 Return<void> customVecInt(customVecInt_cb _cb) override {
209 _cb(hidl_vec<int32_t>());
210 return Void();
211 }
212 Return<void> customVecStr(customVecStr_cb _cb) override {
213 hidl_vec<hidl_string> vec;
214 vec.resize(2);
215 _cb(vec);
216 return Void();
217 }
218
219 Return<void> mystr(mystr_cb _cb) override {
220 _cb(hidl_string());
221 return Void();
222 }
223
224 Return<void> myhandle(myhandle_cb _cb) override {
225 auto h = native_handle_create(0, 1);
226 _cb(h);
227 native_handle_delete(h);
228 return Void();
229 }
230
Andreas Huber86a112b2016-10-19 14:25:16 -0700231private:
232 int32_t mCookie;
233};
Steven Moreland0693f312016-11-09 15:06:14 -0800234
Yifan Hong87ff8232017-01-09 12:07:05 -0800235// Ensure (statically) that the types in IImportRules resolves to the correct types by
236// overriding the methods with fully namespaced types as arguments.
237struct MyImportRules : public ::android::hardware::tests::bar::V1_0::IImportRules {
238 Return<void> rule0a(
239 const ::android::hardware::tests::bar::V1_0::IImportRules::Outer&) override {
240 return Void();
241 }
242
243 Return<void> rule0a1(
244 const ::android::hardware::tests::bar::V1_0::IImportRules::Outer&) override {
245 return Void();
246 }
247
248 Return<void> rule0b(
249 const ::android::hardware::tests::bar::V1_0::IImportRules::Outer&) override {
250 return Void();
251 }
252
253 Return<void> rule0c(const ::android::hardware::tests::foo::V1_0::Outer&) override {
254 return Void();
255 }
256
257 Return<void> rule0d(const ::android::hardware::tests::foo::V1_0::Outer&) override {
258 return Void();
259 }
260
261 Return<void> rule0e(
262 const ::android::hardware::tests::bar::V1_0::IImportRules::Outer::Inner&) override {
263 return Void();
264 }
265
266 Return<void> rule0f(
267 const ::android::hardware::tests::bar::V1_0::IImportRules::Outer::Inner&) override {
268 return Void();
269 }
270
271 Return<void> rule0g(const ::android::hardware::tests::foo::V1_0::Outer::Inner&) override {
272 return Void();
273 }
274
275 Return<void> rule0h(const ::android::hardware::tests::foo::V1_0::Outer::Inner&) override {
276 return Void();
277 }
278
279 Return<void> rule1a(const ::android::hardware::tests::bar::V1_0::Def&) override {
280 return Void();
281 }
282
283 Return<void> rule1b(const ::android::hardware::tests::foo::V1_0::Def&) override {
284 return Void();
285 }
286
287 Return<void> rule2a(const ::android::hardware::tests::foo::V1_0::Unrelated&) override {
288 return Void();
289 }
290
291 Return<void> rule2b(const sp<::android::hardware::tests::foo::V1_0::IFooCallback>&) override {
292 return Void();
293 }
294};
295
Steven Moreland0693f312016-11-09 15:06:14 -0800296struct ServiceNotification : public IServiceNotification {
297 std::mutex mutex;
298 std::condition_variable condition;
299
300 Return<void> onRegistration(const hidl_string &fqName,
301 const hidl_string &name,
302 bool preexisting) override {
303 if (preexisting) {
304 // not interested in things registered from previous runs of hidl_test
305 return Void();
306 }
307
308 std::unique_lock<std::mutex> lock(mutex);
309
310 mRegistered.push_back(std::string(fqName.c_str()) + "/" + name.c_str());
311
312 lock.unlock();
313 condition.notify_one();
314
315 return Void();
316 }
317
318 const std::vector<std::string> &getRegistrations() const {
319 return mRegistered;
320 }
321
322private:
323 std::vector<std::string> mRegistered{};
324};
325
Yifan Hong35d66002016-10-13 12:47:44 -0700326void signal_handler(int signal)
327{
328 if (signal == SIGTERM) {
329 ALOGD("SERVER %s shutting down...", gServiceName.c_str());
330 IPCThreadState::shutdown();
331 ALOGD("SERVER %s shutdown.", gServiceName.c_str());
332 exit(0);
333 }
334}
335
Yifan Hong1dc87932016-08-19 09:51:01 -0700336template <class T>
Yifan Hongccd782b2016-11-28 09:41:46 -0800337static pid_t forkServer(const std::string &serviceName) {
Yifan Hong35d66002016-10-13 12:47:44 -0700338 pid_t pid;
Steven Morelandc7167ca2016-11-28 11:29:55 -0800339
Yifan Hong35d66002016-10-13 12:47:44 -0700340 // use fork to create and kill to destroy server processes.
341 // getStub = true to get the passthrough version as the backend for the
342 // binderized service.
343 if ((pid = fork()) == 0) {
344 // in child process
Martijn Coenenfa55d6e2016-12-20 06:08:31 +0100345 configureRpcThreadpool(1, true /*callerWillJoin*/);
Yifan Hong35d66002016-10-13 12:47:44 -0700346 sp<T> server = T::getService(serviceName, true);
347 gServiceName = serviceName;
348 signal(SIGTERM, signal_handler);
Yifan Hongccd782b2016-11-28 09:41:46 -0800349 ALOGD("SERVER registering %s", serviceName.c_str());
Steven Morelandc7167ca2016-11-28 11:29:55 -0800350 ::android::status_t status = server->registerAsService(serviceName);
351 if (status != ::android::OK) {
Yifan Hongccd782b2016-11-28 09:41:46 -0800352 ALOGE("SERVER could not register %s", serviceName.c_str());
Steven Morelandc7167ca2016-11-28 11:29:55 -0800353 exit(-1);
354 }
Yifan Hongccd782b2016-11-28 09:41:46 -0800355 ALOGD("SERVER starting %s", serviceName.c_str());
Martijn Coenenfa55d6e2016-12-20 06:08:31 +0100356 joinRpcThreadpool();
Yifan Hongccd782b2016-11-28 09:41:46 -0800357 ALOGD("SERVER %s ends.", serviceName.c_str());
Yifan Hong35d66002016-10-13 12:47:44 -0700358 exit(0);
359 }
Steven Morelandc7167ca2016-11-28 11:29:55 -0800360
Yifan Hong35d66002016-10-13 12:47:44 -0700361 // in main process
362 return pid;
Yifan Hong1dc87932016-08-19 09:51:01 -0700363}
Andreas Huber9cd48d02016-08-03 14:25:59 -0700364
Yifan Hongbf459bc2016-08-23 16:50:37 -0700365static void killServer(pid_t pid, const char *serverName) {
366 if(kill(pid, SIGTERM)) {
367 ALOGE("Could not kill %s; errno = %d", serverName, errno);
368 } else {
369 int status;
Yifan Hong35d66002016-10-13 12:47:44 -0700370 ALOGD("Waiting for %s to exit...", serverName);
Yifan Hongbf459bc2016-08-23 16:50:37 -0700371 waitpid(pid, &status, 0);
Yifan Hong35d66002016-10-13 12:47:44 -0700372 if (status != 0) {
373 ALOGE("%s terminates abnormally with status %d", serverName, status);
374 }
375 ALOGD("Continuing...");
Yifan Hongbf459bc2016-08-23 16:50:37 -0700376 }
377}
378
Yifan Hongca890522016-10-12 10:03:41 -0700379class HidlEnvironmentBase : public ::testing::Environment {
Yifan Hong1e81c532016-10-18 18:43:46 -0700380protected:
Yifan Hongccd782b2016-11-28 09:41:46 -0800381 std::vector<std::pair<std::string, pid_t>> mPids;
382
Yifan Hong1dc87932016-08-19 09:51:01 -0700383public:
Steven Moreland01bcb772016-11-08 15:57:25 -0800384 sp<IServiceManager> manager;
Steven Morelandaa2b83a2016-12-21 15:52:11 -0800385 sp<ITokenManager> tokenManager;
Martijn Coenen99e6beb2016-12-01 15:48:42 +0100386 sp<IAllocator> ashmemAllocator;
387 sp<IMemoryTest> memoryTest;
Yifan Hong1e81c532016-10-18 18:43:46 -0700388 sp<IFetcher> fetcher;
Yifan Hong1dc87932016-08-19 09:51:01 -0700389 sp<IFoo> foo;
Martijn Coenen115d4282016-12-19 05:14:04 +0100390 sp<IFoo> dyingFoo;
Yifan Hong1dc87932016-08-19 09:51:01 -0700391 sp<IBar> bar;
Yifan Hongbf459bc2016-08-23 16:50:37 -0700392 sp<IGraph> graphInterface;
393 sp<IPointer> pointerInterface;
Yifan Hong3cccc0f2016-10-13 10:12:28 -0700394 sp<IPointer> validationPointerInterface;
Yifan Hongbf459bc2016-08-23 16:50:37 -0700395
Yifan Hongccd782b2016-11-28 09:41:46 -0800396 template <class T>
397 void addServer(const std::string &name) {
398 mPids.push_back({name, forkServer<T>(name)});
399 }
400
Yifan Hongca890522016-10-12 10:03:41 -0700401 void getServices() {
Steven Moreland01bcb772016-11-08 15:57:25 -0800402 manager = IServiceManager::getService("manager");
403
404 // alternatively:
405 // manager = defaultServiceManager()
406
407 ASSERT_NE(manager, nullptr);
408 ASSERT_TRUE(manager->isRemote()); // manager is always remote
409
Steven Morelandaa2b83a2016-12-21 15:52:11 -0800410 tokenManager = ITokenManager::getService("manager");
411 ASSERT_NE(tokenManager, nullptr);
412 ASSERT_TRUE(tokenManager->isRemote()); // tokenManager is always remote
413
Steven Moreland2a753532016-12-15 12:37:49 -0800414 ashmemAllocator = IAllocator::getService("ashmem");
415 ASSERT_NE(ashmemAllocator, nullptr);
416 ASSERT_TRUE(ashmemAllocator->isRemote()); // allocator is always remote
417
Yifan Hongc70f0d82016-10-10 14:50:22 -0700418 // getStub is true if we are in passthrough mode to skip checking
419 // binderized server, false for binderized mode.
Yifan Hong1e81c532016-10-18 18:43:46 -0700420
Martijn Coenen99e6beb2016-12-01 15:48:42 +0100421 memoryTest = IMemoryTest::getService("memory", gMode == PASSTHROUGH /* getStub */);
422 ASSERT_NE(memoryTest, nullptr);
423 ASSERT_EQ(memoryTest->isRemote(), gMode == BINDERIZED);
424
Yifan Hong1e81c532016-10-18 18:43:46 -0700425 fetcher = IFetcher::getService("fetcher", gMode == PASSTHROUGH /* getStub */);
426 ASSERT_NE(fetcher, nullptr);
427 ASSERT_EQ(fetcher->isRemote(), gMode == BINDERIZED);
428
Yifan Hongc70f0d82016-10-10 14:50:22 -0700429 foo = IFoo::getService("foo", gMode == PASSTHROUGH /* getStub */);
Yifan Hong7a827722016-10-06 17:20:12 -0700430 ASSERT_NE(foo, nullptr);
Yifan Hongc70f0d82016-10-10 14:50:22 -0700431 ASSERT_EQ(foo->isRemote(), gMode == BINDERIZED);
Yifan Hong1dc87932016-08-19 09:51:01 -0700432
Martijn Coenen115d4282016-12-19 05:14:04 +0100433 dyingFoo = IFoo::getService("dyingFoo", gMode == PASSTHROUGH /* getStub */);
434 ASSERT_NE(foo, nullptr);
435 ASSERT_EQ(foo->isRemote(), gMode == BINDERIZED);
436
Yifan Hongc70f0d82016-10-10 14:50:22 -0700437 bar = IBar::getService("foo", gMode == PASSTHROUGH /* getStub */);
Yifan Hong7a827722016-10-06 17:20:12 -0700438 ASSERT_NE(bar, nullptr);
Yifan Hongc70f0d82016-10-10 14:50:22 -0700439 ASSERT_EQ(bar->isRemote(), gMode == BINDERIZED);
Yifan Hong1dc87932016-08-19 09:51:01 -0700440
Yifan Hongc70f0d82016-10-10 14:50:22 -0700441 graphInterface = IGraph::getService("graph", gMode == PASSTHROUGH /* getStub */);
Yifan Hong7a827722016-10-06 17:20:12 -0700442 ASSERT_NE(graphInterface, nullptr);
Yifan Hongc70f0d82016-10-10 14:50:22 -0700443 ASSERT_EQ(graphInterface->isRemote(), gMode == BINDERIZED);
Yifan Hongbf459bc2016-08-23 16:50:37 -0700444
Yifan Hongc70f0d82016-10-10 14:50:22 -0700445 pointerInterface = IPointer::getService("pointer", gMode == PASSTHROUGH /* getStub */);
Yifan Hong3eac8a32016-10-11 10:02:59 -0700446 ASSERT_NE(pointerInterface, nullptr);
Yifan Hongc70f0d82016-10-10 14:50:22 -0700447 ASSERT_EQ(pointerInterface->isRemote(), gMode == BINDERIZED);
Yifan Hong3cccc0f2016-10-13 10:12:28 -0700448
449 // use passthrough mode as the validation object.
450 validationPointerInterface = IPointer::getService("pointer", true /* getStub */);
451 ASSERT_NE(validationPointerInterface, nullptr);
Yifan Hong1dc87932016-08-19 09:51:01 -0700452 }
Yifan Hong1e81c532016-10-18 18:43:46 -0700453
Martijn Coenen115d4282016-12-19 05:14:04 +0100454 void killServer(const char *serverName) {
455 for (const auto &pair : mPids) {
456 if (pair.first == serverName) {
457 ::killServer(pair.second, pair.first.c_str());
458 }
459 }
460 }
461
Yifan Hong1e81c532016-10-18 18:43:46 -0700462 virtual void TearDown() {
463 // clean up by killing server processes.
464 ALOGI("Environment tear-down beginning...");
465 ALOGI("Killing servers...");
Yifan Hongccd782b2016-11-28 09:41:46 -0800466 for (const auto &pair : mPids) {
Martijn Coenen115d4282016-12-19 05:14:04 +0100467 ::killServer(pair.second, pair.first.c_str());
Yifan Hong1e81c532016-10-18 18:43:46 -0700468 }
469 ALOGI("Servers all killed.");
470 ALOGI("Environment tear-down complete.");
471 }
Yifan Hong1dc87932016-08-19 09:51:01 -0700472};
473
Yifan Hongca890522016-10-12 10:03:41 -0700474class PassthroughEnvironment : public HidlEnvironmentBase {
475private:
Yifan Hongca890522016-10-12 10:03:41 -0700476 virtual void SetUp() {
477 ALOGI("Environment setup beginning...");
Yifan Hong1e81c532016-10-18 18:43:46 -0700478 // starts this even for passthrough mode.
479 // this is used in Bar's default implementation
Yifan Hongccd782b2016-11-28 09:41:46 -0800480 addServer<IChild>("child");
Yifan Hong1e81c532016-10-18 18:43:46 -0700481 sleep(1);
Yifan Hongca890522016-10-12 10:03:41 -0700482 getServices();
483 ALOGI("Environment setup complete.");
484 }
485};
486
487class BinderizedEnvironment : public HidlEnvironmentBase {
Yifan Hong1dc87932016-08-19 09:51:01 -0700488public:
489 virtual void SetUp() {
490 ALOGI("Environment setup beginning...");
Yifan Hongca890522016-10-12 10:03:41 -0700491
Martijn Coenen99e6beb2016-12-01 15:48:42 +0100492 addServer<IMemoryTest>("memory");
Yifan Hongccd782b2016-11-28 09:41:46 -0800493 addServer<IChild>("child");
494 addServer<IParent>("parent");
495 addServer<IFetcher>("fetcher");
496 addServer<IBar>("foo");
Martijn Coenen115d4282016-12-19 05:14:04 +0100497 addServer<IFoo>("dyingFoo");
Yifan Hongccd782b2016-11-28 09:41:46 -0800498 addServer<IGraph>("graph");
499 addServer<IPointer>("pointer");
Yifan Hong1dc87932016-08-19 09:51:01 -0700500
Yifan Hong1dc87932016-08-19 09:51:01 -0700501 sleep(1);
Yifan Hongca890522016-10-12 10:03:41 -0700502 getServices();
Yifan Hong1dc87932016-08-19 09:51:01 -0700503 ALOGI("Environment setup complete.");
504 }
Yifan Hong1dc87932016-08-19 09:51:01 -0700505};
506
Yifan Hongca890522016-10-12 10:03:41 -0700507class HidlTest : public ::testing::Test {
508public:
Steven Moreland01bcb772016-11-08 15:57:25 -0800509 sp<IServiceManager> manager;
Steven Morelandaa2b83a2016-12-21 15:52:11 -0800510 sp<ITokenManager> tokenManager;
Martijn Coenen99e6beb2016-12-01 15:48:42 +0100511 sp<IAllocator> ashmemAllocator;
512 sp<IMemoryTest> memoryTest;
Yifan Hong1e81c532016-10-18 18:43:46 -0700513 sp<IFetcher> fetcher;
Yifan Hongca890522016-10-12 10:03:41 -0700514 sp<IFoo> foo;
Martijn Coenen115d4282016-12-19 05:14:04 +0100515 sp<IFoo> dyingFoo;
Yifan Hongca890522016-10-12 10:03:41 -0700516 sp<IBar> bar;
Yifan Hongca890522016-10-12 10:03:41 -0700517 sp<IGraph> graphInterface;
518 sp<IPointer> pointerInterface;
Yifan Hong3cccc0f2016-10-13 10:12:28 -0700519 sp<IPointer> validationPointerInterface;
Yifan Hongca890522016-10-12 10:03:41 -0700520
Martijn Coenen115d4282016-12-19 05:14:04 +0100521 void killServer(const char *serverName) {
522 HidlEnvironmentBase *env;
523 if (gMode == BINDERIZED) {
524 env = gBinderizedEnvironment;
525 } else {
526 env = gPassthroughEnvironment;
527 }
528 env->killServer(serverName);
529 }
530
Yifan Hongca890522016-10-12 10:03:41 -0700531 virtual void SetUp() override {
532 ALOGI("Test setup beginning...");
533 HidlEnvironmentBase *env;
534 if (gMode == BINDERIZED) {
535 env = gBinderizedEnvironment;
536 } else {
537 env = gPassthroughEnvironment;
538 }
Steven Moreland01bcb772016-11-08 15:57:25 -0800539 manager = env->manager;
Steven Morelandaa2b83a2016-12-21 15:52:11 -0800540 tokenManager = env->tokenManager;
Martijn Coenen99e6beb2016-12-01 15:48:42 +0100541 ashmemAllocator = env->ashmemAllocator;
542 memoryTest = env->memoryTest;
Yifan Hong1e81c532016-10-18 18:43:46 -0700543 fetcher = env->fetcher;
Yifan Hongca890522016-10-12 10:03:41 -0700544 foo = env->foo;
Martijn Coenen115d4282016-12-19 05:14:04 +0100545 dyingFoo = env->dyingFoo;
Yifan Hongca890522016-10-12 10:03:41 -0700546 bar = env->bar;
Yifan Hongca890522016-10-12 10:03:41 -0700547 graphInterface = env->graphInterface;
548 pointerInterface = env->pointerInterface;
Yifan Hong3cccc0f2016-10-13 10:12:28 -0700549 validationPointerInterface = env->validationPointerInterface;
Yifan Hongca890522016-10-12 10:03:41 -0700550 ALOGI("Test setup complete");
551 }
552};
553
Yifan Hongf5cc2f72017-01-04 18:02:34 -0800554TEST_F(HidlTest, ToStringTest) {
555 using namespace android::hardware;
556
557 LOG(INFO) << toString(IFoo::Everything{});
558
Martijn Coenenf7b596b2017-01-13 14:07:59 +0100559 // Note that handles don't need to be deleted because MQDescriptor takes ownership
560 // and deletes them when destructed.
Yifan Hongf5cc2f72017-01-04 18:02:34 -0800561 auto handle = native_handle_create(0, 1);
Martijn Coenenf7b596b2017-01-13 14:07:59 +0100562 auto handle2 = native_handle_create(0, 1);
Yifan Hongf5cc2f72017-01-04 18:02:34 -0800563 handle->data[0] = 5;
Martijn Coenenf7b596b2017-01-13 14:07:59 +0100564 handle2->data[0] = 6;
Yifan Hongf5cc2f72017-01-04 18:02:34 -0800565 IFoo::Everything e {
566 .u = {.p = reinterpret_cast<void *>(0x5)},
567 .number = 10,
568 .h = handle,
569 .descSync = {std::vector<GrantorDescriptor>(), handle, 5},
Martijn Coenenf7b596b2017-01-13 14:07:59 +0100570 .descUnsync = {std::vector<GrantorDescriptor>(), handle2, 6},
Yifan Hongf5cc2f72017-01-04 18:02:34 -0800571 .mem = hidl_memory("mymem", handle, 5),
572 .p = reinterpret_cast<void *>(0x6),
573 .vs = {"hello", "world"},
574 .multidimArray = hidl_vec<hidl_string>{"hello", "great", "awesome", "nice"}.data(),
575 .sArray = hidl_vec<hidl_string>{"awesome", "thanks", "you're welcome"}.data(),
576 .anotherStruct = {.first = "first", .last = "last"},
577 .bf = IFoo::BitField::V0 | IFoo::BitField::V2
578 };
579 LOG(INFO) << toString(e);
580 LOG(INFO) << toString(foo);
581 // toString is for debugging purposes only; no good EXPECT
582 // statement can be written here.
Yifan Hongf5cc2f72017-01-04 18:02:34 -0800583}
584
Steven Moreland01bcb772016-11-08 15:57:25 -0800585TEST_F(HidlTest, ServiceListTest) {
586 static const std::set<std::string> binderizedSet = {
587 "android.hardware.tests.pointer@1.0::IPointer/pointer",
588 "android.hardware.tests.bar@1.0::IBar/foo",
589 "android.hardware.tests.inheritance@1.0::IFetcher/fetcher",
Steven Moreland01bcb772016-11-08 15:57:25 -0800590 "android.hardware.tests.inheritance@1.0::IParent/parent",
591 "android.hardware.tests.inheritance@1.0::IParent/child",
592 "android.hardware.tests.inheritance@1.0::IChild/child",
593 "android.hardware.tests.pointer@1.0::IGraph/graph",
594 "android.hardware.tests.inheritance@1.0::IGrandparent/child",
595 "android.hardware.tests.foo@1.0::IFoo/foo",
596 "android.hidl.manager@1.0::IServiceManager/manager",
597 };
598
599 static const std::set<std::string> passthroughSet = {
600 "android.hidl.manager@1.0::IServiceManager/manager"
601 };
602
603 std::set<std::string> activeSet;
604
605 switch(gMode) {
606 case BINDERIZED: {
607 activeSet = binderizedSet;
608 } break;
609
610 case PASSTHROUGH: {
611 activeSet = passthroughSet;
612 } break;
613 default:
614 EXPECT_TRUE(false) << "unrecognized mode";
615 }
616
617 EXPECT_OK(manager->list([&activeSet](const hidl_vec<hidl_string> &registered){
618 std::set<std::string> registeredSet;
619
620 for (size_t i = 0; i < registered.size(); i++) {
621 registeredSet.insert(registered[i]);
622 }
623
624 std::set<std::string> difference;
625 std::set_difference(activeSet.begin(), activeSet.end(),
626 registeredSet.begin(), registeredSet.end(),
627 std::inserter(difference, difference.begin()));
628
629 EXPECT_EQ(difference.size(), 0u) << "service(s) not registered " << to_string(difference);
630 }));
631}
632
633// passthrough TODO(b/32747392)
634TEST_F(HidlTest, ServiceListByInterfaceTest) {
635 if (gMode == BINDERIZED) {
Steven Morelandd39133b2016-11-11 12:30:08 -0800636 EXPECT_OK(manager->listByInterface(IParent::descriptor,
Steven Moreland01bcb772016-11-08 15:57:25 -0800637 [](const hidl_vec<hidl_string> &registered) {
638 std::set<std::string> registeredSet;
639
640 for (size_t i = 0; i < registered.size(); i++) {
641 registeredSet.insert(registered[i]);
642 }
643
644 std::set<std::string> activeSet = {
645 "parent", "child"
646 };
647 std::set<std::string> difference;
648 std::set_difference(activeSet.begin(), activeSet.end(),
649 registeredSet.begin(), registeredSet.end(),
650 std::inserter(difference, difference.begin()));
651
652 EXPECT_EQ(difference.size(), 0u) << "service(s) not registered " << to_string(difference);
653 }));
654 }
655}
656
657// passthrough TODO(b/32747392)
658TEST_F(HidlTest, ServiceParentTest) {
659 if (gMode == BINDERIZED) {
660 sp<IParent> parent = IParent::getService("child");
661
662 EXPECT_NE(parent, nullptr);
663 }
664}
665
Steven Moreland0693f312016-11-09 15:06:14 -0800666// passthrough TODO(b/32747392)
667TEST_F(HidlTest, ServiceNotificationTest) {
668 if (gMode == BINDERIZED) {
669 ServiceNotification *notification = new ServiceNotification();
670
671 std::string instanceName = "test-instance";
672 EXPECT_TRUE(ISimple::registerForNotifications(instanceName, notification));
673
Steven Moreland0693f312016-11-09 15:06:14 -0800674 Simple* instance = new Simple(1);
Steven Morelandc7167ca2016-11-28 11:29:55 -0800675 EXPECT_EQ(::android::OK, instance->registerAsService(instanceName));
Steven Moreland0693f312016-11-09 15:06:14 -0800676
677 std::unique_lock<std::mutex> lock(notification->mutex);
678
679 notification->condition.wait_for(
680 lock,
681 std::chrono::milliseconds(2),
682 [&notification]() {
683 return notification->getRegistrations().size() >= 1;
684 });
685
686 std::vector<std::string> registrations = notification->getRegistrations();
687
688 EXPECT_EQ(registrations.size(), 1u);
689
690 EXPECT_EQ(to_string(registrations.data(), registrations.size()),
Steven Morelandd39133b2016-11-11 12:30:08 -0800691 std::string("['") + Simple::descriptor + "/" + instanceName + "']");
Steven Moreland0693f312016-11-09 15:06:14 -0800692 }
693}
694
695// passthrough TODO(b/32747392)
696TEST_F(HidlTest, ServiceAllNotificationTest) {
697 if (gMode == BINDERIZED) {
698 ServiceNotification *notification = new ServiceNotification();
699
700 std::string instanceOne = "test-instance-one";
701 std::string instanceTwo = "test-instance-two";
702 EXPECT_TRUE(ISimple::registerForNotifications("", notification));
703
Steven Moreland0693f312016-11-09 15:06:14 -0800704 Simple* instanceA = new Simple(1);
Steven Morelandc7167ca2016-11-28 11:29:55 -0800705 EXPECT_EQ(::android::OK, instanceA->registerAsService(instanceOne));
Steven Moreland0693f312016-11-09 15:06:14 -0800706 Simple* instanceB = new Simple(2);
Steven Morelandc7167ca2016-11-28 11:29:55 -0800707 EXPECT_EQ(::android::OK, instanceB->registerAsService(instanceTwo));
Steven Moreland0693f312016-11-09 15:06:14 -0800708
709 std::unique_lock<std::mutex> lock(notification->mutex);
710
711 notification->condition.wait_for(
712 lock,
713 std::chrono::milliseconds(2),
714 [&notification]() {
715 return notification->getRegistrations().size() >= 2;
716 });
717
718 std::vector<std::string> registrations = notification->getRegistrations();
719 std::sort(registrations.begin(), registrations.end());
720
721 EXPECT_EQ(registrations.size(), 2u);
722
Steven Morelandd39133b2016-11-11 12:30:08 -0800723 std::string descriptor = ISimple::descriptor;
Steven Moreland0693f312016-11-09 15:06:14 -0800724
725 EXPECT_EQ(to_string(registrations.data(), registrations.size()),
726 "['" + descriptor + "/" + instanceOne + "', '"
727 + descriptor + "/" + instanceTwo + "']");
728 }
729}
730
Steven Morelandaa2b83a2016-12-21 15:52:11 -0800731TEST_F(HidlTest, TestToken) {
732 Return<uint64_t> ret = tokenManager->createToken(manager);
733 EXPECT_OK(ret);
734 uint64_t token = ret;
735
Martijn Coenenb40ef022017-01-02 15:21:46 +0100736 Return<sp<IBase>> retService = tokenManager->get(token);
737 EXPECT_OK(retService);
738 if (retService.isOk()) {
739 sp<IBase> service = retService;
740 EXPECT_NE(nullptr, service.get());
741 sp<IServiceManager> retManager = IServiceManager::castFrom(service);
Steven Morelandaa2b83a2016-12-21 15:52:11 -0800742
743 // TODO(b/33818800): should have only one Bp per process
744 // EXPECT_EQ(manager, retManager);
745
746 EXPECT_NE(nullptr, retManager.get());
Martijn Coenenb40ef022017-01-02 15:21:46 +0100747 }
Steven Morelandaa2b83a2016-12-21 15:52:11 -0800748
749 Return<bool> unregisterRet = tokenManager->unregister(token);
750
751 EXPECT_OK(unregisterRet);
752 if (unregisterRet.isOk()) {
753 EXPECT_TRUE(ret);
754 }
755}
756
Martijn Coenen99e6beb2016-12-01 15:48:42 +0100757TEST_F(HidlTest, TestSharedMemory) {
758 const uint8_t kValue = 0xCA;
759 hidl_memory mem_copy;
760 EXPECT_OK(ashmemAllocator->allocate(1024, [&](bool success, const hidl_memory& mem) {
761 EXPECT_EQ(success, true);
762
763 sp<IMemory> memory = mapMemory(mem);
764
765 EXPECT_NE(memory, nullptr);
766
767 uint8_t* data = static_cast<uint8_t*>(static_cast<void*>(memory->getPointer()));
768 EXPECT_NE(data, nullptr);
769
770 EXPECT_EQ(memory->getSize(), mem.size());
771
772 memory->update();
773 memset(data, 0, memory->getSize());
774 memory->commit();
775
776 mem_copy = mem;
777 memoryTest->fillMemory(mem, kValue);
778 for (size_t i = 0; i < mem.size(); i++) {
779 EXPECT_EQ(kValue, data[i]);
780 }
781 }));
782
783 // Test the memory persists after the call
784 sp<IMemory> memory = mapMemory(mem_copy);
785
786 EXPECT_NE(memory, nullptr);
787
788 uint8_t* data = static_cast<uint8_t*>(static_cast<void*>(memory->getPointer()));
789 EXPECT_NE(data, nullptr);
790
791 for (size_t i = 0; i < mem_copy.size(); i++) {
792 EXPECT_EQ(kValue, data[i]);
793 }
794}
795
Steven Morelandf31f1652017-01-06 18:33:42 -0800796TEST_F(HidlTest, NullSharedMemory) {
797 hidl_memory memory{};
798
799 EXPECT_EQ(nullptr, memory.handle());
800
801 EXPECT_OK(memoryTest->haveSomeMemory(memory, [&](const hidl_memory &mem) {
802 EXPECT_EQ(nullptr, mem.handle());
803 }));
804}
805
Yifan Hongc75fd472017-01-11 12:37:31 -0800806TEST_F(HidlTest, FooGetDescriptorTest) {
807 EXPECT_OK(foo->interfaceDescriptor([&] (const auto &desc) {
808 EXPECT_EQ(desc, gMode == BINDERIZED
809 ? IBar::descriptor // service is actually IBar in binderized mode
810 : IFoo::descriptor); // dlopened, so service is IFoo
811 }));
812}
813
Yifan Hong1dc87932016-08-19 09:51:01 -0700814TEST_F(HidlTest, FooDoThisTest) {
Iliyan Malchevb31e10c2016-08-13 23:03:25 -0700815 ALOGI("CLIENT call doThis.");
Yifan Hong1dc87932016-08-19 09:51:01 -0700816 EXPECT_OK(foo->doThis(1.0f));
Iliyan Malchevb31e10c2016-08-13 23:03:25 -0700817 ALOGI("CLIENT doThis returned.");
Yifan Hong1dc87932016-08-19 09:51:01 -0700818}
Andreas Huber9cd48d02016-08-03 14:25:59 -0700819
Yifan Hong1dc87932016-08-19 09:51:01 -0700820TEST_F(HidlTest, FooDoThatAndReturnSomethingTest) {
Iliyan Malchevb31e10c2016-08-13 23:03:25 -0700821 ALOGI("CLIENT call doThatAndReturnSomething.");
Steven Moreland2ae5bca2016-12-01 05:56:49 +0000822 int32_t result = foo->doThatAndReturnSomething(2.0f);
823 ALOGI("CLIENT doThatAndReturnSomething returned %d.", result);
824 EXPECT_EQ(result, 666);
Yifan Hong1dc87932016-08-19 09:51:01 -0700825}
Andreas Huber9cd48d02016-08-03 14:25:59 -0700826
Yifan Hong1dc87932016-08-19 09:51:01 -0700827TEST_F(HidlTest, FooDoQuiteABitTest) {
Iliyan Malchevb31e10c2016-08-13 23:03:25 -0700828 ALOGI("CLIENT call doQuiteABit");
Steven Moreland2ae5bca2016-12-01 05:56:49 +0000829 double something = foo->doQuiteABit(1, 2, 3.0f, 4.0);
830 ALOGI("CLIENT doQuiteABit returned %f.", something);
831 EXPECT_DOUBLE_EQ(something, 666.5);
Yifan Hong1dc87932016-08-19 09:51:01 -0700832}
833
834TEST_F(HidlTest, FooDoSomethingElseTest) {
Andreas Huber9cd48d02016-08-03 14:25:59 -0700835
Iliyan Malchevb31e10c2016-08-13 23:03:25 -0700836 ALOGI("CLIENT call doSomethingElse");
Andreas Huberf03332a2016-09-22 15:35:43 -0700837 hidl_array<int32_t, 15> param;
Andreas Huber9cd48d02016-08-03 14:25:59 -0700838 for (size_t i = 0; i < sizeof(param) / sizeof(param[0]); ++i) {
839 param[i] = i;
840 }
Yifan Hong1dc87932016-08-19 09:51:01 -0700841 EXPECT_OK(foo->doSomethingElse(param, [&](const auto &something) {
Iliyan Malchevb31e10c2016-08-13 23:03:25 -0700842 ALOGI("CLIENT doSomethingElse returned %s.",
Andreas Huber5e44a292016-09-27 14:52:39 -0700843 to_string(something).c_str());
Yifan Hong1dc87932016-08-19 09:51:01 -0700844 int32_t expect[] = {0, 2, 4, 6, 8, 10, 12, 14, 16, 18, 20, 22, 24,
845 26, 28, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 1, 2};
Steven Morelande70455b2016-09-14 15:46:36 -0700846 EXPECT_TRUE(isArrayEqual(something, expect, 32));
Yifan Hong1dc87932016-08-19 09:51:01 -0700847 }));
848}
Andreas Huber9cd48d02016-08-03 14:25:59 -0700849
Yifan Hong1dc87932016-08-19 09:51:01 -0700850TEST_F(HidlTest, FooDoStuffAndReturnAStringTest) {
Iliyan Malchevb31e10c2016-08-13 23:03:25 -0700851 ALOGI("CLIENT call doStuffAndReturnAString");
Yifan Hong1dc87932016-08-19 09:51:01 -0700852 EXPECT_OK(foo->doStuffAndReturnAString([&](const auto &something) {
Iliyan Malchevb31e10c2016-08-13 23:03:25 -0700853 ALOGI("CLIENT doStuffAndReturnAString returned '%s'.",
Andreas Huber9cd48d02016-08-03 14:25:59 -0700854 something.c_str());
Yifan Hong1dc87932016-08-19 09:51:01 -0700855 EXPECT_STREQ(something.c_str(), "Hello, world");
Steven Moreland6e3f9f42017-01-30 11:41:49 -0800856 EXPECT_EQ(strlen("Hello, world"), something.size());
Yifan Hong1dc87932016-08-19 09:51:01 -0700857 }));
858}
Andreas Huber9cd48d02016-08-03 14:25:59 -0700859
Yifan Hong1dc87932016-08-19 09:51:01 -0700860TEST_F(HidlTest, FooMapThisVectorTest) {
Andreas Huber9cd48d02016-08-03 14:25:59 -0700861 hidl_vec<int32_t> vecParam;
862 vecParam.resize(10);
863 for (size_t i = 0; i < 10; ++i) {
864 vecParam[i] = i;
865 }
Yifan Hong1dc87932016-08-19 09:51:01 -0700866 EXPECT_OK(foo->mapThisVector(vecParam, [&](const auto &something) {
Iliyan Malchevb31e10c2016-08-13 23:03:25 -0700867 ALOGI("CLIENT mapThisVector returned %s.",
Andreas Huber5e44a292016-09-27 14:52:39 -0700868 to_string(something).c_str());
Yifan Hong1dc87932016-08-19 09:51:01 -0700869 int32_t expect[] = {0, 2, 4, 6, 8, 10, 12, 14, 16, 18};
Steven Morelande70455b2016-09-14 15:46:36 -0700870 EXPECT_TRUE(isArrayEqual(something, expect, something.size()));
Yifan Hong1dc87932016-08-19 09:51:01 -0700871 }));
872}
Andreas Huber9cd48d02016-08-03 14:25:59 -0700873
Yifan Hongdef2cfb2016-12-14 16:00:24 -0800874TEST_F(HidlTest, WrapTest) {
Yifan Hong01e7cde2017-01-09 17:45:45 -0800875 using ::android::hardware::tests::foo::V1_0::BnHwSimple;
Yifan Hongdef2cfb2016-12-14 16:00:24 -0800876 using ::android::hardware::tests::foo::V1_0::BsSimple;
Yifan Hong01e7cde2017-01-09 17:45:45 -0800877 using ::android::hardware::tests::foo::V1_0::BpHwSimple;
Yifan Hongdef2cfb2016-12-14 16:00:24 -0800878 using ::android::hardware::HidlInstrumentor;
879 nsecs_t now;
880 int i = 0;
881
882 now = systemTime();
Yifan Hong01e7cde2017-01-09 17:45:45 -0800883 new BnHwSimple(new Simple(1));
884 EXPECT_LT(systemTime() - now, 2000000) << " for BnHwSimple(nonnull)";
Yifan Hongdef2cfb2016-12-14 16:00:24 -0800885
886 now = systemTime();
Yifan Hong01e7cde2017-01-09 17:45:45 -0800887 new BnHwSimple(nullptr);
888 EXPECT_LT(systemTime() - now, 2000000) << " for BnHwSimple(null)";
Yifan Hongdef2cfb2016-12-14 16:00:24 -0800889
890 now = systemTime();
891 new BsSimple(new Simple(1));
892 EXPECT_LT(systemTime() - now, 2000000) << " for BsSimple(nonnull)";
893
894 now = systemTime();
895 new BsSimple(nullptr);
896 EXPECT_LT(systemTime() - now, 2000000) << " for BsSimple(null)";
897
898 now = systemTime();
Yifan Hong01e7cde2017-01-09 17:45:45 -0800899 new BpHwSimple(nullptr);
900 EXPECT_LT(systemTime() - now, 2000000) << " for BpHwSimple(null)";
Yifan Hongdef2cfb2016-12-14 16:00:24 -0800901
902 now = systemTime();
Zhuoyao Zhangd10feea2017-01-23 17:29:58 -0800903 new ::android::hardware::HidlInstrumentor("", "");
Yifan Hongdef2cfb2016-12-14 16:00:24 -0800904 EXPECT_LT(systemTime() - now, 2000000) << " for HidlInstrumentor";
905
906 now = systemTime();
907 i++;
908 EXPECT_LT(systemTime() - now, 1000) << " for nothing";
909}
910
Yifan Hong1dc87932016-08-19 09:51:01 -0700911TEST_F(HidlTest, FooCallMeTest) {
Yifan Hong11992a62016-11-09 18:07:40 -0800912
913 sp<IFooCallback> fooCb = new FooCallback();
914
Iliyan Malchevb31e10c2016-08-13 23:03:25 -0700915 ALOGI("CLIENT call callMe.");
Iliyan Malchev0acf4192016-08-22 19:33:20 -0700916 // callMe is oneway, should return instantly.
917 nsecs_t now;
918 now = systemTime();
919 EXPECT_OK(foo->callMe(fooCb));
Yifan Hong3eac8a32016-10-11 10:02:59 -0700920 EXPECT_LT(systemTime() - now, ONEWAY_TOLERANCE_NS);
Iliyan Malchevb31e10c2016-08-13 23:03:25 -0700921 ALOGI("CLIENT callMe returned.");
Iliyan Malchev0acf4192016-08-22 19:33:20 -0700922
923 // Bar::callMe will invoke three methods on FooCallback; one will return
924 // right away (even though it is a two-way method); the second one will
Yifan Hong3eac8a32016-10-11 10:02:59 -0700925 // block Bar for DELAY_S seconds, and the third one will return
Iliyan Malchev0acf4192016-08-22 19:33:20 -0700926 // to Bar right away (is oneway) but will itself block for DELAY_S seconds.
927 // We need a way to make sure that these three things have happened within
928 // 2*DELAY_S seconds plus some small tolerance.
929 //
930 // Method FooCallback::reportResults() takes a timeout parameter. It blocks for
931 // that length of time, while waiting for the three methods above to
932 // complete. It returns the information of whether each method was invoked,
933 // as well as how long the body of the method took to execute. We verify
934 // the information returned by reportResults() against the timeout we pass (which
935 // is long enough for the method bodies to execute, plus tolerance), and
936 // verify that eachof them executed, as expected, and took the length of
937 // time to execute that we also expect.
938
Yifan Hongfcf94e42016-12-07 15:49:51 -0800939 const nsecs_t waitNs =
940 3 * DELAY_NS + TOLERANCE_NS;
Iliyan Malchev0acf4192016-08-22 19:33:20 -0700941 const nsecs_t reportResultsNs =
Yifan Hong3eac8a32016-10-11 10:02:59 -0700942 2 * DELAY_NS + TOLERANCE_NS;
Andreas Huber03866f52016-08-30 14:19:52 -0700943
Iliyan Malchev0acf4192016-08-22 19:33:20 -0700944 ALOGI("CLIENT: Waiting for up to %" PRId64 " seconds.",
Yifan Hongfcf94e42016-12-07 15:49:51 -0800945 nanoseconds_to_seconds(waitNs));
Iliyan Malchev0acf4192016-08-22 19:33:20 -0700946
Yifan Hongfcf94e42016-12-07 15:49:51 -0800947 fooCb->reportResults(waitNs,
Iliyan Malchev0acf4192016-08-22 19:33:20 -0700948 [&](int64_t timeLeftNs,
Andreas Huberf03332a2016-09-22 15:35:43 -0700949 const hidl_array<IFooCallback::InvokeInfo, 3> &invokeResults) {
Iliyan Malchev0acf4192016-08-22 19:33:20 -0700950 ALOGI("CLIENT: FooCallback::reportResults() is returning data.");
951 ALOGI("CLIENT: Waited for %" PRId64 " milliseconds.",
Yifan Hongfcf94e42016-12-07 15:49:51 -0800952 nanoseconds_to_milliseconds(waitNs - timeLeftNs));
Iliyan Malchev0acf4192016-08-22 19:33:20 -0700953
Yifan Hongfcf94e42016-12-07 15:49:51 -0800954 EXPECT_LE(waitNs - timeLeftNs, reportResultsNs)
955 << "waited for "
956 << (timeLeftNs >= 0 ? "" : "more than ")
957 << (timeLeftNs >= 0 ? (waitNs - timeLeftNs) : waitNs)
958 << "ns, expect to finish in "
959 << reportResultsNs << " ns";
Iliyan Malchev0acf4192016-08-22 19:33:20 -0700960
961 // two-way method, was supposed to return right away
962 EXPECT_TRUE(invokeResults[0].invoked);
Yifan Hong3eac8a32016-10-11 10:02:59 -0700963 EXPECT_LE(invokeResults[0].timeNs, invokeResults[0].callerBlockedNs);
964 EXPECT_LE(invokeResults[0].callerBlockedNs, TOLERANCE_NS);
Iliyan Malchev0acf4192016-08-22 19:33:20 -0700965 // two-way method, was supposed to block caller for DELAY_NS
966 EXPECT_TRUE(invokeResults[1].invoked);
Yifan Hong3eac8a32016-10-11 10:02:59 -0700967 EXPECT_LE(invokeResults[1].timeNs, invokeResults[1].callerBlockedNs);
968 EXPECT_LE(invokeResults[1].callerBlockedNs,
969 DELAY_NS + TOLERANCE_NS);
Iliyan Malchev0acf4192016-08-22 19:33:20 -0700970 // one-way method, do not block caller, but body was supposed to block for DELAY_NS
971 EXPECT_TRUE(invokeResults[2].invoked);
Yifan Hong3eac8a32016-10-11 10:02:59 -0700972 EXPECT_LE(invokeResults[2].callerBlockedNs, ONEWAY_TOLERANCE_NS);
973 EXPECT_LE(invokeResults[2].timeNs, DELAY_NS + TOLERANCE_NS);
Iliyan Malchev0acf4192016-08-22 19:33:20 -0700974 });
975}
976
Steven Moreland2ae5bca2016-12-01 05:56:49 +0000977
978
Yifan Hong1dc87932016-08-19 09:51:01 -0700979TEST_F(HidlTest, FooUseAnEnumTest) {
980 ALOGI("CLIENT call useAnEnum.");
Steven Moreland2ae5bca2016-12-01 05:56:49 +0000981 IFoo::SomeEnum sleepy = foo->useAnEnum(IFoo::SomeEnum::quux);
982 ALOGI("CLIENT useAnEnum returned %u", (unsigned)sleepy);
983 EXPECT_EQ(sleepy, IFoo::SomeEnum::goober);
Yifan Hong1dc87932016-08-19 09:51:01 -0700984}
Andreas Huber9cd48d02016-08-03 14:25:59 -0700985
Yifan Hong1dc87932016-08-19 09:51:01 -0700986TEST_F(HidlTest, FooHaveAGooberTest) {
Andreas Huber9cd48d02016-08-03 14:25:59 -0700987 hidl_vec<IFoo::Goober> gooberVecParam;
988 gooberVecParam.resize(2);
989 gooberVecParam[0].name = "Hello";
990 gooberVecParam[1].name = "World";
991
Iliyan Malchevb31e10c2016-08-13 23:03:25 -0700992 ALOGI("CLIENT call haveAGooberVec.");
Yifan Hong1dc87932016-08-19 09:51:01 -0700993 EXPECT_OK(foo->haveAGooberVec(gooberVecParam));
Iliyan Malchevb31e10c2016-08-13 23:03:25 -0700994 ALOGI("CLIENT haveAGooberVec returned.");
Andreas Huber9cd48d02016-08-03 14:25:59 -0700995
Iliyan Malchevb31e10c2016-08-13 23:03:25 -0700996 ALOGI("CLIENT call haveaGoober.");
Yifan Hong1dc87932016-08-19 09:51:01 -0700997 EXPECT_OK(foo->haveAGoober(gooberVecParam[0]));
Iliyan Malchevb31e10c2016-08-13 23:03:25 -0700998 ALOGI("CLIENT haveaGoober returned.");
999
1000 ALOGI("CLIENT call haveAGooberArray.");
Andreas Huberf03332a2016-09-22 15:35:43 -07001001 hidl_array<IFoo::Goober, 20> gooberArrayParam;
Yifan Hong1dc87932016-08-19 09:51:01 -07001002 EXPECT_OK(foo->haveAGooberArray(gooberArrayParam));
Iliyan Malchevb31e10c2016-08-13 23:03:25 -07001003 ALOGI("CLIENT haveAGooberArray returned.");
Yifan Hong1dc87932016-08-19 09:51:01 -07001004}
Steven Moreland88ca4512016-08-11 11:24:10 -07001005
Yifan Hong1dc87932016-08-19 09:51:01 -07001006TEST_F(HidlTest, FooHaveATypeFromAnotherFileTest) {
Iliyan Malchevb31e10c2016-08-13 23:03:25 -07001007 ALOGI("CLIENT call haveATypeFromAnotherFile.");
Steven Moreland88ca4512016-08-11 11:24:10 -07001008 Abc abcParam{};
1009 abcParam.x = "alphabet";
1010 abcParam.y = 3.14f;
Yifan Honga65bb2c2016-10-27 13:17:14 -07001011 native_handle_t *handle = native_handle_create(0, 0);
1012 abcParam.z = handle;
Yifan Hong1dc87932016-08-19 09:51:01 -07001013 EXPECT_OK(foo->haveATypeFromAnotherFile(abcParam));
Iliyan Malchevb31e10c2016-08-13 23:03:25 -07001014 ALOGI("CLIENT haveATypeFromAnotherFile returned.");
Yifan Honga65bb2c2016-10-27 13:17:14 -07001015 native_handle_delete(handle);
Steven Moreland88ca4512016-08-11 11:24:10 -07001016 abcParam.z = NULL;
Yifan Hong1dc87932016-08-19 09:51:01 -07001017}
Andreas Huber9cd48d02016-08-03 14:25:59 -07001018
Yifan Hong1dc87932016-08-19 09:51:01 -07001019TEST_F(HidlTest, FooHaveSomeStringsTest) {
Iliyan Malchevb31e10c2016-08-13 23:03:25 -07001020 ALOGI("CLIENT call haveSomeStrings.");
Andreas Huberf03332a2016-09-22 15:35:43 -07001021 hidl_array<hidl_string, 3> stringArrayParam;
Andreas Huber9cd48d02016-08-03 14:25:59 -07001022 stringArrayParam[0] = "What";
1023 stringArrayParam[1] = "a";
1024 stringArrayParam[2] = "disaster";
Steven Moreland67f67b42016-09-29 08:59:02 -07001025 EXPECT_OK(foo->haveSomeStrings(
1026 stringArrayParam,
1027 [&](const auto &out) {
1028 ALOGI("CLIENT haveSomeStrings returned %s.",
1029 to_string(out).c_str());
1030
1031 EXPECT_EQ(to_string(out), "['Hello', 'World']");
1032 }));
Iliyan Malchevb31e10c2016-08-13 23:03:25 -07001033 ALOGI("CLIENT haveSomeStrings returned.");
Yifan Hong1dc87932016-08-19 09:51:01 -07001034}
Andreas Huber9cd48d02016-08-03 14:25:59 -07001035
Yifan Hong1dc87932016-08-19 09:51:01 -07001036TEST_F(HidlTest, FooHaveAStringVecTest) {
Iliyan Malchevb31e10c2016-08-13 23:03:25 -07001037 ALOGI("CLIENT call haveAStringVec.");
Andreas Huber9cd48d02016-08-03 14:25:59 -07001038 hidl_vec<hidl_string> stringVecParam;
1039 stringVecParam.resize(3);
1040 stringVecParam[0] = "What";
1041 stringVecParam[1] = "a";
1042 stringVecParam[2] = "disaster";
Steven Moreland67f67b42016-09-29 08:59:02 -07001043 EXPECT_OK(foo->haveAStringVec(
1044 stringVecParam,
1045 [&](const auto &out) {
1046 ALOGI("CLIENT haveAStringVec returned %s.",
1047 to_string(out).c_str());
1048
1049 EXPECT_EQ(to_string(out), "['Hello', 'World']");
1050 }));
Iliyan Malchevb31e10c2016-08-13 23:03:25 -07001051 ALOGI("CLIENT haveAStringVec returned.");
Yifan Hong1dc87932016-08-19 09:51:01 -07001052}
Andreas Huber6cb08cf2016-08-03 15:44:51 -07001053
Andreas Huberf9d49f12016-09-12 14:58:36 -07001054TEST_F(HidlTest, FooTransposeMeTest) {
Andreas Huberf03332a2016-09-22 15:35:43 -07001055 hidl_array<float, 3, 5> in;
Andreas Huberf9d49f12016-09-12 14:58:36 -07001056 float k = 1.0f;
1057 for (size_t i = 0; i < 3; ++i) {
1058 for (size_t j = 0; j < 5; ++j, ++k) {
1059 in[i][j] = k;
1060 }
1061 }
1062
Andreas Huberf03332a2016-09-22 15:35:43 -07001063 ALOGI("CLIENT call transposeMe(%s).", to_string(in).c_str());
Andreas Huberf9d49f12016-09-12 14:58:36 -07001064
1065 EXPECT_OK(foo->transposeMe(
Andreas Huberf03332a2016-09-22 15:35:43 -07001066 in,
Andreas Huberf9d49f12016-09-12 14:58:36 -07001067 [&](const auto &out) {
1068 ALOGI("CLIENT transposeMe returned %s.",
Andreas Huberf03332a2016-09-22 15:35:43 -07001069 to_string(out).c_str());
Andreas Huberf9d49f12016-09-12 14:58:36 -07001070
1071 for (size_t i = 0; i < 3; ++i) {
1072 for (size_t j = 0; j < 5; ++j) {
Andreas Huberf03332a2016-09-22 15:35:43 -07001073 EXPECT_EQ(out[j][i], in[i][j]);
Andreas Huberf9d49f12016-09-12 14:58:36 -07001074 }
1075 }
1076 }));
1077}
1078
1079TEST_F(HidlTest, FooCallingDrWhoTest) {
1080 IFoo::MultiDimensional in;
1081
1082 size_t k = 0;
1083 for (size_t i = 0; i < 5; ++i) {
1084 for (size_t j = 0; j < 3; ++j, ++k) {
Andreas Huberf03332a2016-09-22 15:35:43 -07001085 in.quuxMatrix[i][j].first = ("First " + std::to_string(k)).c_str();
1086 in.quuxMatrix[i][j].last = ("Last " + std::to_string(15-k)).c_str();
Andreas Huberf9d49f12016-09-12 14:58:36 -07001087 }
1088 }
1089
1090 ALOGI("CLIENT call callingDrWho(%s).",
1091 MultiDimensionalToString(in).c_str());
1092
1093 EXPECT_OK(foo->callingDrWho(
1094 in,
1095 [&](const auto &out) {
1096 ALOGI("CLIENT callingDrWho returned %s.",
1097 MultiDimensionalToString(out).c_str());
1098
Andreas Huber709b62d2016-09-19 11:21:18 -07001099 size_t k = 0;
Andreas Huberf9d49f12016-09-12 14:58:36 -07001100 for (size_t i = 0; i < 5; ++i) {
Andreas Huber709b62d2016-09-19 11:21:18 -07001101 for (size_t j = 0; j < 3; ++j, ++k) {
Andreas Huberf03332a2016-09-22 15:35:43 -07001102 EXPECT_STREQ(
1103 out.quuxMatrix[i][j].first.c_str(),
1104 in.quuxMatrix[4 - i][2 - j].last.c_str());
Andreas Huberf9d49f12016-09-12 14:58:36 -07001105
1106 EXPECT_STREQ(
Andreas Huberf03332a2016-09-22 15:35:43 -07001107 out.quuxMatrix[i][j].last.c_str(),
1108 in.quuxMatrix[4 - i][2 - j].first.c_str());
Andreas Huberf9d49f12016-09-12 14:58:36 -07001109 }
1110 }
1111 }));
1112}
1113
Andreas Huber709b62d2016-09-19 11:21:18 -07001114static std::string numberToEnglish(int x) {
1115 static const char *const kDigits[] = {
1116 "zero",
1117 "one",
1118 "two",
1119 "three",
1120 "four",
1121 "five",
1122 "six",
1123 "seven",
1124 "eight",
1125 "nine",
1126 };
1127
1128 if (x < 0) {
1129 return "negative " + numberToEnglish(-x);
1130 }
1131
1132 if (x < 10) {
1133 return kDigits[x];
1134 }
1135
1136 if (x <= 15) {
1137 static const char *const kSpecialTens[] = {
1138 "ten", "eleven", "twelve", "thirteen", "fourteen", "fifteen",
1139 };
1140
1141 return kSpecialTens[x - 10];
1142 }
1143
1144 if (x < 20) {
1145 return std::string(kDigits[x % 10]) + "teen";
1146 }
1147
1148 if (x < 100) {
1149 static const char *const kDecades[] = {
1150 "twenty", "thirty", "forty", "fifty", "sixty", "seventy",
1151 "eighty", "ninety",
1152 };
1153
1154 return std::string(kDecades[x / 10 - 2]) + kDigits[x % 10];
1155 }
1156
1157 return "positively huge!";
1158}
1159
1160TEST_F(HidlTest, FooTransposeTest) {
1161 IFoo::StringMatrix5x3 in;
1162
Andreas Huber709b62d2016-09-19 11:21:18 -07001163 for (int i = 0; i < 5; ++i) {
Andreas Huberf03332a2016-09-22 15:35:43 -07001164 for (int j = 0; j < 3; ++j) {
1165 in.s[i][j] = numberToEnglish(3 * i + j + 1).c_str();
Andreas Huber709b62d2016-09-19 11:21:18 -07001166 }
1167 }
1168
1169 EXPECT_OK(foo->transpose(
1170 in,
1171 [&](const auto &out) {
1172 EXPECT_EQ(
1173 to_string(out),
1174 "[['one', 'four', 'seven', 'ten', 'thirteen'], "
1175 "['two', 'five', 'eight', 'eleven', 'fourteen'], "
1176 "['three', 'six', 'nine', 'twelve', 'fifteen']]");
1177 }));
1178}
1179
1180TEST_F(HidlTest, FooTranspose2Test) {
Andreas Huberf03332a2016-09-22 15:35:43 -07001181 hidl_array<hidl_string, 5, 3> in;
Andreas Huber709b62d2016-09-19 11:21:18 -07001182
Andreas Huber709b62d2016-09-19 11:21:18 -07001183 for (int i = 0; i < 5; ++i) {
Andreas Huberf03332a2016-09-22 15:35:43 -07001184 for (int j = 0; j < 3; ++j) {
1185 in[i][j] = numberToEnglish(3 * i + j + 1).c_str();
Andreas Huber709b62d2016-09-19 11:21:18 -07001186 }
1187 }
1188
1189 EXPECT_OK(foo->transpose2(
1190 in,
1191 [&](const auto &out) {
1192 EXPECT_EQ(
Andreas Huberf03332a2016-09-22 15:35:43 -07001193 to_string(out),
Andreas Huber709b62d2016-09-19 11:21:18 -07001194 "[['one', 'four', 'seven', 'ten', 'thirteen'], "
1195 "['two', 'five', 'eight', 'eleven', 'fourteen'], "
1196 "['three', 'six', 'nine', 'twelve', 'fifteen']]");
1197 }));
1198}
1199
Yifan Hongb725d672016-10-10 10:14:15 -07001200TEST_F(HidlTest, FooNullNativeHandleTest) {
Martijn Coenen9d97da22017-01-12 17:29:47 +01001201 Abc xyz;
1202 xyz.z = nullptr;
1203 EXPECT_OK(bar->expectNullHandle(nullptr, xyz, [](bool hIsNull, bool xyzHasNull) {
1204 EXPECT_TRUE(hIsNull);
1205 EXPECT_TRUE(xyzHasNull);
1206 }));
Yifan Hongb725d672016-10-10 10:14:15 -07001207}
Steven Moreland67f67b42016-09-29 08:59:02 -07001208
Martijn Coenene1638232016-10-26 12:51:34 +02001209TEST_F(HidlTest, FooNullCallbackTest) {
1210 EXPECT_OK(foo->echoNullInterface(nullptr,
1211 [](const auto receivedNull, const auto &intf) {
1212 EXPECT_TRUE(receivedNull);
1213 EXPECT_EQ(intf, nullptr);
1214 }));
1215}
1216
Steven Moreland67f67b42016-09-29 08:59:02 -07001217TEST_F(HidlTest, FooNonNullCallbackTest) {
1218 hidl_array<hidl_string, 5, 3> in;
1219
1220 EXPECT_FAIL(foo->transpose2(in, nullptr /* _hidl_cb */));
1221}
1222
Andreas Huber5e44a292016-09-27 14:52:39 -07001223TEST_F(HidlTest, FooSendVecTest) {
1224 hidl_vec<uint8_t> in;
1225 in.resize(16);
1226 for (size_t i = 0; i < in.size(); ++i) {
1227 in[i] = i;
1228 }
1229
1230 EXPECT_OK(foo->sendVec(
1231 in,
1232 [&](const auto &out) {
1233 EXPECT_EQ(to_string(in), to_string(out));
1234 }));
1235}
1236
Martijn Coenenafb30cb2017-01-13 00:24:02 +01001237TEST_F(HidlTest, FooSendEmptyVecTest) {
1238 hidl_vec<uint8_t> in;
1239 EXPECT_OK(foo->sendVec(
1240 in,
1241 [&](const auto &out) {
1242 EXPECT_EQ(out.size(), 0u);
1243 EXPECT_EQ(to_string(in), to_string(out));
1244 }));
1245}
1246
Andreas Huber86a112b2016-10-19 14:25:16 -07001247TEST_F(HidlTest, FooHaveAVectorOfInterfacesTest) {
1248 hidl_vec<sp<ISimple> > in;
1249 in.resize(16);
1250 for (size_t i = 0; i < in.size(); ++i) {
1251 in[i] = new Simple(i);
1252 }
1253
1254 EXPECT_OK(foo->haveAVectorOfInterfaces(
1255 in,
1256 [&](const auto &out) {
1257 EXPECT_EQ(in.size(), out.size());
1258 for (size_t i = 0; i < in.size(); ++i) {
Steven Moreland2ae5bca2016-12-01 05:56:49 +00001259 int32_t inCookie = in[i]->getCookie();
1260 int32_t outCookie = out[i]->getCookie();
1261 EXPECT_EQ(inCookie, outCookie);
Andreas Huber86a112b2016-10-19 14:25:16 -07001262 }
1263 }));
1264}
1265
1266TEST_F(HidlTest, FooHaveAVectorOfGenericInterfacesTest) {
Andreas Huber86a112b2016-10-19 14:25:16 -07001267
Yifan Hongc8934042016-11-17 17:10:52 -08001268 hidl_vec<sp<::android::hidl::base::V1_0::IBase> > in;
Andreas Huber86a112b2016-10-19 14:25:16 -07001269 in.resize(16);
1270 for (size_t i = 0; i < in.size(); ++i) {
Yifan Hongc8934042016-11-17 17:10:52 -08001271 sp<ISimple> s = new Simple(i);
1272 in[i] = s;
Andreas Huber86a112b2016-10-19 14:25:16 -07001273 }
1274
1275 EXPECT_OK(foo->haveAVectorOfGenericInterfaces(
1276 in,
1277 [&](const auto &out) {
1278 EXPECT_EQ(in.size(), out.size());
Yifan Hongc8934042016-11-17 17:10:52 -08001279
1280 EXPECT_OK(out[0]->interfaceChain([](const auto &names) {
1281 ASSERT_GT(names.size(), 0u);
1282 ASSERT_STREQ(names[0].c_str(), ISimple::descriptor);
1283 }));
Andreas Huber86a112b2016-10-19 14:25:16 -07001284 for (size_t i = 0; i < in.size(); ++i) {
Yifan Hongc8934042016-11-17 17:10:52 -08001285 sp<ISimple> inSimple = ISimple::castFrom(in[i]);
1286 sp<ISimple> outSimple = ISimple::castFrom(out[i]);
1287
1288 ASSERT_NE(inSimple.get(), nullptr);
1289 ASSERT_NE(outSimple.get(), nullptr);
Martijn Coenen6ec2f0b2016-12-11 01:04:55 +01001290 EXPECT_EQ(in[i], inSimple.get()); // pointers must be equal!
Steven Moreland2ae5bca2016-12-01 05:56:49 +00001291 int32_t inCookie = inSimple->getCookie();
1292 int32_t outCookie = outSimple->getCookie();
1293 EXPECT_EQ(inCookie, outCookie);
Andreas Huber86a112b2016-10-19 14:25:16 -07001294 }
1295 }));
1296}
1297
Yifan Hong8c48ad72016-10-14 11:34:59 -07001298TEST_F(HidlTest, FooStructEmbeddedHandleTest) {
1299 EXPECT_OK(foo->createMyHandle([&](const auto &myHandle) {
1300 EXPECT_EQ(myHandle.guard, 666);
Martijn Coenen2f69a5b2016-11-18 15:26:38 +01001301 const native_handle_t* handle = myHandle.h.getNativeHandle();
1302 EXPECT_EQ(handle->numInts, 10);
1303 EXPECT_EQ(handle->numFds, 0);
Yifan Hong8c48ad72016-10-14 11:34:59 -07001304 int data[] = {2,3,5,7,11,13,17,19,21,23};
Martijn Coenen2f69a5b2016-11-18 15:26:38 +01001305 EXPECT_ARRAYEQ(handle->data, data, 10);
Yifan Hong8c48ad72016-10-14 11:34:59 -07001306 }));
1307
1308 EXPECT_OK(foo->closeHandles());
1309}
1310
1311TEST_F(HidlTest, FooHandleVecTest) {
1312 EXPECT_OK(foo->createHandles(3, [&](const auto &handles) {
1313 EXPECT_EQ(handles.size(), 3ull);
1314 int data[] = {2,3,5,7,11,13,17,19,21,23};
1315 for (size_t i = 0; i < 3; i++) {
1316 const native_handle_t *h = handles[i];
1317 EXPECT_EQ(h->numInts, 10) << " for element " << i;
1318 EXPECT_EQ(h->numFds, 0) << " for element " << i;
1319 EXPECT_ARRAYEQ(h->data, data, 10);
1320 }
1321 }));
1322
1323 EXPECT_OK(foo->closeHandles());
1324}
1325
Martijn Coenen115d4282016-12-19 05:14:04 +01001326struct HidlDeathRecipient : hidl_death_recipient {
1327 std::mutex mutex;
1328 std::condition_variable condition;
1329 wp<IBase> who;
1330 bool fired = false;
1331 uint64_t cookie = 0;
1332
1333 virtual void serviceDied(uint64_t cookie, const wp<IBase>& who) {
1334 std::unique_lock<std::mutex> lock(mutex);
1335 fired = true;
1336 this->cookie = cookie;
1337 this->who = who;
1338 condition.notify_one();
1339 };
1340};
1341
1342TEST_F(HidlTest, DeathRecipientTest) {
Martijn Coenen115d4282016-12-19 05:14:04 +01001343 sp<HidlDeathRecipient> recipient = new HidlDeathRecipient();
1344 sp<HidlDeathRecipient> recipient2 = new HidlDeathRecipient();
1345
1346 EXPECT_TRUE(dyingFoo->linkToDeath(recipient, 0x1481));
1347 EXPECT_TRUE(dyingFoo->linkToDeath(recipient2, 0x2592));
1348 EXPECT_TRUE(dyingFoo->unlinkToDeath(recipient2));
1349
1350 if (gMode != BINDERIZED) {
1351 // Passthrough doesn't fire, nor does it keep state of
1352 // registered death recipients (so it won't fail unlinking
1353 // the same recipient twice).
1354 return;
1355 }
1356
1357 EXPECT_FALSE(dyingFoo->unlinkToDeath(recipient2));
1358 killServer("dyingFoo");
1359
1360 std::unique_lock<std::mutex> lock(recipient->mutex);
1361 recipient->condition.wait_for(lock, std::chrono::milliseconds(1000), [&recipient]() {
1362 return recipient->fired;
1363 });
1364 EXPECT_TRUE(recipient->fired);
1365 EXPECT_EQ(recipient->cookie, 0x1481u);
1366 EXPECT_EQ(recipient->who, dyingFoo);
1367 std::unique_lock<std::mutex> lock2(recipient2->mutex);
1368 recipient2->condition.wait_for(lock2, std::chrono::milliseconds(1000), [&recipient2]() {
1369 return recipient2->fired;
1370 });
1371 EXPECT_FALSE(recipient2->fired);
1372
1373 // Verify servicemanager dropped its reference too
1374 sp<IFoo> deadFoo = IFoo::getService("dyingFoo", false);
1375 if (deadFoo != nullptr) {
1376 // Got a passthrough
1377 EXPECT_FALSE(deadFoo->isRemote());
1378 }
1379}
1380
Yifan Hong1dc87932016-08-19 09:51:01 -07001381TEST_F(HidlTest, BarThisIsNewTest) {
Iliyan Malchev0acf4192016-08-22 19:33:20 -07001382 // Now the tricky part, get access to the derived interface.
Iliyan Malchevb31e10c2016-08-13 23:03:25 -07001383 ALOGI("CLIENT call thisIsNew.");
Yifan Hong1dc87932016-08-19 09:51:01 -07001384 EXPECT_OK(bar->thisIsNew());
Iliyan Malchevb31e10c2016-08-13 23:03:25 -07001385 ALOGI("CLIENT thisIsNew returned.");
Andreas Huber9cd48d02016-08-03 14:25:59 -07001386}
1387
Yifan Hong1e81c532016-10-18 18:43:46 -07001388static void expectGoodChild(const sp<IChild> &child) {
1389 ASSERT_NE(child.get(), nullptr);
1390 EXPECT_OK(child->doGrandparent());
1391 EXPECT_OK(child->doParent());
1392 EXPECT_OK(child->doChild());
1393}
1394
1395static void expectGoodParent(const sp<IParent> &parent) {
1396 ASSERT_NE(parent.get(), nullptr);
1397 EXPECT_OK(parent->doGrandparent());
1398 EXPECT_OK(parent->doParent());
1399 sp<IChild> child = IChild::castFrom(parent);
1400 expectGoodChild(child);
1401}
1402
1403static void expectGoodGrandparent(const sp<IGrandparent> &grandparent) {
1404 ASSERT_NE(grandparent.get(), nullptr);
1405 EXPECT_OK(grandparent->doGrandparent());
1406 sp<IParent> parent = IParent::castFrom(grandparent);
1407 expectGoodParent(parent);
1408}
1409
Yifan Hong5749b2c2016-11-28 12:52:36 -08001410TEST_F(HidlTest, FooHaveAnInterfaceTest) {
1411
1412 sp<ISimple> in = new Complicated(42);
Martijn Coenenb40ef022017-01-02 15:21:46 +01001413 Return<sp<ISimple>> ret = bar->haveAInterface(in);
1414 EXPECT_OK(ret);
1415 sp<ISimple> out = ret;
1416 ASSERT_NE(out.get(), nullptr);
1417 EXPECT_EQ(out->getCookie(), 42);
1418 EXPECT_OK(out->customVecInt([&](const auto &) { }));
1419 EXPECT_OK(out->customVecStr([&](const auto &) { }));
1420 EXPECT_OK(out->interfaceChain([&](const auto &) { }));
1421 EXPECT_OK(out->mystr([&](const auto &) { }));
1422 EXPECT_OK(out->myhandle([&](const auto &) { }));
Yifan Hong5749b2c2016-11-28 12:52:36 -08001423}
1424
Yifan Hong1e81c532016-10-18 18:43:46 -07001425TEST_F(HidlTest, InheritRemoteGrandparentTest) {
Martijn Coenenb40ef022017-01-02 15:21:46 +01001426 Return<sp<IGrandparent>> ret = fetcher->getGrandparent(true);
1427 EXPECT_OK(ret);
1428 expectGoodGrandparent(ret);
Yifan Hong1e81c532016-10-18 18:43:46 -07001429}
1430
1431TEST_F(HidlTest, InheritLocalGrandparentTest) {
Martijn Coenenb40ef022017-01-02 15:21:46 +01001432 Return<sp<IGrandparent>> ret = fetcher->getGrandparent(false);
1433 EXPECT_OK(ret);
1434 expectGoodGrandparent(ret);
Yifan Hong1e81c532016-10-18 18:43:46 -07001435}
1436
Yifan Hong4b0214d2016-12-07 14:57:57 -08001437TEST_F(HidlTest, InheritRemoteParentTest) {
Martijn Coenenb40ef022017-01-02 15:21:46 +01001438 Return<sp<IParent>> ret = fetcher->getParent(true);
1439 EXPECT_OK(ret);
1440 expectGoodParent(ret);
Yifan Hong1e81c532016-10-18 18:43:46 -07001441}
1442
Yifan Hong4b0214d2016-12-07 14:57:57 -08001443TEST_F(HidlTest, InheritLocalParentTest) {
Martijn Coenenb40ef022017-01-02 15:21:46 +01001444 Return<sp<IParent>> ret = fetcher->getParent(false);
1445 EXPECT_OK(ret);
1446 expectGoodParent(ret);
Yifan Hong1e81c532016-10-18 18:43:46 -07001447}
1448
1449TEST_F(HidlTest, InheritRemoteChildTest) {
Martijn Coenenb40ef022017-01-02 15:21:46 +01001450 Return<sp<IChild>> ret = fetcher->getChild(true);
1451 EXPECT_OK(ret);
1452 expectGoodChild(ret);
Yifan Hong1e81c532016-10-18 18:43:46 -07001453}
1454
1455TEST_F(HidlTest, InheritLocalChildTest) {
Martijn Coenenb40ef022017-01-02 15:21:46 +01001456 Return<sp<IChild>> ret = fetcher->getChild(false);
1457 EXPECT_OK(ret);
1458 expectGoodChild(ret);
Yifan Hong1e81c532016-10-18 18:43:46 -07001459}
1460
Andreas Huber5d034772016-09-28 14:23:51 -07001461TEST_F(HidlTest, TestArrayDimensionality) {
1462 hidl_array<int, 2> oneDim;
1463 hidl_array<int, 2, 3> twoDim;
1464 hidl_array<int, 2, 3, 4> threeDim;
1465
1466 EXPECT_EQ(oneDim.size(), 2u);
1467 EXPECT_EQ(twoDim.size(), std::make_tuple(2u, 3u));
1468 EXPECT_EQ(threeDim.size(), std::make_tuple(2u, 3u, 4u));
1469}
1470
Yifan Hongc6752dc2016-12-20 14:00:14 -08001471TEST_F(HidlTest, StructEqualTest) {
1472 using G = IFoo::Goober;
1473 using F = IFoo::Fumble;
1474 G g1{
1475 .q = 42,
1476 .name = "The Ultimate Question of Life, the Universe, and Everything",
1477 .address = "North Pole",
1478 .numbers = std::array<double, 10>{ {1, 2, 3, 4, 5, 6, 7, 8, 9, 10} },
1479 .fumble = F{.data = {.data = 50}},
1480 .gumble = F{.data = {.data = 60}}
1481 };
1482 G g2{
1483 .q = 42,
1484 .name = "The Ultimate Question of Life, the Universe, and Everything",
1485 .address = "North Pole",
1486 .numbers = std::array<double, 10>{ {1, 2, 3, 4, 5, 6, 7, 8, 9, 10} },
1487 .fumble = F{.data = {.data = 50}},
1488 .gumble = F{.data = {.data = 60}}
1489 };
1490 G g3{
1491 .q = 42,
1492 .name = "The Ultimate Question of Life, the Universe, and Everything",
1493 .address = "North Pole",
1494 .numbers = std::array<double, 10>{ {1, 2, 3, 4, 5, 6, 7, 8, 9, 10} },
1495 .fumble = F{.data = {.data = 50}},
1496 .gumble = F{.data = {.data = 61}}
1497 };
1498 // explicitly invoke operator== here.
1499 EXPECT_TRUE(g1 == g2);
1500 EXPECT_TRUE(g1 != g3);
1501}
1502
1503TEST_F(HidlTest, EnumEqualTest) {
1504 using E = IFoo::SomeEnum;
1505 E e1 = E::quux;
1506 E e2 = E::quux;
1507 E e3 = E::goober;
1508 // explicitly invoke operator== here.
1509 EXPECT_TRUE(e1 == e2);
1510 EXPECT_TRUE(e1 != e3);
1511}
1512
Yifan Hongbf459bc2016-08-23 16:50:37 -07001513#if HIDL_RUN_POINTER_TESTS
Andreas Huber9cd48d02016-08-03 14:25:59 -07001514
Yifan Hongbf459bc2016-08-23 16:50:37 -07001515TEST_F(HidlTest, PassAGraphTest) {
1516 IGraph::Graph g;
Yifan Hong398e6fb2016-10-17 11:38:09 -07001517 ::android::simpleGraph(g);
1518 ::android::logSimpleGraph("CLIENT", g);
Yifan Hongbf459bc2016-08-23 16:50:37 -07001519 ALOGI("CLIENT call passAGraph");
1520 EXPECT_OK(graphInterface->passAGraph(g));
1521}
1522
1523TEST_F(HidlTest, GiveAGraphTest) {
1524 EXPECT_OK(graphInterface->giveAGraph([&](const auto &newGraph) {
Yifan Hong398e6fb2016-10-17 11:38:09 -07001525 ::android::logSimpleGraph("CLIENT", newGraph);
1526 EXPECT_TRUE(::android::isSimpleGraph(newGraph));
Yifan Hongbf459bc2016-08-23 16:50:37 -07001527 }));
1528}
1529TEST_F(HidlTest, PassANodeTest) {
1530 IGraph::Node node; node.data = 10;
1531 EXPECT_OK(graphInterface->passANode(node));
1532}
1533TEST_F(HidlTest, PassTwoGraphsTest) {
1534 IGraph::Graph g;
Yifan Hong398e6fb2016-10-17 11:38:09 -07001535 ::android::simpleGraph(g);
Yifan Hongbf459bc2016-08-23 16:50:37 -07001536 EXPECT_OK(graphInterface->passTwoGraphs(&g, &g));
1537}
1538TEST_F(HidlTest, PassAGammaTest) {
1539 IGraph::Theta s; s.data = 500;
1540 IGraph::Alpha a; a.s_ptr = &s;
1541 IGraph::Beta b; b.s_ptr = &s;
1542 IGraph::Gamma c; c.a_ptr = &a; c.b_ptr = &b;
1543 ALOGI("CLIENT calling passAGamma: c.a = %p, c.b = %p, c.a->s = %p, c.b->s = %p",
1544 c.a_ptr, c.b_ptr, c.a_ptr->s_ptr, c.b_ptr->s_ptr);
1545 EXPECT_OK(graphInterface->passAGamma(c));
1546}
1547TEST_F(HidlTest, PassNullTest) {
1548 IGraph::Gamma c;
1549 c.a_ptr = nullptr;
1550 c.b_ptr = nullptr;
1551 EXPECT_OK(graphInterface->passAGamma(c));
1552}
1553TEST_F(HidlTest, PassASimpleRefTest) {
1554 IGraph::Theta s;
1555 s.data = 500;
1556 IGraph::Alpha a;
1557 a.s_ptr = &s;
1558 EXPECT_OK(graphInterface->passASimpleRef(&a));
1559}
1560TEST_F(HidlTest, PassASimpleRefSTest) {
1561 IGraph::Theta s;
1562 s.data = 500;
1563 ALOGI("CLIENT call passASimpleRefS with %p", &s);
1564 EXPECT_OK(graphInterface->passASimpleRefS(&s));
1565}
1566TEST_F(HidlTest, GiveASimpleRefTest) {
1567 EXPECT_OK(graphInterface->giveASimpleRef([&](const auto & a_ptr) {
1568 EXPECT_EQ(a_ptr->s_ptr->data, 500);
1569 }));
1570}
1571TEST_F(HidlTest, GraphReportErrorsTest) {
1572 Return<int32_t> ret = graphInterface->getErrors();
1573 EXPECT_OK(ret);
1574 EXPECT_EQ(int32_t(ret), 0);
1575}
1576
1577TEST_F(HidlTest, PointerPassOldBufferTest) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001578 EXPECT_OK(validationPointerInterface->bar1([&](const auto& sptr, const auto& s) {
Yifan Hongbf459bc2016-08-23 16:50:37 -07001579 EXPECT_OK(pointerInterface->foo1(sptr, s));
1580 }));
1581}
1582TEST_F(HidlTest, PointerPassOldBufferTest2) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001583 EXPECT_OK(validationPointerInterface->bar2([&](const auto& s, const auto& a) {
Yifan Hongbf459bc2016-08-23 16:50:37 -07001584 EXPECT_OK(pointerInterface->foo2(s, a));
1585 }));
1586}
1587TEST_F(HidlTest, PointerPassSameOldBufferPointerTest) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001588 EXPECT_OK(validationPointerInterface->bar3([&](const auto& s, const auto& a, const auto& b) {
Yifan Hongbf459bc2016-08-23 16:50:37 -07001589 EXPECT_OK(pointerInterface->foo3(s, a, b));
1590 }));
1591}
1592TEST_F(HidlTest, PointerPassOnlyTest) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001593 EXPECT_OK(validationPointerInterface->bar4([&](const auto& s) {
Yifan Hongbf459bc2016-08-23 16:50:37 -07001594 EXPECT_OK(pointerInterface->foo4(s));
1595 }));
1596}
1597TEST_F(HidlTest, PointerPassTwoEmbeddedTest) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001598 EXPECT_OK(validationPointerInterface->bar5([&](const auto& a, const auto& b) {
Yifan Hongbf459bc2016-08-23 16:50:37 -07001599 EXPECT_OK(pointerInterface->foo5(a, b));
1600 }));
1601}
1602TEST_F(HidlTest, PointerPassIndirectBufferHasDataTest) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001603 EXPECT_OK(validationPointerInterface->bar6([&](const auto& a) {
Yifan Hongbf459bc2016-08-23 16:50:37 -07001604 EXPECT_OK(pointerInterface->foo6(a));
1605 }));
1606}
1607TEST_F(HidlTest, PointerPassTwoIndirectBufferTest) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001608 EXPECT_OK(validationPointerInterface->bar7([&](const auto& a, const auto& b) {
Yifan Hongbf459bc2016-08-23 16:50:37 -07001609 EXPECT_OK(pointerInterface->foo7(a, b));
1610 }));
1611}
1612TEST_F(HidlTest, PointerPassDeeplyIndirectTest) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001613 EXPECT_OK(validationPointerInterface->bar8([&](const auto& d) {
Yifan Hongbf459bc2016-08-23 16:50:37 -07001614 EXPECT_OK(pointerInterface->foo8(d));
1615 }));
1616}
1617TEST_F(HidlTest, PointerPassStringRefTest) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001618 EXPECT_OK(validationPointerInterface->bar9([&](const auto& str) {
Yifan Hongbf459bc2016-08-23 16:50:37 -07001619 EXPECT_OK(pointerInterface->foo9(str));
1620 }));
1621}
1622TEST_F(HidlTest, PointerPassRefVecTest) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001623 EXPECT_OK(validationPointerInterface->bar10([&](const auto& v) {
Yifan Hongbf459bc2016-08-23 16:50:37 -07001624 EXPECT_OK(pointerInterface->foo10(v));
1625 }));
1626}
1627TEST_F(HidlTest, PointerPassVecRefTest) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001628 EXPECT_OK(validationPointerInterface->bar11([&](const auto& v) {
Yifan Hongbf459bc2016-08-23 16:50:37 -07001629 EXPECT_OK(pointerInterface->foo11(v));
1630 }));
1631}
1632TEST_F(HidlTest, PointerPassArrayRefTest) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001633 EXPECT_OK(validationPointerInterface->bar12([&](const auto& array) {
Yifan Hongbf459bc2016-08-23 16:50:37 -07001634 EXPECT_OK(pointerInterface->foo12(array));
1635 }));
1636}
1637TEST_F(HidlTest, PointerPassRefArrayTest) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001638 EXPECT_OK(validationPointerInterface->bar13([&](const auto& array) {
Yifan Hongbf459bc2016-08-23 16:50:37 -07001639 EXPECT_OK(pointerInterface->foo13(array));
1640 }));
1641}
1642TEST_F(HidlTest, PointerPass3RefTest) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001643 EXPECT_OK(validationPointerInterface->bar14([&](const auto& p3) {
Yifan Hongbf459bc2016-08-23 16:50:37 -07001644 EXPECT_OK(pointerInterface->foo14(p3));
1645 }));
1646}
1647TEST_F(HidlTest, PointerPassInt3RefTest) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001648 EXPECT_OK(validationPointerInterface->bar15([&](const auto& p3) {
Yifan Hongbf459bc2016-08-23 16:50:37 -07001649 EXPECT_OK(pointerInterface->foo15(p3));
1650 }));
1651}
1652TEST_F(HidlTest, PointerPassEmbeddedPointersTest) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001653 EXPECT_OK(validationPointerInterface->bar16([&](const auto& p) {
Yifan Hongbf459bc2016-08-23 16:50:37 -07001654 EXPECT_OK(pointerInterface->foo16(p));
1655 }));
1656}
1657TEST_F(HidlTest, PointerPassEmbeddedPointers2Test) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001658 EXPECT_OK(validationPointerInterface->bar17([&](const auto& p) {
Yifan Hongbf459bc2016-08-23 16:50:37 -07001659 EXPECT_OK(pointerInterface->foo17(p));
1660 }));
1661}
1662TEST_F(HidlTest, PointerPassCopiedStringTest) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001663 EXPECT_OK(validationPointerInterface->bar18([&](const auto& str_ref, const auto& str_ref2, const auto& str) {
Yifan Hongbf459bc2016-08-23 16:50:37 -07001664 EXPECT_OK(pointerInterface->foo18(str_ref, str_ref2, str));
1665 }));
1666}
1667TEST_F(HidlTest, PointerPassCopiedVecTest) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001668 EXPECT_OK(validationPointerInterface->bar19([&](const auto& a_vec_ref, const auto& a_vec, const auto& a_vec_ref2) {
Yifan Hongbf459bc2016-08-23 16:50:37 -07001669 EXPECT_OK(pointerInterface->foo19(a_vec_ref, a_vec, a_vec_ref2));
1670 }));
1671}
Yifan Hong84465902016-09-27 15:52:17 -07001672TEST_F(HidlTest, PointerPassBigRefVecTest) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001673 EXPECT_OK(validationPointerInterface->bar20([&](const auto& v) {
Yifan Hong84465902016-09-27 15:52:17 -07001674 EXPECT_FAIL(pointerInterface->foo20(v));
1675 }));
1676}
Yifan Hongbf459bc2016-08-23 16:50:37 -07001677TEST_F(HidlTest, PointerPassMultidimArrayRefTest) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001678 EXPECT_OK(validationPointerInterface->bar21([&](const auto& v) {
Yifan Hongbf459bc2016-08-23 16:50:37 -07001679 EXPECT_OK(pointerInterface->foo21(v));
1680 }));
1681}
1682TEST_F(HidlTest, PointerPassRefMultidimArrayTest) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001683 EXPECT_OK(validationPointerInterface->bar22([&](const auto& v) {
Yifan Hongbf459bc2016-08-23 16:50:37 -07001684 EXPECT_OK(pointerInterface->foo22(v));
1685 }));
1686}
1687TEST_F(HidlTest, PointerGiveOldBufferTest) {
1688 EXPECT_OK(pointerInterface->bar1([&](const auto& sptr, const auto& s) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001689 EXPECT_OK(validationPointerInterface->foo1(sptr, s));
Yifan Hongbf459bc2016-08-23 16:50:37 -07001690 }));
1691}
1692TEST_F(HidlTest, PointerGiveOldBufferTest2) {
1693 EXPECT_OK(pointerInterface->bar2([&](const auto& s, const auto& a) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001694 EXPECT_OK(validationPointerInterface->foo2(s, a));
Yifan Hongbf459bc2016-08-23 16:50:37 -07001695 }));
1696}
1697TEST_F(HidlTest, PointerGiveSameOldBufferPointerTest) {
1698 EXPECT_OK(pointerInterface->bar3([&](const auto& s, const auto& a, const auto& b) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001699 EXPECT_OK(validationPointerInterface->foo3(s, a, b));
Yifan Hongbf459bc2016-08-23 16:50:37 -07001700 }));
1701}
1702TEST_F(HidlTest, PointerGiveOnlyTest) {
1703 EXPECT_OK(pointerInterface->bar4([&](const auto& s) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001704 EXPECT_OK(validationPointerInterface->foo4(s));
Yifan Hongbf459bc2016-08-23 16:50:37 -07001705 }));
1706}
1707TEST_F(HidlTest, PointerGiveTwoEmbeddedTest) {
1708 EXPECT_OK(pointerInterface->bar5([&](const auto& a, const auto& b) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001709 EXPECT_OK(validationPointerInterface->foo5(a, b));
Yifan Hongbf459bc2016-08-23 16:50:37 -07001710 }));
1711}
1712TEST_F(HidlTest, PointerGiveIndirectBufferHasDataTest) {
1713 EXPECT_OK(pointerInterface->bar6([&](const auto& a) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001714 EXPECT_OK(validationPointerInterface->foo6(a));
Yifan Hongbf459bc2016-08-23 16:50:37 -07001715 }));
1716}
1717TEST_F(HidlTest, PointerGiveTwoIndirectBufferTest) {
1718 EXPECT_OK(pointerInterface->bar7([&](const auto& a, const auto& b) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001719 EXPECT_OK(validationPointerInterface->foo7(a, b));
Yifan Hongbf459bc2016-08-23 16:50:37 -07001720 }));
1721}
1722TEST_F(HidlTest, PointerGiveDeeplyIndirectTest) {
1723 EXPECT_OK(pointerInterface->bar8([&](const auto& d) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001724 EXPECT_OK(validationPointerInterface->foo8(d));
Yifan Hongbf459bc2016-08-23 16:50:37 -07001725 }));
1726}
1727TEST_F(HidlTest, PointerGiveStringRefTest) {
1728 EXPECT_OK(pointerInterface->bar9([&](const auto& str) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001729 EXPECT_OK(validationPointerInterface->foo9(str));
Yifan Hongbf459bc2016-08-23 16:50:37 -07001730 }));
1731}
1732TEST_F(HidlTest, PointerGiveRefVecTest) {
1733 EXPECT_OK(pointerInterface->bar10([&](const auto& v) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001734 EXPECT_OK(validationPointerInterface->foo10(v));
Yifan Hongbf459bc2016-08-23 16:50:37 -07001735 }));
1736}
1737TEST_F(HidlTest, PointerGiveVecRefTest) {
1738 EXPECT_OK(pointerInterface->bar11([&](const auto& v) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001739 EXPECT_OK(validationPointerInterface->foo11(v));
Yifan Hongbf459bc2016-08-23 16:50:37 -07001740 }));
1741}
1742TEST_F(HidlTest, PointerGiveArrayRefTest) {
1743 EXPECT_OK(pointerInterface->bar12([&](const auto& array) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001744 EXPECT_OK(validationPointerInterface->foo12(array));
Yifan Hongbf459bc2016-08-23 16:50:37 -07001745 }));
1746}
1747TEST_F(HidlTest, PointerGiveRefArrayTest) {
1748 EXPECT_OK(pointerInterface->bar13([&](const auto& array) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001749 EXPECT_OK(validationPointerInterface->foo13(array));
Yifan Hongbf459bc2016-08-23 16:50:37 -07001750 }));
1751}
1752TEST_F(HidlTest, PointerGive3RefTest) {
1753 EXPECT_OK(pointerInterface->bar14([&](const auto& p3) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001754 EXPECT_OK(validationPointerInterface->foo14(p3));
Yifan Hongbf459bc2016-08-23 16:50:37 -07001755 }));
1756}
1757TEST_F(HidlTest, PointerGiveInt3RefTest) {
1758 EXPECT_OK(pointerInterface->bar15([&](const auto& p3) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001759 EXPECT_OK(validationPointerInterface->foo15(p3));
Yifan Hongbf459bc2016-08-23 16:50:37 -07001760 }));
1761}
1762TEST_F(HidlTest, PointerGiveEmbeddedPointersTest) {
1763 EXPECT_OK(pointerInterface->bar16([&](const auto& p) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001764 EXPECT_OK(validationPointerInterface->foo16(p));
Yifan Hongbf459bc2016-08-23 16:50:37 -07001765 }));
1766}
1767TEST_F(HidlTest, PointerGiveEmbeddedPointers2Test) {
1768 EXPECT_OK(pointerInterface->bar17([&](const auto& p) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001769 EXPECT_OK(validationPointerInterface->foo17(p));
Yifan Hongbf459bc2016-08-23 16:50:37 -07001770 }));
1771}
1772TEST_F(HidlTest, PointerGiveCopiedStringTest) {
1773 EXPECT_OK(pointerInterface->bar18([&](const auto& str_ref, const auto& str_ref2, const auto& str) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001774 EXPECT_OK(validationPointerInterface->foo18(str_ref, str_ref2, str));
Yifan Hongbf459bc2016-08-23 16:50:37 -07001775 }));
1776}
1777TEST_F(HidlTest, PointerGiveCopiedVecTest) {
1778 EXPECT_OK(pointerInterface->bar19([&](const auto& a_vec_ref, const auto& a_vec, const auto& a_vec_ref2) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001779 EXPECT_OK(validationPointerInterface->foo19(a_vec_ref, a_vec, a_vec_ref2));
Yifan Hongbf459bc2016-08-23 16:50:37 -07001780 }));
1781}
Yifan Hong84465902016-09-27 15:52:17 -07001782// This cannot be enabled until _hidl_error is not ignored when
1783// the remote writeEmbeddedReferencesToParcel.
1784// TEST_F(HidlTest, PointerGiveBigRefVecTest) {
1785// EXPECT_FAIL(pointerInterface->bar20([&](const auto& v) {
1786// }));
1787// }
Yifan Hongbf459bc2016-08-23 16:50:37 -07001788TEST_F(HidlTest, PointerGiveMultidimArrayRefTest) {
1789 EXPECT_OK(pointerInterface->bar21([&](const auto& v) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001790 EXPECT_OK(validationPointerInterface->foo21(v));
Yifan Hongbf459bc2016-08-23 16:50:37 -07001791 }));
1792}
1793TEST_F(HidlTest, PointerGiveRefMultidimArrayTest) {
1794 EXPECT_OK(pointerInterface->bar22([&](const auto& v) {
Yifan Hong3cccc0f2016-10-13 10:12:28 -07001795 EXPECT_OK(validationPointerInterface->foo22(v));
Yifan Hongbf459bc2016-08-23 16:50:37 -07001796 }));
1797}
1798TEST_F(HidlTest, PointerReportErrorsTest) {
1799 Return<int32_t> ret = pointerInterface->getErrors();
1800 EXPECT_OK(ret);
1801 EXPECT_EQ(int32_t(ret), 0);
1802}
1803#endif
1804
Yifan Hongc70f0d82016-10-10 14:50:22 -07001805int forkAndRunTests(TestMode mode) {
1806 pid_t child;
1807 int status;
Andreas Huber9cd48d02016-08-03 14:25:59 -07001808
Yifan Hongc70f0d82016-10-10 14:50:22 -07001809 const char* modeText = (mode == BINDERIZED) ? "BINDERIZED" : "PASSTHROUGH";
1810 ALOGI("Start running tests in %s mode...", modeText);
1811 fprintf(stdout, "Start running tests in %s mode...\n", modeText);
1812 fflush(stdout);
1813
1814 if ((child = fork()) == 0) {
1815 gMode = mode;
1816 if (gMode == PASSTHROUGH) {
Yifan Hongca890522016-10-12 10:03:41 -07001817 gPassthroughEnvironment = static_cast<PassthroughEnvironment *>(
1818 ::testing::AddGlobalTestEnvironment(new PassthroughEnvironment));
Yifan Hongc70f0d82016-10-10 14:50:22 -07001819 } else if (gMode == BINDERIZED) {
Yifan Hongca890522016-10-12 10:03:41 -07001820 gBinderizedEnvironment = static_cast<BinderizedEnvironment *>(
1821 ::testing::AddGlobalTestEnvironment(new BinderizedEnvironment));
Yifan Hongc70f0d82016-10-10 14:50:22 -07001822 }
1823 int testStatus = RUN_ALL_TESTS();
1824 if(testStatus == 0) {
1825 exit(0);
1826 }
1827 int failed = ::testing::UnitTest::GetInstance()->failed_test_count();
1828 if (failed == 0) {
1829 exit(-testStatus);
1830 }
1831 exit(failed);
1832 }
1833 waitpid(child, &status, 0 /* options */);
1834 ALOGI("All tests finished in %s mode.", modeText);
1835 fprintf(stdout, "All tests finished in %s mode.\n", modeText);
1836 fflush(stdout);
Yifan Hong1dc87932016-08-19 09:51:01 -07001837 return status;
Andreas Huber9cd48d02016-08-03 14:25:59 -07001838}
Yifan Hongc70f0d82016-10-10 14:50:22 -07001839
1840void handleStatus(int status, const char *mode) {
1841 if (status != 0) {
1842 if (WIFEXITED(status)) {
1843 status = WEXITSTATUS(status);
1844 if (status < 0) {
Yifan Hong48562fd2016-10-24 15:26:10 -07001845 fprintf(stdout, " RUN_ALL_TESTS returns %d for %s mode.\n", -status, mode);
Yifan Hongc70f0d82016-10-10 14:50:22 -07001846 } else {
Yifan Hong48562fd2016-10-24 15:26:10 -07001847 fprintf(stdout, " %d test(s) failed for %s mode.\n", status, mode);
Yifan Hongc70f0d82016-10-10 14:50:22 -07001848 }
1849 } else {
Yifan Hong48562fd2016-10-24 15:26:10 -07001850 fprintf(stdout, " ERROR: %s child process exited abnormally with %d\n", mode, status);
Yifan Hongc70f0d82016-10-10 14:50:22 -07001851 }
1852 }
1853}
1854
Yifan Hongd12398d2016-10-13 11:05:29 -07001855static void usage(const char *me) {
1856 fprintf(stderr,
1857 "usage: %s [-b] [-p] [GTEST_OPTIONS]\n",
1858 me);
1859
1860 fprintf(stderr, " -b binderized mode only\n");
1861 fprintf(stderr, " -p passthrough mode only\n");
1862 fprintf(stderr, " (if -b and -p are both missing or both present, "
1863 "both modes are tested.)\n");
1864}
1865
Yifan Hongc70f0d82016-10-10 14:50:22 -07001866int main(int argc, char **argv) {
Yifan Hongd12398d2016-10-13 11:05:29 -07001867 const char *me = argv[0];
1868 bool b = false;
1869 bool p = false;
1870 struct option longopts[] = {{0,0,0,0}};
1871 int res;
1872 while ((res = getopt_long(argc, argv, "hbp", longopts, NULL)) >= 0) {
1873 switch (res) {
1874 case 'h': {
1875 usage(me);
1876 exit(1);
1877 } break;
1878
1879 case 'b': {
1880 b = true;
1881 } break;
1882
1883 case 'p': {
1884 p = true;
1885 } break;
1886
1887 case '?':
1888 default: {
1889 // ignore. pass to gTest.
1890 } break;
1891 }
1892 }
1893 if (!b && !p) {
1894 b = p = true;
1895 }
Yifan Hongc70f0d82016-10-10 14:50:22 -07001896
1897 ::testing::InitGoogleTest(&argc, argv);
1898 // put test in child process because RUN_ALL_TESTS
1899 // should not be run twice.
Yifan Hongd12398d2016-10-13 11:05:29 -07001900 int pStatus = p ? forkAndRunTests(PASSTHROUGH) : 0;
1901 int bStatus = b ? forkAndRunTests(BINDERIZED) : 0;
Yifan Hongc70f0d82016-10-10 14:50:22 -07001902
Yifan Hong48562fd2016-10-24 15:26:10 -07001903 fprintf(stdout, "\n=========================================================\n\n"
1904 " Summary:\n\n");
Yifan Hongd12398d2016-10-13 11:05:29 -07001905 if (p) {
1906 ALOGI("PASSTHROUGH Test result = %d", pStatus);
1907 handleStatus(pStatus, "PASSTHROUGH");
1908 }
1909 if (b) {
1910 ALOGI("BINDERIZED Test result = %d", bStatus);
1911 handleStatus(bStatus, "BINDERIZED ");
1912 }
1913
Yifan Hongc70f0d82016-10-10 14:50:22 -07001914 if (pStatus == 0 && bStatus == 0) {
Yifan Hong48562fd2016-10-24 15:26:10 -07001915 fprintf(stdout, " Hooray! All tests passed.\n");
Yifan Hongc70f0d82016-10-10 14:50:22 -07001916 }
Yifan Hong48562fd2016-10-24 15:26:10 -07001917 fprintf(stdout, "\n=========================================================\n\n");
Yifan Hongc70f0d82016-10-10 14:50:22 -07001918
1919 return pStatus + bStatus;
1920}