diff options
| author | 2019-03-08 23:06:43 +0000 | |
|---|---|---|
| committer | 2019-03-08 23:06:43 +0000 | |
| commit | 9b07b1ab4122838c982ca0c59e059cdea9cfe53d (patch) | |
| tree | c57984a0c6273b29b268344854536706e2a29c78 | |
| parent | 36415570df3c7f46ff3bd6f4f61abee66e4ff1dc (diff) | |
| parent | c360a109193590d2e46c4c9b6ab18ca6851f0172 (diff) | |
Merge changes from topic "b127336441"
* changes:
libbinder_ndk: Fix 'isRemote' value for Bn*.
libbinder_ndk: define userdata class in headers
| -rw-r--r-- | libs/binder/ndk/include_ndk/android/binder_interface_utils.h | 94 |
1 files changed, 76 insertions, 18 deletions
diff --git a/libs/binder/ndk/include_ndk/android/binder_interface_utils.h b/libs/binder/ndk/include_ndk/android/binder_interface_utils.h index b82141c932..83a10488e0 100644 --- a/libs/binder/ndk/include_ndk/android/binder_interface_utils.h +++ b/libs/binder/ndk/include_ndk/android/binder_interface_utils.h @@ -106,28 +106,37 @@ class ICInterface : public SharedRefBase { virtual bool isRemote() = 0; /** - * Dumps information about the interface. + * Dumps information about the interface. By default, dumps nothing. */ - virtual binder_status_t dump(int /*fd*/, const char** /*args*/, uint32_t /*numArgs*/) { - return STATUS_OK; - } + virtual inline binder_status_t dump(int /*fd*/, const char** /*args*/, uint32_t /*numArgs*/); + + /** + * Interprets this binder as this underlying interface if this has stored an ICInterface in the + * binder's user data. + * + * This does not do type checking and should only be used when the binder is known to originate + * from ICInterface. Most likely, you want to use I*::fromBinder. + */ + static inline std::shared_ptr<ICInterface> asInterface(AIBinder* binder); /** * Helper method to create a class */ - static AIBinder_Class* defineClass(const char* interfaceDescriptor, - AIBinder_Class_onCreate onCreate, - AIBinder_Class_onDestroy onDestroy, - AIBinder_Class_onTransact onTransact, - AIBinder_onDump onDump = nullptr) { - AIBinder_Class* clazz = - AIBinder_Class_define(interfaceDescriptor, onCreate, onDestroy, onTransact); - if (clazz == nullptr) { - return nullptr; - } - AIBinder_Class_setOnDump(clazz, onDump); - return clazz; - } + static inline AIBinder_Class* defineClass(const char* interfaceDescriptor, + AIBinder_Class_onTransact onTransact); + + private: + class ICInterfaceData { + public: + std::shared_ptr<ICInterface> interface; + + static inline std::shared_ptr<ICInterface> getInterface(AIBinder* binder); + + static inline void* onCreate(void* args); + static inline void onDestroy(void* userData); + static inline binder_status_t onDump(AIBinder* binder, int fd, const char** args, + uint32_t numArgs); + }; }; /** @@ -141,7 +150,7 @@ class BnCInterface : public INTERFACE { SpAIBinder asBinder() override; - bool isRemote() override { return true; } + bool isRemote() override { return false; } protected: /** @@ -176,6 +185,55 @@ class BpCInterface : public INTERFACE { SpAIBinder mBinder; }; +// END OF CLASS DECLARATIONS + +binder_status_t ICInterface::dump(int /*fd*/, const char** /*args*/, uint32_t /*numArgs*/) { + return STATUS_OK; +} + +std::shared_ptr<ICInterface> ICInterface::asInterface(AIBinder* binder) { + return ICInterfaceData::getInterface(binder); +} + +AIBinder_Class* ICInterface::defineClass(const char* interfaceDescriptor, + AIBinder_Class_onTransact onTransact) { + AIBinder_Class* clazz = AIBinder_Class_define(interfaceDescriptor, ICInterfaceData::onCreate, + ICInterfaceData::onDestroy, onTransact); + if (clazz == nullptr) { + return nullptr; + } + + // We can't know if this method is overriden by a subclass interface, so we must register + // ourselves. The default (nothing to dump) is harmless. + AIBinder_Class_setOnDump(clazz, ICInterfaceData::onDump); + return clazz; +} + +std::shared_ptr<ICInterface> ICInterface::ICInterfaceData::getInterface(AIBinder* binder) { + if (binder == nullptr) return nullptr; + + void* userData = AIBinder_getUserData(binder); + if (userData == nullptr) return nullptr; + + return static_cast<ICInterfaceData*>(userData)->interface; +} + +void* ICInterface::ICInterfaceData::onCreate(void* args) { + std::shared_ptr<ICInterface> interface = static_cast<ICInterface*>(args)->ref<ICInterface>(); + ICInterfaceData* data = new ICInterfaceData{interface}; + return static_cast<void*>(data); +} + +void ICInterface::ICInterfaceData::onDestroy(void* userData) { + delete static_cast<ICInterfaceData*>(userData); +} + +binder_status_t ICInterface::ICInterfaceData::onDump(AIBinder* binder, int fd, const char** args, + uint32_t numArgs) { + std::shared_ptr<ICInterface> interface = getInterface(binder); + return interface->dump(fd, args, numArgs); +} + template <typename INTERFACE> SpAIBinder BnCInterface<INTERFACE>::asBinder() { std::lock_guard<std::mutex> l(mMutex); |