1 /* 2 * Copyright (C) 2014 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 <errno.h> 18 #include <fcntl.h> 19 #include <poll.h> 20 #include <pthread.h> 21 #include <stdio.h> 22 #include <stdlib.h> 23 24 #include <gtest/gtest.h> 25 26 #include <binder/Binder.h> 27 #include <binder/IBinder.h> 28 #include <binder/IPCThreadState.h> 29 #include <binder/IServiceManager.h> 30 31 #define ARRAY_SIZE(array) (sizeof array / sizeof array[0]) 32 33 using namespace android; 34 35 static testing::Environment* binder_env; 36 static char *binderservername; 37 static char binderserverarg[] = "--binderserver"; 38 39 static String16 binderLibTestServiceName = String16("test.binderLib"); 40 41 enum BinderLibTestTranscationCode { 42 BINDER_LIB_TEST_NOP_TRANSACTION = IBinder::FIRST_CALL_TRANSACTION, 43 BINDER_LIB_TEST_REGISTER_SERVER, 44 BINDER_LIB_TEST_ADD_SERVER, 45 BINDER_LIB_TEST_CALL_BACK, 46 BINDER_LIB_TEST_NOP_CALL_BACK, 47 BINDER_LIB_TEST_GET_ID_TRANSACTION, 48 BINDER_LIB_TEST_INDIRECT_TRANSACTION, 49 BINDER_LIB_TEST_SET_ERROR_TRANSACTION, 50 BINDER_LIB_TEST_GET_STATUS_TRANSACTION, 51 BINDER_LIB_TEST_ADD_STRONG_REF_TRANSACTION, 52 BINDER_LIB_TEST_LINK_DEATH_TRANSACTION, 53 BINDER_LIB_TEST_WRITE_FILE_TRANSACTION, 54 BINDER_LIB_TEST_PROMOTE_WEAK_REF_TRANSACTION, 55 BINDER_LIB_TEST_EXIT_TRANSACTION, 56 BINDER_LIB_TEST_DELAYED_EXIT_TRANSACTION, 57 BINDER_LIB_TEST_GET_PTR_SIZE_TRANSACTION, 58 }; 59 60 pid_t start_server_process(int arg2) 61 { 62 int ret; 63 pid_t pid; 64 status_t status; 65 int pipefd[2]; 66 char stri[16]; 67 char strpipefd1[16]; 68 char *childargv[] = { 69 binderservername, 70 binderserverarg, 71 stri, 72 strpipefd1, 73 NULL 74 }; 75 76 ret = pipe(pipefd); 77 if (ret < 0) 78 return ret; 79 80 snprintf(stri, sizeof(stri), "%d", arg2); 81 snprintf(strpipefd1, sizeof(strpipefd1), "%d", pipefd[1]); 82 83 pid = fork(); 84 if (pid == -1) 85 return pid; 86 if (pid == 0) { 87 close(pipefd[0]); 88 execv(binderservername, childargv); 89 status = -errno; 90 write(pipefd[1], &status, sizeof(status)); 91 fprintf(stderr, "execv failed, %s\n", strerror(errno)); 92 _exit(EXIT_FAILURE); 93 } 94 close(pipefd[1]); 95 ret = read(pipefd[0], &status, sizeof(status)); 96 //printf("pipe read returned %d, status %d\n", ret, status); 97 close(pipefd[0]); 98 if (ret == sizeof(status)) { 99 ret = status; 100 } else { 101 kill(pid, SIGKILL); 102 if (ret >= 0) { 103 ret = NO_INIT; 104 } 105 } 106 if (ret < 0) { 107 wait(NULL); 108 return ret; 109 } 110 return pid; 111 } 112 113 class BinderLibTestEnv : public ::testing::Environment { 114 public: 115 BinderLibTestEnv() {} 116 sp<IBinder> getServer(void) { 117 return m_server; 118 } 119 120 private: 121 virtual void SetUp() { 122 m_serverpid = start_server_process(0); 123 //printf("m_serverpid %d\n", m_serverpid); 124 ASSERT_GT(m_serverpid, 0); 125 126 sp<IServiceManager> sm = defaultServiceManager(); 127 //printf("%s: pid %d, get service\n", __func__, m_pid); 128 m_server = sm->getService(binderLibTestServiceName); 129 ASSERT_TRUE(m_server != NULL); 130 //printf("%s: pid %d, get service done\n", __func__, m_pid); 131 } 132 virtual void TearDown() { 133 status_t ret; 134 Parcel data, reply; 135 int exitStatus; 136 pid_t pid; 137 138 //printf("%s: pid %d\n", __func__, m_pid); 139 if (m_server != NULL) { 140 ret = m_server->transact(BINDER_LIB_TEST_GET_STATUS_TRANSACTION, data, &reply); 141 EXPECT_EQ(0, ret); 142 ret = m_server->transact(BINDER_LIB_TEST_EXIT_TRANSACTION, data, &reply, TF_ONE_WAY); 143 EXPECT_EQ(0, ret); 144 } 145 if (m_serverpid > 0) { 146 //printf("wait for %d\n", m_pids[i]); 147 pid = wait(&exitStatus); 148 EXPECT_EQ(m_serverpid, pid); 149 EXPECT_TRUE(WIFEXITED(exitStatus)); 150 EXPECT_EQ(0, WEXITSTATUS(exitStatus)); 151 } 152 } 153 154 pid_t m_serverpid; 155 sp<IBinder> m_server; 156 }; 157 158 class BinderLibTest : public ::testing::Test { 159 public: 160 virtual void SetUp() { 161 m_server = static_cast<BinderLibTestEnv *>(binder_env)->getServer(); 162 } 163 virtual void TearDown() { 164 } 165 protected: 166 sp<IBinder> addServer(int32_t *idPtr = NULL) 167 { 168 int ret; 169 int32_t id; 170 Parcel data, reply; 171 sp<IBinder> binder; 172 173 ret = m_server->transact(BINDER_LIB_TEST_ADD_SERVER, data, &reply); 174 EXPECT_EQ(NO_ERROR, ret); 175 176 EXPECT_FALSE(binder != NULL); 177 binder = reply.readStrongBinder(); 178 EXPECT_TRUE(binder != NULL); 179 ret = reply.readInt32(&id); 180 EXPECT_EQ(NO_ERROR, ret); 181 if (idPtr) 182 *idPtr = id; 183 return binder; 184 } 185 void waitForReadData(int fd, int timeout_ms) { 186 int ret; 187 pollfd pfd = pollfd(); 188 189 pfd.fd = fd; 190 pfd.events = POLLIN; 191 ret = poll(&pfd, 1, timeout_ms); 192 EXPECT_EQ(1, ret); 193 } 194 195 sp<IBinder> m_server; 196 }; 197 198 class BinderLibTestBundle : public Parcel 199 { 200 public: 201 BinderLibTestBundle(void) {} 202 BinderLibTestBundle(const Parcel *source) : m_isValid(false) { 203 int32_t mark; 204 int32_t bundleLen; 205 size_t pos; 206 207 if (source->readInt32(&mark)) 208 return; 209 if (mark != MARK_START) 210 return; 211 if (source->readInt32(&bundleLen)) 212 return; 213 pos = source->dataPosition(); 214 if (Parcel::appendFrom(source, pos, bundleLen)) 215 return; 216 source->setDataPosition(pos + bundleLen); 217 if (source->readInt32(&mark)) 218 return; 219 if (mark != MARK_END) 220 return; 221 m_isValid = true; 222 setDataPosition(0); 223 } 224 void appendTo(Parcel *dest) { 225 dest->writeInt32(MARK_START); 226 dest->writeInt32(dataSize()); 227 dest->appendFrom(this, 0, dataSize()); 228 dest->writeInt32(MARK_END); 229 }; 230 bool isValid(void) { 231 return m_isValid; 232 } 233 private: 234 enum { 235 MARK_START = B_PACK_CHARS('B','T','B','S'), 236 MARK_END = B_PACK_CHARS('B','T','B','E'), 237 }; 238 bool m_isValid; 239 }; 240 241 class BinderLibTestEvent 242 { 243 public: 244 BinderLibTestEvent(void) 245 : m_eventTriggered(false) 246 { 247 pthread_mutex_init(&m_waitMutex, NULL); 248 pthread_cond_init(&m_waitCond, NULL); 249 } 250 int waitEvent(int timeout_s) 251 { 252 int ret; 253 pthread_mutex_lock(&m_waitMutex); 254 if (!m_eventTriggered) { 255 #if defined(HAVE_PTHREAD_COND_TIMEDWAIT_RELATIVE) 256 pthread_cond_timeout_np(&m_waitCond, &m_waitMutex, timeout_s * 1000); 257 #else 258 struct timespec ts; 259 clock_gettime(CLOCK_REALTIME, &ts); 260 ts.tv_sec += timeout_s; 261 pthread_cond_timedwait(&m_waitCond, &m_waitMutex, &ts); 262 #endif 263 } 264 ret = m_eventTriggered ? NO_ERROR : TIMED_OUT; 265 pthread_mutex_unlock(&m_waitMutex); 266 return ret; 267 } 268 protected: 269 void triggerEvent(void) { 270 pthread_mutex_lock(&m_waitMutex); 271 pthread_cond_signal(&m_waitCond); 272 m_eventTriggered = true; 273 pthread_mutex_unlock(&m_waitMutex); 274 }; 275 private: 276 pthread_mutex_t m_waitMutex; 277 pthread_cond_t m_waitCond; 278 bool m_eventTriggered; 279 }; 280 281 class BinderLibTestCallBack : public BBinder, public BinderLibTestEvent 282 { 283 public: 284 BinderLibTestCallBack() 285 : m_result(NOT_ENOUGH_DATA) 286 { 287 } 288 status_t getResult(void) 289 { 290 return m_result; 291 } 292 293 private: 294 virtual status_t onTransact(uint32_t code, 295 const Parcel& data, Parcel* reply, 296 uint32_t flags = 0) 297 { 298 (void)reply; 299 (void)flags; 300 switch(code) { 301 case BINDER_LIB_TEST_CALL_BACK: 302 m_result = data.readInt32(); 303 triggerEvent(); 304 return NO_ERROR; 305 default: 306 return UNKNOWN_TRANSACTION; 307 } 308 } 309 310 status_t m_result; 311 }; 312 313 class TestDeathRecipient : public IBinder::DeathRecipient, public BinderLibTestEvent 314 { 315 private: 316 virtual void binderDied(const wp<IBinder>& who) { 317 (void)who; 318 triggerEvent(); 319 }; 320 }; 321 322 TEST_F(BinderLibTest, NopTransaction) { 323 status_t ret; 324 Parcel data, reply; 325 ret = m_server->transact(BINDER_LIB_TEST_NOP_TRANSACTION, data, &reply); 326 EXPECT_EQ(NO_ERROR, ret); 327 } 328 329 TEST_F(BinderLibTest, SetError) { 330 int32_t testValue[] = { 0, -123, 123 }; 331 for (size_t i = 0; i < ARRAY_SIZE(testValue); i++) { 332 status_t ret; 333 Parcel data, reply; 334 data.writeInt32(testValue[i]); 335 ret = m_server->transact(BINDER_LIB_TEST_SET_ERROR_TRANSACTION, data, &reply); 336 EXPECT_EQ(testValue[i], ret); 337 } 338 } 339 340 TEST_F(BinderLibTest, GetId) { 341 status_t ret; 342 int32_t id; 343 Parcel data, reply; 344 ret = m_server->transact(BINDER_LIB_TEST_GET_ID_TRANSACTION, data, &reply); 345 EXPECT_EQ(NO_ERROR, ret); 346 ret = reply.readInt32(&id); 347 EXPECT_EQ(NO_ERROR, ret); 348 EXPECT_EQ(0, id); 349 } 350 351 TEST_F(BinderLibTest, PtrSize) { 352 status_t ret; 353 int32_t ptrsize; 354 Parcel data, reply; 355 sp<IBinder> server = addServer(); 356 ASSERT_TRUE(server != NULL); 357 ret = server->transact(BINDER_LIB_TEST_GET_PTR_SIZE_TRANSACTION, data, &reply); 358 EXPECT_EQ(NO_ERROR, ret); 359 ret = reply.readInt32(&ptrsize); 360 EXPECT_EQ(NO_ERROR, ret); 361 RecordProperty("TestPtrSize", sizeof(void *)); 362 RecordProperty("ServerPtrSize", sizeof(void *)); 363 } 364 365 TEST_F(BinderLibTest, IndirectGetId2) 366 { 367 status_t ret; 368 int32_t id; 369 int32_t count; 370 Parcel data, reply; 371 int32_t serverId[3]; 372 373 data.writeInt32(ARRAY_SIZE(serverId)); 374 for (size_t i = 0; i < ARRAY_SIZE(serverId); i++) { 375 sp<IBinder> server; 376 BinderLibTestBundle datai; 377 378 server = addServer(&serverId[i]); 379 ASSERT_TRUE(server != NULL); 380 data.writeStrongBinder(server); 381 data.writeInt32(BINDER_LIB_TEST_GET_ID_TRANSACTION); 382 datai.appendTo(&data); 383 } 384 385 ret = m_server->transact(BINDER_LIB_TEST_INDIRECT_TRANSACTION, data, &reply); 386 ASSERT_EQ(NO_ERROR, ret); 387 388 ret = reply.readInt32(&id); 389 ASSERT_EQ(NO_ERROR, ret); 390 EXPECT_EQ(0, id); 391 392 ret = reply.readInt32(&count); 393 ASSERT_EQ(NO_ERROR, ret); 394 EXPECT_EQ(ARRAY_SIZE(serverId), count); 395 396 for (size_t i = 0; i < (size_t)count; i++) { 397 BinderLibTestBundle replyi(&reply); 398 EXPECT_TRUE(replyi.isValid()); 399 ret = replyi.readInt32(&id); 400 EXPECT_EQ(NO_ERROR, ret); 401 EXPECT_EQ(serverId[i], id); 402 EXPECT_EQ(replyi.dataSize(), replyi.dataPosition()); 403 } 404 405 EXPECT_EQ(reply.dataSize(), reply.dataPosition()); 406 } 407 408 TEST_F(BinderLibTest, IndirectGetId3) 409 { 410 status_t ret; 411 int32_t id; 412 int32_t count; 413 Parcel data, reply; 414 int32_t serverId[3]; 415 416 data.writeInt32(ARRAY_SIZE(serverId)); 417 for (size_t i = 0; i < ARRAY_SIZE(serverId); i++) { 418 sp<IBinder> server; 419 BinderLibTestBundle datai; 420 BinderLibTestBundle datai2; 421 422 server = addServer(&serverId[i]); 423 ASSERT_TRUE(server != NULL); 424 data.writeStrongBinder(server); 425 data.writeInt32(BINDER_LIB_TEST_INDIRECT_TRANSACTION); 426 427 datai.writeInt32(1); 428 datai.writeStrongBinder(m_server); 429 datai.writeInt32(BINDER_LIB_TEST_GET_ID_TRANSACTION); 430 datai2.appendTo(&datai); 431 432 datai.appendTo(&data); 433 } 434 435 ret = m_server->transact(BINDER_LIB_TEST_INDIRECT_TRANSACTION, data, &reply); 436 ASSERT_EQ(NO_ERROR, ret); 437 438 ret = reply.readInt32(&id); 439 ASSERT_EQ(NO_ERROR, ret); 440 EXPECT_EQ(0, id); 441 442 ret = reply.readInt32(&count); 443 ASSERT_EQ(NO_ERROR, ret); 444 EXPECT_EQ(ARRAY_SIZE(serverId), count); 445 446 for (size_t i = 0; i < (size_t)count; i++) { 447 int32_t counti; 448 449 BinderLibTestBundle replyi(&reply); 450 EXPECT_TRUE(replyi.isValid()); 451 ret = replyi.readInt32(&id); 452 EXPECT_EQ(NO_ERROR, ret); 453 EXPECT_EQ(serverId[i], id); 454 455 ret = replyi.readInt32(&counti); 456 ASSERT_EQ(NO_ERROR, ret); 457 EXPECT_EQ(1, counti); 458 459 BinderLibTestBundle replyi2(&replyi); 460 EXPECT_TRUE(replyi2.isValid()); 461 ret = replyi2.readInt32(&id); 462 EXPECT_EQ(NO_ERROR, ret); 463 EXPECT_EQ(0, id); 464 EXPECT_EQ(replyi2.dataSize(), replyi2.dataPosition()); 465 466 EXPECT_EQ(replyi.dataSize(), replyi.dataPosition()); 467 } 468 469 EXPECT_EQ(reply.dataSize(), reply.dataPosition()); 470 } 471 472 TEST_F(BinderLibTest, CallBack) 473 { 474 status_t ret; 475 Parcel data, reply; 476 sp<BinderLibTestCallBack> callBack = new BinderLibTestCallBack(); 477 data.writeStrongBinder(callBack); 478 ret = m_server->transact(BINDER_LIB_TEST_NOP_CALL_BACK, data, &reply, TF_ONE_WAY); 479 EXPECT_EQ(NO_ERROR, ret); 480 ret = callBack->waitEvent(5); 481 EXPECT_EQ(NO_ERROR, ret); 482 ret = callBack->getResult(); 483 EXPECT_EQ(NO_ERROR, ret); 484 } 485 486 TEST_F(BinderLibTest, AddServer) 487 { 488 sp<IBinder> server = addServer(); 489 ASSERT_TRUE(server != NULL); 490 } 491 492 TEST_F(BinderLibTest, DeathNotificationNoRefs) 493 { 494 status_t ret; 495 496 sp<TestDeathRecipient> testDeathRecipient = new TestDeathRecipient(); 497 498 { 499 sp<IBinder> binder = addServer(); 500 ASSERT_TRUE(binder != NULL); 501 ret = binder->linkToDeath(testDeathRecipient); 502 EXPECT_EQ(NO_ERROR, ret); 503 } 504 IPCThreadState::self()->flushCommands(); 505 ret = testDeathRecipient->waitEvent(5); 506 EXPECT_EQ(NO_ERROR, ret); 507 #if 0 /* Is there an unlink api that does not require a strong reference? */ 508 ret = binder->unlinkToDeath(testDeathRecipient); 509 EXPECT_EQ(NO_ERROR, ret); 510 #endif 511 } 512 513 TEST_F(BinderLibTest, DeathNotificationWeakRef) 514 { 515 status_t ret; 516 wp<IBinder> wbinder; 517 518 sp<TestDeathRecipient> testDeathRecipient = new TestDeathRecipient(); 519 520 { 521 sp<IBinder> binder = addServer(); 522 ASSERT_TRUE(binder != NULL); 523 ret = binder->linkToDeath(testDeathRecipient); 524 EXPECT_EQ(NO_ERROR, ret); 525 wbinder = binder; 526 } 527 IPCThreadState::self()->flushCommands(); 528 ret = testDeathRecipient->waitEvent(5); 529 EXPECT_EQ(NO_ERROR, ret); 530 #if 0 /* Is there an unlink api that does not require a strong reference? */ 531 ret = binder->unlinkToDeath(testDeathRecipient); 532 EXPECT_EQ(NO_ERROR, ret); 533 #endif 534 } 535 536 TEST_F(BinderLibTest, DeathNotificationStrongRef) 537 { 538 status_t ret; 539 sp<IBinder> sbinder; 540 541 sp<TestDeathRecipient> testDeathRecipient = new TestDeathRecipient(); 542 543 { 544 sp<IBinder> binder = addServer(); 545 ASSERT_TRUE(binder != NULL); 546 ret = binder->linkToDeath(testDeathRecipient); 547 EXPECT_EQ(NO_ERROR, ret); 548 sbinder = binder; 549 } 550 { 551 Parcel data, reply; 552 ret = sbinder->transact(BINDER_LIB_TEST_EXIT_TRANSACTION, data, &reply, TF_ONE_WAY); 553 EXPECT_EQ(0, ret); 554 } 555 IPCThreadState::self()->flushCommands(); 556 ret = testDeathRecipient->waitEvent(5); 557 EXPECT_EQ(NO_ERROR, ret); 558 ret = sbinder->unlinkToDeath(testDeathRecipient); 559 EXPECT_EQ(DEAD_OBJECT, ret); 560 } 561 562 TEST_F(BinderLibTest, DeathNotificationMultiple) 563 { 564 status_t ret; 565 const int clientcount = 2; 566 sp<IBinder> target; 567 sp<IBinder> linkedclient[clientcount]; 568 sp<BinderLibTestCallBack> callBack[clientcount]; 569 sp<IBinder> passiveclient[clientcount]; 570 571 target = addServer(); 572 ASSERT_TRUE(target != NULL); 573 for (int i = 0; i < clientcount; i++) { 574 { 575 Parcel data, reply; 576 577 linkedclient[i] = addServer(); 578 ASSERT_TRUE(linkedclient[i] != NULL); 579 callBack[i] = new BinderLibTestCallBack(); 580 data.writeStrongBinder(target); 581 data.writeStrongBinder(callBack[i]); 582 ret = linkedclient[i]->transact(BINDER_LIB_TEST_LINK_DEATH_TRANSACTION, data, &reply, TF_ONE_WAY); 583 EXPECT_EQ(NO_ERROR, ret); 584 } 585 { 586 Parcel data, reply; 587 588 passiveclient[i] = addServer(); 589 ASSERT_TRUE(passiveclient[i] != NULL); 590 data.writeStrongBinder(target); 591 ret = passiveclient[i]->transact(BINDER_LIB_TEST_ADD_STRONG_REF_TRANSACTION, data, &reply, TF_ONE_WAY); 592 EXPECT_EQ(NO_ERROR, ret); 593 } 594 } 595 { 596 Parcel data, reply; 597 ret = target->transact(BINDER_LIB_TEST_EXIT_TRANSACTION, data, &reply, TF_ONE_WAY); 598 EXPECT_EQ(0, ret); 599 } 600 601 for (int i = 0; i < clientcount; i++) { 602 ret = callBack[i]->waitEvent(5); 603 EXPECT_EQ(NO_ERROR, ret); 604 ret = callBack[i]->getResult(); 605 EXPECT_EQ(NO_ERROR, ret); 606 } 607 } 608 609 TEST_F(BinderLibTest, PassFile) { 610 int ret; 611 int pipefd[2]; 612 uint8_t buf[1] = { 0 }; 613 uint8_t write_value = 123; 614 615 ret = pipe2(pipefd, O_NONBLOCK); 616 ASSERT_EQ(0, ret); 617 618 { 619 Parcel data, reply; 620 uint8_t writebuf[1] = { write_value }; 621 622 ret = data.writeFileDescriptor(pipefd[1], true); 623 EXPECT_EQ(NO_ERROR, ret); 624 625 ret = data.writeInt32(sizeof(writebuf)); 626 EXPECT_EQ(NO_ERROR, ret); 627 628 ret = data.write(writebuf, sizeof(writebuf)); 629 EXPECT_EQ(NO_ERROR, ret); 630 631 ret = m_server->transact(BINDER_LIB_TEST_WRITE_FILE_TRANSACTION, data, &reply); 632 EXPECT_EQ(NO_ERROR, ret); 633 } 634 635 ret = read(pipefd[0], buf, sizeof(buf)); 636 EXPECT_EQ(sizeof(buf), ret); 637 EXPECT_EQ(write_value, buf[0]); 638 639 waitForReadData(pipefd[0], 5000); /* wait for other proccess to close pipe */ 640 641 ret = read(pipefd[0], buf, sizeof(buf)); 642 EXPECT_EQ(0, ret); 643 644 close(pipefd[0]); 645 } 646 647 TEST_F(BinderLibTest, PromoteLocal) { 648 sp<IBinder> strong = new BBinder(); 649 wp<IBinder> weak = strong; 650 sp<IBinder> strong_from_weak = weak.promote(); 651 EXPECT_TRUE(strong != NULL); 652 EXPECT_EQ(strong, strong_from_weak); 653 strong = NULL; 654 strong_from_weak = NULL; 655 strong_from_weak = weak.promote(); 656 EXPECT_TRUE(strong_from_weak == NULL); 657 } 658 659 TEST_F(BinderLibTest, PromoteRemote) { 660 int ret; 661 Parcel data, reply; 662 sp<IBinder> strong = new BBinder(); 663 sp<IBinder> server = addServer(); 664 665 ASSERT_TRUE(server != NULL); 666 ASSERT_TRUE(strong != NULL); 667 668 ret = data.writeWeakBinder(strong); 669 EXPECT_EQ(NO_ERROR, ret); 670 671 ret = server->transact(BINDER_LIB_TEST_PROMOTE_WEAK_REF_TRANSACTION, data, &reply); 672 EXPECT_GE(ret, 0); 673 } 674 675 class BinderLibTestService : public BBinder 676 { 677 public: 678 BinderLibTestService(int32_t id) 679 : m_id(id) 680 , m_nextServerId(id + 1) 681 , m_serverStartRequested(false) 682 { 683 pthread_mutex_init(&m_serverWaitMutex, NULL); 684 pthread_cond_init(&m_serverWaitCond, NULL); 685 } 686 ~BinderLibTestService() 687 { 688 exit(EXIT_SUCCESS); 689 } 690 virtual status_t onTransact(uint32_t code, 691 const Parcel& data, Parcel* reply, 692 uint32_t flags = 0) { 693 //printf("%s: code %d\n", __func__, code); 694 (void)flags; 695 696 if (getuid() != (uid_t)IPCThreadState::self()->getCallingUid()) { 697 return PERMISSION_DENIED; 698 } 699 switch (code) { 700 case BINDER_LIB_TEST_REGISTER_SERVER: { 701 int32_t id; 702 sp<IBinder> binder; 703 id = data.readInt32(); 704 binder = data.readStrongBinder(); 705 if (binder == NULL) { 706 return BAD_VALUE; 707 } 708 709 if (m_id != 0) 710 return INVALID_OPERATION; 711 712 pthread_mutex_lock(&m_serverWaitMutex); 713 if (m_serverStartRequested) { 714 m_serverStartRequested = false; 715 m_serverStarted = binder; 716 pthread_cond_signal(&m_serverWaitCond); 717 } 718 pthread_mutex_unlock(&m_serverWaitMutex); 719 return NO_ERROR; 720 } 721 case BINDER_LIB_TEST_ADD_SERVER: { 722 int ret; 723 uint8_t buf[1] = { 0 }; 724 int serverid; 725 726 if (m_id != 0) { 727 return INVALID_OPERATION; 728 } 729 pthread_mutex_lock(&m_serverWaitMutex); 730 if (m_serverStartRequested) { 731 ret = -EBUSY; 732 } else { 733 serverid = m_nextServerId++; 734 m_serverStartRequested = true; 735 736 pthread_mutex_unlock(&m_serverWaitMutex); 737 ret = start_server_process(serverid); 738 pthread_mutex_lock(&m_serverWaitMutex); 739 } 740 if (ret > 0) { 741 if (m_serverStartRequested) { 742 #if defined(HAVE_PTHREAD_COND_TIMEDWAIT_RELATIVE) 743 ret = pthread_cond_timeout_np(&m_serverWaitCond, &m_serverWaitMutex, 5000); 744 #else 745 struct timespec ts; 746 clock_gettime(CLOCK_REALTIME, &ts); 747 ts.tv_sec += 5; 748 ret = pthread_cond_timedwait(&m_serverWaitCond, &m_serverWaitMutex, &ts); 749 #endif 750 } 751 if (m_serverStartRequested) { 752 m_serverStartRequested = false; 753 ret = -ETIMEDOUT; 754 } else { 755 reply->writeStrongBinder(m_serverStarted); 756 reply->writeInt32(serverid); 757 m_serverStarted = NULL; 758 ret = NO_ERROR; 759 } 760 } else if (ret >= 0) { 761 m_serverStartRequested = false; 762 ret = UNKNOWN_ERROR; 763 } 764 pthread_mutex_unlock(&m_serverWaitMutex); 765 return ret; 766 } 767 case BINDER_LIB_TEST_NOP_TRANSACTION: 768 return NO_ERROR; 769 case BINDER_LIB_TEST_NOP_CALL_BACK: { 770 Parcel data2, reply2; 771 sp<IBinder> binder; 772 binder = data.readStrongBinder(); 773 if (binder == NULL) { 774 return BAD_VALUE; 775 } 776 reply2.writeInt32(NO_ERROR); 777 binder->transact(BINDER_LIB_TEST_CALL_BACK, data2, &reply2); 778 return NO_ERROR; 779 } 780 case BINDER_LIB_TEST_GET_ID_TRANSACTION: 781 reply->writeInt32(m_id); 782 return NO_ERROR; 783 case BINDER_LIB_TEST_INDIRECT_TRANSACTION: { 784 int32_t count; 785 uint32_t indirect_code; 786 sp<IBinder> binder; 787 788 count = data.readInt32(); 789 reply->writeInt32(m_id); 790 reply->writeInt32(count); 791 for (int i = 0; i < count; i++) { 792 binder = data.readStrongBinder(); 793 if (binder == NULL) { 794 return BAD_VALUE; 795 } 796 indirect_code = data.readInt32(); 797 BinderLibTestBundle data2(&data); 798 if (!data2.isValid()) { 799 return BAD_VALUE; 800 } 801 BinderLibTestBundle reply2; 802 binder->transact(indirect_code, data2, &reply2); 803 reply2.appendTo(reply); 804 } 805 return NO_ERROR; 806 } 807 case BINDER_LIB_TEST_SET_ERROR_TRANSACTION: 808 reply->setError(data.readInt32()); 809 return NO_ERROR; 810 case BINDER_LIB_TEST_GET_PTR_SIZE_TRANSACTION: 811 reply->writeInt32(sizeof(void *)); 812 return NO_ERROR; 813 case BINDER_LIB_TEST_GET_STATUS_TRANSACTION: 814 return NO_ERROR; 815 case BINDER_LIB_TEST_ADD_STRONG_REF_TRANSACTION: 816 m_strongRef = data.readStrongBinder(); 817 return NO_ERROR; 818 case BINDER_LIB_TEST_LINK_DEATH_TRANSACTION: { 819 int ret; 820 Parcel data2, reply2; 821 sp<TestDeathRecipient> testDeathRecipient = new TestDeathRecipient(); 822 sp<IBinder> target; 823 sp<IBinder> callback; 824 825 target = data.readStrongBinder(); 826 if (target == NULL) { 827 return BAD_VALUE; 828 } 829 callback = data.readStrongBinder(); 830 if (callback == NULL) { 831 return BAD_VALUE; 832 } 833 ret = target->linkToDeath(testDeathRecipient); 834 if (ret == NO_ERROR) 835 ret = testDeathRecipient->waitEvent(5); 836 data2.writeInt32(ret); 837 callback->transact(BINDER_LIB_TEST_CALL_BACK, data2, &reply2); 838 return NO_ERROR; 839 } 840 case BINDER_LIB_TEST_WRITE_FILE_TRANSACTION: { 841 int ret; 842 int32_t size; 843 const void *buf; 844 int fd; 845 846 fd = data.readFileDescriptor(); 847 if (fd < 0) { 848 return BAD_VALUE; 849 } 850 ret = data.readInt32(&size); 851 if (ret != NO_ERROR) { 852 return ret; 853 } 854 buf = data.readInplace(size); 855 if (buf == NULL) { 856 return BAD_VALUE; 857 } 858 ret = write(fd, buf, size); 859 if (ret != size) 860 return UNKNOWN_ERROR; 861 return NO_ERROR; 862 } 863 case BINDER_LIB_TEST_PROMOTE_WEAK_REF_TRANSACTION: { 864 int ret; 865 wp<IBinder> weak; 866 sp<IBinder> strong; 867 Parcel data2, reply2; 868 sp<IServiceManager> sm = defaultServiceManager(); 869 sp<IBinder> server = sm->getService(binderLibTestServiceName); 870 871 weak = data.readWeakBinder(); 872 if (weak == NULL) { 873 return BAD_VALUE; 874 } 875 strong = weak.promote(); 876 877 ret = server->transact(BINDER_LIB_TEST_NOP_TRANSACTION, data2, &reply2); 878 if (ret != NO_ERROR) 879 exit(EXIT_FAILURE); 880 881 if (strong == NULL) { 882 reply->setError(1); 883 } 884 return NO_ERROR; 885 } 886 case BINDER_LIB_TEST_DELAYED_EXIT_TRANSACTION: 887 alarm(10); 888 return NO_ERROR; 889 case BINDER_LIB_TEST_EXIT_TRANSACTION: 890 while (wait(NULL) != -1 || errno != ECHILD) 891 ; 892 exit(EXIT_SUCCESS); 893 default: 894 return UNKNOWN_TRANSACTION; 895 }; 896 } 897 private: 898 int32_t m_id; 899 int32_t m_nextServerId; 900 pthread_mutex_t m_serverWaitMutex; 901 pthread_cond_t m_serverWaitCond; 902 bool m_serverStartRequested; 903 sp<IBinder> m_serverStarted; 904 sp<IBinder> m_strongRef; 905 }; 906 907 int run_server(int index, int readypipefd) 908 { 909 status_t ret; 910 sp<IServiceManager> sm = defaultServiceManager(); 911 { 912 sp<BinderLibTestService> testService = new BinderLibTestService(index); 913 if (index == 0) { 914 ret = sm->addService(binderLibTestServiceName, testService); 915 } else { 916 sp<IBinder> server = sm->getService(binderLibTestServiceName); 917 Parcel data, reply; 918 data.writeInt32(index); 919 data.writeStrongBinder(testService); 920 921 ret = server->transact(BINDER_LIB_TEST_REGISTER_SERVER, data, &reply); 922 } 923 } 924 write(readypipefd, &ret, sizeof(ret)); 925 close(readypipefd); 926 //printf("%s: ret %d\n", __func__, ret); 927 if (ret) 928 return 1; 929 //printf("%s: joinThreadPool\n", __func__); 930 ProcessState::self()->startThreadPool(); 931 IPCThreadState::self()->joinThreadPool(); 932 //printf("%s: joinThreadPool returned\n", __func__); 933 return 1; /* joinThreadPool should not return */ 934 } 935 936 int main(int argc, char **argv) { 937 int ret; 938 939 if (argc == 3 && !strcmp(argv[1], "--servername")) { 940 binderservername = argv[2]; 941 } else { 942 binderservername = argv[0]; 943 } 944 945 if (argc == 4 && !strcmp(argv[1], binderserverarg)) { 946 return run_server(atoi(argv[2]), atoi(argv[3])); 947 } 948 949 ::testing::InitGoogleTest(&argc, argv); 950 binder_env = AddGlobalTestEnvironment(new BinderLibTestEnv()); 951 ProcessState::self()->startThreadPool(); 952 return RUN_ALL_TESTS(); 953 } 954 955