Kea 2.2.0
free_lease_queue.h
Go to the documentation of this file.
1// Copyright (C) 2020-2021 Internet Systems Consortium, Inc. ("ISC")
2//
3// This Source Code Form is subject to the terms of the Mozilla Public
4// License, v. 2.0. If a copy of the MPL was not distributed with this
5// file, You can obtain one at http://mozilla.org/MPL/2.0/.
6
7#ifndef FREE_LEASE_QUEUE_H
8#define FREE_LEASE_QUEUE_H
9
10#include <asiolink/io_address.h>
11#include <dhcpsrv/ip_range.h>
13
14#include <boost/multi_index_container.hpp>
15#include <boost/multi_index/hashed_index.hpp>
16#include <boost/multi_index/identity.hpp>
17#include <boost/multi_index/indexed_by.hpp>
18#include <boost/multi_index/member.hpp>
19#include <boost/multi_index/ordered_index.hpp>
20#include <boost/multi_index/random_access_index.hpp>
21#include <boost/multi_index/sequenced_index.hpp>
22#include <boost/shared_ptr.hpp>
23
24#include <iterator>
25#include <map>
26
27namespace isc {
28namespace dhcp {
29
83public:
84
87
94 void addRange(const AddressRange& range);
95
104 void addRange(const asiolink::IOAddress& start, const asiolink::IOAddress& end);
105
112 void addRange(const PrefixRange& range);
113
123 void addRange(const asiolink::IOAddress& prefix, const uint8_t prefix_length,
124 const uint8_t delegated_length);
125
133 template<typename RangeType>
134 bool removeRange(const RangeType& range) {
135 return (ranges_.get<1>().erase(range.start_) > 0);
136 }
137
147 bool append(const asiolink::IOAddress& address);
148
159 bool append(const asiolink::IOAddress& prefix, const uint8_t delegated_length);
160
173 void append(const AddressRange& range, const asiolink::IOAddress& address);
174
187 void append(const PrefixRange& range, const asiolink::IOAddress& prefix);
188
202 void append(const uint64_t range_index, const asiolink::IOAddress& ip);
203
214 bool use(const AddressRange& range, const asiolink::IOAddress& address);
215
226 bool use(const PrefixRange& range, const asiolink::IOAddress& prefix);
227
237 template<typename RangeType>
238 asiolink::IOAddress next(const RangeType& range) {
239 return (popNextInternal(range, true));
240 }
241
252 template<typename RangeType>
253 asiolink::IOAddress pop(const RangeType& range) {
254 return (popNextInternal(range, false));
255 }
256
267 template<typename RangeType>
268 uint64_t getRangeIndex(const RangeType& range) const {
269 auto cont = ranges_.get<1>().find(range.start_);
270 if (cont == ranges_.get<1>().end()) {
271 isc_throw(BadValue, "container for the specified range " << range.start_
272 << ":" << range.end_ << " does not exist");
273 }
274 return (std::distance(ranges_.get<2>().begin(), ranges_.project<2>(cont)));
275 }
276
277private:
278
285 typedef boost::multi_index_container<
287 boost::multi_index::indexed_by<
288 boost::multi_index::ordered_unique<
289 boost::multi_index::identity<asiolink::IOAddress>
290 >,
291 boost::multi_index::sequenced<>
292 >
293 > Leases;
294
296 typedef boost::shared_ptr<Leases> LeasesPtr;
297
300 struct RangeDescriptor {
302 asiolink::IOAddress range_start_;
304 asiolink::IOAddress range_end_;
306 uint8_t delegated_length_;
308 LeasesPtr leases_;
309 };
310
317 typedef boost::multi_index_container<
318 RangeDescriptor,
319 boost::multi_index::indexed_by<
320 boost::multi_index::ordered_unique<
321 boost::multi_index::member<RangeDescriptor, asiolink::IOAddress,
322 &RangeDescriptor::range_start_>
323 >,
324 boost::multi_index::hashed_unique<
325 boost::multi_index::member<RangeDescriptor, asiolink::IOAddress,
326 &RangeDescriptor::range_start_>
327 >,
328 boost::multi_index::random_access<>
329 >
330 > Ranges;
331
341 template<typename RangeType>
342 void checkRangeBoundaries(const RangeType& range, const asiolink::IOAddress& ip,
343 const bool prefix = false) const;
344
351 void checkRangeOverlaps(const asiolink::IOAddress& start,
352 const asiolink::IOAddress& end) const;
353
359 LeasesPtr getLeases(const AddressRange& range) const;
360
366 LeasesPtr getLeases(const PrefixRange& range) const;
367
377 RangeDescriptor getRangeDescriptor(const uint64_t range_index) const;
378
388 template<typename RangeType>
389 asiolink::IOAddress popNextInternal(const RangeType& range, const bool push) {
390 auto cont = getLeases(range);
391 if (cont->empty()) {
392 return (range.start_.isV4() ? asiolink::IOAddress::IPV4_ZERO_ADDRESS() :
394 }
395 auto& idx = cont->template get<1>();
396 auto next = idx.front();
397 idx.pop_front();
398 if (push) {
399 idx.push_back(next);
400 }
401 return (next);
402 }
403
406 Ranges ranges_;
407};
408
409} // end of namespace isc::dhcp
410} // end of namespace isc
411
412#endif // FREE_LEASE_QUEUE_H
A generic exception that is thrown if a parameter given to a method is considered invalid in that con...
Queue holding free leases for various address and prefix ranges.
bool append(const asiolink::IOAddress &address)
Appends an address to the end of the queue for a range.
uint64_t getRangeIndex(const RangeType &range) const
Returns range index.
asiolink::IOAddress next(const RangeType &range)
Returns next free address or delegated prefix in the range.
bool removeRange(const RangeType &range)
Removes the range from the queue.
void addRange(const AddressRange &range)
Adds new address range to the queue.
bool use(const AddressRange &range, const asiolink::IOAddress &address)
Removes the specified address from the free addresses.
asiolink::IOAddress pop(const RangeType &range)
Pops and returns next free address or delegated prefix in the range.
#define isc_throw(type, stream)
A shortcut macro to insert known values into exception arguments.
Defines the logger used by the top-level component of kea-lfc.
Structure representing IP address range.
Definition: ip_range.h:16
Structure representing delegated prefix range.
Definition: ip_range.h:32