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 local Backbone Router service.
32  */
33 
34 #ifndef BACKBONE_ROUTER_LOCAL_HPP_
35 #define BACKBONE_ROUTER_LOCAL_HPP_
36 
37 #include "openthread-core-config.h"
38 
39 #if OPENTHREAD_FTD && OPENTHREAD_CONFIG_BACKBONE_ROUTER_ENABLE
40 
41 #if (OPENTHREAD_CONFIG_THREAD_VERSION < OT_THREAD_VERSION_1_2)
42 #error "Thread 1.2 or higher version is required for OPENTHREAD_CONFIG_BACKBONE_ROUTER_ENABLE."
43 #endif
44 
45 #if !OPENTHREAD_CONFIG_BORDER_ROUTER_ENABLE
46 #error "OPENTHREAD_CONFIG_BORDER_ROUTER_ENABLE is required for OPENTHREAD_CONFIG_BACKBONE_ROUTER_ENABLE."
47 #endif
48 
49 #if !OPENTHREAD_CONFIG_TMF_NETDATA_SERVICE_ENABLE
50 #error "OPENTHREAD_CONFIG_TMF_NETDATA_SERVICE_ENABLE is required for OPENTHREAD_CONFIG_BACKBONE_ROUTER_ENABLE."
51 #endif
52 
53 #include <openthread/backbone_router.h>
54 #include <openthread/backbone_router_ftd.h>
55 
56 #include "backbone_router/bbr_leader.hpp"
57 #include "common/as_core_type.hpp"
58 #include "common/callback.hpp"
59 #include "common/locator.hpp"
60 #include "common/log.hpp"
61 #include "common/non_copyable.hpp"
62 #include "common/time_ticker.hpp"
63 #include "net/netif.hpp"
64 #include "thread/network_data.hpp"
65 
66 namespace ot {
67 
68 namespace BackboneRouter {
69 
70 /**
71  * Implements the definitions for local Backbone Router service.
72  *
73  */
74 class Local : public InstanceLocator, private NonCopyable
75 {
76     friend class ot::TimeTicker;
77 
78 public:
79     typedef otBackboneRouterDomainPrefixCallback DomainPrefixCallback; ///< Domain Prefix callback.
80 
81     /**
82      * Represents Backbone Router state.
83      *
84      */
85     enum State : uint8_t
86     {
87         kStateDisabled  = OT_BACKBONE_ROUTER_STATE_DISABLED,  ///< Backbone function is disabled.
88         kStateSecondary = OT_BACKBONE_ROUTER_STATE_SECONDARY, ///< Secondary Backbone Router.
89         kStatePrimary   = OT_BACKBONE_ROUTER_STATE_PRIMARY,   ///< The Primary Backbone Router.
90     };
91 
92     /**
93      * Represents registration mode used as input to `AddService()` method.
94      *
95      */
96     enum RegisterMode : uint8_t
97     {
98         kDecideBasedOnState, ///< Decide based on current state.
99         kForceRegistration,  ///< Force registration regardless of current state.
100     };
101 
102     /**
103      * Initializes the local Backbone Router.
104      *
105      * @param[in] aInstance  A reference to the OpenThread instance.
106      *
107      */
108     explicit Local(Instance &aInstance);
109 
110     /**
111      * Enables/disables Backbone function.
112      *
113      * @param[in]  aEnable  TRUE to enable the backbone function, FALSE otherwise.
114      *
115      */
116     void SetEnabled(bool aEnable);
117 
118     /**
119      * Retrieves the Backbone Router state.
120      *
121      *
122      * @returns The current state of Backbone Router.
123      *
124      */
GetState(void) const125     State GetState(void) const { return mState; }
126 
127     /**
128      * Resets the local Thread Network Data.
129      *
130      */
131     void Reset(void);
132 
133     /**
134      * Gets local Backbone Router configuration.
135      *
136      * @param[out]  aConfig  The local Backbone Router configuration.
137      *
138      */
139     void GetConfig(Config &aConfig) const;
140 
141     /**
142      * Sets local Backbone Router configuration.
143      *
144      * @param[in]  aConfig  The configuration to set.
145      *
146      * @retval kErrorNone         Successfully updated configuration.
147      * @retval kErrorInvalidArgs  The configuration in @p aConfig is invalid.
148      *
149      */
150     Error SetConfig(const Config &aConfig);
151 
152     /**
153      * Registers Backbone Router Dataset to Leader.
154      *
155      * @param[in]  aMode  The registration mode to use (decide based on current state or force registration).
156      *
157      * @retval kErrorNone            Successfully added the Service entry.
158      * @retval kErrorInvalidState    Not in the ready state to register.
159      * @retval kErrorNoBufs          Insufficient space to add the Service entry.
160      *
161      */
162     Error AddService(RegisterMode aMode);
163 
164     /**
165      * Indicates whether or not the Backbone Router is Primary.
166      *
167      * @retval  True  if the Backbone Router is Primary.
168      * @retval  False if the Backbone Router is not Primary.
169      *
170      */
IsPrimary(void) const171     bool IsPrimary(void) const { return mState == kStatePrimary; }
172 
173     /**
174      * Indicates whether or not the Backbone Router is enabled.
175      *
176      * @retval  True  if the Backbone Router is enabled.
177      * @retval  False if the Backbone Router is not enabled.
178      *
179      */
IsEnabled(void) const180     bool IsEnabled(void) const { return mState != kStateDisabled; }
181 
182     /**
183      * Sets the Backbone Router registration jitter value.
184      *
185      * @param[in]  aRegistrationJitter the Backbone Router registration jitter value to set.
186      *
187      */
SetRegistrationJitter(uint8_t aRegistrationJitter)188     void SetRegistrationJitter(uint8_t aRegistrationJitter) { mRegistrationJitter = aRegistrationJitter; }
189 
190     /**
191      * Returns the Backbone Router registration jitter value.
192      *
193      * @returns The Backbone Router registration jitter value.
194      *
195      */
GetRegistrationJitter(void) const196     uint8_t GetRegistrationJitter(void) const { return mRegistrationJitter; }
197 
198     /**
199      * Notifies Primary Backbone Router status.
200      *
201      * @param[in]  aState   The state or state change of Primary Backbone Router.
202      * @param[in]  aConfig  The Primary Backbone Router service.
203      *
204      */
205     void HandleBackboneRouterPrimaryUpdate(Leader::State aState, const Config &aConfig);
206 
207     /**
208      * Gets the Domain Prefix configuration.
209      *
210      * @param[out]  aConfig  A reference to the Domain Prefix configuration.
211      *
212      * @retval kErrorNone      Successfully got the Domain Prefix configuration.
213      * @retval kErrorNotFound  No Domain Prefix was configured.
214      *
215      */
216     Error GetDomainPrefix(NetworkData::OnMeshPrefixConfig &aConfig);
217 
218     /**
219      * Removes the local Domain Prefix configuration.
220      *
221      * @param[in]  aPrefix A reference to the IPv6 Domain Prefix.
222      *
223      * @retval kErrorNone         Successfully removed the Domain Prefix.
224      * @retval kErrorInvalidArgs  @p aPrefix is invalid.
225      * @retval kErrorNotFound     No Domain Prefix was configured or @p aPrefix doesn't match.
226      *
227      */
228     Error RemoveDomainPrefix(const Ip6::Prefix &aPrefix);
229 
230     /**
231      * Sets the local Domain Prefix configuration.
232      *
233      * @param[in]  aConfig A reference to the Domain Prefix configuration.
234      *
235      * @returns kErrorNone          Successfully set the local Domain Prefix.
236      * @returns kErrorInvalidArgs   @p aConfig is invalid.
237      *
238      */
239     Error SetDomainPrefix(const NetworkData::OnMeshPrefixConfig &aConfig);
240 
241     /**
242      * Returns a reference to the All Network Backbone Routers Multicast Address.
243      *
244      * @returns A reference to the All Network Backbone Routers Multicast Address.
245      *
246      */
GetAllNetworkBackboneRoutersAddress(void) const247     const Ip6::Address &GetAllNetworkBackboneRoutersAddress(void) const { return mAllNetworkBackboneRouters; }
248 
249     /**
250      * Returns a reference to the All Domain Backbone Routers Multicast Address.
251      *
252      * @returns A reference to the All Domain Backbone Routers Multicast Address.
253      *
254      */
GetAllDomainBackboneRoutersAddress(void) const255     const Ip6::Address &GetAllDomainBackboneRoutersAddress(void) const { return mAllDomainBackboneRouters; }
256 
257     /**
258      * Applies the Mesh Local Prefix.
259      *
260      */
261     void ApplyNewMeshLocalPrefix(void);
262 
263     /**
264      * Updates the subscription of All Domain Backbone Routers Multicast Address.
265      *
266      * @param[in]  aEvent  The Domain Prefix event.
267      *
268      */
269     void HandleDomainPrefixUpdate(DomainPrefixEvent aEvent);
270 
271     /**
272      * Sets the Domain Prefix callback.
273      *
274      * @param[in] aCallback  The callback function.
275      * @param[in] aContext   A user context pointer.
276      *
277      */
SetDomainPrefixCallback(DomainPrefixCallback aCallback,void * aContext)278     void SetDomainPrefixCallback(DomainPrefixCallback aCallback, void *aContext)
279     {
280         mDomainPrefixCallback.Set(aCallback, aContext);
281     }
282 
283 private:
284     enum Action : uint8_t
285     {
286         kActionSet,
287         kActionAdd,
288         kActionRemove,
289     };
290 
291     void SetState(State aState);
292     void RemoveService(void);
293     void HandleTimeTick(void);
294     void AddDomainPrefixToNetworkData(void);
295     void RemoveDomainPrefixFromNetworkData(void);
296     void IncrementSequenceNumber(void);
297 #if OT_SHOULD_LOG_AT(OT_LOG_LEVEL_INFO)
298     static const char *ActionToString(Action aAction);
299     void               LogService(Action aAction, Error aError);
300     void               LogDomainPrefix(Action aAction, Error aError);
301 #else
LogService(Action,Error)302     void LogService(Action, Error) {}
LogDomainPrefix(Action,Error)303     void LogDomainPrefix(Action, Error) {}
304 #endif
305 
306     // Indicates whether or not already add Backbone Router Service to local server data.
307     // Used to check whether or not in restore stage after reset or whether to remove
308     // Backbone Router service for Secondary Backbone Router if it was added by force.
309     bool                            mIsServiceAdded;
310     State                           mState;
311     uint8_t                         mSequenceNumber;
312     uint8_t                         mRegistrationJitter;
313     uint16_t                        mReregistrationDelay;
314     uint16_t                        mRegistrationTimeout;
315     uint32_t                        mMlrTimeout;
316     NetworkData::OnMeshPrefixConfig mDomainPrefixConfig;
317     Ip6::Netif::UnicastAddress      mBbrPrimaryAloc;
318     Ip6::Address                    mAllNetworkBackboneRouters;
319     Ip6::Address                    mAllDomainBackboneRouters;
320     Callback<DomainPrefixCallback>  mDomainPrefixCallback;
321 };
322 
323 } // namespace BackboneRouter
324 
325 DefineMapEnum(otBackboneRouterState, BackboneRouter::Local::State);
326 
327 /**
328  * @}
329  */
330 
331 } // namespace ot
332 
333 #endif // OPENTHREAD_FTD && OPENTHREAD_CONFIG_BACKBONE_ROUTER_ENABLE
334 
335 #endif // BACKBONE_ROUTER_LOCAL_HPP_
336