9 个文件变更+465-19
@@ -238,6 +238,7 @@ extern const char* DM_VERSION_5_1_2;
238extern const char* DM_VERSION_5_1_3;238extern const char* DM_VERSION_5_1_3;
239extern const char* DM_VERSION_5_1_4;239extern const char* DM_VERSION_5_1_4;
240extern const char* DM_VERSION_5_1_5;240extern const char* DM_VERSION_5_1_5;
241+extern const char* DM_VERSION_5_1_6;
241extern const char* DM_CURRENT_VERSION;242extern const char* DM_CURRENT_VERSION;
242extern const char* DM_ACL_AGING_VERSION;243extern const char* DM_ACL_AGING_VERSION;
243extern const char* DM_VERSION_5_0_OLD_MAX; // Estimated highest version number of the old version244extern const char* DM_VERSION_5_0_OLD_MAX; // Estimated highest version number of the old version
@@ -210,7 +210,8 @@ const char* DM_VERSION_5_1_2 = "5.1.2";
210const char* DM_VERSION_5_1_3 = "5.1.3";210const char* DM_VERSION_5_1_3 = "5.1.3";
211const char* DM_VERSION_5_1_4 = "5.1.4";211const char* DM_VERSION_5_1_4 = "5.1.4";
212const char* DM_VERSION_5_1_5 = "5.1.5";212const char* DM_VERSION_5_1_5 = "5.1.5";
213-const char* DM_CURRENT_VERSION = DM_VERSION_5_1_5;213+const char* DM_VERSION_5_1_6 = "5.1.6";
214+const char* DM_CURRENT_VERSION = DM_VERSION_5_1_6;
214const char* DM_ACL_AGING_VERSION = DM_VERSION_5_1_0;215const char* DM_ACL_AGING_VERSION = DM_VERSION_5_1_0;
215const char* DM_VERSION_5_0_OLD_MAX = "5.0.99"; // Estimated highest version number of the old version216const char* DM_VERSION_5_0_OLD_MAX = "5.0.99"; // Estimated highest version number of the old version
216const int32_t OLD_DM_HO_OSTYPE = -1;217const int32_t OLD_DM_HO_OSTYPE = -1;
@@ -369,6 +369,8 @@ public:
369 int32_t tokenId, int32_t userId);369 int32_t tokenId, int32_t userId);
370 DM_EXPORT std::vector<DistributedDeviceProfile::AccessControlProfile> GetAclProfileByDeviceIdAndUserId(370 DM_EXPORT std::vector<DistributedDeviceProfile::AccessControlProfile> GetAclProfileByDeviceIdAndUserId(
371 const std::string &deviceId, int32_t userId, const std::string &remoteDeviceId);371 const std::string &deviceId, int32_t userId, const std::string &remoteDeviceId);
372+ DM_EXPORT std::vector<DistributedDeviceProfile::AccessControlProfile> GetAclProfileByRemoteDeviceIdAndUserId(
373+ const std::string &remoteDeviceId, int32_t remoteUserId, const std::string &localDeviceId, int32_t tokenId = 0);
372 DM_EXPORT std::vector<DistributedDeviceProfile::AccessControlProfile> GetAclList(const std::string localUdid,374 DM_EXPORT std::vector<DistributedDeviceProfile::AccessControlProfile> GetAclList(const std::string localUdid,
373 int32_t localUserId, const std::string remoteUdid, int32_t remoteUserId);375 int32_t localUserId, const std::string remoteUdid, int32_t remoteUserId);
374 DM_EXPORT bool ChecksumAcl(DistributedDeviceProfile::AccessControlProfile &acl,376 DM_EXPORT bool ChecksumAcl(DistributedDeviceProfile::AccessControlProfile &acl,
@@ -438,7 +440,7 @@ public:
438 DM_EXPORT void HandleDistributedAccountLogout(const std::string &localUdid, int32_t userId,440 DM_EXPORT void HandleDistributedAccountLogout(const std::string &localUdid, int32_t userId,
439 const std::string &accountId, const std::string &peerUdid);441 const std::string &accountId, const std::string &peerUdid);
440 DM_EXPORT void HandleSubProfileSwitched(const std::string &localUdid, int32_t userId,442 DM_EXPORT void HandleSubProfileSwitched(const std::string &localUdid, int32_t userId,
441- int32_t currentSubProfileId, int32_t previousSubProfileId);443+ int32_t currentSubProfileId, int32_t previousSubProfileId, const std::string &peerUdid = "");
442 DM_EXPORT bool CheckAclMatchByAccountId(const DistributedDeviceProfile::AccessControlProfile &profile,444 DM_EXPORT bool CheckAclMatchByAccountId(const DistributedDeviceProfile::AccessControlProfile &profile,
443 const std::string &localUdid, int32_t userId, const std::string &accountId);445 const std::string &localUdid, int32_t userId, const std::string &accountId);
444 DM_EXPORT bool CheckAclMatchByAccountId(const DistributedDeviceProfile::AccessControlProfile &profile,446 DM_EXPORT bool CheckAclMatchByAccountId(const DistributedDeviceProfile::AccessControlProfile &profile,
@@ -465,10 +467,12 @@ public:
465 const std::string &accountId, const std::string &peerUdid);467 const std::string &accountId, const std::string &peerUdid);
466 DM_EXPORT int32_t DeleteAclByAccountIdHash(const std::string &localUdid, int32_t userId,468 DM_EXPORT int32_t DeleteAclByAccountIdHash(const std::string &localUdid, int32_t userId,
467 const std::string &accountIdHash, const std::string &peerUdid);469 const std::string &accountIdHash, const std::string &peerUdid);
470+ DM_EXPORT std::vector<std::string> GetPeerUdidsByLocalUdid(const std::string &localUdid);
468 DM_EXPORT int32_t UpdateAclByDualForegroundAccountHash(const std::string &localUdid,471 DM_EXPORT int32_t UpdateAclByDualForegroundAccountHash(const std::string &localUdid,
469 const std::string &peerUdid, const std::vector<ForegroundAccountInfo> &localForegroundAccounts,472 const std::string &peerUdid, const std::vector<ForegroundAccountInfo> &localForegroundAccounts,
470 const std::vector<ForegroundAccountInfo> &peerForegroundAccounts);473 const std::vector<ForegroundAccountInfo> &peerForegroundAccounts);
471- 474+ DM_EXPORT bool IsAuthVersionOrNewer(const DistributedDeviceProfile::AccessControlProfile &acl,
475+ const std::string localUdid, const std::string remoteUdid, const std::string &targetVersion);
472private:476private:
473 int32_t HandleDmAuthForm(DistributedDeviceProfile::AccessControlProfile profiles, DmDiscoveryInfo discoveryInfo);477 int32_t HandleDmAuthForm(DistributedDeviceProfile::AccessControlProfile profiles, DmDiscoveryInfo discoveryInfo);
474 void GetParamBindTypeVec(DistributedDeviceProfile::AccessControlProfile profiles, std::string requestDeviceId,478 void GetParamBindTypeVec(DistributedDeviceProfile::AccessControlProfile profiles, std::string requestDeviceId,
@@ -501,6 +505,11 @@ private:
501 bool IsAccountInForegroundByUserId(int32_t userId,505 bool IsAccountInForegroundByUserId(int32_t userId,
502 const std::vector<ForegroundAccountInfo> &foregroundAccounts);506 const std::vector<ForegroundAccountInfo> &foregroundAccounts);
503 int32_t GetDeviceTypeFromExtraData(const std::string &extraData);507 int32_t GetDeviceTypeFromExtraData(const std::string &extraData);
508+ bool MatchNonLnnAcl(const DistributedDeviceProfile::AccessControlProfile &acl,
509+ const std::string &remoteDeviceId, int32_t remoteUserId, const std::string &localDeviceId, int32_t tokenId);
510+ bool MatchLnnAclWithNonLnnAcl(const DistributedDeviceProfile::AccessControlProfile &lnnAcl,
511+ const DistributedDeviceProfile::AccessControlProfile &nonLnnAcl,
512+ const std::string &remoteDeviceId, int32_t remoteUserId, const std::string &localDeviceId);
504 int32_t CalculateProfileTargetStatus(const DistributedDeviceProfile::AccessControlProfile &profile,513 int32_t CalculateProfileTargetStatus(const DistributedDeviceProfile::AccessControlProfile &profile,
505 const std::string &localUdid, const std::string &peerUdid,514 const std::string &localUdid, const std::string &peerUdid,
506 const std::vector<ForegroundAccountInfo> &localForegroundAccounts,515 const std::vector<ForegroundAccountInfo> &localForegroundAccounts,
@@ -591,6 +600,8 @@ private:
591 const std::string localUdid, const std::string remoteUdid);600 const std::string localUdid, const std::string remoteUdid);
592 std::string GetAclVersionInfo(const std::string localUdid, const std::string remoteUdid,601 std::string GetAclVersionInfo(const std::string localUdid, const std::string remoteUdid,
593 const DistributedDeviceProfile::AccessControlProfile &acl);602 const DistributedDeviceProfile::AccessControlProfile &acl);
603+ std::string GetRemoteAclVersionInfo(const std::string localUdid, const std::string remoteUdid,
604+ const DistributedDeviceProfile::AccessControlProfile &acl);
594 std::string GetAppServiceAuthVersionInfo(std::string localUdid, std::string remoteUdid, int32_t tokenId,605 std::string GetAppServiceAuthVersionInfo(std::string localUdid, std::string remoteUdid, int32_t tokenId,
595 int32_t userId, std::vector<DistributedDeviceProfile::AccessControlProfile> profiles);606 int32_t userId, std::vector<DistributedDeviceProfile::AccessControlProfile> profiles);
596 std::string GetDeviceAuthVersionInfo(std::string localUdid, std::string remoteUdid,607 std::string GetDeviceAuthVersionInfo(std::string localUdid, std::string remoteUdid,
@@ -630,6 +641,14 @@ private:
630 bool MatchAccesserByBothUserIdAndPeerUdid(const std::string &peerUdid, int32_t peerUserId,641 bool MatchAccesserByBothUserIdAndPeerUdid(const std::string &peerUdid, int32_t peerUserId,
631 int32_t localUserId, const DistributedDeviceProfile::AccessControlProfile &aclProfile);642 int32_t localUserId, const DistributedDeviceProfile::AccessControlProfile &aclProfile);
632 bool HasServiceId(const DistributedDeviceProfile::AccessControlProfile &profile, int64_t serviceId);643 bool HasServiceId(const DistributedDeviceProfile::AccessControlProfile &profile, int64_t serviceId);
644+ void CollectMatchedNonLnnAcls(const std::vector<DistributedDeviceProfile::AccessControlProfile> &profiles,
645+ const std::string &remoteDeviceId, int32_t remoteUserId, const std::string &localDeviceId, int32_t tokenId,
646+ std::vector<DistributedDeviceProfile::AccessControlProfile> &matchedNonLnnAcls,
647+ std::vector<DistributedDeviceProfile::AccessControlProfile> &aclProfileVec);
648+ void CollectMatchedLnnAcls(const std::vector<DistributedDeviceProfile::AccessControlProfile> &profiles,
649+ const std::vector<DistributedDeviceProfile::AccessControlProfile> &matchedNonLnnAcls,
650+ const std::string &remoteDeviceId, int32_t remoteUserId, const std::string &localDeviceId,
651+ std::vector<DistributedDeviceProfile::AccessControlProfile> &aclProfileVec);
633 void HandleSyncBackgroundUserIdEventInner(DistributedDeviceProfile::AccessControlProfile &item,652 void HandleSyncBackgroundUserIdEventInner(DistributedDeviceProfile::AccessControlProfile &item,
634 std::vector<DmUserRemovedServiceInfo> &serviceInfos);653 std::vector<DmUserRemovedServiceInfo> &serviceInfos);
635 int32_t FillDmUserRemovedServiceInfoRemote(const DistributedDeviceProfile::AccessControlProfile &item,654 int32_t FillDmUserRemovedServiceInfoRemote(const DistributedDeviceProfile::AccessControlProfile &item,
@@ -420,6 +420,20 @@ std::string DeviceProfileConnector::GetAclVersionInfo(const std::string localUdi
420 return "";420 return "";
421}421}
422 422 
423+std::string DeviceProfileConnector::GetRemoteAclVersionInfo(const std::string localUdid, const std::string remoteUdid,
424+ const DistributedDeviceProfile::AccessControlProfile &acl)
425+{
426+ std::string acerDeviceId = acl.GetAccesser().GetAccesserDeviceId();
427+ std::string aceeDeviceId = acl.GetAccessee().GetAccesseeDeviceId();
428+ if (acerDeviceId == localUdid && aceeDeviceId == remoteUdid) {
429+ return acl.GetAccessee().GetAccesseeExtraData();
430+ }
431+ if (aceeDeviceId == localUdid && acerDeviceId == remoteUdid) {
432+ return acl.GetAccesser().GetAccesserExtraData();
433+ }
434+ return "";
435+}
436+ 
423DM_EXPORT DmOfflineParam DeviceProfileConnector::FilterNeedDeleteACL(const std::string &localDeviceId,437DM_EXPORT DmOfflineParam DeviceProfileConnector::FilterNeedDeleteACL(const std::string &localDeviceId,
424 uint32_t localTokenId, const std::string &remoteDeviceId, const std::string &extra)438 uint32_t localTokenId, const std::string &remoteDeviceId, const std::string &extra)
425{439{
@@ -714,6 +728,106 @@ DM_EXPORT std::vector<AccessControlProfile> DeviceProfileConnector::GetAclProfil
714 return aclProfileVec;728 return aclProfileVec;
715}729}
716 730 
731+bool DeviceProfileConnector::MatchNonLnnAcl(const DistributedDeviceProfile::AccessControlProfile &acl,
732+ const std::string &remoteDeviceId, int32_t remoteUserId, const std::string &localDeviceId, int32_t tokenId)
733+{
734+ bool accesserMatch = (acl.GetAccesser().GetAccesserDeviceId() == remoteDeviceId &&
735+ acl.GetAccesser().GetAccesserUserId() == remoteUserId &&
736+ acl.GetAccessee().GetAccesseeDeviceId() == localDeviceId);
737+ bool accesseeMatch = (acl.GetAccessee().GetAccesseeDeviceId() == remoteDeviceId &&
738+ acl.GetAccessee().GetAccesseeUserId() == remoteUserId &&
739+ acl.GetAccesser().GetAccesserDeviceId() == localDeviceId);
740+
741+ if (tokenId != 0) {
742+ int32_t accesserTokenId = static_cast<int32_t>(acl.GetAccesser().GetAccesserTokenId());
743+ int32_t accesseeTokenId = static_cast<int32_t>(acl.GetAccessee().GetAccesseeTokenId());
744+ accesserMatch = accesserMatch && (accesserTokenId == tokenId);
745+ accesseeMatch = accesseeMatch && (accesseeTokenId == tokenId);
746+ }
747+ return accesserMatch || accesseeMatch;
748+}
749+ 
750+bool DeviceProfileConnector::MatchLnnAclWithNonLnnAcl(const DistributedDeviceProfile::AccessControlProfile &lnnAcl,
751+ const DistributedDeviceProfile::AccessControlProfile &nonLnnAcl,
752+ const std::string &remoteDeviceId, int32_t remoteUserId, const std::string &localDeviceId)
753+{
754+ int32_t accesserDeviceType = GetDeviceTypeFromExtraData(nonLnnAcl.GetAccesser().GetAccesserExtraData());
755+ int32_t accesseeDeviceType = GetDeviceTypeFromExtraData(nonLnnAcl.GetAccessee().GetAccesseeExtraData());
756+ bool lnnAccesserMatch = (lnnAcl.GetAccesser().GetAccesserDeviceId() == remoteDeviceId &&
757+ lnnAcl.GetAccesser().GetAccesserUserId() == remoteUserId &&
758+ lnnAcl.GetAccessee().GetAccesseeDeviceId() == localDeviceId);
759+ bool lnnAccesseeMatch = (lnnAcl.GetAccessee().GetAccesseeDeviceId() == remoteDeviceId &&
760+ lnnAcl.GetAccessee().GetAccesseeUserId() == remoteUserId &&
761+ lnnAcl.GetAccesser().GetAccesserDeviceId() == localDeviceId);
762+
763+ if (accesserDeviceType == DEVICE_TYPE_CAR) {
764+ lnnAccesserMatch = lnnAccesserMatch &&
765+ lnnAcl.GetAccesser().GetAccesserAccountId() == nonLnnAcl.GetAccesser().GetAccesserAccountId() &&
766+ lnnAcl.GetAccesser().GetAccesserUserId() == nonLnnAcl.GetAccesser().GetAccesserUserId();
767+ }
768+ if (accesseeDeviceType == DEVICE_TYPE_CAR) {
769+ lnnAccesseeMatch = lnnAccesseeMatch &&
770+ lnnAcl.GetAccessee().GetAccesseeAccountId() == nonLnnAcl.GetAccessee().GetAccesseeAccountId() &&
771+ lnnAcl.GetAccessee().GetAccesseeUserId() == nonLnnAcl.GetAccessee().GetAccesseeUserId();
772+ }
773+ return lnnAccesserMatch || lnnAccesseeMatch;
774+}
775+ 
776+void DeviceProfileConnector::CollectMatchedNonLnnAcls(
777+ const std::vector<AccessControlProfile> &profiles,
778+ const std::string &remoteDeviceId, int32_t remoteUserId,
779+ const std::string &localDeviceId, int32_t tokenId,
780+ std::vector<AccessControlProfile> &matchedNonLnnAcls,
781+ std::vector<AccessControlProfile> &aclProfileVec)
782+{
783+ for (auto &item : profiles) {
784+ if (IsLnnAcl(item)) {
785+ continue;
786+ }
787+ if (MatchNonLnnAcl(item, remoteDeviceId, remoteUserId, localDeviceId, tokenId)) {
788+ matchedNonLnnAcls.push_back(item);
789+ aclProfileVec.push_back(item);
790+ }
791+ }
792+}
793+ 
794+void DeviceProfileConnector::CollectMatchedLnnAcls(
795+ const std::vector<AccessControlProfile> &profiles,
796+ const std::vector<AccessControlProfile> &matchedNonLnnAcls,
797+ const std::string &remoteDeviceId, int32_t remoteUserId,
798+ const std::string &localDeviceId,
799+ std::vector<AccessControlProfile> &aclProfileVec)
800+{
801+ for (auto &item : profiles) {
802+ if (!IsLnnAcl(item)) {
803+ continue;
804+ }
805+ for (const auto &nonLnnAcl : matchedNonLnnAcls) {
806+ if (MatchLnnAclWithNonLnnAcl(item, nonLnnAcl, remoteDeviceId, remoteUserId, localDeviceId)) {
807+ aclProfileVec.push_back(item);
808+ break;
809+ }
810+ }
811+ }
812+}
813+ 
814+DM_EXPORT std::vector<AccessControlProfile> DeviceProfileConnector::GetAclProfileByRemoteDeviceIdAndUserId(
815+ const std::string &remoteDeviceId, int32_t remoteUserId, const std::string &localDeviceId, int32_t tokenId)
816+{
817+ std::vector<AccessControlProfile> aclProfileVec;
818+ std::vector<AccessControlProfile> profiles = GetAllAclIncludeLnnAcl();
819+ std::vector<AccessControlProfile> matchedNonLnnAcls;
820+
821+ CollectMatchedNonLnnAcls(profiles, remoteDeviceId, remoteUserId, localDeviceId, tokenId,
822+ matchedNonLnnAcls, aclProfileVec);
823+
824+ if (!matchedNonLnnAcls.empty()) {
825+ CollectMatchedLnnAcls(profiles, matchedNonLnnAcls, remoteDeviceId, remoteUserId, localDeviceId,
826+ aclProfileVec);
827+ }
828+ return aclProfileVec;
829+}
830+ 
717DM_EXPORT std::unordered_map<std::string, DmAuthForm> DeviceProfileConnector::GetAppTrustDeviceList(831DM_EXPORT std::unordered_map<std::string, DmAuthForm> DeviceProfileConnector::GetAppTrustDeviceList(
718 const std::string &pkgName, const std::string &deviceId)832 const std::string &pkgName, const std::string &deviceId)
719{833{
@@ -1696,6 +1810,26 @@ bool DeviceProfileConnector::IsAuthNewVersion(const DistributedDeviceProfile::Ac
1696 return false;1810 return false;
1697}1811}
1698 1812 
1813+DM_EXPORT bool DeviceProfileConnector::IsAuthVersionOrNewer(const DistributedDeviceProfile::AccessControlProfile &acl,
1814+ const std::string localUdid, const std::string remoteUdid, const std::string &targetVersion)
1815+{
1816+ std::string extraInfo = GetRemoteAclVersionInfo(localUdid, remoteUdid, acl);
1817+ JsonObject extraInfoJson(extraInfo);
1818+ if (extraInfoJson.IsDiscarded()) {
1819+ LOGE("extraInfoJson error");
1820+ return false;
1821+ }
1822+ if (!extraInfoJson[TAG_DMVERSION].IsString()) {
1823+ LOGE("PARAM_KEY_OS_VERSION error");
1824+ return false;
1825+ }
1826+ std::string dmVersion = extraInfoJson[TAG_DMVERSION].Get<std::string>();
1827+ if (CompareVersion(dmVersion, targetVersion) || dmVersion == targetVersion) {
1828+ return true;
1829+ }
1830+ return false;
1831+}
1832+ 
1699void DeviceProfileConnector::FilterNeedDeleteACLInfos(1833void DeviceProfileConnector::FilterNeedDeleteACLInfos(
1700 std::vector<DistributedDeviceProfile::AccessControlProfile> &profiles,1834 std::vector<DistributedDeviceProfile::AccessControlProfile> &profiles,
1701 const std::string &localUdid, const std::string &peerUdid, DmOfflineParam &offlineParam)1835 const std::string &localUdid, const std::string &peerUdid, DmOfflineParam &offlineParam)
@@ -2582,7 +2716,8 @@ DM_EXPORT int32_t DeviceProfileConnector::HandleDevUnBindEvent(int32_t remoteUse
2582{2716{
2583 LOGI("RemoteUserId %{public}d, remoteUdid %{public}s, localUdid %{public}s, tokenId %{public}s.", remoteUserId,2717 LOGI("RemoteUserId %{public}d, remoteUdid %{public}s, localUdid %{public}s, tokenId %{public}s.", remoteUserId,
2584 GetAnonyString(remoteUdid).c_str(), GetAnonyString(localUdid).c_str(), GetAnonyInt32(tokenId).c_str());2718 GetAnonyString(remoteUdid).c_str(), GetAnonyString(localUdid).c_str(), GetAnonyInt32(tokenId).c_str());
2585- std::vector<AccessControlProfile> profiles = GetAclProfileByDeviceIdAndUserId(remoteUdid, remoteUserId, localUdid);2719+ std::vector<AccessControlProfile> profiles = GetAclProfileByRemoteDeviceIdAndUserId(remoteUdid,
2720+ remoteUserId, localUdid, tokenId);
2586 int32_t bindType = DM_INVALIED_TYPE;2721 int32_t bindType = DM_INVALIED_TYPE;
2587 for (const auto &item : profiles) {2722 for (const auto &item : profiles) {
2588 if (item.GetTrustDeviceId() != remoteUdid) {2723 if (item.GetTrustDeviceId() != remoteUdid) {
@@ -2621,7 +2756,8 @@ DM_EXPORT DmOfflineParam DeviceProfileConnector::HandleAppUnBindEvent(int32_t re
2621{2756{
2622 LOGI("RemoteUserId %{public}d, remoteUdid %{public}s, localUdid %{public}s.",2757 LOGI("RemoteUserId %{public}d, remoteUdid %{public}s, localUdid %{public}s.",
2623 remoteUserId, GetAnonyString(remoteUdid).c_str(), GetAnonyString(localUdid).c_str());2758 remoteUserId, GetAnonyString(remoteUdid).c_str(), GetAnonyString(localUdid).c_str());
2624- std::vector<AccessControlProfile> profiles = GetAclProfileByDeviceIdAndUserId(remoteUdid, remoteUserId, localUdid);2759+ std::vector<AccessControlProfile> profiles = GetAclProfileByRemoteDeviceIdAndUserId(remoteUdid,
2760+ remoteUserId, localUdid, tokenId);
2625 DmOfflineParam offlineParam;2761 DmOfflineParam offlineParam;
2626 if (profiles.empty()) {2762 if (profiles.empty()) {
2627 LOGE("Acl is empty.");2763 LOGE("Acl is empty.");
@@ -2704,7 +2840,8 @@ DM_EXPORT DmOfflineParam DeviceProfileConnector::HandleAppUnBindEvent(int32_t re
2704{2840{
2705 LOGI("RemoteUserId %{public}d, remoteUdid %{public}s, localUdid %{public}s.",2841 LOGI("RemoteUserId %{public}d, remoteUdid %{public}s, localUdid %{public}s.",
2706 remoteUserId, GetAnonyString(remoteUdid).c_str(), GetAnonyString(localUdid).c_str());2842 remoteUserId, GetAnonyString(remoteUdid).c_str(), GetAnonyString(localUdid).c_str());
2707- std::vector<AccessControlProfile> profiles = GetAclProfileByDeviceIdAndUserId(remoteUdid, remoteUserId, localUdid);2843+ std::vector<AccessControlProfile> profiles = GetAclProfileByRemoteDeviceIdAndUserId(remoteUdid,
2844+ remoteUserId, localUdid, peerTokenId);
2708 DmOfflineParam offlineParam;2845 DmOfflineParam offlineParam;
2709 if (profiles.empty()) {2846 if (profiles.empty()) {
2710 LOGE("Acl is empty.");2847 LOGE("Acl is empty.");
@@ -2791,7 +2928,8 @@ DmOfflineParam DeviceProfileConnector::HandleServiceUnBindEvent(int32_t remoteUs
2791{2928{
2792 LOGI("RemoteUserId %{public}d, remoteUdid %{public}s, localUdid %{public}s.",2929 LOGI("RemoteUserId %{public}d, remoteUdid %{public}s, localUdid %{public}s.",
2793 remoteUserId, GetAnonyString(remoteUdid).c_str(), GetAnonyString(localUdid).c_str());2930 remoteUserId, GetAnonyString(remoteUdid).c_str(), GetAnonyString(localUdid).c_str());
2794- std::vector<AccessControlProfile> profiles = GetAclProfileByDeviceIdAndUserId(remoteUdid, remoteUserId, localUdid);2931+ std::vector<AccessControlProfile> profiles = GetAclProfileByRemoteDeviceIdAndUserId(remoteUdid,
2932+ remoteUserId, localUdid, tokenId);
2795 DmOfflineParam offlineParam;2933 DmOfflineParam offlineParam;
2796 if (profiles.empty()) {2934 if (profiles.empty()) {
2797 LOGE("Acl is empty.");2935 LOGE("Acl is empty.");
@@ -4584,15 +4722,32 @@ void DeviceProfileConnector::HandleDistributedAccountLogout(const std::string &l
4584}4722}
4585 4723 
4586void DeviceProfileConnector::HandleSubProfileSwitched(const std::string &localUdid, int32_t userId,4724void DeviceProfileConnector::HandleSubProfileSwitched(const std::string &localUdid, int32_t userId,
4587- int32_t currentSubProfileId, int32_t previousSubProfileId)4725+ int32_t currentSubProfileId, int32_t previousSubProfileId, const std::string &peerUdid)
4588{4726{
4589 LOGI("localUdid %{public}s, userId %{public}d, currentSubProfileId %{public}d, "4727 LOGI("localUdid %{public}s, userId %{public}d, currentSubProfileId %{public}d, "
4590- "previousSubProfileId %{public}d", GetAnonyString(localUdid).c_str(), userId,4728+ "previousSubProfileId %{public}d, peerUdid %{public}s", GetAnonyString(localUdid).c_str(), userId,
4591- currentSubProfileId, previousSubProfileId);4729+ currentSubProfileId, previousSubProfileId, GetAnonyString(peerUdid).c_str());
4592 std::string previousAccountId = MultipleUserConnector::GetAccountIdBySubProfileId(userId, previousSubProfileId);4730 std::string previousAccountId = MultipleUserConnector::GetAccountIdBySubProfileId(userId, previousSubProfileId);
4593 std::string currentAccountId = MultipleUserConnector::GetAccountIdBySubProfileId(userId, currentSubProfileId);4731 std::string currentAccountId = MultipleUserConnector::GetAccountIdBySubProfileId(userId, currentSubProfileId);
4594- UpdateAclStatusByAccountId(localUdid, userId, previousAccountId, INACTIVE);4732+ if (peerUdid.empty()) {
4595- UpdateAclStatusByAccountId(localUdid, userId, currentAccountId, ACTIVE);4733+ UpdateAclStatusByAccountId(localUdid, userId, previousAccountId, INACTIVE);
4734+ UpdateAclStatusByAccountId(localUdid, userId, currentAccountId, ACTIVE);
4735+ } else {
4736+ char previousAccountIdHash[DM_MAX_DEVICE_ID_LEN] = {0};
4737+ char currentAccountIdHash[DM_MAX_DEVICE_ID_LEN] = {0};
4738+ if (Crypto::GetAccountIdHash7(previousAccountId,
4739+ reinterpret_cast<uint8_t *>(previousAccountIdHash)) != DM_OK) {
4740+ LOGE("GetAccountIdHash7 failed for previousAccountId");
4741+ return;
4742+ }
4743+ if (Crypto::GetAccountIdHash7(currentAccountId,
4744+ reinterpret_cast<uint8_t *>(currentAccountIdHash)) != DM_OK) {
4745+ LOGE("GetAccountIdHash7 failed for currentAccountId");
4746+ return;
4747+ }
4748+ UpdateAclStatusByAccountIdHash(localUdid, userId, std::string(previousAccountIdHash), INACTIVE, peerUdid);
4749+ UpdateAclStatusByAccountIdHash(localUdid, userId, std::string(currentAccountIdHash), ACTIVE, peerUdid);
4750+ }
4596}4751}
4597 4752 
4598bool DeviceProfileConnector::IsAccountInForeground(int32_t userId, const std::string &accountIdHash,4753bool DeviceProfileConnector::IsAccountInForeground(int32_t userId, const std::string &accountIdHash,
@@ -5241,6 +5396,31 @@ DM_EXPORT std::map<int32_t, int32_t> DeviceProfileConnector::GetUserIdAndBindLev
5241 }5396 }
5242 return userIdAndBindLevel;5397 return userIdAndBindLevel;
5243}5398}
5399+ 
5400+std::vector<std::string> DeviceProfileConnector::GetPeerUdidsByLocalUdid(const std::string &localUdid)
5401+{
5402+ std::vector<std::string> peerUdids;
5403+ std::vector<DistributedDeviceProfile::AccessControlProfile> profiles = GetAllAclIncludeLnnAcl();
5404+ std::set<std::string> peerUdidSet;
5405+
5406+ for (const auto &item : profiles) {
5407+ std::string accesserUdid = item.GetAccesser().GetAccesserDeviceId();
5408+ std::string accesseeUdid = item.GetAccessee().GetAccesseeDeviceId();
5409+
5410+ if (accesserUdid == localUdid) {
5411+ peerUdidSet.insert(accesseeUdid);
5412+ } else if (accesseeUdid == localUdid) {
5413+ peerUdidSet.insert(accesserUdid);
5414+ }
5415+ }
5416+
5417+ for (const auto &udid : peerUdidSet) {
5418+ peerUdids.push_back(udid);
5419+ }
5420+ LOGI("GetPeerUdidsByLocalUdid: localUdid %{public}s, peerUdids count %{public}zu",
5421+ GetAnonyString(localUdid).c_str(), peerUdids.size());
5422+ return peerUdids;
5423+}
5244#endif5424#endif
5245} // namespace DistributedHardware5425} // namespace DistributedHardware
5246} // namespace OHOS5426} // namespace OHOS
@@ -328,6 +328,7 @@ struct DmAuthContext {
328 void SetCredentialId(DmAuthSide side, DmAuthScope authorizedScope, const std::string &credentialId);328 void SetCredentialId(DmAuthSide side, DmAuthScope authorizedScope, const std::string &credentialId);
329 void SetPublicKey(DmAuthSide side, DmAuthScope authorizedScope, const std::string &publicKey);329 void SetPublicKey(DmAuthSide side, DmAuthScope authorizedScope, const std::string &publicKey);
330 std::string GetAccountId(DmAuthSide side);330 std::string GetAccountId(DmAuthSide side);
331+ std::string GetAccountIdHash(DmAuthSide side);
331 std::string GetAclBundleName(const DmAuthDirection &direction, DmProxyAuthContext &proxyAuthContext);332 std::string GetAclBundleName(const DmAuthDirection &direction, DmProxyAuthContext &proxyAuthContext);
332};333};
333} // namespace DistributedHardware334} // namespace DistributedHardware
@@ -406,7 +406,7 @@ std::string AuthCredentialAgreeState::CreateAuthParamsString(DmAuthScope authori
406 jsonObj[TAG_PEER_USER_SPACE_ID] = std::to_string(authContext->GetUserId(DM_AUTH_REMOTE_SIDE));406 jsonObj[TAG_PEER_USER_SPACE_ID] = std::to_string(authContext->GetUserId(DM_AUTH_REMOTE_SIDE));
407 }407 }
408 jsonObj[TAG_LOWER_USER_ID] = (method == DM_AUTH_CREDENTIAL_ADD_METHOD_GENERATE) ?408 jsonObj[TAG_LOWER_USER_ID] = (method == DM_AUTH_CREDENTIAL_ADD_METHOD_GENERATE) ?
409- authContext->GetAccountId(DM_AUTH_LOCAL_SIDE) : authContext->GetAccountId(DM_AUTH_REMOTE_SIDE);409+ authContext->GetAccountIdHash(DM_AUTH_LOCAL_SIDE) : authContext->GetAccountIdHash(DM_AUTH_REMOTE_SIDE);
410 jsonObj[TAG_SUBJECT] = DM_AUTH_CREDENTIAL_SUBJECT_PRIMARY;410 jsonObj[TAG_SUBJECT] = DM_AUTH_CREDENTIAL_SUBJECT_PRIMARY;
411 jsonObj[TAG_CRED_TYPE] = DM_AUTH_CREDENTIAL_ACCOUNT_UNRELATED;411 jsonObj[TAG_CRED_TYPE] = DM_AUTH_CREDENTIAL_ACCOUNT_UNRELATED;
412 jsonObj[TAG_KEY_FORMAT] = (method == DM_AUTH_CREDENTIAL_ADD_METHOD_GENERATE) ?412 jsonObj[TAG_KEY_FORMAT] = (method == DM_AUTH_CREDENTIAL_ADD_METHOD_GENERATE) ?
@@ -78,6 +78,13 @@ std::string DmAuthContext::GetAccountId(DmAuthSide side)
78 return (side == DM_AUTH_LOCAL_SIDE) ? localAccess.accountId : remoteAccess.accountId;78 return (side == DM_AUTH_LOCAL_SIDE) ? localAccess.accountId : remoteAccess.accountId;
79}79}
80 80 
81+std::string DmAuthContext::GetAccountIdHash(DmAuthSide side)
82+{
83+ DmAccess &localAccess = (direction == DM_AUTH_SOURCE) ? accesser : accessee;
84+ DmAccess &remoteAccess = (direction == DM_AUTH_SOURCE) ? accessee : accesser;
85+ return (side == DM_AUTH_LOCAL_SIDE) ? localAccess.accountIdHash : remoteAccess.accountIdHash;
86+}
87+ 
81std::string DmAuthContext::GetAclBundleName(const DmAuthDirection &direction, DmProxyAuthContext &proxyAuthContext)88std::string DmAuthContext::GetAclBundleName(const DmAuthDirection &direction, DmProxyAuthContext &proxyAuthContext)
82{89{
83 DmProxyAccess &access =90 DmProxyAccess &access =
@@ -503,6 +503,9 @@ private:
503 void HandleRemoteUserRemoved(int32_t userId, const std::string &remoteUdid);503 void HandleRemoteUserRemoved(int32_t userId, const std::string &remoteUdid);
504 void HandleAccountLogoutEvent(int32_t userId, const std::string &accountId,504 void HandleAccountLogoutEvent(int32_t userId, const std::string &accountId,
505 const std::string &peerUdid);505 const std::string &peerUdid);
506+ void ReplyAccountLogoutToPeer(const std::string &peerUdid);
507+ void UpdateAclOnAccountLogout(int32_t userId, const std::string &accountId,
508+ const std::string &peerUdid);
506 void GetHoOsTypeUdids(std::vector<std::string> &peerUdids);509 void GetHoOsTypeUdids(std::vector<std::string> &peerUdids);
507 void DeleteHoDevice(const std::vector<int32_t> &foreGroundUserIds, const std::vector<int32_t> &backGroundUserIds);510 void DeleteHoDevice(const std::vector<int32_t> &foreGroundUserIds, const std::vector<int32_t> &backGroundUserIds);
508 void HandleAccountLogoutEventCallback(const std::string &commonEventType, int32_t currentUserId,511 void HandleAccountLogoutEventCallback(const std::string &commonEventType, int32_t currentUserId,
@@ -540,9 +543,18 @@ private:
540 void ParseAppUnBindRelationShip(const RelationShipChangeMsg &relationShipMsg);543 void ParseAppUnBindRelationShip(const RelationShipChangeMsg &relationShipMsg);
541 void HandleSubProfileDeletedEvent(const std::string& localUdid, const DmAccountEventInfo& eventInfo);544 void HandleSubProfileDeletedEvent(const std::string& localUdid, const DmAccountEventInfo& eventInfo);
542 void HandleSubProfileSwitchedEvent(const std::string& localUdid, const DmAccountEventInfo& eventInfo);545 void HandleSubProfileSwitchedEvent(const std::string& localUdid, const DmAccountEventInfo& eventInfo);
546+ void DeleteOldVersionAclAndCredential(const std::string& localUdid, int32_t userId);
543 void HandleDistributedAccountBoundEvent(const DmAccountEventInfo& eventInfo);547 void HandleDistributedAccountBoundEvent(const DmAccountEventInfo& eventInfo);
548+ void ExecuteDeferredSubProfileSwitched(int32_t subProfileId);
544 void HandleDistributedAccountLoginEvent(const std::string& localUdid, const DmAccountEventInfo& eventInfo);549 void HandleDistributedAccountLoginEvent(const std::string& localUdid, const DmAccountEventInfo& eventInfo);
545 void HandleDistributedAccountLogoutEvent(const std::string& localUdid, const DmAccountEventInfo& eventInfo);550 void HandleDistributedAccountLogoutEvent(const std::string& localUdid, const DmAccountEventInfo& eventInfo);
551+ void StartSubProfileSwitchTimer(const std::string& peerUdid, const DmAccountEventInfo& eventInfo);
552+ void OnSubProfileSwitchTimeout(const std::string& peerUdid);
553+ void CancelSubProfileSwitchTimer(const std::string& peerUdid);
554+ bool ProcessAclForDeletion(const std::string& localUdid,
555+ const DistributedDeviceProfile::AccessControlProfile &item,
556+ std::string &localAccountId, std::vector<DmAclIdParam> &aclsToDelete,
557+ std::vector<std::string> &peerUdidsToDelete);
546#endif558#endif
547 bool CheckConstraintEnabledByNetworkId(const std::string &networkId);559 bool CheckConstraintEnabledByNetworkId(const std::string &networkId);
548 560 
@@ -601,6 +613,15 @@ private:
601#endif613#endif
602 std::mutex foregroundAccountCacheLock_;614 std::mutex foregroundAccountCacheLock_;
603 std::map<std::string, std::vector<ForegroundAccountInfo>> foregroundAccountCache_;615 std::map<std::string, std::vector<ForegroundAccountInfo>> foregroundAccountCache_;
616+#ifdef CAR_DEVICE_ENABLE
617+ std::mutex subProfileCacheLock_;
618+ int32_t cachedSubProfileId_ = -1;
619+ int32_t cachedSubProfileUserId_ = -1;
620+ bool deferredSubProfileSwitched_ = false;
621+ DmAccountEventInfo deferredSwitchedEventInfo_;
622+ std::mutex subProfileSwitchTimerLock_;
623+ std::map<std::string, DmAccountEventInfo> pendingSubProfileSwitchMap_;
624+#endif
604};625};
605} // namespace DistributedHardware626} // namespace DistributedHardware
606} // namespace OHOS627} // namespace OHOS
@@ -101,7 +101,9 @@ namespace {
101 constexpr const char* APP_UNBIND_BY_WIFI_TIMEOUT_TASK = "deviceManagerTimer:appUnbindByWifi";101 constexpr const char* APP_UNBIND_BY_WIFI_TIMEOUT_TASK = "deviceManagerTimer:appUnbindByWifi";
102 constexpr const char* ACCOUNT_COMMON_EVENT_BY_WIFI_TIMEOUT_TASK = "deviceManagerTimer:accountCommonEventByWifi";102 constexpr const char* ACCOUNT_COMMON_EVENT_BY_WIFI_TIMEOUT_TASK = "deviceManagerTimer:accountCommonEventByWifi";
103 constexpr const char* SERVICE_UNBIND_PROXY_BY_WIFI_TIMEOUT_TASK = "deviceManagerTimer:serviceUnbindProxyByWifi";103 constexpr const char* SERVICE_UNBIND_PROXY_BY_WIFI_TIMEOUT_TASK = "deviceManagerTimer:serviceUnbindProxyByWifi";
104+ constexpr const char* SUB_PROFILE_SWITCH_TIMEOUT_TASK = "deviceManagerTimer:subProfileSwitch";
104 const int32_t USER_SWITCH_BY_WIFI_TIMEOUT_S = 2;105 const int32_t USER_SWITCH_BY_WIFI_TIMEOUT_S = 2;
106+ const int32_t SUB_PROFILE_SWITCH_TIMEOUT_S = 2;
105 const int32_t SEND_DELAY_MAX_TIME = 5;107 const int32_t SEND_DELAY_MAX_TIME = 5;
106 const int32_t SEND_DELAY_MIN_TIME = 0;108 const int32_t SEND_DELAY_MIN_TIME = 0;
107 const int32_t DELAY_TIME_SEC_CONVERSION = 1000000; // 1000*1000109 const int32_t DELAY_TIME_SEC_CONVERSION = 1000000; // 1000*1000
@@ -2759,11 +2761,186 @@ void DeviceManagerService::HandleSubProfileSwitchedEvent(const std::string& loca
2759{2761{
2760#if !(defined(__LITEOS_M__) || defined(LITE_DEVICE))2762#if !(defined(__LITEOS_M__) || defined(LITE_DEVICE))
2761#ifdef CAR_DEVICE_ENABLE2763#ifdef CAR_DEVICE_ENABLE
2764+ LOGI("SubProfileSwitched: userId %{public}d, subProfileId %{public}d, previousSubProfileId %{public}d",
2765+ eventInfo.userId, eventInfo.subProfileId, eventInfo.previousSubProfileId);
2766+
2767+ DeleteOldVersionAclAndCredential(localUdid, eventInfo.userId);
2768+
2769+ bool hasCachedSubProfileId = false;
2770+ {
2771+ std::lock_guard<std::mutex> lock(subProfileCacheLock_);
2772+ if (cachedSubProfileId_ == eventInfo.subProfileId && cachedSubProfileUserId_ == eventInfo.userId) {
2773+ cachedSubProfileId_ = -1;
2774+ cachedSubProfileUserId_ = -1;
2775+ hasCachedSubProfileId = true;
2776+ LOGI("SubProfileSwitched: cleared cached subProfileId %{public}d", eventInfo.subProfileId);
2777+ }
2778+ }
2779+ if (hasCachedSubProfileId) {
2780+ LOGI("SubProfileSwitched: accountId is empty and has cached subProfileId, deferring execution");
2781+ {
2782+ std::lock_guard<std::mutex> lock(subProfileCacheLock_);
2783+ deferredSubProfileSwitched_ = true;
2784+ deferredSwitchedEventInfo_ = eventInfo;
2785+ }
2786+ return;
2787+ }
2788+ std::vector<std::string> peerUdids = DeviceProfileConnector::GetInstance().GetPeerUdidsByLocalUdid(localUdid);
2789+ for (const auto& peerUdid : peerUdids) {
2790+ StartSubProfileSwitchTimer(peerUdid, eventInfo);
2791+ }
2762 TriggerForegroundAccountSync();2792 TriggerForegroundAccountSync();
2763- LOGI("SubProfileSwitched: userId %{public}d, previousSubProfileId %{public}d",2793+#endif
2764- eventInfo.userId, eventInfo.previousSubProfileId);2794+#endif
2795+}
2796+ 
2797+void DeviceManagerService::StartSubProfileSwitchTimer(const std::string& peerUdid, const DmAccountEventInfo& eventInfo)
2798+{
2799+#ifdef CAR_DEVICE_ENABLE
2800+ std::lock_guard<std::mutex> lock(subProfileSwitchTimerLock_);
2801+ pendingSubProfileSwitchMap_[peerUdid] = eventInfo;
2802+
2803+ std::string taskName = std::string(SUB_PROFILE_SWITCH_TIMEOUT_TASK) + "_" + peerUdid;
2804+ std::lock_guard<std::mutex> timerLock(timerLocks_);
2805+ if (timer_ == nullptr) {
2806+ timer_ = std::make_shared<DmTimer>();
2807+ }
2808+ timer_->StartTimer(taskName, SUB_PROFILE_SWITCH_TIMEOUT_S, [this, peerUdid](std::string name) {
2809+ OnSubProfileSwitchTimeout(peerUdid);
2810+ });
2811+ LOGI("Started subProfile switch timer for peerUdid %{public}s", GetAnonyString(peerUdid).c_str());
2812+#endif
2813+}
2814+ 
2815+void DeviceManagerService::OnSubProfileSwitchTimeout(const std::string& peerUdid)
2816+{
2817+#ifdef CAR_DEVICE_ENABLE
2818+ LOGI("SubProfile switch timeout for peerUdid %{public}s", GetAnonyString(peerUdid).c_str());
2819+ std::string localUdid = GetLocalDeviceUdid();
2820+ DmAccountEventInfo eventInfo;
2821+ {
2822+ std::lock_guard<std::mutex> lock(subProfileSwitchTimerLock_);
2823+ if (pendingSubProfileSwitchMap_.find(peerUdid) != pendingSubProfileSwitchMap_.end()) {
2824+ eventInfo = pendingSubProfileSwitchMap_[peerUdid];
2825+ pendingSubProfileSwitchMap_.erase(peerUdid);
2826+ } else {
2827+ LOGE("No pending subProfile switch found for peerUdid %{public}s", GetAnonyString(peerUdid).c_str());
2828+ return;
2829+ }
2830+ }
2765 DeviceProfileConnector::GetInstance().HandleSubProfileSwitched(localUdid, eventInfo.userId,2831 DeviceProfileConnector::GetInstance().HandleSubProfileSwitched(localUdid, eventInfo.userId,
2766- eventInfo.subProfileId, eventInfo.previousSubProfileId);2832+ eventInfo.subProfileId, eventInfo.previousSubProfileId, peerUdid);
2833+#endif
2834+}
2835+ 
2836+void DeviceManagerService::CancelSubProfileSwitchTimer(const std::string& peerUdid)
2837+{
2838+#ifdef CAR_DEVICE_ENABLE
2839+ LOGI("Cancel subProfile switch timer for peerUdid %{public}s", GetAnonyString(peerUdid).c_str());
2840+ DmAccountEventInfo eventInfo;
2841+ {
2842+ std::lock_guard<std::mutex> lock(subProfileSwitchTimerLock_);
2843+ if (pendingSubProfileSwitchMap_.find(peerUdid) != pendingSubProfileSwitchMap_.end()) {
2844+ eventInfo = pendingSubProfileSwitchMap_[peerUdid];
2845+ pendingSubProfileSwitchMap_.erase(peerUdid);
2846+ } else {
2847+ LOGI("No pending subProfile switch found for peerUdid %{public}s", GetAnonyString(peerUdid).c_str());
2848+ return;
2849+ }
2850+ }
2851+ std::string taskName = std::string(SUB_PROFILE_SWITCH_TIMEOUT_TASK) + "_" + peerUdid;
2852+ std::lock_guard<std::mutex> timerLock(timerLocks_);
2853+ if (timer_ != nullptr) {
2854+ timer_->DeleteTimer(taskName);
2855+ }
2856+#endif
2857+}
2858+ 
2859+bool DeviceManagerService::ProcessAclForDeletion(const std::string& localUdid,
2860+ const DistributedDeviceProfile::AccessControlProfile &item,
2861+ std::string &localAccountId, std::vector<DmAclIdParam> &aclsToDelete,
2862+ std::vector<std::string> &peerUdidsToDelete)
2863+{
2864+#ifdef CAR_DEVICE_ENABLE
2865+ std::string accesserUdid = item.GetAccesser().GetAccesserDeviceId();
2866+ std::string accesseeUdid = item.GetAccessee().GetAccesseeDeviceId();
2867+
2868+ std::string peerUdid;
2869+ int32_t peerUserId = 0;
2870+
2871+ if (localUdid == accesserUdid) {
2872+ peerUdid = accesseeUdid;
2873+ peerUserId = item.GetAccessee().GetAccesseeUserId();
2874+ if (localAccountId.empty()) {
2875+ localAccountId = item.GetAccesser().GetAccesserAccountId();
2876+ }
2877+ } else if (localUdid == accesseeUdid) {
2878+ peerUdid = accesserUdid;
2879+ peerUserId = item.GetAccesser().GetAccesserUserId();
2880+ if (localAccountId.empty()) {
2881+ localAccountId = item.GetAccessee().GetAccesseeAccountId();
2882+ }
2883+ } else {
2884+ return false;
2885+ }
2886+ bool isNewVersion = DeviceProfileConnector::GetInstance().IsAuthVersionOrNewer(
2887+ item, localUdid, peerUdid, std::string(DM_VERSION_5_1_5));
2888+ if (!isNewVersion) {
2889+ LOGI("Delete old version ACL: accessControlId=%{public}" PRId64", peerUdid=%{public}s",
2890+ item.GetAccessControlId(), GetAnonyString(peerUdid).c_str());
2891+
2892+ DmAclIdParam aclParam;
2893+ aclParam.udid = peerUdid;
2894+ aclParam.userId = item.GetAccesser().GetAccesserUserId();//todo
2895+ aclParam.accessControlId = item.GetAccessControlId();
2896+
2897+ if (localUdid == accesserUdid) {
2898+ aclParam.skId = item.GetAccesser().GetAccesserSessionKeyId();
2899+ aclParam.credId = item.GetAccesser().GetAccesserCredentialIdStr();
2900+ } else {
2901+ aclParam.skId = item.GetAccessee().GetAccesseeSessionKeyId();
2902+ aclParam.credId = item.GetAccessee().GetAccesseeCredentialIdStr();
2903+ }
2904+
2905+ aclsToDelete.push_back(aclParam);
2906+ peerUdidsToDelete.push_back(peerUdid);//todo 去重
2907+ }
2908+ return true;
2909+#else
2910+ return false;
2911+#endif
2912+}
2913+ 
2914+void DeviceManagerService::DeleteOldVersionAclAndCredential(const std::string& localUdid, int32_t userId)
2915+{
2916+#if !(defined(__LITEOS_M__) || defined(LITE_DEVICE))
2917+#ifdef CAR_DEVICE_ENABLE
2918+ LOGI("DeleteOldVersionAclAndCredential start for userId %{public}d", userId);
2919+
2920+ std::vector<DistributedDeviceProfile::AccessControlProfile> profiles =
2921+ DeviceProfileConnector::GetInstance().GetAllAclIncludeLnnAcl();
2922+
2923+ std::vector<std::string> peerUdidsToDelete;
2924+ std::vector<DmAclIdParam> aclsToDelete;
2925+ std::string localAccountId;
2926+
2927+ for (const auto &item : profiles) {
2928+ ProcessAclForDeletion(localUdid, item, localAccountId, aclsToDelete, peerUdidsToDelete);
2929+ }
2930+
2931+ if (!aclsToDelete.empty() && IsDMServiceImplReady()) {
2932+ dmServiceImpl_->DeleteSkCredAndAcl(aclsToDelete);
2933+ }
2934+
2935+ if (!peerUdidsToDelete.empty() && !localAccountId.empty()) {
2936+ std::string accountName = MultipleUserConnector::GetOhosAccountNameByUserId(userId);
2937+ char accountIdHash[DM_MAX_DEVICE_ID_LEN] = {0};
2938+ if (Crypto::GetAccountIdHash(localAccountId, reinterpret_cast<uint8_t *>(accountIdHash)) == DM_OK) {
2939+ NotifyRemoteLocalLogout(peerUdidsToDelete, std::string(accountIdHash), accountName, userId);
2940+ }
2941+ }
2942+
2943+ LOGI("DeleteOldVersionAclAndCredential finished, deleted %{public}zu ACLs", aclsToDelete.size());
2767#endif2944#endif
2768#endif2945#endif
2769}2946}
@@ -2783,6 +2960,9 @@ void DeviceManagerService::HandleDistributedAccountBoundEvent(const DmAccountEve
2783 MultipleUserConnector::SetAccountInfo(eventInfo.userId, eventInfo.subProfileId, dmAccountInfo);2960 MultipleUserConnector::SetAccountInfo(eventInfo.userId, eventInfo.subProfileId, dmAccountInfo);
2784 LOGI("Cached account binding: userId %{public}d, accountId %{public}s, subProfileId %{public}d",2961 LOGI("Cached account binding: userId %{public}d, accountId %{public}s, subProfileId %{public}d",
2785 eventInfo.userId, GetAnonyString(eventInfo.accountId).c_str(), eventInfo.subProfileId);2962 eventInfo.userId, GetAnonyString(eventInfo.accountId).c_str(), eventInfo.subProfileId);
2963+#ifdef CAR_DEVICE_ENABLE
2964+ ExecuteDeferredSubProfileSwitched(eventInfo.subProfileId);
2965+#endif
2786}2966}
2787 2967 
2788void DeviceManagerService::HandleDistributedAccountLoginEvent(const std::string& localUdid,2968void DeviceManagerService::HandleDistributedAccountLoginEvent(const std::string& localUdid,
@@ -2806,6 +2986,37 @@ void DeviceManagerService::HandleDistributedAccountLoginEvent(const std::string&
2806#endif2986#endif
2807}2987}
2808 2988 
2989+void DeviceManagerService::ExecuteDeferredSubProfileSwitched(int32_t subProfileId)
2990+{
2991+#ifdef CAR_DEVICE_ENABLE
2992+ DmAccountEventInfo eventInfo;
2993+ {
2994+ std::lock_guard<std::mutex> lock(subProfileCacheLock_);
2995+ if (!deferredSubProfileSwitched_) {
2996+ LOGI("ExecuteDeferredSubProfileSwitched: no deferred event, skip");
2997+ return;
2998+ }
2999+ if (subProfileId != -1 && deferredSwitchedEventInfo_.subProfileId != subProfileId) {
3000+ LOGI("subProfileId mismatch, deferred %{public}d, incoming %{public}d, skip",
3001+ deferredSwitchedEventInfo_.subProfileId, subProfileId);
3002+ return;
3003+ }
3004+ deferredSubProfileSwitched_ = false;
3005+ eventInfo = deferredSwitchedEventInfo_;
3006+ }
3007+ LOGI("executing deferred switched for userId %{public}d, subProfileId %{public}d",
3008+ eventInfo.userId, eventInfo.subProfileId);
3009+ char localUdid[DEVICE_UUID_LENGTH] = {0};
3010+ GetDevUdid(localUdid, DEVICE_UUID_LENGTH);
3011+ std::string localUdidStr(localUdid);
3012+ std::vector<std::string> peerUdids = DeviceProfileConnector::GetInstance().GetPeerUdidsByLocalUdid(localUdidStr);
3013+ for (const auto& peerUdid : peerUdids) {
3014+ StartSubProfileSwitchTimer(peerUdid, eventInfo);
3015+ }
3016+ TriggerForegroundAccountSync();
3017+#endif
3018+}
3019+ 
2809void DeviceManagerService::HandleDistributedAccountLogoutEvent(const std::string& localUdid,3020void DeviceManagerService::HandleDistributedAccountLogoutEvent(const std::string& localUdid,
2810 const DmAccountEventInfo& eventInfo)3021 const DmAccountEventInfo& eventInfo)
2811{3022{
@@ -3739,9 +3950,11 @@ void DeviceManagerService::HandleForegroundAccountBroadCast(
3739 GetAnonyString(remoteUdid).c_str(), isNeedResponse ? "true" : "false", broadCastId,3950 GetAnonyString(remoteUdid).c_str(), isNeedResponse ? "true" : "false", broadCastId,
3740 isLastBatch ? "true" : "false");3951 isLastBatch ? "true" : "false");
3741 3952
3742- std::string cacheKey = remoteUdid + "_" + std::to_string(broadCastId);3953+#ifdef CAR_DEVICE_ENABLE
3743- std::vector<ForegroundAccountInfo> accountsToProcess;3954+ CancelSubProfileSwitchTimer(remoteUdid);
3955+#endif
3744 3956
3957+ std::string cacheKey = remoteUdid + "_" + std::to_string(broadCastId);
3745 if (!CacheForegroundAccount(cacheKey, foregroundAccount)) {3958 if (!CacheForegroundAccount(cacheKey, foregroundAccount)) {
3746 return;3959 return;
3747 }3960 }
@@ -3751,7 +3964,7 @@ void DeviceManagerService::HandleForegroundAccountBroadCast(
3751 return;3964 return;
3752 }3965 }
3753 3966
3754- accountsToProcess = GetAndClearCachedAccounts(cacheKey);3967+ std::vector<ForegroundAccountInfo> accountsToProcess = GetAndClearCachedAccounts(cacheKey);
3755 DeleteForegroundAccountCacheTimer(cacheKey);3968 DeleteForegroundAccountCacheTimer(cacheKey);
3756 3969
3757 ProcessSyncForegroundAccount(accountsToProcess, remoteUdid);3970 ProcessSyncForegroundAccount(accountsToProcess, remoteUdid);
@@ -5709,6 +5922,9 @@ void DeviceManagerService::ProcessSyncForegroundAccount(
5709 LOGI("udid %{public}s, accounts count %{public}zu", GetAnonyString(peerUdid).c_str(),5922 LOGI("udid %{public}s, accounts count %{public}zu", GetAnonyString(peerUdid).c_str(),
5710 foregroundAccounts.size());5923 foregroundAccounts.size());
5711#if !(defined(__LITEOS_M__) || defined(LITE_DEVICE))5924#if !(defined(__LITEOS_M__) || defined(LITE_DEVICE))
5925+#ifdef CAR_DEVICE_ENABLE
5926+ CancelSubProfileSwitchTimer(peerUdid);
5927+#endif
5712 char localDeviceId[DEVICE_UUID_LENGTH] = {0};5928 char localDeviceId[DEVICE_UUID_LENGTH] = {0};
5713 GetDevUdid(localDeviceId, DEVICE_UUID_LENGTH);5929 GetDevUdid(localDeviceId, DEVICE_UUID_LENGTH);
5714 std::string localUdid = static_cast<std::string>(localDeviceId);5930 std::string localUdid = static_cast<std::string>(localDeviceId);