]> granicus.if.org Git - pdns/commitdiff
rec: Add support for RPZ wildcarded target names
authorRemi Gacogne <remi.gacogne@powerdns.com>
Sun, 23 Apr 2017 18:56:36 +0000 (20:56 +0200)
committerRemi Gacogne <remi.gacogne@powerdns.com>
Sun, 23 Apr 2017 19:31:35 +0000 (21:31 +0200)
pdns/filterpo.cc
pdns/filterpo.hh
pdns/pdns_recursor.cc
regression-tests.recursor/RPZ/command
regression-tests.recursor/RPZ/expected_result
regression-tests.recursor/config.sh

index d87c55ccc02020713060f5a96af2857ca73756c6..09bc0bec7c53c22359555b5b32a3e853899d6e41 100644 (file)
@@ -244,3 +244,31 @@ bool DNSFilterEngine::rmNSIPTrigger(const Netmask& nm, Policy pol, size_t zone)
   pols.erase(nm);
   return true;
 }
+
+DNSRecord DNSFilterEngine::Policy::getCustomRecord(const DNSName& qname) const
+{
+  if (d_kind != PolicyKind::Custom) {
+    throw std::runtime_error("Asking for a custom record from a filtering policy of a non-custom type");
+  }
+
+  DNSRecord result;
+  result.d_name = qname;
+  result.d_type = d_custom->getType();
+  result.d_ttl = d_ttl;
+  result.d_class = QClass::IN;
+  result.d_place = DNSResourceRecord::ANSWER;
+  result.d_content = d_custom;
+
+  if (result.d_type == QType::CNAME) {
+    const auto content = std::dynamic_pointer_cast<CNAMERecordContent>(d_custom);
+    if (content) {
+      DNSName target = content->getTarget();
+      if (target.isWildcard()) {
+        target.chopOff();
+        result.d_content = std::make_shared<CNAMERecordContent>(qname + target);
+      }
+    }
+  }
+
+  return result;
+}
index fb9ee4c1c44c1379bc5ba25f613ab6875ab3319a..68ad7d8b2e0b95786eef29ecbeddc429091e154b 100644 (file)
@@ -74,6 +74,7 @@ public:
     {
       return d_kind == rhs.d_kind; // XXX check d_custom too!
     }
+    DNSRecord getCustomRecord(const DNSName& qname) const;
     PolicyKind d_kind;
     std::shared_ptr<DNSRecordContent> d_custom;
     std::shared_ptr<std::string> d_name;
index 8db27972925ab477fbb8865ecdbf185a62f92d1f..a97b3a661562e9695aa02c7a351d084e796feed8 100644 (file)
@@ -862,12 +862,7 @@ static void startDoResolve(void *p)
           case DNSFilterEngine::PolicyKind::Custom:
             g_stats.policyResults[appliedPolicy.d_kind]++;
             res=RCode::NoError;
-            spoofed.d_name=dc->d_mdp.d_qname;
-            spoofed.d_type=appliedPolicy.d_custom->getType();
-            spoofed.d_ttl = appliedPolicy.d_ttl;
-            spoofed.d_class = 1;
-            spoofed.d_content = appliedPolicy.d_custom;
-            spoofed.d_place = DNSResourceRecord::ANSWER;
+            spoofed=appliedPolicy.getCustomRecord(dc->d_mdp.d_qname);
             ret.push_back(spoofed);
             handleRPZCustom(spoofed, QType(dc->d_mdp.d_qtype), sr, res, ret);
             goto haveAnswer;
@@ -927,12 +922,7 @@ static void startDoResolve(void *p)
           case DNSFilterEngine::PolicyKind::Custom:
             ret.clear();
             res=RCode::NoError;
-            spoofed.d_name=dc->d_mdp.d_qname;
-            spoofed.d_type=appliedPolicy.d_custom->getType();
-            spoofed.d_ttl = appliedPolicy.d_ttl;
-            spoofed.d_class = 1;
-            spoofed.d_content = appliedPolicy.d_custom;
-            spoofed.d_place = DNSResourceRecord::ANSWER;
+            spoofed=appliedPolicy.getCustomRecord(dc->d_mdp.d_qname);
             ret.push_back(spoofed);
             handleRPZCustom(spoofed, QType(dc->d_mdp.d_qtype), sr, res, ret);
             goto haveAnswer;
@@ -992,12 +982,7 @@ static void startDoResolve(void *p)
           case DNSFilterEngine::PolicyKind::Custom:
             ret.clear();
             res=RCode::NoError;
-            spoofed.d_name=dc->d_mdp.d_qname;
-            spoofed.d_type=appliedPolicy.d_custom->getType();
-            spoofed.d_ttl = appliedPolicy.d_ttl;
-            spoofed.d_class = 1;
-            spoofed.d_content = appliedPolicy.d_custom;
-            spoofed.d_place = DNSResourceRecord::ANSWER;
+            spoofed=appliedPolicy.getCustomRecord(dc->d_mdp.d_qname);
             ret.push_back(spoofed);
             handleRPZCustom(spoofed, QType(dc->d_mdp.d_qtype), sr, res, ret);
             goto haveAnswer;
index 420c8969f64efa7b2d9f836d2df36949a9741697..6de706fe8a8347be2202e65ba032bd053ae103f2 100755 (executable)
@@ -32,3 +32,5 @@ echo "==> unsupported2.example.net has an unsupported target, should be ignored
 $SDIG $nameserver 5301 unsupported2.example.net a recurse 2>&1
 echo "==> not-rpz.example.net is _not_ an RPZ target and should be processed"
 $SDIG $nameserver 5301 not-rpz.example.net a recurse 2>&1
+echo "==> echo-me.wildcard-target.example.net is an RPZ wildcard target"
+$SDIG $nameserver 5301 echo-me.wildcard-target.example.net a recurse 2>&1
index d385d00c930246c51917b63e91a6d0064ccd53fe..53fd203f0d7f23d50c3761f53f92e3af94443e5e 100644 (file)
@@ -64,3 +64,7 @@ Rcode: 3 (Non-Existent domain), RD: 1, QR: 1, TC: 0, AA: 0, opcode: 0
 Reply to question for qname='not-rpz.example.net.', qtype=A
 Rcode: 3 (Non-Existent domain), RD: 1, QR: 1, TC: 0, AA: 0, opcode: 0
 0      not-rpz.example.net.    IN      CNAME   5       rpz-not.com.
+==> echo-me.wildcard-target.example.net is an RPZ wildcard target
+Reply to question for qname='echo-me.wildcard-target.example.net.', qtype=A
+Rcode: 3 (Non-Existent domain), RD: 1, QR: 1, TC: 0, AA: 0, opcode: 0
+0      echo-me.wildcard-target.example.net.    IN      CNAME   7200    echo-me.wildcard-target.example.net.walled-garden.example.net.
index 713dd086dc8fbef3c7f92d07c118e846b68de7e9..5420035d800903b3355a30c260766cd66f01d394 100755 (executable)
@@ -578,6 +578,7 @@ www.example.net        CNAME www2.example.net.   ; Local-Data Action
 www3.example.net       CNAME www4.example.net.   ; Local-Data Action (to be changed in preresolve)
 www5.example.net       A     192.0.2.15          ; Override www5.example.net.
 trillian.example.net   CNAME .                   ; NXDOMAIN on apex, allows all sub-names (#4086)
+*.wildcard-target.example.net          CNAME         *.walled-garden.example.net.         ; Special form of Local Data: a CNAME RR with a wildcarded target name
 
 32.4.2.0.192.rpz-ip    CNAME rpz-drop.           ; www4.example.net resolves to 192.0.2.4, drop A responses with that IP