Line data Source code
1 : /* 2 : * Copyright (c) 2021 Project CHIP Authors 3 : * All rights reserved. 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 : /** 19 : * @file 20 : * This file defines the configuration parameters that are required 21 : * for the CHIP Reliable Messaging Protocol. 22 : * 23 : */ 24 : 25 : #include <messaging/ReliableMessageMgr.h> 26 : 27 : #include <platform/CHIPDeviceLayer.h> 28 : #include <system/SystemClock.h> 29 : 30 : #include <platform/CHIPDeviceConfig.h> 31 : 32 : #if CHIP_CONFIG_ENABLE_ICD_SERVER 33 : #include <app/icd/server/ICDConfigurationData.h> // nogncheck 34 : #endif 35 : 36 : namespace chip { 37 : 38 : using namespace System::Clock::Literals; 39 : 40 : #if CONFIG_BUILD_FOR_HOST_UNIT_TEST 41 : static Optional<System::Clock::Timeout> idleRetransTimeoutOverride = NullOptional; 42 : static Optional<System::Clock::Timeout> activeRetransTimeoutOverride = NullOptional; 43 : static Optional<System::Clock::Timeout> activeThresholdTimeOverride = NullOptional; 44 : 45 7 : void OverrideLocalMRPConfig(System::Clock::Timeout idleRetransTimeout, System::Clock::Timeout activeRetransTimeout, 46 : System::Clock::Timeout activeThresholdTime) 47 : { 48 7 : idleRetransTimeoutOverride.SetValue(idleRetransTimeout); 49 7 : activeRetransTimeoutOverride.SetValue(activeRetransTimeout); 50 7 : activeThresholdTimeOverride.SetValue(activeThresholdTime); 51 7 : } 52 : 53 7 : void ClearLocalMRPConfigOverride() 54 : { 55 7 : activeRetransTimeoutOverride.ClearValue(); 56 7 : idleRetransTimeoutOverride.ClearValue(); 57 7 : activeThresholdTimeOverride.ClearValue(); 58 7 : } 59 : #endif 60 : 61 137385 : ReliableMessageProtocolConfig GetDefaultMRPConfig() 62 : { 63 : // Default MRP intervals are defined in spec <4.12.8. Parameters and Constants> 64 : static constexpr const System::Clock::Milliseconds32 idleRetransTimeout = 500_ms32; 65 : static constexpr const System::Clock::Milliseconds32 activeRetransTimeout = 300_ms32; 66 : static constexpr const System::Clock::Milliseconds16 activeThresholdTime = 4000_ms16; 67 137385 : return ReliableMessageProtocolConfig(idleRetransTimeout, activeRetransTimeout, activeThresholdTime); 68 : } 69 : 70 1694 : Optional<ReliableMessageProtocolConfig> GetLocalMRPConfig() 71 : { 72 1694 : ReliableMessageProtocolConfig config(CHIP_CONFIG_MRP_LOCAL_IDLE_RETRY_INTERVAL, CHIP_CONFIG_MRP_LOCAL_ACTIVE_RETRY_INTERVAL); 73 : #if CHIP_CONFIG_ENABLE_ICD_SERVER 74 : // TODO ICD LIT shall not advertise the SII key 75 : // Increase local MRP retry intervals by ICD polling intervals. That is, intervals for 76 : // which the device can be at sleep and not be able to receive any messages). 77 : config.mIdleRetransTimeout += ICDConfigurationData::GetInstance().GetSlowPollingInterval(); 78 : config.mActiveRetransTimeout += ICDConfigurationData::GetInstance().GetFastPollingInterval(); 79 : config.mActiveThresholdTime = ICDConfigurationData::GetInstance().GetActiveModeThreshold(); 80 : #endif 81 : 82 : #if CONFIG_BUILD_FOR_HOST_UNIT_TEST 83 1694 : if (idleRetransTimeoutOverride.HasValue()) 84 : { 85 10 : config.mIdleRetransTimeout = idleRetransTimeoutOverride.Value(); 86 : } 87 : 88 1694 : if (activeRetransTimeoutOverride.HasValue()) 89 : { 90 10 : config.mActiveRetransTimeout = activeRetransTimeoutOverride.Value(); 91 : } 92 : 93 1694 : if (activeThresholdTimeOverride.HasValue()) 94 : { 95 10 : config.mActiveThresholdTime = activeRetransTimeoutOverride.Value(); 96 : } 97 : #endif 98 : 99 3388 : return (config == GetDefaultMRPConfig()) ? Optional<ReliableMessageProtocolConfig>::Missing() 100 1694 : : Optional<ReliableMessageProtocolConfig>::Value(config); 101 : } 102 : 103 6636 : System::Clock::Timestamp GetRetransmissionTimeout(System::Clock::Timestamp activeInterval, System::Clock::Timestamp idleInterval, 104 : System::Clock::Timestamp lastActivityTime, 105 : System::Clock::Timestamp activityThreshold) 106 : { 107 6636 : auto timeSinceLastActivity = (System::SystemClock().GetMonotonicTimestamp() - lastActivityTime); 108 : 109 : // Calculate the retransmission timeout and take into account that an active/idle state change can happen 110 : // in the middle. 111 6636 : System::Clock::Timestamp timeout(0); 112 39816 : for (uint8_t i = 0; i < CHIP_CONFIG_RMP_DEFAULT_MAX_RETRANS + 1; i++) 113 : { 114 33180 : auto baseInterval = ((timeSinceLastActivity + timeout) < activityThreshold) ? activeInterval : idleInterval; 115 33180 : timeout += Messaging::ReliableMessageMgr::GetBackoff(baseInterval, i, /* computeMaxPossible */ true); 116 : } 117 : 118 6636 : return timeout; 119 : } 120 : 121 : } // namespace chip