1 /* 2 * Copyright (C) 2016 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 "Interface.h" 18 19 #include "Annotation.h" 20 #include "ArrayType.h" 21 #include "ConstantExpression.h" 22 #include "DeathRecipientType.h" 23 #include "Method.h" 24 #include "ScalarType.h" 25 #include "StringType.h" 26 #include "VectorType.h" 27 28 #include <unistd.h> 29 30 #include <iostream> 31 #include <memory> 32 #include <sstream> 33 #include <string> 34 #include <unordered_map> 35 36 #include <android-base/logging.h> 37 #include <hidl-util/Formatter.h> 38 #include <hidl-util/StringHelper.h> 39 #include <hwbinder/IBinder.h> 40 41 namespace android { 42 43 const std::unique_ptr<ConstantExpression> Interface::FLAG_ONE_WAY = 44 std::make_unique<LiteralConstantExpression>(ScalarType::KIND_UINT32, 45 hardware::IBinder::FLAG_ONEWAY, "oneway"); 46 const std::unique_ptr<ConstantExpression> Interface::FLAG_CLEAR_BUF = 47 std::make_unique<LiteralConstantExpression>(ScalarType::KIND_UINT32, 48 hardware::IBinder::FLAG_CLEAR_BUF, "clear buf"); 49 50 Interface::Interface(const std::string& localName, const FQName& fullName, const Location& location, 51 Scope* parent, const Reference<Type>& superType, const Hash* fileHash) 52 : Scope(localName, fullName, location, parent), mSuperType(superType), mFileHash(fileHash) {} 53 54 std::string Interface::typeName() const { 55 return "interface " + definedName(); 56 } 57 58 const Hash* Interface::getFileHash() const { 59 return mFileHash; 60 } 61 62 bool Interface::fillPingMethod(Method *method) const { 63 if (method->name() != "ping") { 64 return false; 65 } 66 67 method->fillImplementation( 68 hardware::IBinder::HIDL_PING_TRANSACTION, 69 { 70 {IMPL_INTERFACE, 71 [](auto &out) { 72 out << "return ::android::hardware::Void();\n"; 73 } 74 }, 75 {IMPL_STUB_IMPL, 76 [](auto &out) { 77 out << "return ::android::hardware::Void();\n"; 78 } 79 } 80 }, /*cppImpl*/ 81 { 82 {IMPL_INTERFACE, 83 [](auto &out) { 84 out << "return;\n"; 85 } 86 }, 87 } /*javaImpl*/ 88 ); 89 90 return true; 91 } 92 93 bool Interface::fillLinkToDeathMethod(Method *method) const { 94 if (method->name() != "linkToDeath") { 95 return false; 96 } 97 98 method->fillImplementation( 99 hardware::IBinder::HIDL_LINK_TO_DEATH_TRANSACTION, 100 { 101 {IMPL_INTERFACE, 102 [](auto &out) { 103 out << "(void)cookie;\n" 104 << "return (recipient != nullptr);\n"; 105 } 106 }, 107 {IMPL_PROXY, 108 [](auto &out) { 109 out << "::android::hardware::ProcessState::self()->startThreadPool();\n"; 110 out << "::android::hardware::hidl_binder_death_recipient *binder_recipient" 111 << " = new ::android::hardware::hidl_binder_death_recipient(recipient, cookie, this);\n" 112 << "std::unique_lock<std::mutex> lock(_hidl_mMutex);\n" 113 << "_hidl_mDeathRecipients.push_back(binder_recipient);\n" 114 << "return (remote()->linkToDeath(binder_recipient)" 115 << " == ::android::OK);\n"; 116 } 117 }, 118 {IMPL_STUB, nullptr} 119 }, /*cppImpl*/ 120 { 121 {IMPL_INTERFACE, 122 [](auto &out) { 123 out << "return true;\n"; 124 } 125 }, 126 {IMPL_PROXY, 127 [](auto &out) { 128 out << "return mRemote.linkToDeath(recipient, cookie);\n"; 129 } 130 }, 131 {IMPL_STUB, nullptr} 132 } /*javaImpl*/ 133 ); 134 return true; 135 } 136 137 bool Interface::fillUnlinkToDeathMethod(Method *method) const { 138 if (method->name() != "unlinkToDeath") { 139 return false; 140 } 141 142 method->fillImplementation( 143 hardware::IBinder::HIDL_UNLINK_TO_DEATH_TRANSACTION, 144 { 145 {IMPL_INTERFACE, 146 [](auto &out) { 147 out << "return (recipient != nullptr);\n"; 148 } 149 }, 150 {IMPL_PROXY, 151 [](auto &out) { 152 out << "std::unique_lock<std::mutex> lock(_hidl_mMutex);\n" 153 << "for (auto it = _hidl_mDeathRecipients.rbegin();" 154 << "it != _hidl_mDeathRecipients.rend();" 155 << "++it) {\n"; 156 out.indent([&] { 157 out.sIf("(*it)->getRecipient() == recipient", [&] { 158 out << "::android::status_t status = remote()->unlinkToDeath(*it);\n" 159 << "_hidl_mDeathRecipients.erase(it.base()-1);\n" 160 << "return status == ::android::OK;\n"; 161 }); 162 }).endl(); 163 out << "}\n"; 164 out << "return false;\n"; 165 } 166 }, 167 {IMPL_STUB, nullptr /* don't generate code */} 168 }, /*cppImpl*/ 169 { 170 {IMPL_INTERFACE, 171 [](auto &out) { 172 out << "return true;\n"; 173 } 174 }, 175 {IMPL_PROXY, 176 [](auto &out) { 177 out << "return mRemote.unlinkToDeath(recipient);\n"; 178 } 179 }, 180 {IMPL_STUB, nullptr /* don't generate code */} 181 } /*javaImpl*/ 182 ); 183 return true; 184 } 185 bool Interface::fillSyspropsChangedMethod(Method *method) const { 186 if (method->name() != "notifySyspropsChanged") { 187 return false; 188 } 189 190 method->fillImplementation( 191 hardware::IBinder::HIDL_SYSPROPS_CHANGED_TRANSACTION, 192 { { IMPL_INTERFACE, [](auto &out) { 193 out << "::android::report_sysprop_change();\n"; 194 out << "return ::android::hardware::Void();\n"; 195 } } }, /*cppImpl */ 196 { { IMPL_INTERFACE, [](auto &out) { /* javaImpl */ 197 out << "android.os.HwBinder.enableInstrumentation();\n"; 198 } } } /*javaImpl */ 199 ); 200 return true; 201 } 202 203 bool Interface::fillSetHALInstrumentationMethod(Method *method) const { 204 if (method->name() != "setHALInstrumentation") { 205 return false; 206 } 207 208 method->fillImplementation( 209 hardware::IBinder::HIDL_SET_HAL_INSTRUMENTATION_TRANSACTION, 210 { 211 {IMPL_INTERFACE, 212 [](auto &out) { 213 // do nothing for base class. 214 out << "return ::android::hardware::Void();\n"; 215 } 216 }, 217 {IMPL_STUB, 218 [](auto &out) { 219 out << "configureInstrumentation();\n"; 220 } 221 }, 222 {IMPL_PASSTHROUGH, 223 [](auto &out) { 224 out << "configureInstrumentation();\n"; 225 out << "return ::android::hardware::Void();\n"; 226 } 227 }, 228 }, /*cppImpl */ 229 { { IMPL_INTERFACE, [](auto & /*out*/) { /* javaImpl */ 230 // Not support for Java Impl for now. 231 } } } /*javaImpl */ 232 ); 233 return true; 234 } 235 236 bool Interface::fillDescriptorChainMethod(Method *method) const { 237 if (method->name() != "interfaceChain") { 238 return false; 239 } 240 241 method->fillImplementation( 242 hardware::IBinder::HIDL_DESCRIPTOR_CHAIN_TRANSACTION, 243 { { IMPL_INTERFACE, [this](auto &out) { 244 std::vector<const Interface *> chain = typeChain(); 245 out << "_hidl_cb("; 246 out.block([&] { 247 for (const Interface *iface : chain) { 248 out << iface->fullName() << "::descriptor,\n"; 249 } 250 }); 251 out << ");\n"; 252 out << "return ::android::hardware::Void();\n"; 253 } } }, /* cppImpl */ 254 { { IMPL_INTERFACE, [this](auto &out) { 255 std::vector<const Interface *> chain = typeChain(); 256 out << "return new java.util.ArrayList<String>(java.util.Arrays.asList(\n"; 257 out.indent(); out.indent(); 258 for (size_t i = 0; i < chain.size(); ++i) { 259 if (i != 0) 260 out << ",\n"; 261 out << chain[i]->fullJavaName() << ".kInterfaceName"; 262 } 263 out << "));\n"; 264 out.unindent(); out.unindent(); 265 } } } /* javaImpl */ 266 ); 267 return true; 268 } 269 270 void Interface::emitDigestChain( 271 Formatter& out, const std::string& prefix, const std::vector<const Interface*>& chain, 272 std::function<std::string(std::unique_ptr<ConstantExpression>)> byteToString) const { 273 out.join(chain.begin(), chain.end(), ",\n", [&](const auto& iface) { 274 out << prefix; 275 out << "{"; 276 out.join( 277 iface->getFileHash()->raw().begin(), iface->getFileHash()->raw().end(), ",", 278 [&](const auto& e) { 279 // Use ConstantExpression::cppValue / javaValue 280 // because Java used signed byte for uint8_t. 281 out << byteToString(ConstantExpression::ValueOf(ScalarType::Kind::KIND_UINT8, e)); 282 }); 283 out << "} /* "; 284 out << iface->getFileHash()->hexString(); 285 out << " */"; 286 }); 287 } 288 289 bool Interface::fillHashChainMethod(Method *method) const { 290 if (method->name() != "getHashChain") { 291 return false; 292 } 293 const VectorType *chainType = static_cast<const VectorType *>(&method->results()[0]->type()); 294 const ArrayType *digestType = static_cast<const ArrayType *>(chainType->getElementType()); 295 296 method->fillImplementation( 297 hardware::IBinder::HIDL_HASH_CHAIN_TRANSACTION, 298 { { IMPL_INTERFACE, [this, digestType](auto &out) { 299 std::vector<const Interface *> chain = typeChain(); 300 out << "_hidl_cb("; 301 out.block([&] { 302 emitDigestChain(out, "(" + digestType->getInternalDataCppType() + ")", chain, 303 [](const auto& e) { return e->cppValue(); }); 304 }); 305 out << ");\n"; 306 out << "return ::android::hardware::Void();\n"; 307 } } }, /* cppImpl */ 308 { { IMPL_INTERFACE, [this, digestType, chainType](auto &out) { 309 std::vector<const Interface *> chain = typeChain(); 310 out << "return new " 311 << chainType->getJavaType(false /* forInitializer */) 312 << "(java.util.Arrays.asList(\n"; 313 out.indent(2, [&] { 314 // No need for dimensions when elements are explicitly provided. 315 emitDigestChain(out, "new " + digestType->getJavaType(false /* forInitializer */), 316 chain, [](const auto& e) { return e->javaValue(); }); 317 }); 318 out << "));\n"; 319 } } } /* javaImpl */ 320 ); 321 return true; 322 } 323 324 bool Interface::fillGetDescriptorMethod(Method *method) const { 325 if (method->name() != "interfaceDescriptor") { 326 return false; 327 } 328 329 method->fillImplementation( 330 hardware::IBinder::HIDL_GET_DESCRIPTOR_TRANSACTION, 331 { { IMPL_INTERFACE, [this](auto &out) { 332 out << "_hidl_cb(" 333 << fullName() 334 << "::descriptor);\n" 335 << "return ::android::hardware::Void();\n"; 336 } } }, /* cppImpl */ 337 { { IMPL_INTERFACE, [this](auto &out) { 338 out << "return " 339 << fullJavaName() 340 << ".kInterfaceName;\n"; 341 } } } /* javaImpl */ 342 ); 343 return true; 344 } 345 346 bool Interface::fillGetDebugInfoMethod(Method *method) const { 347 if (method->name() != "getDebugInfo") { 348 return false; 349 } 350 351 static const std::string sArch = 352 "#if defined(__LP64__)\n" 353 "::android::hidl::base::V1_0::DebugInfo::Architecture::IS_64BIT\n" 354 "#else\n" 355 "::android::hidl::base::V1_0::DebugInfo::Architecture::IS_32BIT\n" 356 "#endif\n"; 357 358 method->fillImplementation( 359 hardware::IBinder::HIDL_GET_REF_INFO_TRANSACTION, 360 { 361 {IMPL_INTERFACE, 362 [](auto &out) { 363 // getDebugInfo returns N/A for local objects. 364 out << "::android::hidl::base::V1_0::DebugInfo info = {};\n"; 365 out << "info.pid = -1;\n"; 366 out << "info.ptr = 0;\n"; 367 out << "info.arch = \n" << sArch << ";\n"; 368 out << "_hidl_cb(info);\n"; 369 out << "return ::android::hardware::Void();\n"; 370 } 371 }, 372 {IMPL_STUB_IMPL, 373 [](auto &out) { 374 out << "::android::hidl::base::V1_0::DebugInfo info = {};\n"; 375 out << "info.pid = ::android::hardware::details::getPidIfSharable();\n"; 376 out << "info.ptr = ::android::hardware::details::debuggable()" 377 << "? reinterpret_cast<uint64_t>(this) : 0;\n"; 378 out << "info.arch = \n" << sArch << ";\n"; 379 out << "_hidl_cb(info);\n"; 380 out << "return ::android::hardware::Void();\n"; 381 } 382 } 383 }, /* cppImpl */ 384 { { IMPL_INTERFACE, [method](auto &out) { 385 const Type &refInfo = method->results().front()->type(); 386 out << refInfo.getJavaType(false /* forInitializer */) << " info = new " 387 << refInfo.getJavaType(true /* forInitializer */) << "();\n" 388 << "info.pid = android.os.HidlSupport.getPidIfSharable();\n" 389 << "info.ptr = 0;\n" 390 << "info.arch = android.hidl.base.V1_0.DebugInfo.Architecture.UNKNOWN;\n" 391 << "return info;\n"; 392 } } } /* javaImpl */ 393 ); 394 395 return true; 396 } 397 398 bool Interface::fillDebugMethod(Method *method) const { 399 if (method->name() != "debug") { 400 return false; 401 } 402 403 method->fillImplementation(hardware::IBinder::HIDL_DEBUG_TRANSACTION, 404 { 405 {IMPL_INTERFACE, 406 [](auto& out) { 407 out << "(void)fd;\n" 408 << "(void)options;\n" 409 << "return ::android::hardware::Void();\n"; 410 }}, 411 }, /* cppImpl */ 412 { 413 {IMPL_INTERFACE, [](auto& out) { out << "return;\n"; }}, 414 } /* javaImpl */ 415 ); 416 417 return true; 418 } 419 420 void Interface::addUserDefinedMethod(Method* method) { 421 CHECK(!method->isHidlReserved()); 422 mUserMethods.push_back(method); 423 } 424 425 std::vector<const Reference<Type>*> Interface::getReferences() const { 426 std::vector<const Reference<Type>*> ret; 427 428 if (!isIBase()) { 429 ret.push_back(&mSuperType); 430 } 431 432 for (const auto* method : methods()) { 433 const auto& references = method->getReferences(); 434 ret.insert(ret.end(), references.begin(), references.end()); 435 } 436 437 return ret; 438 } 439 440 std::vector<const Reference<Type>*> Interface::getStrongReferences() const { 441 // Interface is a special case as a reference: 442 // its definiton must be completed for extension but 443 // not necessary for other references. 444 445 std::vector<const Reference<Type>*> ret; 446 if (!isIBase()) { 447 ret.push_back(&mSuperType); 448 } 449 450 for (const auto* method : methods()) { 451 const auto& references = method->getStrongReferences(); 452 ret.insert(ret.end(), references.begin(), references.end()); 453 } 454 455 return ret; 456 } 457 458 status_t Interface::resolveInheritance() { 459 size_t serial = hardware::IBinder::FIRST_CALL_TRANSACTION; 460 for (const auto* ancestor : superTypeChain()) { 461 serial += ancestor->mUserMethods.size(); 462 } 463 464 for (Method* method : mUserMethods) { 465 if (serial > hardware::IBinder::LAST_CALL_TRANSACTION) { 466 std::cerr << "ERROR: More than " << hardware::IBinder::LAST_CALL_TRANSACTION 467 << " methods (including super and reserved) are not allowed at " << location() 468 << std::endl; 469 return UNKNOWN_ERROR; 470 } 471 472 method->setSerialId(serial); 473 serial++; 474 } 475 476 return Scope::resolveInheritance(); 477 } 478 479 status_t Interface::validate() const { 480 CHECK(isIBase() == mSuperType.isEmptyReference()); 481 482 if (!isIBase() && !mSuperType->isInterface()) { 483 std::cerr << "ERROR: You can only extend interfaces at " << mSuperType.location() 484 << std::endl; 485 return UNKNOWN_ERROR; 486 } 487 488 status_t err; 489 490 err = validateUniqueNames(); 491 if (err != OK) return err; 492 493 return Scope::validate(); 494 } 495 496 void Interface::getAlignmentAndSize(size_t* align, size_t* size) const { 497 *align = 8; 498 *size = 8; 499 } 500 501 status_t Interface::validateUniqueNames() const { 502 std::unordered_map<std::string, const Interface*> registeredMethodNames; 503 for (auto const& tuple : allSuperMethodsFromRoot()) { 504 // No need to check super method uniqueness 505 registeredMethodNames[tuple.method()->name()] = tuple.interface(); 506 } 507 508 for (const Method* method : mUserMethods) { 509 auto registered = registeredMethodNames.find(method->name()); 510 511 if (registered != registeredMethodNames.end()) { 512 const Interface* definedInType = registered->second; 513 514 if (definedInType == this) { 515 // Defined in this interface 516 std::cerr << "ERROR: Redefinition of method '" << method->name() << "'"; 517 } else if (definedInType->isIBase()) { 518 // Defined in IBase 519 std::cerr << "ERROR: Redefinition of reserved method '" << method->name() << "'"; 520 } else { 521 // Defined in super not IBase 522 std::cerr << "ERROR: Redefinition of method '" << method->name() 523 << "' defined in interface '" << definedInType->fullName() << "'"; 524 } 525 std::cerr << " at " << method->location() << std::endl; 526 return UNKNOWN_ERROR; 527 } 528 529 registeredMethodNames[method->name()] = this; 530 } 531 532 return OK; 533 } 534 535 status_t Interface::validateAnnotations() const { 536 for (const Annotation* annotation : annotations()) { 537 const std::string name = annotation->name(); 538 539 if (name == "SensitiveData") { 540 continue; 541 } 542 543 std::cerr << "WARNING: Unrecognized annotation '" << name << "' for " << typeName() 544 << " at " << location() << ". Only @SensitiveData is supported." << std::endl; 545 // ideally would be error, but we don't want to break downstream 546 // return UNKNOWN_ERROR; 547 } 548 549 for (const Method* method : methods()) { 550 for (const Annotation* annotation : method->annotations()) { 551 const std::string name = annotation->name(); 552 553 if (name == "entry" || name == "exit" || name == "callflow") { 554 continue; 555 } 556 557 std::cerr << "ERROR: Unrecognized annotation '" << name 558 << "' for method: " << method->name() << " at " << method->location() 559 << ". An annotation should be one of: " 560 << "@entry, @exit, or @callflow." << std::endl; 561 return UNKNOWN_ERROR; 562 } 563 } 564 return OK; // not calling superclass which is more restrictive 565 } 566 567 bool Interface::addAllReservedMethods(const std::map<std::string, Method*>& allReservedMethods) { 568 // use a sorted map to insert them in serial ID order. 569 std::map<int32_t, Method *> reservedMethodsById; 570 for (const auto& pair : allReservedMethods) { 571 Method *method = pair.second->copySignature(); 572 bool fillSuccess = fillPingMethod(method) 573 || fillDescriptorChainMethod(method) 574 || fillGetDescriptorMethod(method) 575 || fillHashChainMethod(method) 576 || fillSyspropsChangedMethod(method) 577 || fillLinkToDeathMethod(method) 578 || fillUnlinkToDeathMethod(method) 579 || fillSetHALInstrumentationMethod(method) 580 || fillGetDebugInfoMethod(method) 581 || fillDebugMethod(method); 582 583 if (!fillSuccess) { 584 std::cerr << "ERROR: hidl-gen does not recognize a reserved method " << method->name() 585 << std::endl; 586 return false; 587 } 588 if (!reservedMethodsById.emplace(method->getSerialId(), method).second) { 589 std::cerr << "ERROR: hidl-gen uses duplicated serial id for " << method->name() 590 << " and " << reservedMethodsById[method->getSerialId()]->name() 591 << ", serialId = " << method->getSerialId() << std::endl; 592 return false; 593 } 594 } 595 for (const auto &pair : reservedMethodsById) { 596 this->mReservedMethods.push_back(pair.second); 597 } 598 return true; 599 } 600 601 bool Interface::hasSensitiveDataAnnotation() const { 602 for (const auto& annotation : annotations()) { 603 if (annotation->name() == "SensitiveData") { 604 return true; 605 } 606 } 607 608 return false; 609 } 610 611 const Interface* Interface::superType() const { 612 if (isIBase()) return nullptr; 613 if (!mSuperType->isInterface()) { 614 // This is actually an error 615 // that would be caught in validate 616 return nullptr; 617 } 618 return static_cast<const Interface*>(mSuperType.get()); 619 } 620 621 std::vector<const Interface *> Interface::typeChain() const { 622 std::vector<const Interface *> v; 623 const Interface *iface = this; 624 while (iface != nullptr) { 625 v.push_back(iface); 626 iface = iface->superType(); 627 } 628 return v; 629 } 630 631 std::vector<const Interface *> Interface::superTypeChain() const { 632 return isIBase() ? std::vector<const Interface*>() : superType()->typeChain(); 633 } 634 635 bool Interface::isElidableType() const { 636 return true; 637 } 638 639 bool Interface::isInterface() const { 640 return true; 641 } 642 643 const std::vector<Method *> &Interface::userDefinedMethods() const { 644 return mUserMethods; 645 } 646 647 const std::vector<Method *> &Interface::hidlReservedMethods() const { 648 return mReservedMethods; 649 } 650 651 std::vector<Method *> Interface::methods() const { 652 std::vector<Method *> v(mUserMethods); 653 v.insert(v.end(), mReservedMethods.begin(), mReservedMethods.end()); 654 return v; 655 } 656 657 std::vector<InterfaceAndMethod> Interface::allMethodsFromRoot() const { 658 std::vector<InterfaceAndMethod> v; 659 std::vector<const Interface *> chain = typeChain(); 660 for (auto it = chain.rbegin(); it != chain.rend(); ++it) { 661 const Interface *iface = *it; 662 for (Method *userMethod : iface->userDefinedMethods()) { 663 v.push_back(InterfaceAndMethod(iface, userMethod)); 664 } 665 } 666 for (Method *reservedMethod : hidlReservedMethods()) { 667 v.push_back(InterfaceAndMethod( 668 *chain.rbegin(), // IBase 669 reservedMethod)); 670 } 671 return v; 672 } 673 674 std::vector<InterfaceAndMethod> Interface::allSuperMethodsFromRoot() const { 675 return isIBase() ? std::vector<InterfaceAndMethod>() : superType()->allMethodsFromRoot(); 676 } 677 678 std::string Interface::getBaseName() const { 679 return fqName().getInterfaceBaseName(); 680 } 681 682 std::string Interface::getAdapterName() const { 683 return fqName().getInterfaceAdapterName(); 684 } 685 686 std::string Interface::getProxyName() const { 687 return fqName().getInterfaceProxyName(); 688 } 689 690 std::string Interface::getStubName() const { 691 return fqName().getInterfaceStubName(); 692 } 693 694 std::string Interface::getHwName() const { 695 return fqName().getInterfaceHwName(); 696 } 697 698 std::string Interface::getPassthroughName() const { 699 return fqName().getInterfacePassthroughName(); 700 } 701 702 FQName Interface::getProxyFqName() const { 703 return fqName().getInterfaceProxyFqName(); 704 } 705 706 FQName Interface::getStubFqName() const { 707 return fqName().getInterfaceStubFqName(); 708 } 709 710 FQName Interface::getPassthroughFqName() const { 711 return fqName().getInterfacePassthroughFqName(); 712 } 713 714 std::string Interface::getCppType(StorageMode mode, 715 bool specifyNamespaces) const { 716 const std::string base = 717 std::string(specifyNamespaces ? "::android::" : "") 718 + "sp<" 719 + fullName() 720 + ">"; 721 722 switch (mode) { 723 case StorageMode_Stack: 724 case StorageMode_Result: 725 return base; 726 727 case StorageMode_Argument: 728 return "const " + base + "&"; 729 } 730 } 731 732 std::string Interface::getJavaType(bool /* forInitializer */) const { 733 return fullJavaName(); 734 } 735 736 std::string Interface::getVtsType() const { 737 if (StringHelper::EndsWith(definedName(), "Callback")) { 738 return "TYPE_HIDL_CALLBACK"; 739 } else { 740 return "TYPE_HIDL_INTERFACE"; 741 } 742 } 743 744 void Interface::emitReaderWriter( 745 Formatter &out, 746 const std::string &name, 747 const std::string &parcelObj, 748 bool parcelObjIsPointer, 749 bool isReader, 750 ErrorMode mode) const { 751 const std::string parcelObjDeref = 752 parcelObj + (parcelObjIsPointer ? "->" : "."); 753 754 if (isReader) { 755 out << "{\n"; 756 out.indent(); 757 758 const std::string binderName = "_hidl_binder"; 759 out << "::android::sp<::android::hardware::IBinder> " 760 << binderName << ";\n"; 761 762 out << "_hidl_err = "; 763 out << parcelObjDeref 764 << "readNullableStrongBinder(&" 765 << binderName 766 << ");\n"; 767 768 handleError(out, mode); 769 770 out << name 771 << " = " 772 << "::android::hardware::fromBinder<" 773 << fqName().cppName() 774 << "," 775 << getProxyFqName().cppName() 776 << "," 777 << getStubFqName().cppName() 778 << ">(" 779 << binderName 780 << ");\n"; 781 782 out.unindent(); 783 out << "}\n\n"; 784 } else { 785 out << "if (" << name << " == nullptr) {\n"; 786 out.indent(); 787 out << "_hidl_err = "; 788 out << parcelObjDeref 789 << "writeStrongBinder(nullptr);\n"; 790 out.unindent(); 791 out << "} else {\n"; 792 out.indent(); 793 out << "::android::sp<::android::hardware::IBinder> _hidl_binder = " 794 << "::android::hardware::getOrCreateCachedBinder(" << name << ".get());\n"; 795 out << "if (_hidl_binder.get() != nullptr) {\n"; 796 out.indent([&] { 797 out << "_hidl_err = " 798 << parcelObjDeref 799 << "writeStrongBinder(_hidl_binder);\n"; 800 }); 801 out << "} else {\n"; 802 out.indent([&] { 803 out << "_hidl_err = ::android::UNKNOWN_ERROR;\n"; 804 }); 805 out << "}\n"; 806 out.unindent(); 807 out << "}\n"; 808 809 handleError(out, mode); 810 } 811 } 812 813 void Interface::emitHidlDefinition(Formatter& out) const { 814 if (getDocComment() != nullptr) getDocComment()->emit(out); 815 out << typeName() << " "; 816 817 const Interface* super = superType(); 818 if (super != nullptr && !super->isIBase()) { 819 out << "extends " << super->fqName().getRelativeFQName(fqName()) << " "; 820 } 821 822 out << "{"; 823 824 out.indent([&] { 825 const std::vector<const NamedType*>& definedTypes = getSortedDefinedTypes(); 826 if (definedTypes.size() > 0 || userDefinedMethods().size() > 0) out << "\n"; 827 828 out.join(definedTypes.begin(), definedTypes.end(), "\n", 829 [&](auto t) { t->emitHidlDefinition(out); }); 830 831 if (definedTypes.size() > 0 && userDefinedMethods().size() > 0) out << "\n"; 832 833 out.join(userDefinedMethods().begin(), userDefinedMethods().end(), "\n", 834 [&](auto method) { method->emitHidlDefinition(out); }); 835 }); 836 837 out << "};\n"; 838 } 839 840 void Interface::emitPackageTypeDeclarations(Formatter& out) const { 841 Scope::emitPackageTypeDeclarations(out); 842 843 out << "static inline std::string toString(" << getCppArgumentType() << " o);\n\n"; 844 } 845 846 void Interface::emitPackageTypeHeaderDefinitions(Formatter& out) const { 847 Scope::emitPackageTypeHeaderDefinitions(out); 848 849 out << "static inline std::string toString(" << getCppArgumentType() << " o) "; 850 851 out.block([&] { 852 out << "std::string os = \"[class or subclass of \";\n" 853 << "os += " << fullName() << "::descriptor;\n" 854 << "os += \"]\";\n" 855 << "os += o->isRemote() ? \"@remote\" : \"@local\";\n" 856 << "return os;\n"; 857 }).endl().endl(); 858 } 859 860 void Interface::emitTypeDefinitions(Formatter& out, const std::string& prefix) const { 861 std::string space = prefix.empty() ? "" : (prefix + "::"); 862 863 Scope::emitTypeDefinitions(out, space + definedName()); 864 } 865 866 void Interface::emitJavaReaderWriter( 867 Formatter &out, 868 const std::string &parcelObj, 869 const std::string &argName, 870 bool isReader) const { 871 if (isReader) { 872 out << fullJavaName() 873 << ".asInterface(" 874 << parcelObj 875 << ".readStrongBinder());\n"; 876 } else { 877 out << parcelObj 878 << ".writeStrongBinder(" 879 << argName 880 << " == null ? null : " 881 << argName 882 << ".asBinder());\n"; 883 } 884 } 885 886 void Interface::emitVtsAttributeDeclaration(Formatter& out) const { 887 for (const auto &type : getSubTypes()) { 888 // Skip for TypeDef as it is just an alias of a defined type. 889 if (type->isTypeDef()) { 890 continue; 891 } 892 out << "attribute: {\n"; 893 out.indent(); 894 type->emitVtsTypeDeclarations(out); 895 out.unindent(); 896 out << "}\n\n"; 897 } 898 } 899 900 void Interface::emitVtsMethodDeclaration(Formatter& out, bool isInherited) const { 901 for (const auto &method : methods()) { 902 if (method->isHidlReserved()) { 903 continue; 904 } 905 906 out << "api: {\n"; 907 out.indent(); 908 out << "name: \"" << method->name() << "\"\n"; 909 out << "is_inherited: " << (isInherited ? "true" : "false") << "\n"; 910 // Generate declaration for each return value. 911 for (const auto &result : method->results()) { 912 out << "return_type_hidl: {\n"; 913 out.indent(); 914 out << "name: \"" << result->name() << "\"\n"; 915 result->type().emitVtsAttributeType(out); 916 out.unindent(); 917 out << "}\n"; 918 } 919 // Generate declaration for each input argument 920 for (const auto &arg : method->args()) { 921 out << "arg: {\n"; 922 out.indent(); 923 out << "name: \"" << arg->name() << "\"\n"; 924 arg->type().emitVtsAttributeType(out); 925 out.unindent(); 926 out << "}\n"; 927 } 928 // Generate declaration for each annotation. 929 for (const auto &annotation : method->annotations()) { 930 out << "callflow: {\n"; 931 out.indent(); 932 const std::string name = annotation->name(); 933 if (name == "entry") { 934 out << "entry: true\n"; 935 } else if (name == "exit") { 936 out << "exit: true\n"; 937 } else if (name == "callflow") { 938 const AnnotationParam *param = 939 annotation->getParam("next"); 940 if (param != nullptr) { 941 for (const auto& value : param->getValues()) { 942 out << "next: " << value << "\n"; 943 } 944 } 945 } else { 946 CHECK(false); 947 } 948 out.unindent(); 949 out << "}\n"; 950 } 951 out.unindent(); 952 out << "}\n\n"; 953 } 954 } 955 956 void Interface::emitVtsAttributeType(Formatter& out) const { 957 out << "type: " << getVtsType() << "\n" 958 << "predefined_type: \"" 959 << fullName() 960 << "\"\n"; 961 } 962 963 bool Interface::deepIsJavaCompatible(std::unordered_set<const Type*>* visited) const { 964 if (hasSensitiveDataAnnotation()) { 965 return false; 966 } 967 968 if (superType() != nullptr && !superType()->isJavaCompatible(visited)) { 969 return false; 970 } 971 972 for (const auto* method : methods()) { 973 if (!method->deepIsJavaCompatible(visited)) { 974 return false; 975 } 976 } 977 978 return Scope::deepIsJavaCompatible(visited); 979 } 980 981 bool Interface::isNeverStrongReference() const { 982 return true; 983 } 984 985 const FQName gIBaseFqName = FQName("android.hidl.base", "1.0", "IBase"); 986 const FQName gIManagerFqName = FQName("android.hidl.manager", "1.0", "IServiceManager"); 987 988 } // namespace android 989 990