Skip to content

Commit

Permalink
auth: prevent createReverse6 from generating illegal IDN record
Browse files Browse the repository at this point in the history
Closes #7524
  • Loading branch information
BozhanL committed Dec 16, 2024
1 parent 628de35 commit a2fba57
Show file tree
Hide file tree
Showing 2 changed files with 57 additions and 1 deletion.
10 changes: 10 additions & 0 deletions pdns/lua-record.cc
Original file line number Diff line number Diff line change
Expand Up @@ -1047,6 +1047,16 @@ static void setupLuaRecords(LuaContext& lua) // NOLINT(readability-function-cogn
string dashed=ip6.toString();
boost::replace_all(dashed, ":", "-");

// https://github.com/PowerDNS/pdns/issues/7524
if (boost::ends_with(dashed, "-")) {
// "a--a-" -> "a--a-0"
dashed.push_back('0');
}
if (boost::starts_with(dashed, "-") || dashed.compare(2, 2, "--") == 0) {
// "-a--a" -> "0-a--a" "aa--a" -> "0aa--a"
dashed.insert(0, "0");
}

for(int i=31; i>=0; --i)
fmt % labels[i];
fmt % dashed;
Expand Down
48 changes: 47 additions & 1 deletion regression-tests.auth-py/test_LuaRecords.py
Original file line number Diff line number Diff line change
Expand Up @@ -166,8 +166,14 @@ class TestLuaRecords(AuthTest):
createforward6.example.org. 3600 IN NS ns1.example.org.
createforward6.example.org. 3600 IN NS ns2.example.org.
* IN LUA AAAA "filterForward(createForward6(), newNMG{{'2000::/3'}}, 'fe80::1')"
"""
""",
# the separate createforward6 zone is because some of the code in lua-record.cc insists on working relatively to the zone apex
'no-filter.createforward6.example.org': """
no-filter.createforward6.example.org. 3600 IN SOA {soa}
no-filter.createforward6.example.org. 3600 IN NS ns1.example.org.
no-filter.createforward6.example.org. 3600 IN NS ns2.example.org.
* IN LUA AAAA "createForward6()"
"""
}
_web_rrsets = []

Expand Down Expand Up @@ -1048,6 +1054,46 @@ def testCreateForwardAndReverse(self):
self.assertRcodeEqual(res, dns.rcode.NOERROR)
self.assertEqual(res.answer, response.answer)

def testCreateForwardAndReverseWithZero(self):
"""
Fix #7524
"""
expected = {
".no-filter.createforward6.example.org." : (dns.rdatatype.AAAA, {
"0--0" : "::",
"0--1" : "::1",
"0aa--0" : "aa::",
"0aa--1" : "aa::1",
"2001--0" : "2001::",
"a-b--c" : "a:b::c",
"a--b-c" : "a::b:c"
}),
".createreverse6.example.org." : (dns.rdatatype.PTR, {
"0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0" : "0--0.example.com.",
"1.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0" : "0--1.example.com.",
"0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.a.a.0.0" : "0aa--0.example.com.",
"1.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.a.a.0.0" : "0aa--1.example.com.",
"0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.1.0.0.2" : "2001--0.example.com.",
"c.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.b.0.0.0.a.0.0.0" : "a-b--c.example.com.",
"c.0.0.0.b.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.a.0.0.0" : "a--b-c.example.com."
})
}

for suffix, v in expected.items():
qtype, pairs = v
for prefix, target in pairs.items():
name = prefix + suffix

query = dns.message.make_query(name, qtype)
response = dns.message.make_response(query)
response.answer.append(dns.rrset.from_text(
name, 0, dns.rdataclass.IN, qtype, target))

res = self.sendUDPQuery(query)
print(res)
self.assertRcodeEqual(res, dns.rcode.NOERROR)
self.assertEqual(res.answer, response.answer)

def _getCounter(self, tcp=False):
"""
Helper function for shared/non-shared testing
Expand Down

0 comments on commit a2fba57

Please sign in to comment.