1 /*
2  *  Copyright (c) 2019, The OpenThread Authors.
3  *  All rights reserved.
4  *
5  *  Redistribution and use in source and binary forms, with or without
6  *  modification, are permitted provided that the following conditions are met:
7  *  1. Redistributions of source code must retain the above copyright
8  *     notice, this list of conditions and the following disclaimer.
9  *  2. Redistributions in binary form must reproduce the above copyright
10  *     notice, this list of conditions and the following disclaimer in the
11  *     documentation and/or other materials provided with the distribution.
12  *  3. Neither the name of the copyright holder nor the
13  *     names of its contributors may be used to endorse or promote products
14  *     derived from this software without specific prior written permission.
15  *
16  *  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
17  *  AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18  *  IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
19  *  ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
20  *  LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
21  *  CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
22  *  SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
23  *  INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
24  *  CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
25  *  ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
26  *  POSSIBILITY OF SUCH DAMAGE.
27  */
28 
29 /**
30  * @file
31  *   This file includes definitions for Primary Backbone Router service management in the Thread Network.
32  */
33 
34 #ifndef BACKBONE_ROUTER_LEADER_HPP_
35 #define BACKBONE_ROUTER_LEADER_HPP_
36 
37 #include "openthread-core-config.h"
38 
39 #if (OPENTHREAD_CONFIG_THREAD_VERSION >= OT_THREAD_VERSION_1_2)
40 
41 #include <openthread/backbone_router.h>
42 #include <openthread/backbone_router_ftd.h>
43 #include <openthread/ip6.h>
44 
45 #include "coap/coap.hpp"
46 #include "coap/coap_message.hpp"
47 #include "common/locator.hpp"
48 #include "common/log.hpp"
49 #include "common/non_copyable.hpp"
50 #include "net/ip6_address.hpp"
51 
52 namespace ot {
53 
54 namespace BackboneRouter {
55 
56 typedef otBackboneRouterConfig Config;
57 
58 constexpr uint16_t kDefaultRegistrationDelay  = 5;                 ///< Default registration delay (in sec).
59 constexpr uint32_t kDefaultMlrTimeout         = 3600;              ///< Default MLR Timeout (in sec).
60 constexpr uint32_t kMinMlrTimeout             = 300;               ///< Minimum MLR Timeout (in sec).
61 constexpr uint32_t kMaxMlrTimeout             = 0x7fffffff / 1000; ///< Max MLR Timeout (in sec ~ about 24 days.
62 constexpr uint8_t  kDefaultRegistrationJitter = 5;                 ///< Default registration jitter (in sec).
63 constexpr uint8_t  kParentAggregateDelay      = 5;                 ///< Parent Aggregate Delay (in sec).
64 
65 static_assert(kDefaultMlrTimeout >= kMinMlrTimeout && kDefaultMlrTimeout <= kMaxMlrTimeout,
66               "kDefaultMlrTimeout is not in valid range");
67 static_assert(kMaxMlrTimeout * 1000 > kMaxMlrTimeout, "SecToMsec(kMaxMlrTimeout) will overflow");
68 static_assert(kParentAggregateDelay > 1, "kParentAggregateDelay should be larger than 1 second");
69 
70 /**
71  * Represents Domain Prefix changes.
72  *
73  */
74 enum DomainPrefixEvent : uint8_t
75 {
76     kDomainPrefixAdded     = OT_BACKBONE_ROUTER_DOMAIN_PREFIX_ADDED,   ///< Domain Prefix Added.
77     kDomainPrefixRemoved   = OT_BACKBONE_ROUTER_DOMAIN_PREFIX_REMOVED, ///< Domain Prefix Removed.
78     kDomainPrefixRefreshed = OT_BACKBONE_ROUTER_DOMAIN_PREFIX_CHANGED, ///< Domain Prefix Changed.
79     kDomainPrefixUnchanged,                                            ///< Domain Prefix did not change.
80 };
81 
82 /**
83  * Implements the basic Primary Backbone Router service operations.
84  *
85  */
86 class Leader : public InstanceLocator, private NonCopyable
87 {
88 public:
89     // Primary Backbone Router Service state or state change.
90     enum State : uint8_t
91     {
92         kStateNone = 0,       ///< Not exist (trigger Backbone Router register its service).
93         kStateAdded,          ///< Newly added.
94         kStateRemoved,        ///< Newly removed (trigger Backbone Router register its service).
95         kStateToTriggerRereg, ///< Short address or sequence number changes (trigger re-registration).
96                               ///< May also have ReregistrationDelay or MlrTimeout update.
97         kStateRefreshed,      ///< Only ReregistrationDelay or MlrTimeout changes.
98         kStateUnchanged,      ///< No change on Primary Backbone Router information (only for logging).
99     };
100 
101     /**
102      * Initializes the `Leader`.
103      *
104      * @param[in] aInstance  A reference to the OpenThread instance.
105      *
106      */
107     explicit Leader(Instance &aInstance);
108 
109     /**
110      * Resets the cached Primary Backbone Router.
111      *
112      */
113     void Reset(void);
114 
115     /**
116      * Updates the cached Primary Backbone Router if any when new network data is available.
117      *
118      */
119     void Update(void);
120 
121     /**
122      * Gets the Primary Backbone Router in the Thread Network.
123      *
124      * @param[out]  aConfig        The Primary Backbone Router information.
125      *
126      * @retval kErrorNone          Successfully got the Primary Backbone Router information.
127      * @retval kErrorNotFound      No Backbone Router in the Thread Network.
128      *
129      */
130     Error GetConfig(Config &aConfig) const;
131 
132     /**
133      * Gets the Backbone Router Service ID.
134      *
135      * @param[out]  aServiceId     The reference whether to put the Backbone Router Service ID.
136      *
137      * @retval kErrorNone          Successfully got the Backbone Router Service ID.
138      * @retval kErrorNotFound      Backbone Router service doesn't exist.
139      *
140      */
141     Error GetServiceId(uint8_t &aServiceId) const;
142 
143     /**
144      * Gets the short address of the Primary Backbone Router.
145      *
146      * @returns short address of Primary Backbone Router, or Mac::kShortAddrInvalid if no Primary Backbone Router.
147      *
148      */
GetServer16(void) const149     uint16_t GetServer16(void) const { return mConfig.mServer16; }
150 
151     /**
152      * Indicates whether or not there is Primary Backbone Router.
153      *
154      * @retval TRUE   If there is Primary Backbone Router.
155      * @retval FALSE  If there is no Primary Backbone Router.
156      *
157      */
HasPrimary(void) const158     bool HasPrimary(void) const { return mConfig.mServer16 != Mac::kShortAddrInvalid; }
159 
160     /**
161      * Gets the Domain Prefix in the Thread Network.
162      *
163      * @retval A pointer to the Domain Prefix or nullptr if there is no Domain Prefix.
164      *
165      */
GetDomainPrefix(void) const166     const Ip6::Prefix *GetDomainPrefix(void) const
167     {
168         return (mDomainPrefix.GetLength() == 0) ? nullptr : &mDomainPrefix;
169     }
170 
171     /**
172      * Indicates whether or not the Domain Prefix is available in the Thread Network.
173      *
174      * @retval TRUE   If there is Domain Prefix.
175      * @retval FALSE  If there is no Domain Prefix.
176      *
177      */
HasDomainPrefix(void) const178     bool HasDomainPrefix(void) const { return (mDomainPrefix.GetLength() > 0); }
179 
180     /**
181      * Indicates whether or not the address is a Domain Unicast Address.
182      *
183      * @param[in]  aAddress A reference to the address.
184      *
185      * @retval true  @p aAddress is a Domain Unicast Address.
186      * @retval false @p aAddress is not a Domain Unicast Address.
187      *
188      */
189     bool IsDomainUnicast(const Ip6::Address &aAddress) const;
190 
191 private:
192     void UpdateBackboneRouterPrimary(void);
193     void UpdateDomainPrefixConfig(void);
194 #if OT_SHOULD_LOG_AT(OT_LOG_LEVEL_INFO)
195     void               LogBackboneRouterPrimary(State aState, const Config &aConfig) const;
196     static const char *StateToString(State aState);
197     static const char *DomainPrefixEventToString(DomainPrefixEvent aEvent);
198 #else
LogBackboneRouterPrimary(State,const Config &) const199     void LogBackboneRouterPrimary(State, const Config &) const {}
200 #endif
201 
202     Config      mConfig;       ///< Primary Backbone Router information.
203     Ip6::Prefix mDomainPrefix; ///< Domain Prefix in the Thread network.
204 };
205 
206 } // namespace BackboneRouter
207 
208 /**
209  * @}
210  */
211 
212 } // namespace ot
213 
214 #endif // (OPENTHREAD_CONFIG_THREAD_VERSION >= OT_THREAD_VERSION_1_2)
215 
216 #endif // BACKBONE_ROUTER_LEADER_HPP_
217