diff --git a/src/core/config/openthread-core-config-check.h b/src/core/config/openthread-core-config-check.h index 1f3a7c59c..53a9544df 100644 --- a/src/core/config/openthread-core-config-check.h +++ b/src/core/config/openthread-core-config-check.h @@ -678,4 +678,13 @@ "OPENTHREAD_LIB_SPINEL_RX_FRAME_BUFFER_SIZE. Pass the macro to source code under"\ "src/lib/spinel." #endif + +#ifdef OPENTHREAD_CONFIG_SRP_CLIENT_UPDATE_TX_MIN_DELAY +#error "OPENTHREAD_CONFIG_SRP_CLIENT_UPDATE_TX_MIN_DELAY was removed." +#endif + +#ifdef OPENTHREAD_CONFIG_SRP_CLIENT_UPDATE_TX_MAX_DELAY +#error "OPENTHREAD_CONFIG_SRP_CLIENT_UPDATE_TX_MAX_DELAY was removed." +#endif + #endif // OPENTHREAD_CORE_CONFIG_CHECK_H_ diff --git a/src/core/config/srp_client.h b/src/core/config/srp_client.h index 34c9abfb6..c5eaca64b 100644 --- a/src/core/config/srp_client.h +++ b/src/core/config/srp_client.h @@ -225,38 +225,6 @@ #define OPENTHREAD_CONFIG_SRP_CLIENT_EARLY_LEASE_RENEW_FACTOR_DENOMINATOR 2 #endif -/** - * @def OPENTHREAD_CONFIG_SRP_CLIENT_UPDATE_TX_MIN_DELAY - * - * Specifies the minimum value (in msec) for the short random delay wait time before sending an update message. - * - * The random delay is chosen uniformly from the min up to max value `OPENTHREAD_CONFIG_SRP_CLIENT_UPDATE_TX_MAX_DELAY`. - * - * When there is a change (e.g., a new service is added/removed) that requires an update, the SRP client will wait for - * a short delay before preparing and sending an SRP update message to server. This allows user to provide more change - * that are then all sent in same update message. The delay is only applied on the first change that triggers an - * update message transmission. Subsequent changes (API calls) while waiting for the tx to start will not reset the - * delay timer. - * - */ -#ifndef OPENTHREAD_CONFIG_SRP_CLIENT_UPDATE_TX_MIN_DELAY -#define OPENTHREAD_CONFIG_SRP_CLIENT_UPDATE_TX_MIN_DELAY 10 -#endif - -/** - * @def OPENTHREAD_CONFIG_SRP_CLIENT_UPDATE_TX_MIN_DELAY - * - * Specifies the maximum value (in msec) for the short random delay wait time before sending an update message. - * - * The random delay is chosen uniformly from the min `OPENTHREAD_CONFIG_SRP_CLIENT_UPDATE_TX_MIN_DELAY` up to max value. - * - * See `OPENTHREAD_CONFIG_SRP_CLIENT_UPDATE_TX_MIN_DELAY` for more details. - * - */ -#ifndef OPENTHREAD_CONFIG_SRP_CLIENT_UPDATE_TX_MAX_DELAY -#define OPENTHREAD_CONFIG_SRP_CLIENT_UPDATE_TX_MAX_DELAY 700 -#endif - /** * @def OPENTHREAD_CONFIG_SRP_CLIENT_MIN_RETRY_WAIT_INTERVAL * diff --git a/src/core/net/netif.cpp b/src/core/net/netif.cpp index 0701436c1..999507662 100644 --- a/src/core/net/netif.cpp +++ b/src/core/net/netif.cpp @@ -415,6 +415,10 @@ void Netif::SignalUnicastAddressChange(AddressEvent aEvent, const UnicastAddress Get().Signal(event); +#if OPENTHREAD_CONFIG_SRP_CLIENT_ENABLE + Get().HandleUnicastAddressEvent(aEvent, aAddress); +#endif + #if OPENTHREAD_CONFIG_HISTORY_TRACKER_ENABLE Get().RecordAddressEvent(aEvent, aAddress); #endif diff --git a/src/core/net/srp_client.cpp b/src/core/net/srp_client.cpp index ebc28ce51..33b65ff0d 100644 --- a/src/core/net/srp_client.cpp +++ b/src/core/net/srp_client.cpp @@ -175,6 +175,96 @@ bool Client::Service::Matches(const Service &aOther) const return (strcmp(GetName(), aOther.GetName()) == 0) && (strcmp(GetInstanceName(), aOther.GetInstanceName()) == 0); } +//--------------------------------------------------------------------- +// Client::TxJitter + +const uint32_t Client::TxJitter::kMaxJitters[] = { + Client::kMaxTxJitterOnDeviceReboot, // (0) kOnDeviceReboot + Client::kMaxTxJitterOnServerStart, // (1) kOnServerStart + Client::kMaxTxJitterOnServerRestart, // (2) kOnServerRestart + Client::kMaxTxJitterOnServerSwitch, // (3) kOnServerSwitch + Client::kMaxTxJitterOnSlaacAddrAdd, // (4) kOnSlaacAddrAdd + Client::kMaxTxJitterOnSlaacAddrRemove, // (5) kOnSlaacAddrRemove +}; + +void Client::TxJitter::Request(Reason aReason) +{ + static_assert(0 == kOnDeviceReboot, "kOnDeviceReboot value is incorrect"); + static_assert(1 == kOnServerStart, "kOnServerStart value is incorrect"); + static_assert(2 == kOnServerRestart, "kOnServerRestart value is incorrect"); + static_assert(3 == kOnServerSwitch, "kOnServerSwitch value is incorrect"); + static_assert(4 == kOnSlaacAddrAdd, "kOnSlaacAddrAdd value is incorrect"); + static_assert(5 == kOnSlaacAddrRemove, "kOnSlaacAddrRemove value is incorrect"); + + uint32_t maxJitter = kMaxJitters[aReason]; + + LogInfo("Requesting max tx jitter %lu (%s)", ToUlong(maxJitter), ReasonToString(aReason)); + + if (mRequestedMax != 0) + { + // If we have a previous request, adjust the `mRequestedMax` + // based on the time elapsed since that request was made. + + uint32_t duration = TimerMilli::GetNow() - mRequestTime; + + mRequestedMax = (mRequestedMax > duration) ? mRequestedMax - duration : 0; + } + + mRequestedMax = Max(mRequestedMax, maxJitter); + mRequestTime = TimerMilli::GetNow(); +} + +uint32_t Client::TxJitter::DetermineDelay(void) +{ + uint32_t delay; + uint32_t maxJitter = kMaxTxJitterDefault; + + if (mRequestedMax != 0) + { + uint32_t duration = TimerMilli::GetNow() - mRequestTime; + + if (duration >= mRequestedMax) + { + LogInfo("Requested max tx jitter %lu already expired", ToUlong(mRequestedMax)); + } + else + { + maxJitter = Max(mRequestedMax - duration, kMaxTxJitterDefault); + LogInfo("Applying remaining max jitter %lu", ToUlong(maxJitter)); + } + + mRequestedMax = 0; + } + + delay = Random::NonCrypto::GetUint32InRange(kMinTxJitter, maxJitter); + LogInfo("Use random tx jitter %lu from [%lu, %lu]", ToUlong(delay), ToUlong(kMinTxJitter), ToUlong(maxJitter)); + + return delay; +} + +#if OT_SHOULD_LOG_AT(OT_LOG_LEVEL_INFO) +const char *Client::TxJitter::ReasonToString(Reason aReason) +{ + static const char *const kReasonStrings[] = { + "OnDeviceReboot", // (0) kOnDeviceReboot + "OnServerStart", // (1) kOnServerStart + "OnServerRestart", // (2) kOnServerRestart + "OnServerSwitch", // (3) kOnServerSwitch + "OnSlaacAddrAdd", // (4) kOnSlaacAddrAdd + "OnSlaacAddrRemove", // (5) kOnSlaacAddrRemove + }; + + static_assert(0 == kOnDeviceReboot, "kOnDeviceReboot value is incorrect"); + static_assert(1 == kOnServerStart, "kOnServerStart value is incorrect"); + static_assert(2 == kOnServerRestart, "kOnServerRestart value is incorrect"); + static_assert(3 == kOnServerSwitch, "kOnServerSwitch value is incorrect"); + static_assert(4 == kOnSlaacAddrAdd, "kOnSlaacAddrAdd value is incorrect"); + static_assert(5 == kOnSlaacAddrRemove, "kOnSlaacAddrRemove value is incorrect"); + + return kReasonStrings[aReason]; +} +#endif + //--------------------------------------------------------------------- // Client::AutoStart @@ -183,7 +273,7 @@ bool Client::Service::Matches(const Service &aOther) const Client::AutoStart::AutoStart(void) { Clear(); - mState = kDefaultMode ? kSelectedNone : kDisabled; + mState = kDefaultMode ? kFirstTimeSelecting : kDisabled; } bool Client::AutoStart::HasSelectedServer(void) const @@ -193,7 +283,8 @@ bool Client::AutoStart::HasSelectedServer(void) const switch (mState) { case kDisabled: - case kSelectedNone: + case kFirstTimeSelecting: + case kReselecting: break; case kSelectedUnicastPreferred: @@ -224,18 +315,20 @@ void Client::AutoStart::InvokeCallback(const Ip6::SockAddr *aServerSockAddr) con const char *Client::AutoStart::StateToString(State aState) { static const char *const kStateStrings[] = { - "Disabled", // (0) kDisabled - "Idle", // (1) kSelectedNone - "Unicast-prf", // (2) kSelectedUnicastPreferred - "Anycast", // (3) kSelectedAnycast - "Unicast", // (4) kSelectedUnicast + "Disabled", // (0) kDisabled + "1stTimeSelect", // (1) kFirstTimeSelecting + "Reselect", // (2) kReselecting + "Unicast-prf", // (3) kSelectedUnicastPreferred + "Anycast", // (4) kSelectedAnycast + "Unicast", // (5) kSelectedUnicast }; static_assert(0 == kDisabled, "kDisabled value is incorrect"); - static_assert(1 == kSelectedNone, "kSelectedNone value is incorrect"); - static_assert(2 == kSelectedUnicastPreferred, "kSelectedUnicastPreferred value is incorrect"); - static_assert(3 == kSelectedAnycast, "kSelectedAnycast value is incorrect"); - static_assert(4 == kSelectedUnicast, "kSelectedUnicast value is incorrect"); + static_assert(1 == kFirstTimeSelecting, "kFirstTimeSelecting value is incorrect"); + static_assert(2 == kReselecting, "kReselecting value is incorrect"); + static_assert(3 == kSelectedUnicastPreferred, "kSelectedUnicastPreferred value is incorrect"); + static_assert(4 == kSelectedAnycast, "kSelectedAnycast value is incorrect"); + static_assert(5 == kSelectedUnicast, "kSelectedUnicast value is incorrect"); return kStateStrings[aState]; } @@ -270,6 +363,9 @@ Client::Client(Instance &aInstance) , mSocket(aInstance, *this) , mDomainName(kDefaultDomainName) , mTimer(aInstance) +#if OPENTHREAD_CONFIG_SRP_CLIENT_AUTO_START_API_ENABLE + , mGuardTimer(aInstance) +#endif { mHostInfo.Init(); @@ -444,6 +540,10 @@ void Client::HandleRoleChanged(void) { if (Get().IsAttached()) { +#if OPENTHREAD_CONFIG_SRP_CLIENT_AUTO_START_API_ENABLE + ApplyAutoStartGuardOnAttach(); +#endif + VerifyOrExit(GetState() == kStatePaused); Resume(); } @@ -524,6 +624,36 @@ exit: return error; } +void Client::HandleUnicastAddressEvent(Ip6::Netif::AddressEvent aEvent, const Ip6::Netif::UnicastAddress &aAddress) +{ + // This callback from `Netif` signals an impending addition or + // removal of a unicast address, occurring before `Notifier` + // events. If `AutoAddress` is enabled, we check whether the + // address origin is SLAAC (e.g., an OMR address) and request a + // longer `TxJitter`. This helps randomize the next SRP + // update transmission time when triggered by an OMR prefix + // change. + + VerifyOrExit(IsRunning()); + VerifyOrExit(mHostInfo.IsAutoAddressEnabled()); + + VerifyOrExit(aAddress.GetOrigin() == Ip6::Netif::kOriginSlaac); + +#if OPENTHREAD_CONFIG_SRP_CLIENT_AUTO_START_API_ENABLE + // The `mGuardTimer`, started by `ApplyAutoStartGuardOnAttach()`, + // tracks a guard interval after the attach event. If an + // address change occurs within this short window, we do not + // apply a longer TX jitter, as this likely indicates a device + // reboot. + VerifyOrExit(!mGuardTimer.IsRunning()); +#endif + + mTxJitter.Request((aEvent == Ip6::Netif::kAddressAdded) ? TxJitter::kOnSlaacAddrAdd : TxJitter::kOnSlaacAddrRemove); + +exit: + return; +} + bool Client::ShouldUpdateHostAutoAddresses(void) const { bool shouldUpdate = false; @@ -736,7 +866,7 @@ void Client::SetState(State aState) break; case kStateToUpdate: - mTimer.Start(Random::NonCrypto::GetUint32InRange(kUpdateTxMinDelay, kUpdateTxMaxDelay)); + mTimer.Start(mTxJitter.DetermineDelay()); break; case kStateUpdating: @@ -778,7 +908,8 @@ bool Client::ChangeHostAndServiceStates(const ItemState *aNewStates, ServiceStat switch (mAutoStart.GetState()) { case AutoStart::kDisabled: - case AutoStart::kSelectedNone: + case AutoStart::kFirstTimeSelecting: + case AutoStart::kReselecting: break; case AutoStart::kSelectedUnicastPreferred: @@ -2056,19 +2187,46 @@ void Client::EnableAutoStartMode(AutoStartCallback aCallback, void *aContext) VerifyOrExit(mAutoStart.GetState() == AutoStart::kDisabled); - mAutoStart.SetState(AutoStart::kSelectedNone); + mAutoStart.SetState(AutoStart::kFirstTimeSelecting); + ApplyAutoStartGuardOnAttach(); + ProcessAutoStart(); exit: return; } +void Client::ApplyAutoStartGuardOnAttach(void) +{ + VerifyOrExit(Get().IsAttached()); + VerifyOrExit(!IsRunning()); + VerifyOrExit(mAutoStart.GetState() == AutoStart::kFirstTimeSelecting); + + // The `mGuardTimer` tracks a guard interval after the attach + // event while `AutoStart` has yet to select a server for the + // first time. + // + // This is used by `ProcessAutoStart()` to apply different TX + // jitter values. If server selection occurs within this short + // window, a shorter TX jitter is used. This typically represents + // the device rebooting or being paired. + // + // The guard time is also checked when handling SLAAC address change + // events, to decide whether or not to request longer TX jitter. + + mGuardTimer.Start(kGuardTimeAfterAttachToUseShorterTxJitter); + +exit: + return; +} + void Client::ProcessAutoStart(void) { Ip6::SockAddr serverSockAddr; DnsSrpAnycast::Info anycastInfo; DnsSrpUnicast::Info unicastInfo; - bool shouldRestart = false; + AutoStart::State oldAutoStartState = mAutoStart.GetState(); + bool shouldRestart = false; // If auto start mode is enabled, we check the Network Data entries // to discover and select the preferred SRP server to register with. @@ -2083,7 +2241,7 @@ void Client::ProcessAutoStart(void) if (IsRunning()) { - VerifyOrExit(mAutoStart.GetState() != AutoStart::kSelectedNone); + VerifyOrExit(mAutoStart.HasSelectedServer()); } // There are three types of entries in Network Data: @@ -2131,15 +2289,69 @@ void Client::ProcessAutoStart(void) Stop(kRequesterAuto, kResetRetryInterval); } - if (!serverSockAddr.GetAddress().IsUnspecified()) + if (serverSockAddr.GetAddress().IsUnspecified()) { - IgnoreError(Start(serverSockAddr, kRequesterAuto)); + if (mAutoStart.HasSelectedServer()) + { + mAutoStart.SetState(AutoStart::kReselecting); + } + + ExitNow(); } - else + + // Before calling `Start()`, determine the trigger reason for + // starting the client with the newly discovered server based on + // `AutoStart` state transitions. This reason is then used to + // select the appropriate TX jitter interval (randomizing the + // initial SRP update transmission to the new server). + + switch (oldAutoStartState) { - mAutoStart.SetState(AutoStart::kSelectedNone); + case AutoStart::kDisabled: + break; + + case AutoStart::kFirstTimeSelecting: + + // If the device is attaching to an established Thread mesh + // (e.g., after a reboot or pairing), the Network Data it + // receives should already include a server entry, leading to + // a quick server selection after attachment. The `mGuardTimer`, + // started by `ApplyAutoStartGuardOnAttach()`, tracks a guard + // interval after the attach event. If server selection + // occurs within this short window, a shorter TX jitter is + // used (`TxJitter::kOnDeviceReboot`), allowing the device to + // register quickly and become discoverable. + // + // If server discovery takes longer, a longer TX jitter + // is used (`TxJitter::kOnServerStart`). This situation + // can indicate a server/BR starting up or a network-wide + // restart of many nodes (e.g., due to a power outage). + + if (mGuardTimer.IsRunning()) + { + mTxJitter.Request(TxJitter::kOnDeviceReboot); + } + else + { + mTxJitter.Request(TxJitter::kOnServerStart); + } + + break; + + case AutoStart::kReselecting: + // Server is restarted (or possibly a new server started). + mTxJitter.Request(TxJitter::kOnServerRestart); + break; + + case AutoStart::kSelectedUnicastPreferred: + case AutoStart::kSelectedAnycast: + case AutoStart::kSelectedUnicast: + mTxJitter.Request(TxJitter::kOnServerSwitch); + break; } + IgnoreError(Start(serverSockAddr, kRequesterAuto)); + exit: return; } @@ -2230,7 +2442,8 @@ void Client::SelectNextServer(bool aDisallowSwitchOnRegisteredHost) case AutoStart::kSelectedAnycast: case AutoStart::kDisabled: - case AutoStart::kSelectedNone: + case AutoStart::kFirstTimeSelecting: + case AutoStart::kReselecting: ExitNow(); } diff --git a/src/core/net/srp_client.hpp b/src/core/net/srp_client.hpp index f45b95364..077a5a2cb 100644 --- a/src/core/net/srp_client.hpp +++ b/src/core/net/srp_client.hpp @@ -49,6 +49,7 @@ #include "crypto/ecdsa.hpp" #include "net/dns_types.hpp" #include "net/ip6.hpp" +#include "net/netif.hpp" #include "net/udp6.hpp" #include "thread/network_data_service.hpp" @@ -71,6 +72,7 @@ namespace Srp { class Client : public InstanceLocator, private NonCopyable { friend class ot::Notifier; + friend class ot::Ip6::Netif; using DnsSrpUnicast = NetworkData::Service::DnsSrpUnicast; using DnsSrpAnycast = NetworkData::Service::DnsSrpAnycast; @@ -853,13 +855,28 @@ private: OPENTHREAD_CONFIG_SRP_CLIENT_EARLY_LEASE_RENEW_FACTOR_DENOMINATOR; // ------------------------------- - // When there is a change (e.g., a new service is added/removed) - // that requires an update, the SRP client will wait for a short - // delay as specified by `kUpdateTxDelay` before sending an SRP - // update to server. This allows the user to provide more change - // that are then all sent in same update message. - static constexpr uint32_t kUpdateTxMinDelay = OPENTHREAD_CONFIG_SRP_CLIENT_UPDATE_TX_MIN_DELAY; // in msec. - static constexpr uint32_t kUpdateTxMaxDelay = OPENTHREAD_CONFIG_SRP_CLIENT_UPDATE_TX_MAX_DELAY; // in msec. + // TX jitter constants + // + // When changes trigger a new SRP update message transmission a random + // jitter delay is applied before sending the update message to server. + // This can occur due to changes in client services or host info, + // or `AutoStart` selecting a server for the first time or switching + // to a new server thus requiring re-registration. + // + // The constants below specify jitter ranges applied based on + // different trigger reasons. All values are in milliseconds. + // Also see `TxJitter` class. + + static constexpr uint32_t kMinTxJitter = 10; + static constexpr uint32_t kMaxTxJitterDefault = 500; + static constexpr uint32_t kMaxTxJitterOnDeviceReboot = 700; + static constexpr uint32_t kMaxTxJitterOnServerStart = 10 * Time::kOneSecondInMsec; + static constexpr uint32_t kMaxTxJitterOnServerRestart = 10 * Time::kOneSecondInMsec; + static constexpr uint32_t kMaxTxJitterOnServerSwitch = 10 * Time::kOneSecondInMsec; + static constexpr uint32_t kMaxTxJitterOnSlaacAddrAdd = 10 * Time::kOneSecondInMsec; + static constexpr uint32_t kMaxTxJitterOnSlaacAddrRemove = 10 * Time::kOneSecondInMsec; + + static constexpr uint32_t kGuardTimeAfterAttachToUseShorterTxJitter = 1000; // ------------------------------- // Retry related constants @@ -945,16 +962,47 @@ private: kForServicesAppendedInMessage, }; + class TxJitter : public Clearable + { + // Manages the random TX jitter to use when sending SRP update + // messages. + + public: + enum Reason + { + kOnDeviceReboot, + kOnServerStart, + kOnServerRestart, + kOnServerSwitch, + kOnSlaacAddrAdd, + kOnSlaacAddrRemove, + }; + + TxJitter(void) { Clear(); } + void Request(Reason aReason); + uint32_t DetermineDelay(void); + + private: + static const uint32_t kMaxJitters[]; +#if OT_SHOULD_LOG_AT(OT_LOG_LEVEL_INFO) + static const char *ReasonToString(Reason aReason); +#endif + + uint32_t mRequestedMax; + TimeMilli mRequestTime; + }; + #if OPENTHREAD_CONFIG_SRP_CLIENT_AUTO_START_API_ENABLE class AutoStart : public Clearable { public: enum State : uint8_t{ - kDisabled, // AutoStart is disabled. - kSelectedNone, // AutoStart is enabled but not yet selected any servers. - kSelectedUnicastPreferred, // AutoStart selected a preferred unicast entry (address in service data). - kSelectedAnycast, // AutoStart selected an anycast entry with `mAnycastSeqNum`. - kSelectedUnicast, // AutoStart selected a unicast entry (address in server data). + kDisabled, // Disabled. + kFirstTimeSelecting, // Trying to select a server for the first time since AutoStart was enabled. + kReselecting, // Trying to select a server again (previously selected server was removed). + kSelectedUnicastPreferred, // Has selected a preferred unicast entry (address in service data). + kSelectedAnycast, // Has selected an anycast entry with `mAnycastSeqNum`. + kSelectedUnicast, // Has selected a unicast entry (address in server data). }; AutoStart(void); @@ -1012,6 +1060,7 @@ private: void Pause(void); void HandleNotifierEvents(Events aEvents); void HandleRoleChanged(void); + void HandleUnicastAddressEvent(Ip6::Netif::AddressEvent aEvent, const Ip6::Netif::UnicastAddress &aAddress); bool ShouldUpdateHostAutoAddresses(void) const; bool ShouldHostAutoAddressRegister(const Ip6::Netif::UnicastAddress &aUnicastAddress) const; Error UpdateHostInfoStateOnAddressChange(void); @@ -1056,8 +1105,10 @@ private: bool ShouldRenewEarly(const Service &aService) const; void HandleTimer(void); #if OPENTHREAD_CONFIG_SRP_CLIENT_AUTO_START_API_ENABLE + void ApplyAutoStartGuardOnAttach(void); void ProcessAutoStart(void); Error SelectUnicastEntry(DnsSrpUnicast::Origin aOrigin, DnsSrpUnicast::Info &aInfo) const; + void HandleGuardTimer(void) {} #if OPENTHREAD_CONFIG_SRP_CLIENT_SWITCH_SERVER_ON_FAILURE void SelectNextServer(bool aDisallowSwitchOnRegisteredHost); #endif @@ -1077,6 +1128,10 @@ private: using DelayTimer = TimerMilliIn; using ClientSocket = Ip6::Udp::SocketIn; +#if OPENTHREAD_CONFIG_SRP_CLIENT_AUTO_START_API_ENABLE + using GuardTimer = TimerMilliIn; +#endif + State mState; uint8_t mTxFailureRetryCount : 4; bool mShouldRemoveKeyLease : 1; @@ -1097,6 +1152,7 @@ private: uint32_t mKeyLease; uint32_t mDefaultLease; uint32_t mDefaultKeyLease; + TxJitter mTxJitter; ClientSocket mSocket; @@ -1106,7 +1162,8 @@ private: LinkedList mServices; DelayTimer mTimer; #if OPENTHREAD_CONFIG_SRP_CLIENT_AUTO_START_API_ENABLE - AutoStart mAutoStart; + GuardTimer mGuardTimer; + AutoStart mAutoStart; #endif }; diff --git a/tests/scripts/thread-cert/test_dnssd_name_with_special_chars.py b/tests/scripts/thread-cert/test_dnssd_name_with_special_chars.py index 6adf538bc..62c13e740 100755 --- a/tests/scripts/thread-cert/test_dnssd_name_with_special_chars.py +++ b/tests/scripts/thread-cert/test_dnssd_name_with_special_chars.py @@ -84,7 +84,7 @@ class TestDnssdNameWithSpecialChars(thread_cert.TestCase): server.srp_server_set_enabled(True) client.srp_client_enable_auto_start_mode() - self.simulator.go(5) + self.simulator.go(15) # Register a single service with the instance name containing special chars client.srp_client_set_host_name('host1') diff --git a/tests/scripts/thread-cert/test_srp_auto_host_address.py b/tests/scripts/thread-cert/test_srp_auto_host_address.py index 1612a30cf..2f86db58f 100755 --- a/tests/scripts/thread-cert/test_srp_auto_host_address.py +++ b/tests/scripts/thread-cert/test_srp_auto_host_address.py @@ -74,6 +74,7 @@ class SrpAutoHostAddress(thread_cert.TestCase): client.start() self.simulator.go(15) self.assertEqual(client.get_state(), 'leader') + client.srp_client_stop() server.start() self.simulator.go(5) @@ -88,8 +89,9 @@ class SrpAutoHostAddress(thread_cert.TestCase): #------------------------------------------------------------------- # Check auto start mode on SRP client + client.srp_client_enable_auto_start_mode() self.assertEqual(client.srp_client_get_auto_start_mode(), 'Enabled') - self.simulator.go(2) + self.simulator.go(15) self.assertEqual(client.srp_client_get_state(), 'Enabled') @@ -135,7 +137,7 @@ class SrpAutoHostAddress(thread_cert.TestCase): client.add_prefix('fd00:abba:cafe:bee::/64', 'paos') client.register_netdata() - self.simulator.go(5) + self.simulator.go(15) slaac_addr = [addr.strip() for addr in client.get_addrs() if addr.strip().startswith('fd00:abba:cafe:bee:')] self.assertEqual(len(slaac_addr), 1) @@ -147,7 +149,7 @@ class SrpAutoHostAddress(thread_cert.TestCase): client.add_prefix('fd00:9:8:7::/64', 'paos') client.register_netdata() - self.simulator.go(5) + self.simulator.go(15) slaac_addr = [addr.strip() for addr in client.get_addrs() if addr.strip().startswith('fd00:9:8:7:')] self.assertEqual(len(slaac_addr), 1) @@ -160,7 +162,7 @@ class SrpAutoHostAddress(thread_cert.TestCase): client.add_prefix('fd00:a:b:c::/64', 'aos') client.register_netdata() - self.simulator.go(5) + self.simulator.go(15) slaac_addr = [addr.strip() for addr in client.get_addrs() if addr.strip().startswith('fd00:a:b:c:')] self.assertEqual(len(slaac_addr), 1) @@ -173,7 +175,7 @@ class SrpAutoHostAddress(thread_cert.TestCase): client.remove_prefix('fd00:abba:cafe:bee::/64') client.register_netdata() - self.simulator.go(5) + self.simulator.go(15) self.check_registered_addresses(client, server) @@ -184,7 +186,7 @@ class SrpAutoHostAddress(thread_cert.TestCase): client.remove_prefix('fd00:9:8:7::/64') client.register_netdata() - self.simulator.go(5) + self.simulator.go(15) self.check_registered_addresses(client, server) diff --git a/tests/scripts/thread-cert/test_srp_client_remove_host.py b/tests/scripts/thread-cert/test_srp_client_remove_host.py index 298014518..681893914 100755 --- a/tests/scripts/thread-cert/test_srp_client_remove_host.py +++ b/tests/scripts/thread-cert/test_srp_client_remove_host.py @@ -81,7 +81,7 @@ class SrpRemoveHost(thread_cert.TestCase): server.srp_server_set_enabled(True) client.srp_client_enable_auto_start_mode() - self.simulator.go(5) + self.simulator.go(15) #------------------------------------------------------------------------------------- # Register a single service and verify that it worked. diff --git a/tests/scripts/thread-cert/test_srp_client_save_server_info.py b/tests/scripts/thread-cert/test_srp_client_save_server_info.py index 5018aad08..ca657897d 100755 --- a/tests/scripts/thread-cert/test_srp_client_save_server_info.py +++ b/tests/scripts/thread-cert/test_srp_client_save_server_info.py @@ -48,7 +48,7 @@ SERVER1 = 2 SERVER2 = 3 SERVER3 = 4 -WAIT_TIME = 5 +WAIT_TIME = 16 MAX_ITER = 5 diff --git a/tests/scripts/thread-cert/test_srp_lease.py b/tests/scripts/thread-cert/test_srp_lease.py index b259c21a5..863c91a38 100755 --- a/tests/scripts/thread-cert/test_srp_lease.py +++ b/tests/scripts/thread-cert/test_srp_lease.py @@ -114,7 +114,7 @@ class SrpRegisterSingleService(thread_cert.TestCase): # Start the client again, the same service should be successfully registered. client.srp_client_enable_auto_start_mode() - self.simulator.go(2) + self.simulator.go(15) self.check_host_and_service(server, client) @@ -132,7 +132,7 @@ class SrpRegisterSingleService(thread_cert.TestCase): # Start the client again, the same service should be successfully registered. client.srp_client_enable_auto_start_mode() - self.simulator.go(2) + self.simulator.go(15) self.check_host_and_service(server, client) diff --git a/tests/scripts/thread-cert/test_srp_many_services_mtu_check.py b/tests/scripts/thread-cert/test_srp_many_services_mtu_check.py index 65dfd2e99..37221c5f4 100755 --- a/tests/scripts/thread-cert/test_srp_many_services_mtu_check.py +++ b/tests/scripts/thread-cert/test_srp_many_services_mtu_check.py @@ -84,7 +84,7 @@ class SrpManyServicesMtuCheck(thread_cert.TestCase): server.srp_server_set_enabled(True) client.srp_client_enable_auto_start_mode() - self.simulator.go(5) + self.simulator.go(15) # Register 8 services with long name, 6 sub-types and long txt record. # The 8 services won't be fit in a single MTU (1280 bytes) UDP message diff --git a/tests/scripts/thread-cert/test_srp_register_services_diff_lease.py b/tests/scripts/thread-cert/test_srp_register_services_diff_lease.py index 6247527d8..3399dd310 100755 --- a/tests/scripts/thread-cert/test_srp_register_services_diff_lease.py +++ b/tests/scripts/thread-cert/test_srp_register_services_diff_lease.py @@ -84,7 +84,7 @@ class SrpRegisterServicesDiffLease(thread_cert.TestCase): server.srp_server_set_enabled(True) client.srp_client_enable_auto_start_mode() - self.simulator.go(5) + self.simulator.go(15) client.srp_client_set_host_name('host') client.srp_client_enable_auto_host_address() diff --git a/tests/scripts/thread-cert/test_srp_server_anycast_mode.py b/tests/scripts/thread-cert/test_srp_server_anycast_mode.py index 5086a7baa..7bae2e72b 100755 --- a/tests/scripts/thread-cert/test_srp_server_anycast_mode.py +++ b/tests/scripts/thread-cert/test_srp_server_anycast_mode.py @@ -147,7 +147,7 @@ class TestSrpServerAnycastMode(thread_cert.TestCase): # server and uses the proper address and port number. client.srp_client_enable_auto_start_mode() - self.simulator.go(5) + self.simulator.go(15) if addr_mode == 'anycast': server_alocs = server.get_ip6_address(config.ADDRESS_TYPE.ALOC) diff --git a/tests/scripts/thread-cert/test_srp_server_reboot_port.py b/tests/scripts/thread-cert/test_srp_server_reboot_port.py index b38bcfe9e..d7f0a4c34 100755 --- a/tests/scripts/thread-cert/test_srp_server_reboot_port.py +++ b/tests/scripts/thread-cert/test_srp_server_reboot_port.py @@ -109,7 +109,7 @@ class SrpServerRebootPort(thread_cert.TestCase): client.srp_client_set_host_name('my-host') client.srp_client_set_host_address('2001::1') client.srp_client_add_service('my-service', '_ipps._tcp', 12345, 0, 0, ['abc', 'def=', 'xyz=XYZ']) - self.simulator.go(5) + self.simulator.go(16) self.check_host_and_service(server, client, '2001::1') ports = [server.get_srp_server_port()] @@ -129,7 +129,7 @@ class SrpServerRebootPort(thread_cert.TestCase): # re-registered. # server.srp_server_set_enabled(True) - self.simulator.go(5) + self.simulator.go(16) self.assertEqual(client.srp_client_get_state(), 'Enabled') self.assertEqual(client.srp_client_get_server_address(), server.get_mleid()) self.assertNotEqual(old_port, server.get_srp_server_port()) diff --git a/tests/scripts/thread-cert/test_srp_sub_type.py b/tests/scripts/thread-cert/test_srp_sub_type.py index e9b6fdc4a..bbd8efa17 100755 --- a/tests/scripts/thread-cert/test_srp_sub_type.py +++ b/tests/scripts/thread-cert/test_srp_sub_type.py @@ -80,7 +80,7 @@ class SrpSubType(thread_cert.TestCase): server.srp_server_set_enabled(True) client.srp_client_enable_auto_start_mode() - self.simulator.go(5) + self.simulator.go(15) # Register a single service with 3 subtypes and verify that it worked. diff --git a/tests/scripts/thread-cert/test_srp_ttl.py b/tests/scripts/thread-cert/test_srp_ttl.py index 9c3a149db..70a60721e 100755 --- a/tests/scripts/thread-cert/test_srp_ttl.py +++ b/tests/scripts/thread-cert/test_srp_ttl.py @@ -85,6 +85,7 @@ class SrpTtl(thread_cert.TestCase): self.simulator.go(config.ROUTER_STARTUP_DELAY) self.assertEqual(client.get_state(), 'router') + self.simulator.go(15) self.assertEqual(client.srp_client_get_auto_start_mode(), 'Enabled') client.srp_client_set_host_name('my-host') diff --git a/tests/toranj/cli/test-400-srp-client-server.py b/tests/toranj/cli/test-400-srp-client-server.py index 0e3edb2bc..2a3cd32ab 100755 --- a/tests/toranj/cli/test-400-srp-client-server.py +++ b/tests/toranj/cli/test-400-srp-client-server.py @@ -61,11 +61,12 @@ verify(client.get_state() == 'router') verify(server.srp_server_get_state() == 'disabled') verify(server.srp_server_get_addr_mode() == 'unicast') verify(client.srp_client_get_state() == 'Disabled') -verify(client.srp_client_get_auto_start_mode() == 'Enabled') # Start server and client and register single service server.srp_server_enable() +client.srp_client_enable_auto_start_mode() +verify(client.srp_client_get_auto_start_mode() == 'Enabled') client.srp_client_set_host_name('host') client.srp_client_set_host_address('fd00::cafe') client.srp_client_add_service('ins', '_test._udp', 777, 2, 1) diff --git a/tests/toranj/cli/test-501-multi-br-failure-recovery.py b/tests/toranj/cli/test-501-multi-br-failure-recovery.py index ecf41b999..338c955c5 100755 --- a/tests/toranj/cli/test-501-multi-br-failure-recovery.py +++ b/tests/toranj/cli/test-501-multi-br-failure-recovery.py @@ -147,6 +147,7 @@ verify(br2.srp_server_get_state() == 'disabled') # Register SRP services on all nodes for node in nodes_non_br: + node.srp_client_enable_auto_start_mode() verify(node.srp_client_get_auto_start_mode() == 'Enabled') node.srp_client_set_host_name('host' + str(node.index)) node.srp_client_enable_auto_host_address() diff --git a/tests/toranj/cli/test-502-multi-br-leader-failure-recovery.py b/tests/toranj/cli/test-502-multi-br-leader-failure-recovery.py index 71d2ebc1b..6b6e9dfa9 100755 --- a/tests/toranj/cli/test-502-multi-br-leader-failure-recovery.py +++ b/tests/toranj/cli/test-502-multi-br-leader-failure-recovery.py @@ -147,6 +147,7 @@ verify(br2.srp_server_get_state() == 'disabled') # Register SRP services on all nodes for node in nodes_non_br: + node.srp_client_enable_auto_start_mode() verify(node.srp_client_get_auto_start_mode() == 'Enabled') node.srp_client_set_host_name('host' + str(node.index)) node.srp_client_enable_auto_host_address() diff --git a/tests/toranj/openthread-core-toranj-config.h b/tests/toranj/openthread-core-toranj-config.h index 33686ca7a..9f6b66a8d 100644 --- a/tests/toranj/openthread-core-toranj-config.h +++ b/tests/toranj/openthread-core-toranj-config.h @@ -175,6 +175,8 @@ #define OPENTHREAD_CONFIG_SRP_CLIENT_DOMAIN_NAME_API_ENABLE 1 +#define OPENTHREAD_CONFIG_SRP_CLIENT_AUTO_START_DEFAULT_MODE 0 + #define OPENTHREAD_CONFIG_HISTORY_TRACKER_ENABLE 1 #define OPENTHREAD_CONFIG_DNSSD_SERVER_ENABLE 1 diff --git a/tests/unit/test_srp_adv_proxy.cpp b/tests/unit/test_srp_adv_proxy.cpp index 08b4a9470..dec83df65 100644 --- a/tests/unit/test_srp_adv_proxy.cpp +++ b/tests/unit/test_srp_adv_proxy.cpp @@ -940,7 +940,7 @@ void TestSrpAdvProxy(void) sProcessedClientCallback = false; - AdvanceTime(5 * 1000); + AdvanceTime(15 * 1000); // This time we should only see new host registration // since that's the only thing that changes diff --git a/tests/unit/test_srp_server.cpp b/tests/unit/test_srp_server.cpp index f0218e004..2f655f2bf 100644 --- a/tests/unit/test_srp_server.cpp +++ b/tests/unit/test_srp_server.cpp @@ -892,7 +892,7 @@ void TestUpdateLeaseShortVariant(void) srpClient->EnableAutoStartMode(nullptr, nullptr); VerifyOrQuit(srpClient->IsAutoStartModeEnabled()); - AdvanceTime(2000); + AdvanceTime(15 * 1000); VerifyOrQuit(srpClient->IsRunning()); SuccessOrQuit(srpClient->SetHostName(kHostName));