From: Marcin Siodelski Date: Tue, 9 Jun 2015 10:35:14 +0000 (+0200) Subject: [3070] Parse rapid-commit parameter for subnet6. X-Git-Tag: trac3732a_base~15^2~7 X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=87d22f85c39e41f5dcd88be7958dde3f0bc195b0;p=thirdparty%2Fkea.git [3070] Parse rapid-commit parameter for subnet6. --- diff --git a/src/bin/dhcp6/dhcp6.spec b/src/bin/dhcp6/dhcp6.spec index 609f368240..e0fa45be45 100644 --- a/src/bin/dhcp6/dhcp6.spec +++ b/src/bin/dhcp6/dhcp6.spec @@ -245,6 +245,12 @@ "item_default": "" }, + { "item_name": "rapid-commit", + "item_type": "boolean", + "item_optional": false, + "item_default": false + }, + { "item_name": "renew-timer", "item_type": "integer", "item_optional": false, diff --git a/src/bin/dhcp6/json_config_parser.cc b/src/bin/dhcp6/json_config_parser.cc index 9e0589f367..54b3190a8f 100644 --- a/src/bin/dhcp6/json_config_parser.cc +++ b/src/bin/dhcp6/json_config_parser.cc @@ -404,6 +404,8 @@ protected: parser = new PdPoolListParser(config_id, pools_); } else if (config_id.compare("option-data") == 0) { parser = new OptionDataListParser(config_id, options_, AF_INET6); + } else if (config_id.compare("rapid-commit") == 0) { + parser = new BooleanParser(config_id, boolean_values_); } else { isc_throw(NotImplemented, "unsupported parameter: " << config_id); } @@ -473,12 +475,16 @@ protected: } } - stringstream tmp; - tmp << addr << "/" << static_cast(len) - << " with params t1=" << t1 << ", t2=" << t2 << ", pref=" - << pref << ", valid=" << valid; + bool rapid_commit = boolean_values_->getOptionalParam("rapid-commit", false); - LOG_INFO(dhcp6_logger, DHCP6_CONFIG_NEW_SUBNET).arg(tmp.str()); + std::ostringstream output; + output << addr << "/" << static_cast(len) + << " with params t1=" << t1 << ", t2=" + << t2 << ", preferred-lifetime=" << pref + << ", valid-lifetime=" << valid + << ", rapid-commit is " << (rapid_commit ? "enabled" : "disabled"); + + LOG_INFO(dhcp6_logger, DHCP6_CONFIG_NEW_SUBNET).arg(output.str()); // Create a new subnet. Subnet6* subnet6 = new Subnet6(addr, len, t1, t2, pref, valid, @@ -491,6 +497,9 @@ protected: subnet6->setInterfaceId(opt); } + // Enable or disable Rapid Commit option support for the subnet. + subnet6->setRapidCommit(rapid_commit); + // Try setting up client class (if specified) try { string client_class = string_values_->getParam("client-class"); diff --git a/src/bin/dhcp6/tests/config_parser_unittest.cc b/src/bin/dhcp6/tests/config_parser_unittest.cc index bb0a7bbb8e..7c3e3b1bca 100644 --- a/src/bin/dhcp6/tests/config_parser_unittest.cc +++ b/src/bin/dhcp6/tests/config_parser_unittest.cc @@ -495,6 +495,38 @@ public: CfgMgr::instance().clear(); } + /// @brief Tests teh Rapid Commit configuration for a subnet. + /// + /// This test configures the server with a given configuration and + /// verifies if the Rapid Commit has been configured successfully + /// for a subnet. + /// + /// @param config Server configuration, possibly including the + /// 'rapid-commit' parameter. + /// @param exp_rapid_commit Expected value of the Rapid Commit flag + /// within a subnet. + void testRapidCommit(const std::string& config, + const bool exp_rapid_commit) { + // Clear any existing configuration. + CfgMgr::instance().clear(); + + // Configure the server. + ElementPtr json = Element::fromJSON(config); + + // Make sure that the configuration was successful. + ConstElementPtr status; + EXPECT_NO_THROW(status = configureDhcp6Server(srv_, json)); + checkResult(status, 0); + + // Get the subnet. + Subnet6Ptr subnet = CfgMgr::instance().getStagingCfg()->getCfgSubnets6()-> + selectSubnet(IOAddress("2001:db8:1::5"), classify_); + ASSERT_TRUE(subnet); + + // Check the Rapid Commit flag for the subnet. + EXPECT_EQ(exp_rapid_commit, subnet->getRapidCommit()); + } + int rcode_; ///< Return code (see @ref isc::config::parseAnswer) Dhcpv6Srv srv_; ///< Instance of the Dhcp6Srv used during tests ConstElementPtr comment_; ///< Comment (see @ref isc::config::parseAnswer) @@ -1088,6 +1120,54 @@ TEST_F(Dhcp6ParserTest, subnetInterfaceAndInterfaceId) { EXPECT_TRUE(errorContainsPosition(status, "")); } +// This test checks the configuration of the Rapid Commit option +// support for the subnet. +TEST_F(Dhcp6ParserTest, subnetRapidCommit) { + { + // rapid-commit implicitly set to false. + SCOPED_TRACE("Default Rapid Commit setting"); + testRapidCommit("{ \"preferred-lifetime\": 3000," + "\"rebind-timer\": 2000, " + "\"renew-timer\": 1000, " + "\"subnet6\": [ { " + " \"pools\": [ { \"pool\": \"2001:db8:1::1 - " + "2001:db8:1::ffff\" } ]," + " \"subnet\": \"2001:db8:1::/64\" } ]," + "\"valid-lifetime\": 4000 }", + false); + } + + { + SCOPED_TRACE("Enable Rapid Commit"); + // rapid-commit explicitly set to true. + testRapidCommit("{ \"preferred-lifetime\": 3000," + "\"rebind-timer\": 2000, " + "\"renew-timer\": 1000, " + "\"subnet6\": [ { " + " \"pools\": [ { \"pool\": \"2001:db8:1::1 - " + "2001:db8:1::ffff\" } ]," + " \"rapid-commit\": True," + " \"subnet\": \"2001:db8:1::/64\" } ]," + "\"valid-lifetime\": 4000 }", + true); + } + + { + SCOPED_TRACE("Disable Rapid Commit"); + // rapid-commit explicitly set to false. + testRapidCommit("{ \"preferred-lifetime\": 3000," + "\"rebind-timer\": 2000, " + "\"renew-timer\": 1000, " + "\"subnet6\": [ { " + " \"pools\": [ { \"pool\": \"2001:db8:1::1 - " + "2001:db8:1::ffff\" } ]," + " \"rapid-commit\": False," + " \"subnet\": \"2001:db8:1::/64\" } ]," + "\"valid-lifetime\": 4000 }", + false); + } +} + // This test checks that multiple pools can be defined and handled properly. // The test defines 2 subnets, each with 2 pools. TEST_F(Dhcp6ParserTest, multiplePools) { diff --git a/src/lib/dhcpsrv/parsers/dhcp_parsers.cc b/src/lib/dhcpsrv/parsers/dhcp_parsers.cc index 68da05f44a..f6b293e2f9 100644 --- a/src/lib/dhcpsrv/parsers/dhcp_parsers.cc +++ b/src/lib/dhcpsrv/parsers/dhcp_parsers.cc @@ -1030,10 +1030,9 @@ PoolParser::commit() { SubnetConfigParser::SubnetConfigParser(const std::string&, ParserContextPtr global_context, const isc::asiolink::IOAddress& default_addr) - : uint32_values_(new Uint32Storage()), - string_values_(new StringStorage()), - boolean_values_(new BooleanStorage()), - pools_(new PoolStorage()), global_context_(global_context), + : boolean_values_(new BooleanStorage()), uint32_values_(new Uint32Storage()), + string_values_(new StringStorage()), pools_(new PoolStorage()), + global_context_(global_context), relay_info_(new isc::dhcp::Subnet::RelayInfo(default_addr)), options_(new CfgOption()) { // The first parameter should always be "subnet", but we don't check diff --git a/src/lib/dhcpsrv/parsers/dhcp_parsers.h b/src/lib/dhcpsrv/parsers/dhcp_parsers.h index efed05e61a..fe55a099e6 100644 --- a/src/lib/dhcpsrv/parsers/dhcp_parsers.h +++ b/src/lib/dhcpsrv/parsers/dhcp_parsers.h @@ -1057,6 +1057,9 @@ private: protected: + /// Storage for subnet-specific boolean values. + BooleanStoragePtr boolean_values_; + /// Storage for subnet-specific integer values. Uint32StoragePtr uint32_values_;