]> git.ipfire.org Git - thirdparty/pdns.git/commitdiff
dnsdist: Add support for declaring TimedIP sets from YAML
authorRemi Gacogne <remi.gacogne@powerdns.com>
Tue, 4 Nov 2025 10:08:44 +0000 (11:08 +0100)
committerRemi Gacogne <remi.gacogne@powerdns.com>
Thu, 13 Nov 2025 09:42:19 +0000 (10:42 +0100)
Signed-off-by: Remi Gacogne <remi.gacogne@powerdns.com>
pdns/dnsdistdist/dnsdist-configuration-yaml.cc
pdns/dnsdistdist/dnsdist-rust-bridge.hh
pdns/dnsdistdist/dnsdist-rust-lib/rust-middle-in.rs
pdns/dnsdistdist/dnsdist-rust-lib/rust-post-in.rs
pdns/dnsdistdist/dnsdist-selectors-definitions.yml
pdns/dnsdistdist/dnsdist-settings-definitions.yml

index da4503ad650b4bff50497a6be11d3cd8cd94e0f1..078dc726460b43d316afa0dcb8398768e6ef6e60 100644 (file)
@@ -62,7 +62,7 @@ namespace dnsdist::configuration::yaml
 
 using XSKMap = std::vector<std::shared_ptr<XskSocket>>;
 
-using RegisteredTypes = std::variant<std::shared_ptr<DNSDistPacketCache>, std::shared_ptr<dnsdist::rust::settings::DNSSelector>, std::shared_ptr<dnsdist::rust::settings::DNSActionWrapper>, std::shared_ptr<dnsdist::rust::settings::DNSResponseActionWrapper>, std::shared_ptr<NetmaskGroup>, std::shared_ptr<KeyValueStore>, std::shared_ptr<KeyValueLookupKey>, std::shared_ptr<RemoteLoggerInterface>, std::shared_ptr<ServerPolicy>, std::shared_ptr<XSKMap>>;
+using RegisteredTypes = std::variant<std::shared_ptr<DNSDistPacketCache>, std::shared_ptr<dnsdist::rust::settings::DNSSelector>, std::shared_ptr<dnsdist::rust::settings::DNSActionWrapper>, std::shared_ptr<dnsdist::rust::settings::DNSResponseActionWrapper>, std::shared_ptr<NetmaskGroup>, std::shared_ptr<KeyValueStore>, std::shared_ptr<KeyValueLookupKey>, std::shared_ptr<RemoteLoggerInterface>, std::shared_ptr<ServerPolicy>, std::shared_ptr<TimedIPSetRule>, std::shared_ptr<XSKMap>>;
 static LockGuarded<std::unordered_map<std::string, RegisteredTypes>> s_registeredTypesMap;
 static std::atomic<bool> s_inConfigCheckMode;
 static std::atomic<bool> s_inClientMode;
@@ -1265,7 +1265,7 @@ bool loadConfigurationFromFile(const std::string& fileName, [[maybe_unused]] boo
 void addLuaBindingsForYAMLObjects([[maybe_unused]] LuaContext& luaCtx)
 {
 #if defined(HAVE_YAML_CONFIGURATION)
-  using ReturnValue = boost::optional<boost::variant<std::shared_ptr<DNSDistPacketCache>, std::shared_ptr<DNSRule>, std::shared_ptr<DNSAction>, std::shared_ptr<DNSResponseAction>, std::shared_ptr<NetmaskGroup>, std::shared_ptr<KeyValueStore>, std::shared_ptr<KeyValueLookupKey>, std::shared_ptr<RemoteLoggerInterface>, std::shared_ptr<ServerPolicy>, std::shared_ptr<XSKMap>>>;
+  using ReturnValue = boost::optional<boost::variant<std::shared_ptr<DNSDistPacketCache>, std::shared_ptr<DNSRule>, std::shared_ptr<DNSAction>, std::shared_ptr<DNSResponseAction>, std::shared_ptr<NetmaskGroup>, std::shared_ptr<KeyValueStore>, std::shared_ptr<KeyValueLookupKey>, std::shared_ptr<RemoteLoggerInterface>, std::shared_ptr<ServerPolicy>, std::shared_ptr<TimedIPSetRule>, std::shared_ptr<XSKMap>>>;
 
   luaCtx.writeFunction("getObjectFromYAMLConfiguration", [](const std::string& name) -> ReturnValue {
     auto map = s_registeredTypesMap.lock();
@@ -1300,6 +1300,9 @@ void addLuaBindingsForYAMLObjects([[maybe_unused]] LuaContext& luaCtx)
     if (auto* ptr = std::get_if<std::shared_ptr<ServerPolicy>>(&item->second)) {
       return ReturnValue(*ptr);
     }
+    if (auto* ptr = std::get_if<std::shared_ptr<TimedIPSetRule>>(&item->second)) {
+      return ReturnValue(*ptr);
+    }
     if (auto* ptr = std::get_if<std::shared_ptr<XSKMap>>(&item->second)) {
       return ReturnValue(*ptr);
     }
@@ -1636,6 +1639,16 @@ std::shared_ptr<DNSSelector> getKeyValueStoreRangeLookupSelector([[maybe_unused]
 #endif
 }
 
+std::shared_ptr<DNSSelector> getTimedIPSetSelector(const TimedIPSetSelectorConfiguration& config)
+{
+  auto obj = dnsdist::configuration::yaml::getRegisteredTypeByName<TimedIPSetRule>(std::string(config.set_name));
+  if (!obj) {
+    throw std::runtime_error("Uanble to find a timed IP set named '" + std::string(config.set_name));
+  }
+  auto selector = std::dynamic_pointer_cast<DNSRule>(obj);
+  return newDNSSelector(std::move(selector), config.name);
+}
+
 std::shared_ptr<DNSActionWrapper> getDnstapLogAction([[maybe_unused]] const DnstapLogActionConfiguration& config)
 {
 #if defined(DISABLE_PROTOBUF) || !defined(HAVE_FSTRM)
@@ -1870,6 +1883,17 @@ void registerNMGObjects(const ::rust::Vec<NetmaskGroupConfiguration>& nmgs)
   }
 }
 
+void registerTimedIPSetObjects(const ::rust::Vec<TimedIpSetConfiguration>& sets)
+{
+  for (const auto& timedIPSet : sets) {
+    auto obj = dnsdist::configuration::yaml::getRegisteredTypeByName<TimedIPSetRule>(std::string(timedIPSet.name));
+    if (!obj) {
+      obj = std::make_shared<TimedIPSetRule>();
+      dnsdist::configuration::yaml::registerType<TimedIPSetRule>(obj, timedIPSet.name);
+    }
+  }
+}
+
 std::shared_ptr<DNSSelector> getLuaSelector(const LuaSelectorConfiguration& config)
 {
   dnsdist::selectors::LuaSelectorFunction function;
index 73071aea5671af3b1ea9a52134b07437b45f1853..be86c01e1446d94ec3618874e7b5b6208b5cf543 100644 (file)
@@ -34,11 +34,13 @@ struct ProtobufLoggerConfiguration;
 struct DnstapLoggerConfiguration;
 struct KeyValueStoresConfiguration;
 struct NetmaskGroupConfiguration;
+struct TimedIpSetConfiguration;
 
 void registerProtobufLogger(const ProtobufLoggerConfiguration& config);
 void registerDnstapLogger(const DnstapLoggerConfiguration& config);
 void registerKVSObjects(const KeyValueStoresConfiguration& config);
 void registerNMGObjects(const ::rust::Vec<NetmaskGroupConfiguration>& nmgs);
+void registerTimedIPSetObjects(const ::rust::Vec<TimedIpSetConfiguration>& sets);
 
 #include "dnsdist-rust-bridge-actions-generated.hh"
 #include "dnsdist-rust-bridge-selectors-generated.hh"
index 8e12ed8e78a072712c1fdc993a27d6409a75b0cf..8bfac01e27df3240ef0c9c014c9389874aae7c1b 100644 (file)
@@ -16,6 +16,7 @@
         fn registerDnstapLogger(config: &DnstapLoggerConfiguration);
         fn registerKVSObjects(config: &KeyValueStoresConfiguration);
         fn registerNMGObjects(nmgs: &Vec<NetmaskGroupConfiguration>);
+        fn registerTimedIPSetObjects(sets: &Vec<TimedIpSetConfiguration>);
     }
 }
 
index 0b5c5123d5fb964df1e199ff2f135eab4e06f77f..796284a8f0b13c2a7ee85b676d1b9167ff524ef2 100644 (file)
@@ -83,6 +83,7 @@ fn get_global_configuration_from_serde(
     config.ring_buffers = serde.ring_buffers;
     config.security_polling = serde.security_polling;
     config.snmp = serde.snmp;
+    config.timed_ip_sets = serde.timed_ip_sets;
     config.tuning = serde.tuning;
     config.webserver = serde.webserver;
     config.xsk = serde.xsk;
@@ -92,6 +93,8 @@ fn get_global_configuration_from_serde(
     dnsdistsettings::registerKVSObjects(&config.key_value_stores);
     // this needs to be done before the rules so that they can refer to the NMG objects
     dnsdistsettings::registerNMGObjects(&config.netmask_groups);
+    // this needs to be done before the rules so that they can refer to the TimeIPSet objects
+    dnsdistsettings::registerTimedIPSetObjects(&config.timed_ip_sets);
     // this needs to be done BEFORE the rules so that they can refer to the selectors
     // by name
     config.selectors = get_selectors_from_serde(&serde.selectors)?;
index 9430c97a4765f121b22c1b1d78108b917d1ea705..06250af11fdb9ff59a75aed75904b557235ec75c 100644 (file)
@@ -420,5 +420,13 @@ Set the ``source`` parameter to ``false`` to match against destination address i
     - name: "tcp"
       type: "bool"
       description: "Match TCP traffic if true, UDP traffic if false"
+- name: "TimedIPSet"
+  skip-cpp: true
+  skip-rust: true
+  description: "Can be used to handle IP addresses differently for a certain time"
+  parameters:
+    - name: "set_name"
+      type: "String"
+      description: "The Timed IP set to use"
 - name: "TrailingData"
   description: "Matches if the query has trailing data"
index b0f7a70b3cf2b34acbe9dd4768eb2e68ece92dc1..410f0500af7d0bbd2e894b1c6da40b4e65a72510 100644 (file)
@@ -129,6 +129,10 @@ global:
       type: "SnmpConfiguration"
       default: true
       description: "SNMP-related settings"
+    - name: "timed_ip_sets"
+      type: "Vec<TimedIpSetConfiguration>"
+      default: true
+      description: "Runtime-modifiable IP address sets"
     - name: "tuning"
       type: "TuningConfiguration"
       default: true
@@ -2169,6 +2173,13 @@ response_rule:
       type: "ResponseAction"
       description: "The action taken if the selector matches"
 
+timed_ip_set:
+  description: "Runtime-modifiable IP address set"
+  parameters:
+    - name: "name"
+      type: "String"
+      description: "The name of this set"
+
 xsk:
   description: "An ``XSK`` / ``AF_XDP`` sockets map"
   parameters: