Matter SDK Coverage Report
Current view: top level - app/icd/server - ICDConfigurationData.h (source / functions) Coverage Total Hit
Test: SHA:2a48c1efeab1c0f76f3adb3a0940b0f7de706453 Lines: 100.0 % 22 22
Test Date: 2026-01-31 08:14:20 Functions: 100.0 % 12 12

            Line data    Source code
       1              : /**
       2              :  *
       3              :  *    Copyright (c) 2023 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              : #pragma once
      19              : 
      20              : #include <app-common/zap-generated/cluster-enums.h>
      21              : #include <app/icd/server/ICDServerConfig.h>
      22              : #include <lib/core/Optional.h>
      23              : #include <lib/support/BitFlags.h>
      24              : #include <lib/support/TimeUtils.h>
      25              : #include <optional>
      26              : #include <platform/CHIPDeviceConfig.h>
      27              : #include <protocols/secure_channel/CheckInCounter.h>
      28              : #include <system/SystemClock.h>
      29              : 
      30              : namespace chip {
      31              : 
      32              : namespace app {
      33              : // Forward declaration of ICDManager to allow it to be friend with ICDConfigurationData.
      34              : class ICDManager;
      35              : } // namespace app
      36              : 
      37              : namespace Testing {
      38              : // Forward declaration of ICDConfigurationDataTestAccess tests to allow it to be friend with the ICDConfigurationData.
      39              : // Used in unit tests
      40              : class ICDConfigurationDataTestAccess;
      41              : } // namespace Testing
      42              : 
      43              : /**
      44              :  * @brief ICDConfigurationData manages and stores ICD related configurations for the ICDManager.
      45              :  *        Goal of the class is to expose ICD information to all consummers without creating circular dependencies
      46              :  *        since the ICDManager is appart of the App layer
      47              :  *
      48              :  *        Anyone can read the ICD configurations but only the ICDManager can changes those configurations.
      49              :  */
      50              : class ICDConfigurationData
      51              : {
      52              : public:
      53              :     static constexpr uint32_t kICDCounterPersistenceIncrement = 100;
      54              : 
      55              :     enum class ICDMode : uint8_t
      56              :     {
      57              :         SIT, // Short Interval Time ICD
      58              :         LIT, // Long Interval Time ICD
      59              :     };
      60              : 
      61          141 :     static ICDConfigurationData & GetInstance() { return instance; };
      62              : 
      63              :     // This represents the ICDManagement Cluster's fixed value mIdleModeDuration Attribute
      64            2 :     System::Clock::Seconds32 GetIdleModeDuration() { return mIdleModeDuration; }
      65              : 
      66           58 :     System::Clock::Milliseconds32 GetActiveModeDuration() { return mActiveModeDuration; }
      67              : 
      68           11 :     System::Clock::Milliseconds16 GetActiveModeThreshold() { return mActiveThreshold; }
      69              : 
      70            4 :     System::Clock::Milliseconds32 GetGuaranteedStayActiveDuration() { return kGuaranteedStayActiveDuration; }
      71              : 
      72              :     Protocols::SecureChannel::CheckInCounter & GetICDCounter() { return mICDCounter; }
      73              : 
      74              :     uint16_t GetClientsSupportedPerFabric() { return mFabricClientsSupported; }
      75              : 
      76           10 :     System::Clock::Milliseconds32 GetSITPollingThreshold() { return kSITPollingThreshold; }
      77              : 
      78           16 :     System::Clock::Milliseconds32 GetFastPollingInterval() { return mFastPollingInterval; }
      79              : 
      80              :     System::Clock::Milliseconds16 GetMinLitActiveModeThreshold() { return kMinLitActiveModeThreshold; }
      81              : 
      82              :     System::Clock::Seconds32 GetMaximumCheckInBackoff() { return mMaximumCheckInBackOff; }
      83              : 
      84            4 :     BitFlags<app::Clusters::IcdManagement::Feature> GetFeatureMap() { return mFeatureMap; }
      85              : 
      86              :     /**
      87              :      * The returned value will depend on the devices operating mode.
      88              :      * If ICDMode == SIT && the configured slow poll interval is superior to the maximum threshold (15s), the function will return
      89              :      * the threshold kSITPollingThreshold (<= 15s). If ICDMode == SIT but the configured slow poll interval is equal or inferior to
      90              :      * the threshold, the function will the return the configured slow poll interval. If ICDMode == LIT, the function will return
      91              :      * the configured slow poll interval.
      92              :      *
      93              :      * @return System::Clock::Milliseconds32
      94              :      */
      95              :     System::Clock::Milliseconds32 GetSlowPollingInterval();
      96              : 
      97              :     /**
      98              :      * @brief Indicates if the device should apply the ShortIdleModeDuration instead of the normal IdleModeDuration.
      99              :      *
     100              :      * Uses ShortIdle only when:
     101              :      *  - ShortIdleModeDuration < IdleModeDuration
     102              :      *  - Long Idle Time feature is supported
     103              :      *  - Device currently operates in SIT mode
     104              :      *
     105              :      * NOTE: To make full use of the ShortIdleModeDuration, users SHOULD also set ICD_REPORT_ON_ENTER_ACTIVE_MODE
     106              :      *
     107              :      * @return true if ShortIdleModeDuration shall be used, false otherwise.
     108              :      */
     109              :     bool ShouldUseShortIdle();
     110              : 
     111              :     /**
     112              :      * @brief Returns the appropriate Idle duration based on current operating conditions.
     113              :      *
     114              :      * If ShouldUseShortIdle() is true, returns ShortIdleModeDuration; otherwise returns IdleModeDuration.
     115              :      *
     116              :      * @return Effective IdleMode duration in seconds.
     117              :      */
     118              :     System::Clock::Seconds32 GetModeBasedIdleModeDuration();
     119              : 
     120           27 :     ICDMode GetICDMode() { return mICDMode; }
     121              : 
     122              : private:
     123              :     // Singleton Object
     124           63 :     ICDConfigurationData()
     125          126 :     {
     126              :         // Initialize feature map
     127              : #if CHIP_CONFIG_ENABLE_ICD_CIP
     128              :         mFeatureMap.Set(app::Clusters::IcdManagement::Feature::kCheckInProtocolSupport);
     129              : #endif // CHIP_CONFIG_ENABLE_ICD_CIP
     130              : #if CHIP_CONFIG_ENABLE_ICD_UAT
     131              :         mFeatureMap.Set(app::Clusters::IcdManagement::Feature::kUserActiveModeTrigger);
     132              : #endif // CHIP_CONFIG_ENABLE_ICD_UAT
     133              : #if CHIP_CONFIG_ENABLE_ICD_LIT
     134              :         mFeatureMap.Set(app::Clusters::IcdManagement::Feature::kLongIdleTimeSupport);
     135              : #if CHIP_CONFIG_ENABLE_ICD_DSLS
     136              :         mFeatureMap.Set(app::Clusters::IcdManagement::Feature::kDynamicSitLitSupport);
     137              : #endif // CHIP_CONFIG_ENABLE_ICD_DSLS
     138              : #endif // CHIP_CONFIG_ENABLE_ICD_LIT
     139           63 :     }
     140              :     static ICDConfigurationData instance;
     141              : 
     142              :     // ICD related information is managed by the ICDManager but stored in the ICDConfigurationData to enable consummers to access it
     143              :     // without creating a circular dependency. To avoid allowing consummers changing the state of the ICD mode without going through
     144              :     // the ICDManager, the ICDManager is a friend that can access the private setters. If a consummer needs to be notified when a
     145              :     // value is changed, they can leverage the Observer events the ICDManager generates. See src/app/icd/server/ICDStateObserver.h
     146              :     friend class chip::app::ICDManager;
     147              : 
     148              :     friend class chip::Testing::ICDConfigurationDataTestAccess;
     149              : 
     150           16 :     void SetICDMode(ICDMode mode) { mICDMode = mode; };
     151              :     void SetFastPollingInterval(System::Clock::Milliseconds32 fastPollInterval) { mFastPollingInterval = fastPollInterval; };
     152              : 
     153              :     /**
     154              :      * @brief Sets the slow polling interval for the ICD.
     155              :      *
     156              :      * If LIT support is not enabled, the interval cannot be set higher than the SIT polling threshold.
     157              :      * If LIT support is enabled, any value is accepted.
     158              :      *
     159              :      * @param[in] slowPollInterval The slow polling interval in milliseconds.
     160              :      * @return CHIP_ERROR CHIP_NO_ERROR on success, CHIP_ERROR_INVALID_ARGUMENT if the value is invalid.
     161              :      */
     162              :     CHIP_ERROR SetSlowPollingInterval(System::Clock::Milliseconds32 slowPollInterval);
     163              : 
     164              :     /**
     165              :      * @brief Sets the SIT Idle polling interval.
     166              :      *
     167              :      * This function sets the slow/idle polling interval, which is used when the configured
     168              :      * slow polling interval exceeds the allowed threshold for SIT mode. The provided value must
     169              :      * be less than, or equal to the SIT polling threshold (kSITPollingThreshold).
     170              :      *
     171              :      * This SIT Slow Polling configuration allows ICD LIT device to configure a longer SlowPollingInterval
     172              :      * when operating as LIT, but use a faster SlowPollingInterval when the device must operate in SIT mode
     173              :      *
     174              :      * @param[in] pollingInterval The SIT slow polling interval in milliseconds.
     175              :      * @return CHIP_ERROR CHIP_NO_ERROR on success, CHIP_ERROR_INVALID_ARGUMENT if the value is invalid.
     176              :      */
     177              :     CHIP_ERROR SetSITPollingInterval(System::Clock::Milliseconds32 pollingInterval);
     178              : 
     179              :     static constexpr System::Clock::Milliseconds16 kMinLitActiveModeThreshold = System::Clock::Milliseconds16(5000);
     180              : 
     181              :     /**
     182              :      * @brief Change the ActiveModeDuration or the IdleModeDuration value
     183              :      *        If only one value is provided, check will be done agaisn't the other already set value.
     184              :      *
     185              :      * @param[in] activeModeDuration new ActiveModeDuration value
     186              :      * @param[in] idleModeDuration new IdleModeDuration value
     187              :      *                                The precision of the IdleModeDuration must be seconds.
     188              :      * Note: mIdleModeDuration is expressed in seconds. The idleModeDuration parameter is in milliseconds for backward compatibility
     189              :      * reasons. The conversion to seconds is done inside the function.
     190              :      *
     191              :      * @return CHIP_ERROR CHIP_ERROR_INVALID_ARGUMENT is returned if idleModeDuration_ms is smaller than activeModeDuration_ms
     192              :      *                                                is returned if idleModeDuration_ms is greater than 64800000 ms
     193              :      *                                                is returned if idleModeDuration_ms is smaller than 1000 ms
     194              :      *                                                is returned if no valid values are provided
     195              :      *                    CHIP_NO_ERROR is returned if the new intervals were set
     196              :      */
     197              :     CHIP_ERROR SetModeDurations(Optional<System::Clock::Milliseconds32> activeModeDuration,
     198              :                                 Optional<System::Clock::Milliseconds32> idleModeDuration);
     199              : 
     200              :     /**
     201              :      * @brief Change the ActiveModeDuration, IdleModeDuration and/or ShortIdleModeDuration values.
     202              :      *
     203              :      * At least one of the three parameters must be provided. Omitted parameters keep their current stored values.
     204              :      *
     205              :      * Constraints:
     206              :      *  - activeModeDuration (ms) must be <= resulting idleModeDuration (s)
     207              :      *  - idleModeDuration (s) must be within [kMinIdleModeDuration, kMaxIdleModeDuration]
     208              :      *  - shortIdleModeDuration (s) must be <= resulting idleModeDuration (s)
     209              :      *
     210              :      * NOTE: to keep previous behavior, If shortIdleModeDuration is not provided, mShortIdleModeDuration can be clamped to resulting
     211              :      * idleModeDuration if the later becomes lesser than the previous mShortIdleModeDuration.
     212              :      *
     213              :      * @param[in] activeModeDuration      New ActiveModeDuration in milliseconds (optional).
     214              :      * @param[in] idleModeDuration        New IdleModeDuration in seconds (optional).
     215              :      * @param[in] shortIdleModeDuration   New ShortIdleModeDuration in seconds (optional, must not exceed IdleModeDuration).
     216              :      *
     217              :      * @return CHIP_NO_ERROR on success.
     218              :      * @return CHIP_ERROR_INVALID_ARGUMENT when:
     219              :      *         - no parameter is provided
     220              :      *         - activeModeDuration > resulting idleModeDuration
     221              :      *         - idleModeDuration is greater than 64800 s or is smaller than 1 s
     222              :      *         - shortIdleModeDuration > resulting idleModeDuration
     223              :      */
     224              :     CHIP_ERROR SetModeDurations(std::optional<System::Clock::Milliseconds32> activeModeDuration,
     225              :                                 std::optional<System::Clock::Seconds32> idleModeDuration,
     226              :                                 std::optional<System::Clock::Seconds32> shortIdleModeDuration);
     227              : 
     228            2 :     void SetFeatureMap(BitFlags<app::Clusters::IcdManagement::Feature> featureMap) { mFeatureMap = featureMap; }
     229              : 
     230              :     static constexpr System::Clock::Seconds32 kMaxIdleModeDuration = System::Clock::Seconds32(18 * kSecondsPerHour);
     231              :     static constexpr System::Clock::Seconds32 kMinIdleModeDuration = System::Clock::Seconds32(1);
     232              :     // As defined in the spec, the maximum guaranteed duration for the StayActiveDuration is 30s  "Matter Application
     233              :     // Clusters: 9.17.7.5.1. PromisedActiveDuration Field"
     234              :     static constexpr System::Clock::Milliseconds32 kGuaranteedStayActiveDuration = System::Clock::Milliseconds32(30000);
     235              : 
     236              :     static_assert((CHIP_CONFIG_ICD_IDLE_MODE_DURATION_SEC) <= kMaxIdleModeDuration.count(),
     237              :                   "Spec requires the IdleModeDuration to be equal or inferior to 64800s.");
     238              :     static_assert((CHIP_CONFIG_ICD_IDLE_MODE_DURATION_SEC) >= kMinIdleModeDuration.count(),
     239              :                   "Spec requires the IdleModeDuration to be equal or greater to 1s.");
     240           63 :     System::Clock::Seconds32 mIdleModeDuration = System::Clock::Seconds32(CHIP_CONFIG_ICD_IDLE_MODE_DURATION_SEC);
     241              : 
     242              :     // Shorter idleModeDuration when a LIT capable device operates in SIT mode.
     243           63 :     System::Clock::Seconds32 mShortIdleModeDuration = System::Clock::Seconds32(CHIP_CONFIG_ICD_SHORT_IDLE_MODE_DURATION_SEC);
     244              :     static_assert((CHIP_CONFIG_ICD_SHORT_IDLE_MODE_DURATION_SEC <= CHIP_CONFIG_ICD_IDLE_MODE_DURATION_SEC),
     245              :                   "mShortIdleModeDuration must be lesser or equal than mIdleModeDuration.");
     246              : 
     247              :     static_assert(System::Clock::Milliseconds32(CHIP_CONFIG_ICD_ACTIVE_MODE_DURATION_MS) <=
     248              :                       System::Clock::Seconds32(CHIP_CONFIG_ICD_IDLE_MODE_DURATION_SEC),
     249              :                   "Spec requires the IdleModeDuration be equal or greater to the ActiveModeDuration.");
     250           63 :     System::Clock::Milliseconds32 mActiveModeDuration = System::Clock::Milliseconds32(CHIP_CONFIG_ICD_ACTIVE_MODE_DURATION_MS);
     251              : 
     252           63 :     System::Clock::Milliseconds16 mActiveThreshold = System::Clock::Milliseconds16(CHIP_CONFIG_ICD_ACTIVE_MODE_THRESHOLD_MS);
     253              : 
     254              :     Protocols::SecureChannel::CheckInCounter mICDCounter;
     255              : 
     256              :     static_assert((CHIP_CONFIG_ICD_CLIENTS_SUPPORTED_PER_FABRIC) >= 1,
     257              :                   "Spec requires the minimum of supported clients per fabric be equal or greater to 1.");
     258              :     uint16_t mFabricClientsSupported = CHIP_CONFIG_ICD_CLIENTS_SUPPORTED_PER_FABRIC;
     259              : 
     260              :     static_assert((CHIP_CONFIG_ICD_MAXIMUM_CHECK_IN_BACKOFF_SEC) <= kMaxIdleModeDuration.count(),
     261              :                   "Spec requires the MaximumCheckInBackOff to be equal or inferior to 64800s");
     262              :     static_assert((CHIP_CONFIG_ICD_IDLE_MODE_DURATION_SEC) <= (CHIP_CONFIG_ICD_MAXIMUM_CHECK_IN_BACKOFF_SEC),
     263              :                   "Spec requires the MaximumCheckInBackOff to be equal or superior to the IdleModeDuration");
     264           63 :     System::Clock::Seconds32 mMaximumCheckInBackOff = System::Clock::Seconds32(CHIP_CONFIG_ICD_MAXIMUM_CHECK_IN_BACKOFF_SEC);
     265              : 
     266              :     // SIT ICDs SHALL have a SlowPollingThreshold shorter than or equal to 15s (spec 9.16.1.5)
     267              :     static constexpr System::Clock::Milliseconds32 kSitIcdSlowPollMaximum = System::Clock::Milliseconds32(15000);
     268              :     static_assert((CHIP_DEVICE_CONFIG_ICD_SIT_SLOW_POLL_LIMIT).count() <= kSitIcdSlowPollMaximum.count(),
     269              :                   "Spec requires the maximum slow poll interval for the SIT device to be smaller or equal than 15 s.");
     270              :     static constexpr System::Clock::Milliseconds32 kSITPollingThreshold = CHIP_DEVICE_CONFIG_ICD_SIT_SLOW_POLL_LIMIT;
     271              : 
     272              : #if CHIP_CONFIG_ENABLE_ICD_LIT == 0
     273              :     static_assert((CHIP_DEVICE_CONFIG_ICD_SLOW_POLL_INTERVAL <= kSitIcdSlowPollMaximum),
     274              :                   "LIT support is required for slow polling intervals superior to 15 seconds");
     275              : #endif
     276              :     // The Polling interval used in Idle mode
     277           63 :     System::Clock::Milliseconds32 mLITPollingInterval = CHIP_DEVICE_CONFIG_ICD_SLOW_POLL_INTERVAL;
     278              :     // The Polling interval used in Active mode
     279           63 :     System::Clock::Milliseconds32 mFastPollingInterval = CHIP_DEVICE_CONFIG_ICD_FAST_POLL_INTERVAL;
     280              : 
     281              :     static_assert((CHIP_DEVICE_CONFIG_ICD_SIT_POLLING_INTERVAL <= kSitIcdSlowPollMaximum),
     282              :                   "The SIT polling intervals must not exceed 15 seconds");
     283              :     // The Polling interval used in Idle mode when a LIT capable device operates in SIT mode and that is mLITPollingInterval is
     284              :     // greater than mSITPollingInterval
     285           63 :     System::Clock::Milliseconds32 mSITPollingInterval = CHIP_DEVICE_CONFIG_ICD_SIT_POLLING_INTERVAL;
     286              : 
     287              :     BitFlags<app::Clusters::IcdManagement::Feature> mFeatureMap;
     288              : 
     289              :     ICDMode mICDMode = ICDMode::SIT;
     290              : };
     291              : 
     292              : } // namespace chip
        

Generated by: LCOV version 2.0-1