Matter SDK Coverage Report
Current view: top level - app/server - Dnssd.cpp (source / functions) Coverage Total Hit
Test: SHA:4d2388ac7eed75b2fe5e05e20de377999c632502 Lines: 59.1 % 137 81
Test Date: 2025-07-26 07:12:52 Functions: 66.7 % 15 10

            Line data    Source code
       1              : /*
       2              :  *
       3              :  *    Copyright (c) 2021 Project CHIP Authors
       4              :  *
       5              :  *    Licensed under the Apache License, Version 2.0 (the "License");
       6              :  *    you may not use this file except in compliance with the License.
       7              :  *    You may obtain a copy of the License at
       8              :  *
       9              :  *        http://www.apache.org/licenses/LICENSE-2.0
      10              :  *
      11              :  *    Unless required by applicable law or agreed to in writing, software
      12              :  *    distributed under the License is distributed on an "AS IS" BASIS,
      13              :  *    WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
      14              :  *    See the License for the specific language governing permissions and
      15              :  *    limitations under the License.
      16              :  */
      17              : 
      18              : #include <app/server/Dnssd.h>
      19              : 
      20              : #include <app-common/zap-generated/cluster-enums.h>
      21              : #include <inttypes.h>
      22              : #include <lib/core/Optional.h>
      23              : #include <lib/dnssd/Advertiser.h>
      24              : #include <lib/dnssd/ServiceNaming.h>
      25              : #include <lib/support/DefaultStorageKeyAllocator.h>
      26              : #include <lib/support/Span.h>
      27              : #include <lib/support/logging/CHIPLogging.h>
      28              : #include <messaging/ReliableMessageProtocolConfig.h>
      29              : #include <platform/CHIPDeviceConfig.h>
      30              : #include <platform/CHIPDeviceLayer.h>
      31              : #include <platform/CommissionableDataProvider.h>
      32              : #include <platform/ConfigurationManager.h>
      33              : #include <platform/DeviceInstanceInfoProvider.h>
      34              : #include <protocols/secure_channel/PASESession.h>
      35              : #if CHIP_ENABLE_ROTATING_DEVICE_ID && defined(CHIP_DEVICE_CONFIG_ROTATING_DEVICE_ID_UNIQUE_ID)
      36              : #include <setup_payload/AdditionalDataPayloadGenerator.h>
      37              : #endif
      38              : #include <credentials/FabricTable.h>
      39              : #include <setup_payload/SetupPayload.h>
      40              : #include <system/TimeSource.h>
      41              : 
      42              : #include <algorithm>
      43              : 
      44              : using namespace chip;
      45              : using namespace chip::DeviceLayer;
      46              : 
      47              : namespace chip {
      48              : namespace app {
      49              : namespace {
      50              : 
      51            2 : void OnPlatformEvent(const DeviceLayer::ChipDeviceEvent * event)
      52              : {
      53            2 :     switch (event->Type)
      54              :     {
      55            1 :     case DeviceLayer::DeviceEventType::kDnssdInitialized:
      56              :     case DeviceLayer::DeviceEventType::kDnssdRestartNeeded:
      57            1 :         app::DnssdServer::Instance().StartServer();
      58            1 :         break;
      59            1 :     default:
      60            1 :         break;
      61              :     }
      62            2 : }
      63              : 
      64            2 : void OnPlatformEventWrapper(const DeviceLayer::ChipDeviceEvent * event, intptr_t arg)
      65              : {
      66              :     (void) arg;
      67            2 :     OnPlatformEvent(event);
      68            2 : }
      69              : 
      70              : } // namespace
      71              : 
      72              : constexpr System::Clock::Timestamp DnssdServer::kTimeoutCleared;
      73              : 
      74            7 : bool DnssdServer::HaveOperationalCredentials()
      75              : {
      76            7 :     VerifyOrDie(mFabricTable != nullptr);
      77              : 
      78              :     // Look for any fabric info that has a useful operational identity.
      79            7 :     return mFabricTable->FabricCount() != 0;
      80              : }
      81              : 
      82              : #if CHIP_DEVICE_CONFIG_ENABLE_EXTENDED_DISCOVERY
      83              : 
      84              : void DnssdServer::SetExtendedDiscoveryTimeoutSecs(int32_t secs)
      85              : {
      86              :     ChipLogDetail(Discovery, "Setting extended discovery timeout to %" PRId32 "s", secs);
      87              :     mExtendedDiscoveryTimeoutSecs = MakeOptional(secs);
      88              : 
      89              :     if (mExtendedDiscoveryExpiration != kTimeoutCleared &&
      90              :         mExtendedDiscoveryExpiration > mTimeSource.GetMonotonicTimestamp() + System::Clock::Seconds32(secs))
      91              :     {
      92              :         // Reset our timer to the new (shorter) timeout.
      93              :         ScheduleExtendedDiscoveryExpiration();
      94              :     }
      95              : }
      96              : 
      97              : int32_t DnssdServer::GetExtendedDiscoveryTimeoutSecs()
      98              : {
      99              :     return mExtendedDiscoveryTimeoutSecs.ValueOr(CHIP_DEVICE_CONFIG_EXTENDED_DISCOVERY_TIMEOUT_SECS);
     100              : }
     101              : 
     102              : /// Callback from Extended Discovery Expiration timer
     103              : void HandleExtendedDiscoveryExpiration(System::Layer * aSystemLayer, void * aAppState)
     104              : {
     105              :     DnssdServer::Instance().OnExtendedDiscoveryExpiration(aSystemLayer, aAppState);
     106              : }
     107              : 
     108              : void DnssdServer::OnExtendedDiscoveryExpiration(System::Layer * aSystemLayer, void * aAppState)
     109              : {
     110              :     ChipLogDetail(Discovery, "Extended discovery timed out");
     111              : 
     112              :     mExtendedDiscoveryExpiration = kTimeoutCleared;
     113              : 
     114              :     // Reset our advertising, now that we have flagged ourselves as possibly not
     115              :     // needing extended discovery anymore.
     116              :     StartServer();
     117              : }
     118              : 
     119              : CHIP_ERROR DnssdServer::ScheduleExtendedDiscoveryExpiration()
     120              : {
     121              :     int32_t extendedDiscoveryTimeoutSecs = GetExtendedDiscoveryTimeoutSecs();
     122              :     if (extendedDiscoveryTimeoutSecs == CHIP_DEVICE_CONFIG_DISCOVERY_NO_TIMEOUT)
     123              :     {
     124              :         return CHIP_NO_ERROR;
     125              :     }
     126              :     ChipLogDetail(Discovery, "Scheduling extended discovery timeout in %" PRId32 "s", extendedDiscoveryTimeoutSecs);
     127              : 
     128              :     mExtendedDiscoveryExpiration = mTimeSource.GetMonotonicTimestamp() + System::Clock::Seconds32(extendedDiscoveryTimeoutSecs);
     129              : 
     130              :     return DeviceLayer::SystemLayer().StartTimer(System::Clock::Seconds32(extendedDiscoveryTimeoutSecs),
     131              :                                                  HandleExtendedDiscoveryExpiration, nullptr);
     132              : }
     133              : #endif // CHIP_DEVICE_CONFIG_ENABLE_EXTENDED_DISCOVERY
     134              : 
     135            0 : CHIP_ERROR DnssdServer::GetCommissionableInstanceName(char * buffer, size_t bufferLen)
     136              : {
     137            0 :     auto & mdnsAdvertiser = chip::Dnssd::ServiceAdvertiser::Instance();
     138            0 :     return mdnsAdvertiser.GetCommissionableInstanceName(buffer, bufferLen);
     139              : }
     140              : 
     141           11 : CHIP_ERROR DnssdServer::SetEphemeralDiscriminator(Optional<uint16_t> discriminator)
     142              : {
     143           11 :     VerifyOrReturnError(discriminator.ValueOr(0) <= kMaxDiscriminatorValue, CHIP_ERROR_INVALID_ARGUMENT);
     144           11 :     mEphemeralDiscriminator = discriminator;
     145              : 
     146           11 :     return CHIP_NO_ERROR;
     147              : }
     148              : 
     149              : #if CHIP_CONFIG_ENABLE_ICD_SERVER
     150              : template <class AdvertisingParams>
     151              : void DnssdServer::AddICDKeyToAdvertisement(AdvertisingParams & advParams)
     152              : {
     153              :     if (mICDManager == nullptr)
     154              :     {
     155              :         ChipLogError(Discovery, "Invalid pointer to the ICDManager which is required for adding Dnssd advertisement key");
     156              :         return;
     157              :     }
     158              : 
     159              :     Dnssd::ICDModeAdvertise ICDModeToAdvertise = Dnssd::ICDModeAdvertise::kNone;
     160              :     // Only advertise the ICD key if the device can operate as a LIT
     161              :     if (mICDManager->SupportsFeature(Clusters::IcdManagement::Feature::kLongIdleTimeSupport))
     162              :     {
     163              :         if (mICDManager->GetICDMode() == ICDConfigurationData::ICDMode::LIT)
     164              :         {
     165              :             ICDModeToAdvertise = Dnssd::ICDModeAdvertise::kLIT;
     166              :         }
     167              :         else
     168              :         {
     169              :             ICDModeToAdvertise = Dnssd::ICDModeAdvertise::kSIT;
     170              :         }
     171              :     }
     172              : 
     173              :     advParams.SetICDModeToAdvertise(ICDModeToAdvertise);
     174              : }
     175              : #endif
     176              : 
     177            7 : void DnssdServer::GetPrimaryOrFallbackMACAddress(MutableByteSpan & mac)
     178              : {
     179            7 :     if (ConfigurationMgr().GetPrimaryMACAddress(mac) != CHIP_NO_ERROR)
     180              :     {
     181              :         // Only generate a fallback "MAC" once, so we don't keep constantly changing our host name.
     182            0 :         if (std::all_of(std::begin(mFallbackMAC), std::end(mFallbackMAC), [](uint8_t v) { return v == 0; }))
     183              :         {
     184            0 :             ChipLogError(Discovery, "Failed to get primary mac address of device. Generating a random one.");
     185            0 :             Crypto::DRBG_get_bytes(mFallbackMAC, sizeof(mFallbackMAC));
     186              :         }
     187            0 :         VerifyOrDie(mac.size() == sizeof(mFallbackMAC)); // kPrimaryMACAddressLength
     188            0 :         memcpy(mac.data(), mFallbackMAC, sizeof(mFallbackMAC));
     189              :     }
     190            7 : }
     191              : 
     192              : /// Set MDNS operational advertisement
     193           12 : CHIP_ERROR DnssdServer::AdvertiseOperational()
     194              : {
     195           12 :     VerifyOrReturnError(mFabricTable != nullptr, CHIP_ERROR_INCORRECT_STATE);
     196              : 
     197           12 :     for (const FabricInfo & fabricInfo : *mFabricTable)
     198              :     {
     199            0 :         if (!fabricInfo.ShouldAdvertiseIdentity())
     200              :         {
     201            0 :             continue;
     202              :         }
     203              : 
     204              :         uint8_t macBuffer[DeviceLayer::ConfigurationManager::kPrimaryMACAddressLength];
     205            0 :         MutableByteSpan mac(macBuffer);
     206            0 :         GetPrimaryOrFallbackMACAddress(mac);
     207              : 
     208            0 :         auto advertiseParameters = chip::Dnssd::OperationalAdvertisingParameters()
     209            0 :                                        .SetPeerId(fabricInfo.GetPeerId())
     210            0 :                                        .SetMac(mac)
     211            0 :                                        .SetPort(GetSecuredPort())
     212            0 :                                        .SetInterfaceId(GetInterfaceId())
     213            0 :                                        .SetLocalMRPConfig(GetLocalMRPConfig().std_optional())
     214            0 :                                        .EnableIpV4(SecuredIPv4PortMatchesIPv6Port());
     215              : 
     216              : #if CHIP_CONFIG_ENABLE_ICD_SERVER
     217              :         AddICDKeyToAdvertisement(advertiseParameters);
     218              : #endif
     219              : 
     220              : #if INET_CONFIG_ENABLE_TCP_ENDPOINT
     221            0 :         advertiseParameters.SetTCPSupportModes(mTCPServerEnabled ? chip::Dnssd::TCPModeAdvertise::kTCPClientServer
     222              :                                                                  : chip::Dnssd::TCPModeAdvertise::kTCPClient);
     223              : #endif
     224            0 :         auto & mdnsAdvertiser = chip::Dnssd::ServiceAdvertiser::Instance();
     225              : 
     226            0 :         ChipLogProgress(Discovery, "Advertise operational node " ChipLogFormatX64 "-" ChipLogFormatX64,
     227              :                         ChipLogValueX64(advertiseParameters.GetPeerId().GetCompressedFabricId()),
     228              :                         ChipLogValueX64(advertiseParameters.GetPeerId().GetNodeId()));
     229              :         // Should we keep trying to advertise the other operational
     230              :         // identities on failure?
     231            0 :         ReturnErrorOnFailure(mdnsAdvertiser.Advertise(advertiseParameters));
     232              :     }
     233           12 :     return CHIP_NO_ERROR;
     234              : }
     235              : 
     236            7 : CHIP_ERROR DnssdServer::Advertise(bool commissionableNode, chip::Dnssd::CommissioningMode mode)
     237              : {
     238            7 :     auto advertiseParameters = chip::Dnssd::CommissionAdvertisingParameters()
     239            7 :                                    .SetPort(commissionableNode ? GetSecuredPort() : GetUnsecuredPort())
     240            7 :                                    .SetInterfaceId(GetInterfaceId())
     241            7 :                                    .EnableIpV4(!commissionableNode || SecuredIPv4PortMatchesIPv6Port());
     242            7 :     advertiseParameters.SetCommissionAdvertiseMode(commissionableNode ? chip::Dnssd::CommssionAdvertiseMode::kCommissionableNode
     243              :                                                                       : chip::Dnssd::CommssionAdvertiseMode::kCommissioner);
     244              : 
     245            7 :     advertiseParameters.SetCommissioningMode(mode);
     246              : 
     247              :     char pairingInst[chip::Dnssd::kKeyPairingInstructionMaxLength + 1];
     248              : 
     249              :     uint8_t macBuffer[DeviceLayer::ConfigurationManager::kPrimaryMACAddressLength];
     250            7 :     MutableByteSpan mac(macBuffer);
     251            7 :     GetPrimaryOrFallbackMACAddress(mac);
     252            7 :     advertiseParameters.SetMac(mac);
     253              : 
     254              :     uint16_t value;
     255              :     uint32_t val32;
     256            7 :     if (DeviceLayer::GetDeviceInstanceInfoProvider()->GetVendorId(value) != CHIP_NO_ERROR)
     257              :     {
     258            0 :         ChipLogDetail(Discovery, "Vendor ID not known");
     259              :     }
     260              :     else
     261              :     {
     262            7 :         advertiseParameters.SetVendorId(std::make_optional<uint16_t>(value));
     263              :     }
     264              : 
     265            7 :     if (DeviceLayer::GetDeviceInstanceInfoProvider()->GetProductId(value) != CHIP_NO_ERROR)
     266              :     {
     267            0 :         ChipLogDetail(Discovery, "Product ID not known");
     268              :     }
     269              :     else
     270              :     {
     271            7 :         advertiseParameters.SetProductId(std::make_optional<uint16_t>(value));
     272              :     }
     273              : 
     274              : #if CHIP_DEVICE_CONFIG_ENABLE_JOINT_FABRIC
     275              :     {
     276              :         uint8_t jointFabricMode;
     277              :         CHIP_ERROR error = DeviceLayer::GetDeviceInstanceInfoProvider()->GetJointFabricMode(jointFabricMode);
     278              :         if (error == CHIP_NO_ERROR)
     279              :         {
     280              :             advertiseParameters.SetJointFabricMode(static_cast<Dnssd::JointFabricMode>(jointFabricMode));
     281              :         }
     282              :         else
     283              :         {
     284              :             ChipLogDetail(Discovery, "Failed getting Joint Fabric Mode with error (%" CHIP_ERROR_FORMAT ")!", error.Format());
     285              :         }
     286              :     }
     287              : #endif // CHIP_DEVICE_CONFIG_ENABLE_JOINT_FABRIC
     288              : 
     289            7 :     if (DeviceLayer::ConfigurationMgr().IsCommissionableDeviceTypeEnabled() &&
     290            7 :         DeviceLayer::ConfigurationMgr().GetDeviceTypeId(val32) == CHIP_NO_ERROR)
     291              :     {
     292            0 :         advertiseParameters.SetDeviceType(std::make_optional<uint32_t>(val32));
     293              :     }
     294              : 
     295              :     char deviceName[chip::Dnssd::kKeyDeviceNameMaxLength + 1];
     296            7 :     if (DeviceLayer::ConfigurationMgr().IsCommissionableDeviceNameEnabled() &&
     297            7 :         DeviceLayer::ConfigurationMgr().GetCommissionableDeviceName(deviceName, sizeof(deviceName)) == CHIP_NO_ERROR)
     298              :     {
     299            0 :         advertiseParameters.SetDeviceName(std::make_optional<const char *>(deviceName));
     300              :     }
     301              : 
     302            7 :     advertiseParameters.SetLocalMRPConfig(GetLocalMRPConfig().std_optional());
     303              : 
     304              : #if CHIP_CONFIG_ENABLE_ICD_SERVER
     305              :     AddICDKeyToAdvertisement(advertiseParameters);
     306              : #endif
     307              : 
     308            7 :     if (commissionableNode)
     309              :     {
     310            7 :         uint16_t discriminator = 0;
     311            7 :         CHIP_ERROR error       = DeviceLayer::GetCommissionableDataProvider()->GetSetupDiscriminator(discriminator);
     312            7 :         if (error != CHIP_NO_ERROR)
     313              :         {
     314            0 :             ChipLogError(Discovery,
     315              :                          "Setup discriminator read error (%" CHIP_ERROR_FORMAT ")! Critical error, will not be commissionable.",
     316              :                          error.Format());
     317            0 :             return error;
     318              :         }
     319              : 
     320              :         // Override discriminator with temporary one if one is set
     321            7 :         discriminator = mEphemeralDiscriminator.ValueOr(discriminator);
     322              : 
     323            7 :         advertiseParameters.SetShortDiscriminator(static_cast<uint8_t>((discriminator >> 8) & 0x0F))
     324            7 :             .SetLongDiscriminator(discriminator);
     325              : 
     326              : #if CHIP_ENABLE_ROTATING_DEVICE_ID && defined(CHIP_DEVICE_CONFIG_ROTATING_DEVICE_ID_UNIQUE_ID)
     327              :         char rotatingDeviceIdHexBuffer[RotatingDeviceId::kHexMaxLength];
     328              :         ReturnErrorOnFailure(GenerateRotatingDeviceId(rotatingDeviceIdHexBuffer, MATTER_ARRAY_SIZE(rotatingDeviceIdHexBuffer)));
     329              :         advertiseParameters.SetRotatingDeviceId(std::make_optional<const char *>(rotatingDeviceIdHexBuffer));
     330              : #endif
     331              : 
     332            7 :         if (!HaveOperationalCredentials())
     333              :         {
     334            7 :             if (DeviceLayer::ConfigurationMgr().GetInitialPairingHint(value) != CHIP_NO_ERROR)
     335              :             {
     336            0 :                 ChipLogDetail(Discovery, "DNS-SD Pairing Hint not set");
     337              :             }
     338              :             else
     339              :             {
     340            7 :                 advertiseParameters.SetPairingHint(std::make_optional<uint16_t>(value));
     341              :             }
     342              : 
     343            7 :             if (DeviceLayer::ConfigurationMgr().GetInitialPairingInstruction(pairingInst, sizeof(pairingInst)) != CHIP_NO_ERROR)
     344              :             {
     345            0 :                 ChipLogDetail(Discovery, "DNS-SD Pairing Instruction not set");
     346              :             }
     347              :             else
     348              :             {
     349            7 :                 advertiseParameters.SetPairingInstruction(std::make_optional<const char *>(pairingInst));
     350              :             }
     351              :         }
     352              :         else
     353              :         {
     354            0 :             if (DeviceLayer::ConfigurationMgr().GetSecondaryPairingHint(value) != CHIP_NO_ERROR)
     355              :             {
     356            0 :                 ChipLogDetail(Discovery, "DNS-SD Pairing Hint not set");
     357              :             }
     358              :             else
     359              :             {
     360            0 :                 advertiseParameters.SetPairingHint(std::make_optional<uint16_t>(value));
     361              :             }
     362              : 
     363            0 :             if (DeviceLayer::ConfigurationMgr().GetSecondaryPairingInstruction(pairingInst, sizeof(pairingInst)) != CHIP_NO_ERROR)
     364              :             {
     365            0 :                 ChipLogDetail(Discovery, "DNS-SD Pairing Instruction not set");
     366              :             }
     367              :             else
     368              :             {
     369            0 :                 advertiseParameters.SetPairingInstruction(std::make_optional<const char *>(pairingInst));
     370              :             }
     371              :         }
     372              :     }
     373              : #if CHIP_DEVICE_CONFIG_ENABLE_COMMISSIONER_PASSCODE
     374              :     else
     375              :     {
     376              :         advertiseParameters.SetCommissionerPasscodeSupported(std::make_optional<bool>(true));
     377              :     }
     378              : #endif
     379              : 
     380            7 :     auto & mdnsAdvertiser = chip::Dnssd::ServiceAdvertiser::Instance();
     381              : 
     382            7 :     ChipLogProgress(Discovery, "Advertise commission parameter vendorID=%u productID=%u discriminator=%04u/%02u cm=%u cp=%u jf=%u",
     383              :                     advertiseParameters.GetVendorId().value_or(0), advertiseParameters.GetProductId().value_or(0),
     384              :                     advertiseParameters.GetLongDiscriminator(), advertiseParameters.GetShortDiscriminator(),
     385              :                     to_underlying(advertiseParameters.GetCommissioningMode()),
     386              :                     advertiseParameters.GetCommissionerPasscodeSupported().value_or(false) ? 1 : 0,
     387              : #if CHIP_DEVICE_CONFIG_ENABLE_JOINT_FABRIC
     388              :                     advertiseParameters.GetJointFabricMode().Raw()
     389              : #else
     390              :                     0 // Dummy value when Joint Fabric is disabled
     391              : #endif // CHIP_DEVICE_CONFIG_ENABLE_JOINT_FABRIC
     392              :     );
     393              : 
     394            7 :     return mdnsAdvertiser.Advertise(advertiseParameters);
     395              : }
     396              : 
     397            0 : CHIP_ERROR DnssdServer::AdvertiseCommissioner()
     398              : {
     399            0 :     return Advertise(false /* commissionableNode */, chip::Dnssd::CommissioningMode::kDisabled);
     400              : }
     401              : 
     402            7 : CHIP_ERROR DnssdServer::AdvertiseCommissionableNode(chip::Dnssd::CommissioningMode mode)
     403              : {
     404              : #if CHIP_DEVICE_CONFIG_ENABLE_EXTENDED_DISCOVERY
     405              :     mCurrentCommissioningMode = mode;
     406              :     if (mode != Dnssd::CommissioningMode::kDisabled)
     407              :     {
     408              :         // We're not doing extended discovery right now.
     409              :         DeviceLayer::SystemLayer().CancelTimer(HandleExtendedDiscoveryExpiration, nullptr);
     410              :         mExtendedDiscoveryExpiration = kTimeoutCleared;
     411              :     }
     412              : #endif // CHIP_DEVICE_CONFIG_ENABLE_EXTENDED_DISCOVERY
     413              : 
     414            7 :     return Advertise(true /* commissionableNode */, mode);
     415              : }
     416              : 
     417           12 : void DnssdServer::StartServer()
     418              : {
     419           12 :     Dnssd::CommissioningMode mode = Dnssd::CommissioningMode::kDisabled;
     420           12 :     if (mCommissioningModeProvider)
     421              :     {
     422           12 :         mode = mCommissioningModeProvider->GetCommissioningMode();
     423              :     }
     424           12 :     return StartServer(mode);
     425              : }
     426              : 
     427            0 : void DnssdServer::StopServer()
     428              : {
     429              :     // Make sure we don't hold on to a dangling fabric table pointer.
     430            0 :     mFabricTable = nullptr;
     431              : 
     432            0 :     DeviceLayer::PlatformMgr().RemoveEventHandler(OnPlatformEventWrapper, 0);
     433              : 
     434              : #if CHIP_DEVICE_CONFIG_ENABLE_EXTENDED_DISCOVERY
     435              :     if (mExtendedDiscoveryExpiration != kTimeoutCleared)
     436              :     {
     437              :         DeviceLayer::SystemLayer().CancelTimer(HandleExtendedDiscoveryExpiration, nullptr);
     438              :         mExtendedDiscoveryExpiration = kTimeoutCleared;
     439              :     }
     440              : #endif // CHIP_DEVICE_CONFIG_ENABLE_EXTENDED_DISCOVERY
     441              : 
     442            0 :     if (Dnssd::ServiceAdvertiser::Instance().IsInitialized())
     443              :     {
     444            0 :         auto err = Dnssd::ServiceAdvertiser::Instance().RemoveServices();
     445            0 :         if (err != CHIP_NO_ERROR)
     446              :         {
     447            0 :             ChipLogError(Discovery, "Failed to remove advertised services: %" CHIP_ERROR_FORMAT, err.Format());
     448              :         }
     449              : 
     450            0 :         Dnssd::ServiceAdvertiser::Instance().Shutdown();
     451              :     }
     452            0 : }
     453              : 
     454           12 : void DnssdServer::StartServer(Dnssd::CommissioningMode mode)
     455              : {
     456           12 :     ChipLogProgress(Discovery, "Updating services using commissioning mode %d", static_cast<int>(mode));
     457              : 
     458           12 :     DeviceLayer::PlatformMgr().AddEventHandler(OnPlatformEventWrapper, 0);
     459              : 
     460           12 :     CHIP_ERROR err = Dnssd::ServiceAdvertiser::Instance().Init(chip::DeviceLayer::UDPEndPointManager());
     461           12 :     if (err != CHIP_NO_ERROR)
     462              :     {
     463            0 :         ChipLogError(Discovery, "Failed to initialize advertiser: %" CHIP_ERROR_FORMAT, err.Format());
     464              :     }
     465              : 
     466           12 :     err = Dnssd::ServiceAdvertiser::Instance().RemoveServices();
     467           12 :     if (err != CHIP_NO_ERROR)
     468              :     {
     469            0 :         ChipLogError(Discovery, "Failed to remove advertised services: %" CHIP_ERROR_FORMAT, err.Format());
     470              :     }
     471              : 
     472           12 :     err = AdvertiseOperational();
     473           12 :     if (err != CHIP_NO_ERROR)
     474              :     {
     475            0 :         ChipLogError(Discovery, "Failed to advertise operational node: %" CHIP_ERROR_FORMAT, err.Format());
     476              :     }
     477              : 
     478           12 :     if (mode != Dnssd::CommissioningMode::kDisabled)
     479              :     {
     480            7 :         err = AdvertiseCommissionableNode(mode);
     481            7 :         if (err != CHIP_NO_ERROR)
     482              :         {
     483            0 :             ChipLogError(Discovery, "Failed to advertise commissionable node: %" CHIP_ERROR_FORMAT, err.Format());
     484              :         }
     485              :     }
     486              : #if CHIP_DEVICE_CONFIG_ENABLE_EXTENDED_DISCOVERY
     487              :     else if (GetExtendedDiscoveryTimeoutSecs() != CHIP_DEVICE_CONFIG_DISCOVERY_DISABLED)
     488              :     {
     489              :         bool alwaysAdvertiseExtended = (GetExtendedDiscoveryTimeoutSecs() == CHIP_DEVICE_CONFIG_DISCOVERY_NO_TIMEOUT);
     490              :         // We do extended discovery advertising in three cases:
     491              :         // 1) We don't have a timeout for extended discovery.
     492              :         // 2) We are transitioning out of commissioning mode (basic or enhanced)
     493              :         //    and should therefore start extended discovery.
     494              :         // 3) We are resetting advertising while we are in the middle of an
     495              :         //    existing extended discovery advertising period.
     496              :         if (alwaysAdvertiseExtended || mCurrentCommissioningMode != Dnssd::CommissioningMode::kDisabled ||
     497              :             mExtendedDiscoveryExpiration != kTimeoutCleared)
     498              :         {
     499              :             err = AdvertiseCommissionableNode(mode);
     500              :             if (err != CHIP_NO_ERROR)
     501              :             {
     502              :                 ChipLogError(Discovery, "Failed to advertise extended commissionable node: %" CHIP_ERROR_FORMAT, err.Format());
     503              :             }
     504              :             if (mExtendedDiscoveryExpiration == kTimeoutCleared)
     505              :             {
     506              :                 // set timeout
     507              :                 ScheduleExtendedDiscoveryExpiration();
     508              :             }
     509              :         }
     510              :     }
     511              : #endif // CHIP_DEVICE_CONFIG_ENABLE_EXTENDED_DISCOVERY
     512              : 
     513              : #if CHIP_DEVICE_CONFIG_ENABLE_COMMISSIONER_DISCOVERY
     514              :     err = AdvertiseCommissioner();
     515              :     if (err != CHIP_NO_ERROR)
     516              :     {
     517              :         ChipLogError(Discovery, "Failed to advertise commissioner: %" CHIP_ERROR_FORMAT, err.Format());
     518              :     }
     519              : #endif // CHIP_DEVICE_CONFIG_ENABLE_COMMISSIONER_DISCOVERY
     520              : 
     521           12 :     err = Dnssd::ServiceAdvertiser::Instance().FinalizeServiceUpdate();
     522           12 :     if (err != CHIP_NO_ERROR)
     523              :     {
     524            0 :         ChipLogError(Discovery, "Failed to finalize service update: %" CHIP_ERROR_FORMAT, err.Format());
     525              :     }
     526           12 : }
     527              : 
     528              : #if CHIP_ENABLE_ROTATING_DEVICE_ID && defined(CHIP_DEVICE_CONFIG_ROTATING_DEVICE_ID_UNIQUE_ID)
     529              : CHIP_ERROR DnssdServer::GenerateRotatingDeviceId(char rotatingDeviceIdHexBuffer[], size_t rotatingDeviceIdHexBufferSize)
     530              : {
     531              :     AdditionalDataPayloadGeneratorParams additionalDataPayloadParams;
     532              :     uint8_t rotatingDeviceIdUniqueId[chip::DeviceLayer::ConfigurationManager::kRotatingDeviceIDUniqueIDLength];
     533              :     MutableByteSpan rotatingDeviceIdUniqueIdSpan(rotatingDeviceIdUniqueId);
     534              :     size_t rotatingDeviceIdValueOutputSize = 0;
     535              : 
     536              :     ReturnErrorOnFailure(
     537              :         chip::DeviceLayer::GetDeviceInstanceInfoProvider()->GetRotatingDeviceIdUniqueId(rotatingDeviceIdUniqueIdSpan));
     538              :     ReturnErrorOnFailure(
     539              :         chip::DeviceLayer::ConfigurationMgr().GetLifetimeCounter(additionalDataPayloadParams.rotatingDeviceIdLifetimeCounter));
     540              :     additionalDataPayloadParams.rotatingDeviceIdUniqueId = rotatingDeviceIdUniqueIdSpan;
     541              : 
     542              :     return AdditionalDataPayloadGenerator().generateRotatingDeviceIdAsHexString(
     543              :         additionalDataPayloadParams, rotatingDeviceIdHexBuffer, rotatingDeviceIdHexBufferSize, rotatingDeviceIdValueOutputSize);
     544              : }
     545              : #endif
     546              : 
     547            0 : void DnssdServer::OnICDModeChange()
     548              : {
     549              :     // ICDMode changed, restart DNS-SD advertising, because SII and ICD key are affected by this change.
     550              :     // StartServer will take care of setting the operational and commissionable advertisements
     551            0 :     StartServer();
     552            0 : }
     553              : 
     554              : } // namespace app
     555              : } // namespace chip
        

Generated by: LCOV version 2.0-1