mirror of
https://gitlab.isc.org/isc-projects/kea
synced 2025-08-30 21:45:37 +00:00
[master] Merge branch 'trac3974'
This commit is contained in:
@@ -43,6 +43,50 @@
|
||||
}
|
||||
]
|
||||
},
|
||||
|
||||
{ "item_name": "expired-leases-processing",
|
||||
"item_type": "map",
|
||||
"item_optional": false,
|
||||
"item_default": {},
|
||||
"map_item_spec": [
|
||||
{
|
||||
"item_name": "reclaim-timer-wait-time",
|
||||
"item_type": "integer",
|
||||
"item_optional": false,
|
||||
"item_default": 10
|
||||
},
|
||||
{
|
||||
"item_name": "flush-reclaimed-timer-wait-time",
|
||||
"item_type": "integer",
|
||||
"item_optional": false,
|
||||
"item_default": 25
|
||||
},
|
||||
{
|
||||
"item_name": "hold-reclaimed-time",
|
||||
"item_type": "integer",
|
||||
"item_optional": false,
|
||||
"item_default": 3600
|
||||
},
|
||||
{
|
||||
"item_name": "max-reclaim-leases",
|
||||
"item_type": "integer",
|
||||
"item_optional": false,
|
||||
"item_default": 100
|
||||
},
|
||||
{
|
||||
"item_name": "max-reclaim-time",
|
||||
"item_type": "integer",
|
||||
"item_optional": false,
|
||||
"item_default": 250
|
||||
},
|
||||
{
|
||||
"item_name": "unwarned-reclaim-cycles",
|
||||
"item_type": "integer",
|
||||
"item_optional": false,
|
||||
"item_default": 5
|
||||
}
|
||||
]
|
||||
},
|
||||
|
||||
{ "item_name": "renew-timer",
|
||||
"item_type": "integer",
|
||||
|
@@ -24,6 +24,7 @@
|
||||
#include <dhcpsrv/option_space_container.h>
|
||||
#include <dhcpsrv/parsers/dbaccess_parser.h>
|
||||
#include <dhcpsrv/parsers/dhcp_parsers.h>
|
||||
#include <dhcpsrv/parsers/expiration_config_parser.h>
|
||||
#include <dhcpsrv/parsers/host_reservation_parser.h>
|
||||
#include <dhcpsrv/parsers/host_reservations_list_parser.h>
|
||||
#include <dhcpsrv/parsers/ifaces_config_parser.h>
|
||||
@@ -405,6 +406,8 @@ namespace dhcp {
|
||||
parser = new BooleanParser(config_id, globalContext()->boolean_values_);
|
||||
} else if (config_id.compare("control-socket") == 0) {
|
||||
parser = new ControlSocketParser(config_id);
|
||||
} else if (config_id.compare("expired-leases-processing") == 0) {
|
||||
parser = new ExpirationConfigParser();
|
||||
} else {
|
||||
isc_throw(DhcpConfigError,
|
||||
"unsupported global configuration parameter: "
|
||||
|
@@ -29,6 +29,7 @@
|
||||
#include <dhcp/tests/iface_mgr_test_config.h>
|
||||
#include <dhcpsrv/subnet.h>
|
||||
#include <dhcpsrv/cfgmgr.h>
|
||||
#include <dhcpsrv/cfg_expiration.h>
|
||||
#include <dhcpsrv/cfg_hosts.h>
|
||||
#include <dhcpsrv/cfg_subnets4.h>
|
||||
#include <dhcpsrv/testutils/config_result_check.h>
|
||||
@@ -3712,4 +3713,73 @@ TEST_F(Dhcp4ParserTest, declineTimerError) {
|
||||
EXPECT_TRUE(errorContainsPosition(status, "<string>"));
|
||||
}
|
||||
|
||||
// Check that configuration for the expired leases processing may be
|
||||
// specified.
|
||||
TEST_F(Dhcp4ParserTest, expiredLeasesProcessing) {
|
||||
// Create basic configuration with the expiration specific parameters.
|
||||
string config = "{ " + genIfaceConfig() + "," +
|
||||
"\"expired-leases-processing\": "
|
||||
"{"
|
||||
" \"reclaim-timer-wait-time\": 20,"
|
||||
" \"flush-reclaimed-timer-wait-time\": 35,"
|
||||
" \"hold-reclaimed-time\": 1800,"
|
||||
" \"max-reclaim-leases\": 50,"
|
||||
" \"max-reclaim-time\": 100,"
|
||||
" \"unwarned-reclaim-cycles\": 10"
|
||||
"},"
|
||||
"\"subnet4\": [ ]"
|
||||
"}";
|
||||
|
||||
ElementPtr json = Element::fromJSON(config);
|
||||
|
||||
ConstElementPtr status;
|
||||
EXPECT_NO_THROW(status = configureDhcp4Server(*srv_, json));
|
||||
|
||||
// Returned value should be 0 (success)
|
||||
checkResult(status, 0);
|
||||
|
||||
// The value of decline-probation-perion must be equal to the
|
||||
// value specified.
|
||||
CfgExpirationPtr cfg = CfgMgr::instance().getStagingCfg()->getCfgExpiration();
|
||||
ASSERT_TRUE(cfg);
|
||||
|
||||
// Verify that parameters are correct.
|
||||
EXPECT_EQ(20, cfg->getReclaimTimerWaitTime());
|
||||
EXPECT_EQ(35, cfg->getFlushReclaimedTimerWaitTime());
|
||||
EXPECT_EQ(1800, cfg->getHoldReclaimedTime());
|
||||
EXPECT_EQ(50, cfg->getMaxReclaimLeases());
|
||||
EXPECT_EQ(100, cfg->getMaxReclaimTime());
|
||||
EXPECT_EQ(10, cfg->getUnwarnedReclaimCycles());
|
||||
}
|
||||
|
||||
// Check that invalid configuration for the expired leases processing is
|
||||
// causing an error.
|
||||
TEST_F(Dhcp4ParserTest, expiredLeasesProcessingError) {
|
||||
// Create basic configuration with the expiration specific parameters.
|
||||
// One of the parameters holds invalid value.
|
||||
string config = "{ " + genIfaceConfig() + "," +
|
||||
"\"expired-leases-processing\": "
|
||||
"{"
|
||||
" \"reclaim-timer-wait-time\": -5,"
|
||||
" \"flush-reclaimed-timer-wait-time\": 35,"
|
||||
" \"hold-reclaimed-time\": 1800,"
|
||||
" \"max-reclaim-leases\": 50,"
|
||||
" \"max-reclaim-time\": 100,"
|
||||
" \"unwarned-reclaim-cycles\": 10"
|
||||
"},"
|
||||
"\"subnet4\": [ ]"
|
||||
"}";
|
||||
|
||||
ElementPtr json = Element::fromJSON(config);
|
||||
|
||||
ConstElementPtr status;
|
||||
EXPECT_NO_THROW(status = configureDhcp4Server(*srv_, json));
|
||||
|
||||
// Returned value should be 0 (error)
|
||||
checkResult(status, 1);
|
||||
|
||||
// Check that the error contains error position.
|
||||
EXPECT_TRUE(errorContainsPosition(status, "<string>"));
|
||||
}
|
||||
|
||||
}
|
||||
|
@@ -38,6 +38,50 @@
|
||||
]
|
||||
},
|
||||
|
||||
{ "item_name": "expired-leases-processing",
|
||||
"item_type": "map",
|
||||
"item_optional": false,
|
||||
"item_default": {},
|
||||
"map_item_spec": [
|
||||
{
|
||||
"item_name": "reclaim-timer-wait-time",
|
||||
"item_type": "integer",
|
||||
"item_optional": false,
|
||||
"item_default": 10
|
||||
},
|
||||
{
|
||||
"item_name": "flush-reclaimed-timer-wait-time",
|
||||
"item_type": "integer",
|
||||
"item_optional": false,
|
||||
"item_default": 25
|
||||
},
|
||||
{
|
||||
"item_name": "hold-reclaimed-time",
|
||||
"item_type": "integer",
|
||||
"item_optional": false,
|
||||
"item_default": 3600
|
||||
},
|
||||
{
|
||||
"item_name": "max-reclaim-leases",
|
||||
"item_type": "integer",
|
||||
"item_optional": false,
|
||||
"item_default": 100
|
||||
},
|
||||
{
|
||||
"item_name": "max-reclaim-time",
|
||||
"item_type": "integer",
|
||||
"item_optional": false,
|
||||
"item_default": 250
|
||||
},
|
||||
{
|
||||
"item_name": "unwarned-reclaim-cycles",
|
||||
"item_type": "integer",
|
||||
"item_optional": false,
|
||||
"item_default": 5
|
||||
}
|
||||
]
|
||||
},
|
||||
|
||||
{ "item_name": "renew-timer",
|
||||
"item_type": "integer",
|
||||
"item_optional": false,
|
||||
|
@@ -30,6 +30,7 @@
|
||||
#include <dhcpsrv/parsers/dbaccess_parser.h>
|
||||
#include <dhcpsrv/parsers/dhcp_config_parser.h>
|
||||
#include <dhcpsrv/parsers/dhcp_parsers.h>
|
||||
#include <dhcpsrv/parsers/expiration_config_parser.h>
|
||||
#include <dhcpsrv/parsers/host_reservation_parser.h>
|
||||
#include <dhcpsrv/parsers/host_reservations_list_parser.h>
|
||||
#include <dhcpsrv/parsers/ifaces_config_parser.h>
|
||||
@@ -697,6 +698,8 @@ namespace dhcp {
|
||||
parser = new RSOOListConfigParser(config_id);
|
||||
} else if (config_id.compare("control-socket") == 0) {
|
||||
parser = new ControlSocketParser(config_id);
|
||||
} else if (config_id.compare("expired-leases-processing") == 0) {
|
||||
parser = new ExpirationConfigParser();
|
||||
} else {
|
||||
isc_throw(DhcpConfigError,
|
||||
"unsupported global configuration parameter: "
|
||||
|
@@ -26,6 +26,7 @@
|
||||
#include <dhcp6/dhcp6_srv.h>
|
||||
#include <dhcpsrv/addr_utilities.h>
|
||||
#include <dhcpsrv/cfgmgr.h>
|
||||
#include <dhcpsrv/cfg_expiration.h>
|
||||
#include <dhcpsrv/cfg_hosts.h>
|
||||
#include <dhcpsrv/subnet.h>
|
||||
#include <dhcpsrv/subnet_selector.h>
|
||||
@@ -4046,5 +4047,74 @@ TEST_F(Dhcp6ParserTest, declineTimerError) {
|
||||
EXPECT_TRUE(errorContainsPosition(status, "<string>"));
|
||||
}
|
||||
|
||||
// Check that configuration for the expired leases processing may be
|
||||
// specified.
|
||||
TEST_F(Dhcp6ParserTest, expiredLeasesProcessing) {
|
||||
// Create basic configuration with the expiration specific parameters.
|
||||
string config = "{ " + genIfaceConfig() + "," +
|
||||
"\"expired-leases-processing\": "
|
||||
"{"
|
||||
" \"reclaim-timer-wait-time\": 20,"
|
||||
" \"flush-reclaimed-timer-wait-time\": 35,"
|
||||
" \"hold-reclaimed-time\": 1800,"
|
||||
" \"max-reclaim-leases\": 50,"
|
||||
" \"max-reclaim-time\": 100,"
|
||||
" \"unwarned-reclaim-cycles\": 10"
|
||||
"},"
|
||||
"\"subnet6\": [ ]"
|
||||
"}";
|
||||
|
||||
ElementPtr json = Element::fromJSON(config);
|
||||
|
||||
ConstElementPtr status;
|
||||
EXPECT_NO_THROW(status = configureDhcp6Server(srv_, json));
|
||||
|
||||
// Returned value should be 0 (success)
|
||||
checkResult(status, 0);
|
||||
|
||||
// The value of decline-probation-perion must be equal to the
|
||||
// value specified.
|
||||
CfgExpirationPtr cfg = CfgMgr::instance().getStagingCfg()->getCfgExpiration();
|
||||
ASSERT_TRUE(cfg);
|
||||
|
||||
// Verify that parameters are correct.
|
||||
EXPECT_EQ(20, cfg->getReclaimTimerWaitTime());
|
||||
EXPECT_EQ(35, cfg->getFlushReclaimedTimerWaitTime());
|
||||
EXPECT_EQ(1800, cfg->getHoldReclaimedTime());
|
||||
EXPECT_EQ(50, cfg->getMaxReclaimLeases());
|
||||
EXPECT_EQ(100, cfg->getMaxReclaimTime());
|
||||
EXPECT_EQ(10, cfg->getUnwarnedReclaimCycles());
|
||||
}
|
||||
|
||||
// Check that invalid configuration for the expired leases processing is
|
||||
// causing an error.
|
||||
TEST_F(Dhcp6ParserTest, expiredLeasesProcessingError) {
|
||||
// Create basic configuration with the expiration specific parameters.
|
||||
// One of the parameters holds invalid value.
|
||||
string config = "{ " + genIfaceConfig() + "," +
|
||||
"\"expired-leases-processing\": "
|
||||
"{"
|
||||
" \"reclaim-timer-wait-time\": -5,"
|
||||
" \"flush-reclaimed-timer-wait-time\": 35,"
|
||||
" \"hold-reclaimed-time\": 1800,"
|
||||
" \"max-reclaim-leases\": 50,"
|
||||
" \"max-reclaim-time\": 100,"
|
||||
" \"unwarned-reclaim-cycles\": 10"
|
||||
"},"
|
||||
"\"subnet6\": [ ]"
|
||||
"}";
|
||||
|
||||
ElementPtr json = Element::fromJSON(config);
|
||||
|
||||
ConstElementPtr status;
|
||||
EXPECT_NO_THROW(status = configureDhcp6Server(srv_, json));
|
||||
|
||||
// Returned value should be 0 (error)
|
||||
checkResult(status, 1);
|
||||
|
||||
// Check that the error contains error position.
|
||||
EXPECT_TRUE(errorContainsPosition(status, "<string>"));
|
||||
}
|
||||
|
||||
|
||||
};
|
||||
|
@@ -80,6 +80,7 @@ libkea_dhcpsrv_la_SOURCES += base_host_data_source.h
|
||||
libkea_dhcpsrv_la_SOURCES += callout_handle_store.h
|
||||
libkea_dhcpsrv_la_SOURCES += cfg_hosts.cc cfg_hosts.h
|
||||
libkea_dhcpsrv_la_SOURCES += cfg_iface.cc cfg_iface.h
|
||||
libkea_dhcpsrv_la_SOURCES += cfg_expiration.cc cfg_expiration.h
|
||||
libkea_dhcpsrv_la_SOURCES += cfg_option.cc cfg_option.h
|
||||
libkea_dhcpsrv_la_SOURCES += cfg_option_def.cc cfg_option_def.h
|
||||
libkea_dhcpsrv_la_SOURCES += cfg_rsoo.cc cfg_rsoo.h
|
||||
@@ -131,6 +132,8 @@ libkea_dhcpsrv_la_SOURCES += parsers/dbaccess_parser.cc
|
||||
libkea_dhcpsrv_la_SOURCES += parsers/dbaccess_parser.h
|
||||
libkea_dhcpsrv_la_SOURCES += parsers/dhcp_parsers.cc
|
||||
libkea_dhcpsrv_la_SOURCES += parsers/dhcp_parsers.h
|
||||
libkea_dhcpsrv_la_SOURCES += parsers/expiration_config_parser.cc
|
||||
libkea_dhcpsrv_la_SOURCES += parsers/expiration_config_parser.h
|
||||
libkea_dhcpsrv_la_SOURCES += parsers/host_reservation_parser.cc
|
||||
libkea_dhcpsrv_la_SOURCES += parsers/host_reservation_parser.h
|
||||
libkea_dhcpsrv_la_SOURCES += parsers/host_reservations_list_parser.h
|
||||
|
108
src/lib/dhcpsrv/cfg_expiration.cc
Normal file
108
src/lib/dhcpsrv/cfg_expiration.cc
Normal file
@@ -0,0 +1,108 @@
|
||||
// Copyright (C) 2015 Internet Systems Consortium, Inc. ("ISC")
|
||||
//
|
||||
// Permission to use, copy, modify, and/or distribute this software for any
|
||||
// purpose with or without fee is hereby granted, provided that the above
|
||||
// copyright notice and this permission notice appear in all copies.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES WITH
|
||||
// REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
|
||||
// AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR ANY SPECIAL, DIRECT,
|
||||
// INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
|
||||
// LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE
|
||||
// OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
|
||||
// PERFORMANCE OF THIS SOFTWARE.
|
||||
|
||||
#include <dhcpsrv/cfg_expiration.h>
|
||||
#include <exceptions/exceptions.h>
|
||||
#include <limits.h>
|
||||
|
||||
namespace isc {
|
||||
namespace dhcp {
|
||||
|
||||
// Default values
|
||||
const uint16_t CfgExpiration::DEFAULT_RECLAIM_TIMER_WAIT_TIME = 10;
|
||||
const uint16_t CfgExpiration::DEFAULT_FLUSH_RECLAIMED_TIMER_WAIT_TIME = 25;
|
||||
const uint32_t CfgExpiration::DEFAULT_HOLD_RECLAIMED_TIME = 3600;
|
||||
const uint32_t CfgExpiration::DEFAULT_MAX_RECLAIM_LEASES = 100;
|
||||
const uint16_t CfgExpiration::DEFAULT_MAX_RECLAIM_TIME = 250;
|
||||
const uint16_t CfgExpiration::DEFAULT_UNWARNED_RECLAIM_CYCLES = 5;
|
||||
|
||||
// Maximum values.
|
||||
const uint16_t CfgExpiration::LIMIT_RECLAIM_TIMER_WAIT_TIME =
|
||||
std::numeric_limits<uint16_t>::max();
|
||||
const uint16_t CfgExpiration::LIMIT_FLUSH_RECLAIMED_TIMER_WAIT_TIME =
|
||||
std::numeric_limits<uint16_t>::max();
|
||||
const uint32_t CfgExpiration::LIMIT_HOLD_RECLAIMED_TIME =
|
||||
std::numeric_limits<uint32_t>::max();
|
||||
const uint32_t CfgExpiration::LIMIT_MAX_RECLAIM_LEASES =
|
||||
std::numeric_limits<uint32_t>::max();
|
||||
const uint16_t CfgExpiration::LIMIT_MAX_RECLAIM_TIME = 10000;
|
||||
const uint16_t CfgExpiration::LIMIT_UNWARNED_RECLAIM_CYCLES =
|
||||
std::numeric_limits<uint16_t>::max();
|
||||
|
||||
CfgExpiration::CfgExpiration()
|
||||
: reclaim_timer_wait_time_(DEFAULT_RECLAIM_TIMER_WAIT_TIME),
|
||||
flush_reclaimed_timer_wait_time_(DEFAULT_FLUSH_RECLAIMED_TIMER_WAIT_TIME),
|
||||
hold_reclaimed_time_(DEFAULT_HOLD_RECLAIMED_TIME),
|
||||
max_reclaim_leases_(DEFAULT_MAX_RECLAIM_LEASES),
|
||||
max_reclaim_time_(DEFAULT_MAX_RECLAIM_TIME),
|
||||
unwarned_reclaim_cycles_(DEFAULT_UNWARNED_RECLAIM_CYCLES) {
|
||||
}
|
||||
|
||||
void
|
||||
CfgExpiration::setReclaimTimerWaitTime(const int64_t reclaim_timer_wait_time) {
|
||||
rangeCheck(reclaim_timer_wait_time, LIMIT_RECLAIM_TIMER_WAIT_TIME,
|
||||
"reclaim-timer-wait-time");
|
||||
reclaim_timer_wait_time_ = reclaim_timer_wait_time;
|
||||
}
|
||||
|
||||
void
|
||||
CfgExpiration::setFlushReclaimedTimerWaitTime(const int64_t flush_reclaimed_wait_time) {
|
||||
rangeCheck(flush_reclaimed_wait_time, LIMIT_FLUSH_RECLAIMED_TIMER_WAIT_TIME,
|
||||
"flush-reclaimed-timer-wait-time");
|
||||
flush_reclaimed_timer_wait_time_ = flush_reclaimed_wait_time;
|
||||
}
|
||||
|
||||
void
|
||||
CfgExpiration::setHoldReclaimedTime(const int64_t hold_reclaimed_time) {
|
||||
rangeCheck(hold_reclaimed_time, LIMIT_HOLD_RECLAIMED_TIME, "hold-reclaimed-time");
|
||||
hold_reclaimed_time_ = hold_reclaimed_time;
|
||||
}
|
||||
|
||||
void
|
||||
CfgExpiration::setMaxReclaimLeases(const int64_t max_reclaim_leases) {
|
||||
rangeCheck(max_reclaim_leases, LIMIT_MAX_RECLAIM_LEASES, "max-reclaim-leases");
|
||||
max_reclaim_leases_ = max_reclaim_leases;
|
||||
}
|
||||
|
||||
void
|
||||
CfgExpiration::setMaxReclaimTime(const int64_t max_reclaim_time) {
|
||||
rangeCheck(max_reclaim_time, LIMIT_MAX_RECLAIM_TIME, "max-reclaim-time");
|
||||
max_reclaim_time_ = max_reclaim_time;
|
||||
}
|
||||
|
||||
void
|
||||
CfgExpiration::setUnwarnedReclaimCycles(const int64_t unwarned_reclaim_cycles) {
|
||||
rangeCheck(unwarned_reclaim_cycles, LIMIT_UNWARNED_RECLAIM_CYCLES,
|
||||
"unwarned-reclaim-cycles");
|
||||
unwarned_reclaim_cycles_ = unwarned_reclaim_cycles;
|
||||
}
|
||||
|
||||
void
|
||||
CfgExpiration::rangeCheck(const int64_t value, const uint64_t max_value,
|
||||
const std::string& config_parameter_name) const {
|
||||
if (value < 0) {
|
||||
isc_throw(OutOfRange, "value for configuration parameter '"
|
||||
<< config_parameter_name << "' must not be negtive");
|
||||
|
||||
} else if (value > max_value) {
|
||||
isc_throw(OutOfRange, "out range value '" << value << "' for configuration"
|
||||
" parameter '" << config_parameter_name << "', expected maximum"
|
||||
" value of '" << max_value << "'");
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
}
|
||||
}
|
227
src/lib/dhcpsrv/cfg_expiration.h
Normal file
227
src/lib/dhcpsrv/cfg_expiration.h
Normal file
@@ -0,0 +1,227 @@
|
||||
// Copyright (C) 2015 Internet Systems Consortium, Inc. ("ISC")
|
||||
//
|
||||
// Permission to use, copy, modify, and/or distribute this software for any
|
||||
// purpose with or without fee is hereby granted, provided that the above
|
||||
// copyright notice and this permission notice appear in all copies.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES WITH
|
||||
// REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
|
||||
// AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR ANY SPECIAL, DIRECT,
|
||||
// INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
|
||||
// LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE
|
||||
// OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
|
||||
// PERFORMANCE OF THIS SOFTWARE.
|
||||
|
||||
#ifndef CFG_EXPIRATION_H
|
||||
#define CFG_EXPIRATION_H
|
||||
|
||||
#include <boost/shared_ptr.hpp>
|
||||
#include <stdint.h>
|
||||
#include <string>
|
||||
|
||||
namespace isc {
|
||||
namespace dhcp {
|
||||
|
||||
/// @brief Holds configuration parameters pertaining to lease expiration
|
||||
/// and lease affinity.
|
||||
///
|
||||
/// This class holds the values of the following configuration parameters:
|
||||
///
|
||||
/// - reclaim-timer-wait-time - is the time between two cycles of processing
|
||||
/// expired leases, expressed in seconds, i.e. the time between the end of
|
||||
/// one cycle and the beginning of the next cycle. If this value is 0, the
|
||||
/// expired leases are not processed.
|
||||
///
|
||||
/// - flush-reclaimed-timer-wait-time - is the time between two cycles of
|
||||
/// recycling "expired-reclaimed" leases, expressed in seconds. If this
|
||||
/// value is 0, the expired leases are removed by the leases reclamation
|
||||
/// routine rather than recycling function. The recycling function is not
|
||||
/// executed and the value of the "hold-reclaimed-time" is ignored.
|
||||
///
|
||||
/// - hold-reclaimed-time -is the time for which "expired-reclaimed" leases
|
||||
/// are held in the lease database in the "expired-reclaimed" state after
|
||||
/// they expire. If this time is set to 0, the recycling function is not
|
||||
/// executed and the value of the "recycle-timer-wait-time" is ignored.
|
||||
/// This value is expressed in seconds.
|
||||
///
|
||||
/// - max-reclaim-leases - is the maximum number of leases to be processed
|
||||
/// in a single cycle. If this value is 0, all expired leases are
|
||||
/// processed in a single cycle, unless the maximum processing time
|
||||
/// (configured with the "max-time") parameter elapses first.
|
||||
///
|
||||
/// - max-reclaim-time - the maximum time that a single processing cycle
|
||||
/// may last, expressed in milliseconds. If this value is 0, there is no
|
||||
/// limitation for the maximum processing time. This value is expressed
|
||||
/// in milliseconds.
|
||||
///
|
||||
/// - unwarned-reclaim-cycles - is the number of consecutive processing
|
||||
/// cycles of expired leases, after which the system issues a warning if
|
||||
/// there are still expired leases in the database. If this value is 0,
|
||||
/// the warning is never issued.
|
||||
///
|
||||
/// The @c CfgExpiration class provides a collection of accessors and
|
||||
/// modifiers to manage the data. Each accessor checks if the given value
|
||||
/// is in range allowed for this value.
|
||||
class CfgExpiration {
|
||||
public:
|
||||
|
||||
/// @name Default values.
|
||||
//@{
|
||||
///
|
||||
/// @brief Default value for reclaim-timer-wait-time.
|
||||
static const uint16_t DEFAULT_RECLAIM_TIMER_WAIT_TIME;
|
||||
|
||||
/// @brief Default value for flush-reclaimed-timer-wait-time.
|
||||
static const uint16_t DEFAULT_FLUSH_RECLAIMED_TIMER_WAIT_TIME;
|
||||
|
||||
/// @brief Default value for hold-reclaimed-time.
|
||||
static const uint32_t DEFAULT_HOLD_RECLAIMED_TIME;
|
||||
|
||||
/// @brief Default value for max-reclaim-leases.
|
||||
static const uint32_t DEFAULT_MAX_RECLAIM_LEASES;
|
||||
|
||||
/// @brief Default value for max-reclaim-time.
|
||||
static const uint16_t DEFAULT_MAX_RECLAIM_TIME;
|
||||
|
||||
/// @brief Default value for unwarned-reclaim-cycles.
|
||||
static const uint16_t DEFAULT_UNWARNED_RECLAIM_CYCLES;
|
||||
|
||||
//@}
|
||||
|
||||
/// @name Upper limits for the parameters
|
||||
//@{
|
||||
///
|
||||
/// @brief Maximum value for reclaim-timer-wait-time.
|
||||
static const uint16_t LIMIT_RECLAIM_TIMER_WAIT_TIME;
|
||||
|
||||
/// @brief Maximum value for flush-reclaimed-timer-wait-time.
|
||||
static const uint16_t LIMIT_FLUSH_RECLAIMED_TIMER_WAIT_TIME;
|
||||
|
||||
/// @brief Maximum value for hold-reclaimed-time.
|
||||
static const uint32_t LIMIT_HOLD_RECLAIMED_TIME;
|
||||
|
||||
/// @brief Maximum value for max-reclaim-leases.
|
||||
static const uint32_t LIMIT_MAX_RECLAIM_LEASES;
|
||||
|
||||
/// @brief Defalt value for max-reclaim-time.
|
||||
static const uint16_t LIMIT_MAX_RECLAIM_TIME;
|
||||
|
||||
/// @brief Maximum value for unwarned-reclaim-cycles.
|
||||
static const uint16_t LIMIT_UNWARNED_RECLAIM_CYCLES;
|
||||
|
||||
//@}
|
||||
|
||||
/// @brief Constructor.
|
||||
///
|
||||
/// Sets all parameters to their defaults.
|
||||
CfgExpiration();
|
||||
|
||||
/// @brief Returns reclaim-timer-wait-time
|
||||
uint16_t getReclaimTimerWaitTime() const {
|
||||
return (reclaim_timer_wait_time_);
|
||||
}
|
||||
|
||||
/// @brief Sets reclaim-timer-wait-time
|
||||
///
|
||||
/// @param reclaim_timer_wait_time New value.
|
||||
void setReclaimTimerWaitTime(const int64_t reclaim_timer_wait_time);
|
||||
|
||||
/// @brief Returns flush-reclaimed-timer-wait-time.
|
||||
uint16_t getFlushReclaimedTimerWaitTime() const {
|
||||
return (flush_reclaimed_timer_wait_time_);
|
||||
}
|
||||
|
||||
/// @brief Sets flush-reclaimed-timer-wait-time.
|
||||
///
|
||||
/// @param flush_reclaimed_wait_time New value.
|
||||
void setFlushReclaimedTimerWaitTime(const int64_t flush_reclaimed_wait_time);
|
||||
|
||||
/// @brief Returns hold-reclaimed-time.
|
||||
uint32_t getHoldReclaimedTime() const {
|
||||
return (hold_reclaimed_time_);
|
||||
}
|
||||
|
||||
/// @brief Sets hold-reclaimed-time
|
||||
///
|
||||
/// @param hold_reclaimed_time New value.
|
||||
void setHoldReclaimedTime(const int64_t hold_reclaimed_time);
|
||||
|
||||
/// @brief Returns max-reclaim-leases.
|
||||
uint32_t getMaxReclaimLeases() const {
|
||||
return (max_reclaim_leases_);
|
||||
}
|
||||
|
||||
/// @brief Sets max-reclaim-leases.
|
||||
///
|
||||
/// @param max_reclaim_leases New value.
|
||||
void setMaxReclaimLeases(const int64_t max_reclaim_leases);
|
||||
|
||||
/// @brief Returns max-reclaim-time.
|
||||
uint16_t getMaxReclaimTime() const {
|
||||
return (max_reclaim_time_);
|
||||
}
|
||||
|
||||
/// @brief Sets max-reclaim-time.
|
||||
///
|
||||
/// @param max_reclaim_time New value.
|
||||
void setMaxReclaimTime(const int64_t max_reclaim_time);
|
||||
|
||||
/// @brief Returns unwarned-reclaim-cycles.
|
||||
uint16_t getUnwarnedReclaimCycles() const {
|
||||
return (unwarned_reclaim_cycles_);
|
||||
}
|
||||
|
||||
/// @brief Sets unwarned-reclaim-cycles.
|
||||
///
|
||||
/// @param unwarned_reclaim_cycles New value.
|
||||
void setUnwarnedReclaimCycles(const int64_t unwarned_reclaim_cycles);
|
||||
|
||||
private:
|
||||
|
||||
/// @brief Checks if the value being set by one of the modifiers is
|
||||
/// within an allowed range.
|
||||
///
|
||||
/// @param value Value to be checked.
|
||||
/// @param max_value Maximum allowed value.
|
||||
/// @param config_parameter_name A name of the configuration parameter
|
||||
/// (used for logging purposes if value is out of range).
|
||||
///
|
||||
/// @throw isc::OutOfRange if the value is negative or greater than
|
||||
/// the maximum value.
|
||||
void rangeCheck(const int64_t value, const uint64_t max_value,
|
||||
const std::string& config_parameter_name) const;
|
||||
|
||||
/// @brief reclaim-timer-wait-time
|
||||
uint16_t reclaim_timer_wait_time_;
|
||||
|
||||
/// @brief flush-reclaimed-timer-wait-time
|
||||
uint16_t flush_reclaimed_timer_wait_time_;
|
||||
|
||||
/// @brief hold-reclaimed-time
|
||||
uint32_t hold_reclaimed_time_;
|
||||
|
||||
/// @brief max-reclaim-leases
|
||||
uint32_t max_reclaim_leases_;
|
||||
|
||||
/// @brief max-reclaim-time
|
||||
uint16_t max_reclaim_time_;
|
||||
|
||||
/// @brief unwarned-reclaim-cycles.
|
||||
uint16_t unwarned_reclaim_cycles_;
|
||||
|
||||
};
|
||||
|
||||
/// @name Pointers to the @c CfgExpiration objects.
|
||||
//@{
|
||||
/// @brief Pointer to the Non-const object.
|
||||
typedef boost::shared_ptr<CfgExpiration> CfgExpirationPtr;
|
||||
|
||||
/// @brief Pointer to the const object.
|
||||
typedef boost::shared_ptr<const CfgExpiration> ConstCfgExpirationPtr;
|
||||
|
||||
//@}
|
||||
|
||||
} // end of isc::dhcp namespace
|
||||
} // end of isc namespace
|
||||
|
||||
#endif // CFG_EXPIRATION_H
|
80
src/lib/dhcpsrv/parsers/expiration_config_parser.cc
Normal file
80
src/lib/dhcpsrv/parsers/expiration_config_parser.cc
Normal file
@@ -0,0 +1,80 @@
|
||||
// Copyright (C) 2015 Internet Systems Consortium, Inc. ("ISC")
|
||||
//
|
||||
// Permission to use, copy, modify, and/or distribute this software for any
|
||||
// purpose with or without fee is hereby granted, provided that the above
|
||||
// copyright notice and this permission notice appear in all copies.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES WITH
|
||||
// REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
|
||||
// AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR ANY SPECIAL, DIRECT,
|
||||
// INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
|
||||
// LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE
|
||||
// OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
|
||||
// PERFORMANCE OF THIS SOFTWARE.
|
||||
|
||||
#include <cc/data.h>
|
||||
#include <dhcpsrv/cfg_expiration.h>
|
||||
#include <dhcpsrv/cfgmgr.h>
|
||||
#include <dhcpsrv/parsers/expiration_config_parser.h>
|
||||
#include <boost/foreach.hpp>
|
||||
|
||||
using namespace isc::data;
|
||||
|
||||
namespace isc {
|
||||
namespace dhcp {
|
||||
|
||||
ExpirationConfigParser::ExpirationConfigParser()
|
||||
: DhcpConfigParser() {
|
||||
}
|
||||
|
||||
void
|
||||
ExpirationConfigParser::build(ConstElementPtr expiration_config) {
|
||||
CfgExpirationPtr cfg = CfgMgr::instance().getStagingCfg()->getCfgExpiration();
|
||||
|
||||
BOOST_FOREACH(ConfigPair config_element, expiration_config->mapValue()) {
|
||||
|
||||
// Get parameter name and value.
|
||||
std::string param_name = config_element.first;
|
||||
ConstElementPtr param_value = config_element.second;
|
||||
|
||||
try {
|
||||
// Set configuration parameters.
|
||||
if (param_name == "reclaim-timer-wait-time") {
|
||||
cfg->setReclaimTimerWaitTime(param_value->intValue());
|
||||
|
||||
} else if (param_name == "flush-reclaimed-timer-wait-time") {
|
||||
cfg->setFlushReclaimedTimerWaitTime(param_value->intValue());
|
||||
|
||||
} else if (param_name == "hold-reclaimed-time") {
|
||||
cfg->setHoldReclaimedTime(param_value->intValue());
|
||||
|
||||
} else if (param_name == "max-reclaim-leases") {
|
||||
cfg->setMaxReclaimLeases(param_value->intValue());
|
||||
|
||||
} else if (param_name == "max-reclaim-time") {
|
||||
cfg->setMaxReclaimTime(param_value->intValue());
|
||||
|
||||
} else if (param_name == "unwarned-reclaim-cycles") {
|
||||
cfg->setUnwarnedReclaimCycles(param_value->intValue());
|
||||
|
||||
} else {
|
||||
isc_throw(DhcpConfigError, "unsupported parameter '"
|
||||
<< param_name << "'");
|
||||
}
|
||||
|
||||
} catch (const std::exception& ex) {
|
||||
// Append position of the configuration parameter to the error
|
||||
// message.
|
||||
isc_throw(DhcpConfigError, ex.what() << " ("
|
||||
<< param_value->getPosition() << ")");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
ExpirationConfigParser::commit() {
|
||||
// Nothing to do.
|
||||
}
|
||||
|
||||
} // end of namespace isc::dhcp
|
||||
} // end of namespace isc
|
69
src/lib/dhcpsrv/parsers/expiration_config_parser.h
Normal file
69
src/lib/dhcpsrv/parsers/expiration_config_parser.h
Normal file
@@ -0,0 +1,69 @@
|
||||
// Copyright (C) 2015 Internet Systems Consortium, Inc. ("ISC")
|
||||
//
|
||||
// Permission to use, copy, modify, and/or distribute this software for any
|
||||
// purpose with or without fee is hereby granted, provided that the above
|
||||
// copyright notice and this permission notice appear in all copies.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES WITH
|
||||
// REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
|
||||
// AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR ANY SPECIAL, DIRECT,
|
||||
// INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
|
||||
// LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE
|
||||
// OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
|
||||
// PERFORMANCE OF THIS SOFTWARE.
|
||||
|
||||
#ifndef EXPIRATION_CONFIG_PARSER_H
|
||||
#define EXPIRATION_CONFIG_PARSER_H
|
||||
|
||||
#include <dhcpsrv/parsers/dhcp_config_parser.h>
|
||||
|
||||
namespace isc {
|
||||
namespace dhcp {
|
||||
|
||||
|
||||
/// @brief Parser for the configuration parameters pertaining to the
|
||||
/// processing of expired leases.
|
||||
///
|
||||
/// This parser iterates over parameters stored in the map and tries to
|
||||
/// set the appropriate values in the @c CfgExpiration object of the
|
||||
/// Configuration Manager.
|
||||
///
|
||||
/// Currently supported parameters are:
|
||||
/// - reclaim-timer-wait-time,
|
||||
/// - flush-reclaimed-timer-wait-time,
|
||||
/// - hold-reclaimed-time,
|
||||
/// - max-reclaim-leases,
|
||||
/// - max-reclaim-time,
|
||||
/// - unwarned-reclaim-cycles.
|
||||
///
|
||||
/// These parameters are optional and the default values are used for
|
||||
/// those that aren't specified.
|
||||
///
|
||||
/// The parser checks if the values of the specified parameters are within
|
||||
/// the allowed ranges and throws exception if they are. Each parameter
|
||||
/// has a corresponding maximum value defined in the @c CfgExpiration class.
|
||||
/// None of them may be negative.
|
||||
class ExpirationConfigParser : public DhcpConfigParser {
|
||||
public:
|
||||
|
||||
/// @brief Constructor
|
||||
ExpirationConfigParser();
|
||||
|
||||
/// @brief Parses parameters in the JSON map, pertaining to the processing
|
||||
/// of the expired leases.
|
||||
///
|
||||
/// @param value pointer to the content of parsed values
|
||||
///
|
||||
/// @throw DhcpConfigError if unknown parameter specified or the
|
||||
/// parameter contains invalid value..
|
||||
virtual void build(isc::data::ConstElementPtr value);
|
||||
|
||||
/// @brief Does nothing.
|
||||
virtual void commit();
|
||||
|
||||
};
|
||||
|
||||
} // end of namespace isc::dhcp
|
||||
} // end of namespace isc
|
||||
|
||||
#endif // EXPIRATION_CONFIG_PARSER_H
|
@@ -31,6 +31,7 @@ SrvConfig::SrvConfig()
|
||||
cfg_option_def_(new CfgOptionDef()), cfg_option_(new CfgOption()),
|
||||
cfg_subnets4_(new CfgSubnets4()), cfg_subnets6_(new CfgSubnets6()),
|
||||
cfg_hosts_(new CfgHosts()), cfg_rsoo_(new CfgRSOO()),
|
||||
cfg_expiration_(new CfgExpiration()),
|
||||
decline_timer_(0) {
|
||||
}
|
||||
|
||||
@@ -39,6 +40,7 @@ SrvConfig::SrvConfig(const uint32_t sequence)
|
||||
cfg_option_def_(new CfgOptionDef()), cfg_option_(new CfgOption()),
|
||||
cfg_subnets4_(new CfgSubnets4()), cfg_subnets6_(new CfgSubnets6()),
|
||||
cfg_hosts_(new CfgHosts()), cfg_rsoo_(new CfgRSOO()),
|
||||
cfg_expiration_(new CfgExpiration()),
|
||||
decline_timer_(0) {
|
||||
}
|
||||
|
||||
|
@@ -15,6 +15,7 @@
|
||||
#ifndef DHCPSRV_CONFIG_H
|
||||
#define DHCPSRV_CONFIG_H
|
||||
|
||||
#include <dhcpsrv/cfg_expiration.h>
|
||||
#include <dhcpsrv/cfg_hosts.h>
|
||||
#include <dhcpsrv/cfg_iface.h>
|
||||
#include <dhcpsrv/cfg_option.h>
|
||||
@@ -259,6 +260,18 @@ public:
|
||||
return (cfg_rsoo_);
|
||||
}
|
||||
|
||||
/// @brief Returns pointer to the object holding configuration pertaining
|
||||
/// to processing expired leases.
|
||||
CfgExpirationPtr getCfgExpiration() {
|
||||
return (cfg_expiration_);
|
||||
}
|
||||
|
||||
/// @brief Returns pointer to the const object holding configuration
|
||||
/// pertaining to processing expired leases.
|
||||
ConstCfgExpirationPtr getCfgExpiration() const {
|
||||
return (cfg_expiration_);
|
||||
}
|
||||
|
||||
//@}
|
||||
|
||||
/// @brief Returns non-const reference to an array that stores
|
||||
@@ -441,6 +454,10 @@ private:
|
||||
/// RFC 6422 for the definition of the RSOO-enabled option.
|
||||
CfgRSOOPtr cfg_rsoo_;
|
||||
|
||||
/// @brief Pointer to the configuration pertaining to processing of
|
||||
/// expired leases.
|
||||
CfgExpirationPtr cfg_expiration_;
|
||||
|
||||
/// @brief Pointer to the control-socket information
|
||||
isc::data::ConstElementPtr control_socket_;
|
||||
|
||||
|
@@ -65,6 +65,7 @@ libdhcpsrv_unittests_SOURCES += alloc_engine_hooks_unittest.cc
|
||||
libdhcpsrv_unittests_SOURCES += alloc_engine4_unittest.cc
|
||||
libdhcpsrv_unittests_SOURCES += alloc_engine6_unittest.cc
|
||||
libdhcpsrv_unittests_SOURCES += callout_handle_store_unittest.cc
|
||||
libdhcpsrv_unittests_SOURCES += cfg_expiration_unittest.cc
|
||||
libdhcpsrv_unittests_SOURCES += cfg_hosts_unittest.cc
|
||||
libdhcpsrv_unittests_SOURCES += cfg_iface_unittest.cc
|
||||
libdhcpsrv_unittests_SOURCES += cfg_mac_source_unittest.cc
|
||||
@@ -80,6 +81,7 @@ libdhcpsrv_unittests_SOURCES += d2_client_unittest.cc
|
||||
libdhcpsrv_unittests_SOURCES += d2_udp_unittest.cc
|
||||
libdhcpsrv_unittests_SOURCES += daemon_unittest.cc
|
||||
libdhcpsrv_unittests_SOURCES += dbaccess_parser_unittest.cc
|
||||
libdhcpsrv_unittests_SOURCES += expiration_config_parser_unittest.cc
|
||||
libdhcpsrv_unittests_SOURCES += host_mgr_unittest.cc
|
||||
libdhcpsrv_unittests_SOURCES += host_unittest.cc
|
||||
libdhcpsrv_unittests_SOURCES += host_reservation_parser_unittest.cc
|
||||
|
161
src/lib/dhcpsrv/tests/cfg_expiration_unittest.cc
Normal file
161
src/lib/dhcpsrv/tests/cfg_expiration_unittest.cc
Normal file
@@ -0,0 +1,161 @@
|
||||
// Copyright (C) 2015 Internet Systems Consortium, Inc. ("ISC")
|
||||
//
|
||||
// Permission to use, copy, modify, and/or distribute this software for any
|
||||
// purpose with or without fee is hereby granted, provided that the above
|
||||
// copyright notice and this permission notice appear in all copies.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES WITH
|
||||
// REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
|
||||
// AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR ANY SPECIAL, DIRECT,
|
||||
// INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
|
||||
// LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE
|
||||
// OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
|
||||
// PERFORMANCE OF THIS SOFTWARE.
|
||||
|
||||
#include <config.h>
|
||||
#include <dhcpsrv/cfg_expiration.h>
|
||||
#include <exceptions/exceptions.h>
|
||||
#include <boost/function.hpp>
|
||||
#include <gtest/gtest.h>
|
||||
#include <stdint.h>
|
||||
|
||||
using namespace isc;
|
||||
using namespace isc::dhcp;
|
||||
|
||||
namespace {
|
||||
|
||||
/// @brief Type definition of the @c CfgExpiration modified function.
|
||||
typedef boost::function<void(CfgExpiration*, const int64_t)> ModifierFun;
|
||||
/// @brief Type definition of the @c CfgExpiration accessor function
|
||||
/// returning uint16_t value.
|
||||
typedef boost::function<uint16_t(CfgExpiration*)> AccessorFunUint16;
|
||||
/// @brief Type definition of the @c CfgExpiration accessor function
|
||||
/// returning uint32_t value.
|
||||
typedef boost::function<uint32_t(CfgExpiration*)> AccessorFunUint32;
|
||||
|
||||
/// @brief Tests the accessor and modifier function for a particular
|
||||
/// configuration parameter held in @c CfgExpiration.
|
||||
///
|
||||
/// This is a simple test which tries to set the given parameter to
|
||||
/// different values:
|
||||
/// - value greater than maximum allowed for this parameter - expects
|
||||
/// the exception to be thrown,
|
||||
/// - value lower than 0 - expects the exception to be thrown,
|
||||
/// - value equal to the maximum allowed,
|
||||
/// - value equal to maximum allowed minus 1.
|
||||
///
|
||||
/// @param limit Maximum allowed value for the parameter.
|
||||
/// @param modifier Pointer to the modifier function to be tested.
|
||||
/// @param accessor Pointer to the accessor function to be tested.
|
||||
/// @tparam ReturnType Type of the value returned by the accessor,
|
||||
/// i.e. uint16_t or uint32_t.
|
||||
template<typename ReturnType>
|
||||
void
|
||||
testAccessModify(const int64_t limit, const ModifierFun& modifier,
|
||||
const boost::function<ReturnType(CfgExpiration*)>& accessor) {
|
||||
CfgExpiration cfg;
|
||||
|
||||
// Setting the value to maximum allowed + 1 should result in
|
||||
// an exception.
|
||||
ASSERT_THROW(modifier(&cfg, limit + 1), OutOfRange);
|
||||
|
||||
// Setting to the negative value should result in an exception.
|
||||
ASSERT_THROW(modifier(&cfg, -1), OutOfRange);
|
||||
|
||||
// Setting the value to the maximum allowed should pass.
|
||||
ASSERT_NO_THROW(modifier(&cfg, limit));
|
||||
EXPECT_EQ(limit, accessor(&cfg));
|
||||
|
||||
// Setting the value to the maximum allowed - 1 should pass.
|
||||
ASSERT_NO_THROW(modifier(&cfg, limit - 1));
|
||||
EXPECT_EQ(limit - 1, accessor(&cfg));
|
||||
|
||||
// Setting the value to 0 should pass.
|
||||
ASSERT_NO_THROW(modifier(&cfg, 0));
|
||||
EXPECT_EQ(0, accessor(&cfg));
|
||||
}
|
||||
|
||||
/// @brief Tests that modifier and the accessor returning uint16_t value
|
||||
/// work as expected.
|
||||
///
|
||||
/// @param limit Maximum allowed value for the parameter.
|
||||
/// @param modifier Pointer to the modifier function to be tested.
|
||||
/// @param accessor Pointer to the accessor function to be tested.
|
||||
void
|
||||
testAccessModifyUint16(const int64_t limit, const ModifierFun& modifier,
|
||||
const AccessorFunUint16& accessor) {
|
||||
testAccessModify<uint16_t>(limit, modifier, accessor);
|
||||
}
|
||||
|
||||
/// @brief Tests that modifier and the accessor returning uint32_t value
|
||||
/// work as expected.
|
||||
///
|
||||
/// @param limit Maximum allowed value for the parameter.
|
||||
/// @param modifier Pointer to the modifier function to be tested.
|
||||
/// @param accessor Pointer to the accessor function to be tested.
|
||||
void
|
||||
testAccessModifyUint32(const int64_t limit, const ModifierFun& modifier,
|
||||
const AccessorFunUint32& accessor) {
|
||||
testAccessModify<uint32_t>(limit, modifier, accessor);
|
||||
}
|
||||
|
||||
/// Test the default values of CfgExpiration object.
|
||||
TEST(CfgExpirationTest, defaults) {
|
||||
CfgExpiration cfg;
|
||||
EXPECT_EQ(CfgExpiration::DEFAULT_RECLAIM_TIMER_WAIT_TIME,
|
||||
cfg.getReclaimTimerWaitTime());
|
||||
EXPECT_EQ(CfgExpiration::DEFAULT_FLUSH_RECLAIMED_TIMER_WAIT_TIME,
|
||||
cfg.getFlushReclaimedTimerWaitTime());
|
||||
EXPECT_EQ(CfgExpiration::DEFAULT_HOLD_RECLAIMED_TIME,
|
||||
cfg.getHoldReclaimedTime());
|
||||
EXPECT_EQ(CfgExpiration::DEFAULT_MAX_RECLAIM_LEASES,
|
||||
cfg.getMaxReclaimLeases());
|
||||
EXPECT_EQ(CfgExpiration::DEFAULT_MAX_RECLAIM_TIME,
|
||||
cfg.getMaxReclaimTime());
|
||||
EXPECT_EQ(CfgExpiration::DEFAULT_UNWARNED_RECLAIM_CYCLES,
|
||||
cfg.getUnwarnedReclaimCycles());
|
||||
}
|
||||
|
||||
// Test the {get,set}ReclaimTimerWaitTime.
|
||||
TEST(CfgExpirationTest, getReclaimTimerWaitTime) {
|
||||
testAccessModify<uint16_t>(CfgExpiration::LIMIT_RECLAIM_TIMER_WAIT_TIME,
|
||||
&CfgExpiration::setReclaimTimerWaitTime,
|
||||
&CfgExpiration::getReclaimTimerWaitTime);
|
||||
}
|
||||
|
||||
// Test the {get,set}FlushReclaimedTimerWaitTime.
|
||||
TEST(CfgExpirationTest, getFlushReclaimedTimerWaitTime) {
|
||||
testAccessModifyUint16(CfgExpiration::LIMIT_FLUSH_RECLAIMED_TIMER_WAIT_TIME,
|
||||
&CfgExpiration::setFlushReclaimedTimerWaitTime,
|
||||
&CfgExpiration::getFlushReclaimedTimerWaitTime);
|
||||
}
|
||||
|
||||
// Test the {get,set}HoldReclaimedTime.
|
||||
TEST(CfgExpirationTest, getHoldReclaimedTime) {
|
||||
testAccessModifyUint32(CfgExpiration::LIMIT_HOLD_RECLAIMED_TIME,
|
||||
&CfgExpiration::setHoldReclaimedTime,
|
||||
&CfgExpiration::getHoldReclaimedTime);
|
||||
}
|
||||
|
||||
// Test the {get,set}MaxReclaimLeases.
|
||||
TEST(CfgExpirationTest, getMaxReclaimLeases) {
|
||||
testAccessModifyUint32(CfgExpiration::LIMIT_MAX_RECLAIM_LEASES,
|
||||
&CfgExpiration::setMaxReclaimLeases,
|
||||
&CfgExpiration::getMaxReclaimLeases);
|
||||
}
|
||||
|
||||
// Test the {get,set}MaxReclaimTime.
|
||||
TEST(CfgExpirationTest, getMaxReclaimTime) {
|
||||
testAccessModifyUint16(CfgExpiration::LIMIT_MAX_RECLAIM_TIME,
|
||||
&CfgExpiration::setMaxReclaimTime,
|
||||
&CfgExpiration::getMaxReclaimTime);
|
||||
}
|
||||
|
||||
// Test the {get,set}UnwarnedReclaimCycles.
|
||||
TEST(CfgExpirationTest, getUnwarnedReclaimCycles) {
|
||||
testAccessModifyUint16(CfgExpiration::LIMIT_UNWARNED_RECLAIM_CYCLES,
|
||||
&CfgExpiration::setUnwarnedReclaimCycles,
|
||||
&CfgExpiration::getUnwarnedReclaimCycles);
|
||||
}
|
||||
|
||||
} // end of anonymous namespace
|
268
src/lib/dhcpsrv/tests/expiration_config_parser_unittest.cc
Normal file
268
src/lib/dhcpsrv/tests/expiration_config_parser_unittest.cc
Normal file
@@ -0,0 +1,268 @@
|
||||
// Copyright (C) 2015 Internet Systems Consortium, Inc. ("ISC")
|
||||
//
|
||||
// Permission to use, copy, modify, and/or distribute this software for any
|
||||
// purpose with or without fee is hereby granted, provided that the above
|
||||
// copyright notice and this permission notice appear in all copies.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES WITH
|
||||
// REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
|
||||
// AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR ANY SPECIAL, DIRECT,
|
||||
// INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
|
||||
// LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE
|
||||
// OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
|
||||
// PERFORMANCE OF THIS SOFTWARE.
|
||||
|
||||
#include <config.h>
|
||||
|
||||
#include <cc/data.h>
|
||||
#include <dhcpsrv/cfgmgr.h>
|
||||
#include <dhcpsrv/cfg_expiration.h>
|
||||
#include <dhcpsrv/parsers/expiration_config_parser.h>
|
||||
#include <gtest/gtest.h>
|
||||
#include <sstream>
|
||||
#include <stdint.h>
|
||||
#include <string>
|
||||
|
||||
using namespace isc::data;
|
||||
using namespace isc::dhcp;
|
||||
|
||||
namespace {
|
||||
|
||||
/// @brief Test fixture class for @c ExpirationConfigParser.
|
||||
class ExpirationConfigParserTest : public ::testing::Test {
|
||||
protected:
|
||||
|
||||
/// @brief Setup for each test.
|
||||
///
|
||||
/// Clears the configuration in the @c CfgMgr.
|
||||
virtual void SetUp();
|
||||
|
||||
/// @brief Cleans up after each test.
|
||||
///
|
||||
/// Clears the configuration in the @c CfgMgr.
|
||||
virtual void TearDown();
|
||||
|
||||
/// @brief Include a specified parameter in the configuration.
|
||||
///
|
||||
/// If the specified parameter already exists, its value is replaced.
|
||||
///
|
||||
/// @param param_name Parameter name.
|
||||
/// @param value Parameter value.
|
||||
void addParam(const std::string& param_name, const int64_t value);
|
||||
|
||||
/// @brief Creates configuration and parses it with the parser under test.
|
||||
///
|
||||
/// This method creates the JSON configuration form the parameters
|
||||
/// specified using the @c ExpirationConfigParserTest::addParam method.
|
||||
/// It then uses the parser to parse this configuration. Any exceptions
|
||||
/// emitted by the parser are propagated to the caller (they aren't
|
||||
/// caught by this method).
|
||||
///
|
||||
/// @return Pointer to the parsed configuration.
|
||||
CfgExpirationPtr renderConfig() const;
|
||||
|
||||
/// @brief Tests that the out of range parameter value is not accepted.
|
||||
///
|
||||
/// This test checks that the negative value and the value which is
|
||||
/// greater than the maximum for the given parameter is not accepted.
|
||||
///
|
||||
/// @param param Parameter name.
|
||||
/// @param max_value Maximum value allowed for the parameter.
|
||||
void testOutOfRange(const std::string& param, const uint64_t max_value);
|
||||
|
||||
private:
|
||||
|
||||
/// @brief Holds configuration parameters specified for a test.
|
||||
std::map<std::string, int64_t> config_params_;
|
||||
|
||||
};
|
||||
|
||||
void
|
||||
ExpirationConfigParserTest::SetUp() {
|
||||
CfgMgr::instance().clear();
|
||||
}
|
||||
|
||||
void
|
||||
ExpirationConfigParserTest::TearDown() {
|
||||
CfgMgr::instance().clear();
|
||||
}
|
||||
|
||||
void
|
||||
ExpirationConfigParserTest::addParam(const std::string& param_name,
|
||||
const int64_t value) {
|
||||
config_params_[param_name] = value;
|
||||
}
|
||||
|
||||
CfgExpirationPtr
|
||||
ExpirationConfigParserTest::renderConfig() const {
|
||||
std::ostringstream s;
|
||||
// Create JSON configuration from the parameters in the map.
|
||||
s << "{";
|
||||
for (std::map<std::string, int64_t>::const_iterator param =
|
||||
config_params_.begin(); param != config_params_.end();
|
||||
++param) {
|
||||
// Include comma sign if we're at the subsequent parameter.
|
||||
if (std::distance(config_params_.begin(), param) > 0) {
|
||||
s << ",";
|
||||
}
|
||||
s << "\"" << param->first << "\": " << param->second;
|
||||
}
|
||||
s << "}";
|
||||
|
||||
ElementPtr config_element = Element::fromJSON(s.str());
|
||||
|
||||
// Parse the configuration. This may emit exceptions.
|
||||
ExpirationConfigParser parser;
|
||||
parser.build(config_element);
|
||||
|
||||
// No exception so return configuration.
|
||||
return (CfgMgr::instance().getStagingCfg()->getCfgExpiration());
|
||||
}
|
||||
|
||||
void
|
||||
ExpirationConfigParserTest::testOutOfRange(const std::string& param,
|
||||
const uint64_t max_value) {
|
||||
// Remove any existing parameters which would influence the
|
||||
// behavior of the test.
|
||||
config_params_.clear();
|
||||
|
||||
// Negative value is not allowed.
|
||||
addParam(param, -3);
|
||||
EXPECT_THROW(renderConfig(), DhcpConfigError)
|
||||
<< "test for negative value of '" << param << "' failed";
|
||||
|
||||
// Value greater than maximum is not allowed.
|
||||
addParam(param, max_value + 1);
|
||||
EXPECT_THROW(renderConfig(), DhcpConfigError)
|
||||
<< "test for out of range value of '" << param << "' failed";
|
||||
|
||||
// Value in range should be accepted.
|
||||
addParam(param, max_value);
|
||||
EXPECT_NO_THROW(renderConfig())
|
||||
<< "test for in range value of '" << param << "' failed";
|
||||
|
||||
// Value of 0 should be accepted.
|
||||
addParam(param, 0);
|
||||
EXPECT_NO_THROW(renderConfig())
|
||||
<< "test for zero value of '" << param << "' failed";
|
||||
}
|
||||
|
||||
|
||||
// This test verifies that all parameters for the expiration may be configured.
|
||||
TEST_F(ExpirationConfigParserTest, allParameters) {
|
||||
// Create configuration which overrides default values of all parameters.
|
||||
addParam("reclaim-timer-wait-time", 20);
|
||||
addParam("flush-reclaimed-timer-wait-time", 35);
|
||||
addParam("hold-reclaimed-time", 1800);
|
||||
addParam("max-reclaim-leases", 50);
|
||||
addParam("max-reclaim-time", 100);
|
||||
addParam("unwarned-reclaim-cycles", 10);
|
||||
|
||||
CfgExpirationPtr cfg;
|
||||
ASSERT_NO_THROW(cfg = renderConfig());
|
||||
EXPECT_EQ(20, cfg->getReclaimTimerWaitTime());
|
||||
EXPECT_EQ(35, cfg->getFlushReclaimedTimerWaitTime());
|
||||
EXPECT_EQ(1800, cfg->getHoldReclaimedTime());
|
||||
EXPECT_EQ(50, cfg->getMaxReclaimLeases());
|
||||
EXPECT_EQ(100, cfg->getMaxReclaimTime());
|
||||
EXPECT_EQ(10, cfg->getUnwarnedReclaimCycles());
|
||||
}
|
||||
|
||||
// This test verifies that default values are used if no parameter is
|
||||
// specified.
|
||||
TEST_F(ExpirationConfigParserTest, noParameters) {
|
||||
CfgExpirationPtr cfg;
|
||||
ASSERT_NO_THROW(cfg = renderConfig());
|
||||
EXPECT_EQ(CfgExpiration::DEFAULT_RECLAIM_TIMER_WAIT_TIME,
|
||||
cfg->getReclaimTimerWaitTime());
|
||||
EXPECT_EQ(CfgExpiration::DEFAULT_FLUSH_RECLAIMED_TIMER_WAIT_TIME,
|
||||
cfg->getFlushReclaimedTimerWaitTime());
|
||||
EXPECT_EQ(CfgExpiration::DEFAULT_HOLD_RECLAIMED_TIME,
|
||||
cfg->getHoldReclaimedTime());
|
||||
EXPECT_EQ(CfgExpiration::DEFAULT_MAX_RECLAIM_LEASES,
|
||||
cfg->getMaxReclaimLeases());
|
||||
EXPECT_EQ(CfgExpiration::DEFAULT_MAX_RECLAIM_TIME,
|
||||
cfg->getMaxReclaimTime());
|
||||
EXPECT_EQ(CfgExpiration::DEFAULT_UNWARNED_RECLAIM_CYCLES,
|
||||
cfg->getUnwarnedReclaimCycles());
|
||||
}
|
||||
|
||||
// This test verifies that a subset of parameters may be specified and
|
||||
// that default values are used for those that aren't specified.
|
||||
TEST_F(ExpirationConfigParserTest, someParameters) {
|
||||
addParam("reclaim-timer-wait-time", 15);
|
||||
addParam("hold-reclaimed-time", 2000);
|
||||
addParam("max-reclaim-time", 200);
|
||||
|
||||
CfgExpirationPtr cfg;
|
||||
ASSERT_NO_THROW(cfg = renderConfig());
|
||||
EXPECT_EQ(15, cfg->getReclaimTimerWaitTime());
|
||||
EXPECT_EQ(CfgExpiration::DEFAULT_FLUSH_RECLAIMED_TIMER_WAIT_TIME,
|
||||
cfg->getFlushReclaimedTimerWaitTime());
|
||||
EXPECT_EQ(2000, cfg->getHoldReclaimedTime());
|
||||
EXPECT_EQ(CfgExpiration::DEFAULT_MAX_RECLAIM_LEASES,
|
||||
cfg->getMaxReclaimLeases());
|
||||
EXPECT_EQ(200, cfg->getMaxReclaimTime());
|
||||
EXPECT_EQ(CfgExpiration::DEFAULT_UNWARNED_RECLAIM_CYCLES,
|
||||
cfg->getUnwarnedReclaimCycles());
|
||||
}
|
||||
|
||||
// This test verifies that another subset of parameters may be specified
|
||||
// and that default values are used for those that aren't specified.
|
||||
TEST_F(ExpirationConfigParserTest, otherParameters) {
|
||||
addParam("flush-reclaimed-timer-wait-time", 50);
|
||||
addParam("max-reclaim-leases", 60);
|
||||
addParam("unwarned-reclaim-cycles", 20);
|
||||
|
||||
CfgExpirationPtr cfg;
|
||||
ASSERT_NO_THROW(cfg = renderConfig());
|
||||
|
||||
EXPECT_EQ(CfgExpiration::DEFAULT_RECLAIM_TIMER_WAIT_TIME,
|
||||
cfg->getReclaimTimerWaitTime());
|
||||
EXPECT_EQ(50, cfg->getFlushReclaimedTimerWaitTime());
|
||||
EXPECT_EQ(CfgExpiration::DEFAULT_HOLD_RECLAIMED_TIME,
|
||||
cfg->getHoldReclaimedTime());
|
||||
EXPECT_EQ(60, cfg->getMaxReclaimLeases());
|
||||
EXPECT_EQ(CfgExpiration::DEFAULT_MAX_RECLAIM_TIME,
|
||||
cfg->getMaxReclaimTime());
|
||||
EXPECT_EQ(20, cfg->getUnwarnedReclaimCycles());
|
||||
}
|
||||
|
||||
// This test verifies that the exception is thrown if unsupported
|
||||
// parameter is specified.
|
||||
TEST_F(ExpirationConfigParserTest, invalidParameter) {
|
||||
addParam("reclaim-timer-wait-time", 20);
|
||||
addParam("invalid-parameter", 20);
|
||||
|
||||
EXPECT_THROW(renderConfig(), DhcpConfigError);
|
||||
}
|
||||
|
||||
// This test verifies that negative parameter values are not allowed.
|
||||
TEST_F(ExpirationConfigParserTest, outOfRangeValues) {
|
||||
testOutOfRange("reclaim-timer-wait-time",
|
||||
CfgExpiration::LIMIT_RECLAIM_TIMER_WAIT_TIME);
|
||||
testOutOfRange("flush-reclaimed-timer-wait-time",
|
||||
CfgExpiration::LIMIT_FLUSH_RECLAIMED_TIMER_WAIT_TIME);
|
||||
testOutOfRange("hold-reclaimed-time",
|
||||
CfgExpiration::LIMIT_HOLD_RECLAIMED_TIME);
|
||||
testOutOfRange("max-reclaim-leases",
|
||||
CfgExpiration::LIMIT_MAX_RECLAIM_LEASES);
|
||||
testOutOfRange("max-reclaim-time",
|
||||
CfgExpiration::LIMIT_MAX_RECLAIM_TIME);
|
||||
testOutOfRange("unwarned-reclaim-cycles",
|
||||
CfgExpiration::LIMIT_UNWARNED_RECLAIM_CYCLES);
|
||||
}
|
||||
|
||||
// This test verifies that it is not allowed to specify a value as
|
||||
// a text.
|
||||
TEST_F(ExpirationConfigParserTest, notNumberValue) {
|
||||
// The value should not be in quotes.
|
||||
std::string config = "{ \"reclaim-timer-wait-time\": \"10\" }";
|
||||
ElementPtr config_element = Element::fromJSON(config);
|
||||
|
||||
// Parse the configuration. It should throw exception.
|
||||
ExpirationConfigParser parser;
|
||||
EXPECT_THROW(parser.build(config_element), DhcpConfigError);
|
||||
}
|
||||
|
||||
} // end of anonymous namespace
|
Reference in New Issue
Block a user