]> git.ipfire.org Git - thirdparty/kea.git/commitdiff
[#2785] Almost done
authorFrancis Dupont <fdupont@isc.org>
Tue, 21 Mar 2023 11:06:34 +0000 (12:06 +0100)
committerFrancis Dupont <fdupont@isc.org>
Fri, 24 Mar 2023 08:55:52 +0000 (09:55 +0100)
doc/examples/kea4/all-keys.json
doc/sphinx/arm/dhcp4-srv.rst
src/bin/dhcp4/dhcp4_srv.cc
src/bin/dhcp4/json_config_parser.cc
src/bin/dhcp4/tests/config_parser_unittest.cc
src/bin/dhcp4/tests/get_config_unittest.cc
src/lib/dhcpsrv/srv_config.cc
src/lib/dhcpsrv/srv_config.h
src/lib/dhcpsrv/tests/srv_config_unittest.cc

index 86f5038659be9a73bcd637ec073f5fb4f1ac3dd9..005438ecb0c23f70f9e44c489321348535c00d72 100644 (file)
         // Parameters for triggering behaviors compatible with broken or
         // non-compliant clients, relays or other agents
         "compatibility": {
+            // Ignore DHCP Server Identifier option if set to true.
+            // Enabling this will cause Kea to accept any query even
+            // if the address in the option belongs to another server
+            // instead of dropping it. This config option defaults to
+            // false, as enabling it breaks RFC compliance.
+            "ignore-dhcp-server-identifier": false,
+
             // Ignore Relay Agent Information Link Selection suboption if set
             // to true. Enabling this will cause Kea use normal subnet
             // selection logic instead of attempting to use the subnet
index 8e8777d308354fc511d456b9ec43acb39569940e..7e4184a655d28c0cdf345a6c30ff35a2264ebcb7 100644 (file)
@@ -1521,8 +1521,8 @@ Parameter Request List option (or its equivalent for vendor options):
 
 
 In the example above, the ``domain-name-servers`` option respects the global
-``always-send`` flag and is always added to responses, but for subnet 
-``192.0.3.0/24``, the value is taken from the subnet-level option data 
+``always-send`` flag and is always added to responses, but for subnet
+``192.0.3.0/24``, the value is taken from the subnet-level option data
 specification.
 
 At the opposite of ``always-send`` if the ``never-send`` flag is set to
@@ -7638,6 +7638,24 @@ or in terms of the log message above, the tuple length ``y`` becomes ``x``.
       }
     }
 
+Ignore DHCP Server Identifier
+-----------------------------
+
+With ``"ignore-dhcp-server-identifier": true``, the server does not check the
+address in the DHCP Server Identifier option i.e. whether a query is sent
+to this server or another one (and in the second case dropping the query).
+
+.. code-block:: json
+
+    {
+      "Dhcp4": {
+        "compatibility": {
+          "ignore-dhcp-server-identifier": true
+        }
+      }
+    }
+
+
 Ignore RAI Link Selection
 -------------------------
 
index 8431c2750d62ed059d5999914bccfde3c6048c2b..8a63102ff95ddbb7f9e1ae840b3d9141755db07e 100644 (file)
@@ -4036,6 +4036,12 @@ Dhcpv4Srv::acceptServerId(const Pkt4Ptr& query) const {
         }
     }
 
+    // Skip address check if configured to ignore the server id.
+    SrvConfigPtr cfg = CfgMgr::instance().getCurrentCfg();
+    if (cfg->getIgnoreServerIdentifier()) {
+        return (true);
+    }
+
     // This function iterates over all interfaces on which the
     // server is listening to find the one which has a socket bound
     // to the address carried in the server identifier option.
@@ -4067,8 +4073,6 @@ Dhcpv4Srv::acceptServerId(const Pkt4Ptr& query) const {
     /// know the reservations for the client communicating with the server.
     /// We may revise some of these choices in the future.
 
-    SrvConfigPtr cfg = CfgMgr::instance().getCurrentCfg();
-
     // Check if there is at least one subnet configured with this server
     // identifier.
     ConstCfgSubnets4Ptr cfg_subnets = cfg->getCfgSubnets4();
index fd0378ced0f656b5bfeef9f40d5785d0f25b8664..09466e89b3ec0fcd53d1de249b6f8a143ff47c83 100644 (file)
@@ -584,6 +584,9 @@ processDhcp4Config(isc::data::ConstElementPtr config_set) {
                 if (kv.first == "lenient-option-parsing") {
                     CfgMgr::instance().getStagingCfg()->setLenientOptionParsing(
                         kv.second->boolValue());
+                } else if (kv.first == "ignore-dhcp-server-identifier") {
+                    CfgMgr::instance().getStagingCfg()->setIgnoreServerIdentifier(
+                        kv.second->boolValue());
                 } else if (kv.first == "ignore-rai-link-selection") {
                     CfgMgr::instance().getStagingCfg()->setIgnoreRAILinkSelection(
                         kv.second->boolValue());
index 4077ce15dbf5ae13f149963d895b7b0501e6835d..271185129aed5414aabc977fcff7f2d84af3effa 100644 (file)
@@ -1701,6 +1701,7 @@ TEST_F(Dhcp4ParserTest, compatibility) {
         "\"renew-timer\": 1000, "
         "\"compatibility\": { "
         "    \"lenient-option-parsing\": true,"
+        "    \"ignore-dhcp-server-identifier\": true,"
         "    \"ignore-rai-link-selection\": true,"
         "    \"exclude-first-last-24\": true"
         "},"
@@ -1715,6 +1716,7 @@ TEST_F(Dhcp4ParserTest, compatibility) {
 
     // Check defaults: they should be false.
     EXPECT_FALSE(CfgMgr::instance().getStagingCfg()->getLenientOptionParsing());
+    EXPECT_FALSE(CfgMgr::instance().getStagingCfg()->getIgnoreServerIdentifier());
     EXPECT_FALSE(CfgMgr::instance().getStagingCfg()->getIgnoreRAILinkSelection());
     EXPECT_FALSE(CfgMgr::instance().getStagingCfg()->getExcludeFirstLast24());
 
@@ -1724,6 +1726,7 @@ TEST_F(Dhcp4ParserTest, compatibility) {
     checkResult(status, 0);
 
     EXPECT_TRUE(CfgMgr::instance().getStagingCfg()->getLenientOptionParsing());
+    EXPECT_TRUE(CfgMgr::instance().getStagingCfg()->getIgnoreServerIdentifier());
     EXPECT_TRUE(CfgMgr::instance().getStagingCfg()->getIgnoreRAILinkSelection());
     EXPECT_TRUE(CfgMgr::instance().getStagingCfg()->getExcludeFirstLast24());
 }
index be9b62dc69eece28f9ce0b5f0d84a79edc9bf4be..782b64c318c8f81c22cd5cf241a0bd150c123a26 100644 (file)
@@ -351,6 +351,7 @@ const char* EXTRACTED_CONFIGS[] = {
 "{\n"
 "        \"compatibility\": {\n"
 "            \"exclude-first-last-24\": true,\n"
+"            \"ignore-dhcp-server-identifier\": true,\n"
 "            \"ignore-rai-link-selection\": true,\n"
 "            \"lenient-option-parsing\": true\n"
 "        },\n"
@@ -3772,6 +3773,7 @@ const char* UNPARSED_CONFIGS[] = {
 "        \"calculate-tee-times\": false,\n"
 "        \"compatibility\": {\n"
 "            \"exclude-first-last-24\": true,\n"
+"            \"ignore-dhcp-server-identifier\": true,\n"
 "            \"ignore-rai-link-selection\": true,\n"
 "            \"lenient-option-parsing\": true\n"
 "        },\n"
index 6d1df21612b43c882f1ac0fbaaaad198dfecaa01..b44d410baf646b06019bf9e3b767ad25bfc5b67f 100644 (file)
@@ -47,8 +47,9 @@ SrvConfig::SrvConfig()
       decline_timer_(0), echo_v4_client_id_(true), dhcp4o6_port_(0),
       d2_client_config_(new D2ClientConfig()),
       configured_globals_(new CfgGlobals()), cfg_consist_(new CfgConsistency()),
-      lenient_option_parsing_(false), ignore_rai_link_selection_(false),
-      exclude_first_last_24_(false), reservations_lookup_first_(false) {
+      lenient_option_parsing_(false), ignore_dhcp_server_identifier_(false),
+      ignore_rai_link_selection_(false), exclude_first_last_24_(false),
+      reservations_lookup_first_(false) {
 }
 
 SrvConfig::SrvConfig(const uint32_t sequence)
@@ -66,8 +67,9 @@ SrvConfig::SrvConfig(const uint32_t sequence)
       decline_timer_(0), echo_v4_client_id_(true), dhcp4o6_port_(0),
       d2_client_config_(new D2ClientConfig()),
       configured_globals_(new CfgGlobals()), cfg_consist_(new CfgConsistency()),
-      lenient_option_parsing_(false), ignore_rai_link_selection_(false),
-      exclude_first_last_24_(false), reservations_lookup_first_(false) {
+      lenient_option_parsing_(false), ignore_dhcp_server_identifier_(false),
+      ignore_rai_link_selection_(false), exclude_first_last_24_(false),
+      reservations_lookup_first_(false) {
 }
 
 std::string
@@ -637,6 +639,9 @@ SrvConfig::toElement() const {
     if (getLenientOptionParsing()) {
         compatibility->set("lenient-option-parsing", Element::create(true));
     }
+    if (getIgnoreServerIdentifier()) {
+        compatibility->set("ignore-dhcp-server-identifier", Element::create(true));
+    }
     if (getIgnoreRAILinkSelection()) {
         compatibility->set("ignore-rai-link-selection", Element::create(true));
     }
index ab5e8da0b2bf571606cf6dc3f28c8b65de078232..4790341735a6dc2caf5e1ef599f08a7b2d8e4fbe 100644 (file)
@@ -991,6 +991,21 @@ public:
         return lenient_option_parsing_;
     }
 
+    /// @brief Set ignore DHCP Server Identifier compatibility flag.
+    ///
+    /// @param value the boolean value to be set when configuring DHCP
+    /// Server Identifier usage preferences.
+    void setIgnoreServerIdentifier(bool const value) {
+        ignore_dhcp_server_identifier_ = value;
+    }
+
+    /// @brief Get ignore DHCP Server Identifier compatibility flag.
+    ///
+    /// @return the configured value for DHCP Server Identifier usage preferences.
+    bool getIgnoreServerIdentifier() const {
+        return (ignore_dhcp_server_identifier_);
+    }
+
     /// @brief Set ignore RAI Link Selection compatibility flag.
     ///
     /// @param value the boolean value to be set when configuring RAI Link
@@ -1187,6 +1202,8 @@ private:
     //@{
     /// @brief Indicates whether lenient option parsing is enabled
     bool lenient_option_parsing_;
+    /// @brief Indicates whether DHCP server identifier option will be ignored
+    bool ignore_dhcp_server_identifier_;
     /// @brief Indicates whether RAI link-selection suboptions will be ignored
     bool ignore_rai_link_selection_;
     /// @brief Indicates whether exclude .0 .255 from subnets bigger than /24.
index 3935cdc8dc97c75859977b5f9428b87a4964f7ca..67150a578c58ca5cd19e68bea0f7a468156a154e 100644 (file)
@@ -315,28 +315,34 @@ TEST_F(SrvConfigTest, compatibility) {
 
     // Check that defaults are false.
     EXPECT_FALSE(conf.getLenientOptionParsing());
+    EXPECT_FALSE(conf.getIgnoreServerIdentifier());
     EXPECT_FALSE(conf.getIgnoreRAILinkSelection());
     EXPECT_FALSE(conf.getExcludeFirstLast24());
 
     // Check that they can be modified to true.
     conf.setLenientOptionParsing(true);
+    conf.setIgnoreServerIdentifier(true);
     conf.setIgnoreRAILinkSelection(true);
     conf.setExcludeFirstLast24(true);
     EXPECT_TRUE(conf.getLenientOptionParsing());
+    EXPECT_TRUE(conf.getIgnoreServerIdentifier());
     EXPECT_TRUE(conf.getIgnoreRAILinkSelection());
     EXPECT_TRUE(conf.getExcludeFirstLast24());
 
     // Check that default values can be restored.
     conf.setLenientOptionParsing(false);
+    conf.setIgnoreServerIdentifier(false);
     conf.setIgnoreRAILinkSelection(false);
     conf.setExcludeFirstLast24(false);
     EXPECT_FALSE(conf.getLenientOptionParsing());
+    EXPECT_FALSE(conf.getIgnoreServerIdentifier());
     EXPECT_FALSE(conf.getIgnoreRAILinkSelection());
     EXPECT_FALSE(conf.getExcludeFirstLast24());
 
     // Check the other constructor has the same default.
     SrvConfig conf1(1);
     EXPECT_FALSE(conf1.getLenientOptionParsing());
+    EXPECT_FALSE(conf.getIgnoreServerIdentifier());
     EXPECT_FALSE(conf1.getIgnoreRAILinkSelection());
     EXPECT_FALSE(conf1.getExcludeFirstLast24());
 }