static int solve_answer(int state, knot_pkt_t *pkt, knotd_qdata_t *qdata, void *ctx)
{
+ int old_state = state;
+
/* Do not solve if already solved, e.g. in a module. */
- if (state == KNOTD_IN_STATE_HIT || state == KNOTD_IN_STATE_NODATA) {
+ if (state == KNOTD_IN_STATE_HIT) {
return state;
}
/* Get answer to QNAME. */
state = solve_name(state, pkt, qdata);
+ /* Promote NODATA from a module if nothing found in zone. */
+ if (state == KNOTD_IN_STATE_MISS && old_state == KNOTD_IN_STATE_NODATA) {
+ state = old_state;
+ }
+
/* Is authoritative answer unless referral.
* Must check before we chase the CNAME chain. */
if (state != KNOTD_IN_STATE_DELEG) {
resp.check(rcode="NOERROR", rdata=random_client)
# check NODATA response when querying different type
- resp = knot.dig("d" + str(random.randint(1, dname_count)) + ".example.com", "AAAA", source=random_client)
+ resp = knot.dig("d" + str(random.randint(2, dname_count)) + ".example.com", "AAAA", source=random_client)
resp.check(rcode="NOERROR")
resp.check_count(1, "SOA", section="authority")
+ # check that NODATA behaviour does not shadow existing RR in the zone
+ resp = knot.dig("d1.example.com", "AAAA", source=random_client)
+ resp.check(rcode="NOERROR", rdata="1::4")
+
# Restart with subnet module.
knot.clear_modules(zone)
knot.add_module(zone, mod_subnet);
resp = knot.dig("d" + str(random.randint(1, dname_count)) + ".example.com", "A", source=random_client)
resp.check(rcode="NOERROR", rdata=random_client)
- resp = knot.dig("d" + str(random.randint(1, dname_count)) + ".example.com", "AAAA", source=random_client)
+ resp = knot.dig("d" + str(random.randint(2, dname_count)) + ".example.com", "AAAA", source=random_client)
resp.check(rcode="NOERROR")
resp.check_count(1, "SOA", section="authority")
+ resp = knot.dig("d1.example.com", "AAAA", source=random_client)
+ resp.check(rcode="NOERROR", rdata="1::4")
+
# Switch subnet file.
shutil.move(subnet2_filename, subnet_filename)
knot.ctl("-f zone-reload example.com.", wait=True)
resp = knot.dig("d" + str(random.randint(1, dname_count)) + ".example.com", "A", source=random_client)
resp.check(rcode="NOERROR", rdata=expected_rdata, nordata=random_client)
- resp = knot.dig("d" + str(random.randint(1, dname_count)) + ".example.com", "AAAA", source=random_client)
+ resp = knot.dig("d" + str(random.randint(2, dname_count)) + ".example.com", "AAAA", source=random_client)
resp.check(rcode="NOERROR")
resp.check_count(1, "SOA", section="authority")
+
+ resp = knot.dig("d1.example.com", "AAAA", source=random_client)
+ resp.check(rcode="NOERROR", rdata="1::4")