From 34a9255a7da12ed23c71accb5f4d30a711a45943 Mon Sep 17 00:00:00 2001 From: "xialiangwei1@huawei.com" Date: Fri, 3 Jul 2026 16:06:04 +0800 Subject: [PATCH] dispatcher Signed-off-by: xialiangwei1@huawei.com Co-Authored-By:Agent --- .../mo_dispatcher_complex_type_manager.h | 1 + .../include/mo_dispatcher_metadata_manager.h | 5 +++ .../include/mo_dispatcher_types.h | 1 + .../mo_dispatcher_complex_type_manager.cpp | 9 +++++ .../src/mo_dispatcher_metadata_manager.cpp | 21 +++++++++++ .../src/modular_object_dispatcher.cpp | 36 ++++++++++++++++++- 6 files changed, 72 insertions(+), 1 deletion(-) diff --git a/frameworks/c/ability_runtime/include/mo_dispatcher_complex_type_manager.h b/frameworks/c/ability_runtime/include/mo_dispatcher_complex_type_manager.h index 2cddfc70af..af14ea24da 100644 --- a/frameworks/c/ability_runtime/include/mo_dispatcher_complex_type_manager.h +++ b/frameworks/c/ability_runtime/include/mo_dispatcher_complex_type_manager.h @@ -110,6 +110,7 @@ public: static bool VariantEquals(const MoVariantStorage& lhs, const OH_AbilityRuntime_ModObjDispatcher_Variant* rhs); static void RegisterStructMetadata(const std::vector& structs); + static void UnregisterStructMetadata(const std::vector& structs); static bool GetStructFieldType(const std::string& structName, const std::string& fieldName, std::shared_ptr* fieldType); static bool GetStructFieldNames(const std::string& structName, std::vector* fieldNames); diff --git a/frameworks/c/ability_runtime/include/mo_dispatcher_metadata_manager.h b/frameworks/c/ability_runtime/include/mo_dispatcher_metadata_manager.h index adc2b70dad..ccae9cb50a 100644 --- a/frameworks/c/ability_runtime/include/mo_dispatcher_metadata_manager.h +++ b/frameworks/c/ability_runtime/include/mo_dispatcher_metadata_manager.h @@ -34,6 +34,11 @@ public: AbilityRuntime_ErrorCode EnsureLoaded(OHOS::IRemoteObject* proxy); + // Clear all cached metadata and reset loaded state. + // Called when the remote proxy dies to release cached memory. + // The metadataManager object itself remains valid; only its cached data is released. + void ClearCache(); + AbilityRuntime_ErrorCode QueryMainServiceInterfaceMemberIds(const char** names, uint32_t count, uint32_t* memberIds) const; diff --git a/frameworks/c/ability_runtime/include/mo_dispatcher_types.h b/frameworks/c/ability_runtime/include/mo_dispatcher_types.h index d17edccb0c..09e590c231 100644 --- a/frameworks/c/ability_runtime/include/mo_dispatcher_types.h +++ b/frameworks/c/ability_runtime/include/mo_dispatcher_types.h @@ -130,6 +130,7 @@ private: struct OH_AbilityRuntime_ModularObjectDispatcher { OHOS::sptr proxy = nullptr; std::shared_ptr metadataManager; + OHOS::sptr deathRecipient; }; struct OH_AbilityRuntime_ModularObjectDispatcher_TypeDescriptor { diff --git a/frameworks/c/ability_runtime/src/mo_dispatcher_complex_type_manager.cpp b/frameworks/c/ability_runtime/src/mo_dispatcher_complex_type_manager.cpp index 77d8ed1600..96a00558b1 100644 --- a/frameworks/c/ability_runtime/src/mo_dispatcher_complex_type_manager.cpp +++ b/frameworks/c/ability_runtime/src/mo_dispatcher_complex_type_manager.cpp @@ -1722,6 +1722,15 @@ void ModObjDispatcherComplexTypeManager::RegisterStructMetadata(const std::vecto } } +void ModObjDispatcherComplexTypeManager::UnregisterStructMetadata(const std::vector& structs) +{ + std::lock_guard lock(g_structMetaMutex); + for (const auto& structMeta : structs) { + g_structFieldTypes.erase(structMeta.name); + g_structFieldOrder.erase(structMeta.name); + } +} + bool ModObjDispatcherComplexTypeManager::GetStructFieldType(const std::string& structName, const std::string& fieldName, std::shared_ptr* fieldType) { diff --git a/frameworks/c/ability_runtime/src/mo_dispatcher_metadata_manager.cpp b/frameworks/c/ability_runtime/src/mo_dispatcher_metadata_manager.cpp index f5d231cad1..b64e83557d 100644 --- a/frameworks/c/ability_runtime/src/mo_dispatcher_metadata_manager.cpp +++ b/frameworks/c/ability_runtime/src/mo_dispatcher_metadata_manager.cpp @@ -281,6 +281,27 @@ AbilityRuntime_ErrorCode ModObjDispatcherMetadataManager::EnsureLoaded(OHOS::IRe return ABILITY_RUNTIME_ERROR_CODE_NO_ERROR; } +// -------- ClearCache -------- + +void ModObjDispatcherMetadataManager::ClearCache() +{ + std::lock_guard lock(mutex_); + if (!loaded_) { + return; + } + ModObjDispatcherComplexTypeManager::UnregisterStructMetadata(structs_); + loaded_ = false; + version_.clear(); + mainServiceInterface_.clear(); + interfaces_.clear(); + enums_.clear(); + structs_.clear(); + nameToMemberId_.clear(); + memberIdToName_.clear(); + memberIdToMethod_.clear(); + TAG_LOGI(AAFwkTag::EXT, "ClearCache: metadata cache cleared"); +} + // -------- RequestMetadataJson -------- AbilityRuntime_ErrorCode ModObjDispatcherMetadataManager::RequestMetadataJson(OHOS::IRemoteObject* proxy, diff --git a/frameworks/c/ability_runtime/src/modular_object_dispatcher.cpp b/frameworks/c/ability_runtime/src/modular_object_dispatcher.cpp index 611f7dfdab..16c48625ba 100644 --- a/frameworks/c/ability_runtime/src/modular_object_dispatcher.cpp +++ b/frameworks/c/ability_runtime/src/modular_object_dispatcher.cpp @@ -24,6 +24,28 @@ using OHOS::AbilityRuntime::ModObjDispatcherParamCodec; using OHOS::MessageOption; using OHOS::MessageParcel; +namespace OHOS::AbilityRuntime { +// Death recipient that clears cached metadata when the remote proxy dies. +// Holds weak_ptr to avoid extending metadataManager lifetime beyond the dispatcher. +class ProxyDeathRecipient : public IRemoteObject::DeathRecipient { +public: + explicit ProxyDeathRecipient(std::weak_ptr metadataManager) + : metadataManager_(std::move(metadataManager)) {} + ~ProxyDeathRecipient() override = default; + void OnRemoteDied(const wptr &remote) override + { + auto mgr = metadataManager_.lock(); + if (mgr != nullptr) { + TAG_LOGI(AAFwkTag::EXT, "Remote proxy died, clearing metadata cache"); + mgr->ClearCache(); + } + } + +private: + std::weak_ptr metadataManager_; +}; +} // namespace OHOS::AbilityRuntime + namespace { AbilityRuntime_ErrorCode CopyStringToBuffer(const std::string& src, char* dst, uint32_t max) { @@ -53,6 +75,13 @@ AbilityRuntime_ErrorCode OH_AbilityRuntime_ModObjDispatcher_CreateMainServiceIns } dispatcher->proxy = remoteProxy->remote; dispatcher->metadataManager = std::make_shared(); + // Register death recipient to auto-release cached metadata when the remote peer dies. + // Uses weak_ptr so the recipient does not extend metadataManager's lifetime. + dispatcher->deathRecipient = OHOS::sptr::MakeSptr( + dispatcher->metadataManager); + if (dispatcher->proxy != nullptr && dispatcher->deathRecipient != nullptr) { + dispatcher->proxy->AddDeathRecipient(dispatcher->deathRecipient); + } *ppModObjDispatcher = dispatcher; return ABILITY_RUNTIME_ERROR_CODE_NO_ERROR; } @@ -82,7 +111,12 @@ void OH_AbilityRuntime_ModObjDispatcher_Release(OH_AbilityRuntime_ModObjDispatch if (ppModObjDispatcher == nullptr || *ppModObjDispatcher == nullptr) { return; } - delete *ppModObjDispatcher; + auto* dispatcher = *ppModObjDispatcher; + if (dispatcher->proxy != nullptr && dispatcher->deathRecipient != nullptr) { + dispatcher->proxy->RemoveDeathRecipient(dispatcher->deathRecipient); + } + dispatcher->deathRecipient = nullptr; + delete dispatcher; *ppModObjDispatcher = nullptr; }