ref: e2d8479a029334d8bcd66be2d7cf1ed52abeca12
parent: effc5f4f6cd0ffea758a131315bb6640bebc6f6b
author: cinap_lenrek <cinap_lenrek@felloff.net>
date: Fri Dec 13 20:49:55 EST 2024
ndb/dns: don't refuse queries when delegated subareas We used to always provide soa and ns hints when we where not authoritative. This changed with the last commit, where we would instead return refused error. But this breaks when we want to explicitely delegate to another nameserver, so add parameter to inmyarea() to get the delegated soa out, and provide delegated nameservers when we have one.
--- a/sys/src/cmd/ndb/dblookup.c
+++ b/sys/src/cmd/ndb/dblookup.c
@@ -164,7 +164,7 @@
* don't call it non-existent if it's not ours
* (unless we're a resolver).
*/
- if(err == Rname && (!inmyarea(dp->name) || cfg.resolver))
+ if(err == Rname && (!inmyarea(dp->name, nil) || cfg.resolver))
err = Rserver;
dp->respcode = err;
}
@@ -848,7 +848,7 @@
for(nt = mydoms; nt != nil; nt = nt->entry)
if(rp->host && cistrcmp(rp->host->name, nt->val) == 0)
break;
- if(nt == nil || inmyarea(rp->owner->name))
+ if(nt == nil || inmyarea(rp->owner->name, nil))
return 0;
dnslog("bad delegation %R from %I/%s; "
"no further logging of them",
--- a/sys/src/cmd/ndb/dn.c
+++ b/sys/src/cmd/ndb/dn.c
@@ -526,7 +526,7 @@
for(i = 0; i < HTLEN; i++)
for(dp = ht[i]; dp; dp = dp->next){
- area = inmyarea(dp->name);
+ area = inmyarea(dp->name, nil);
l = &dp->rr;
for(rp = *l; rp; rp = *l){
if(rp->db){
@@ -539,7 +539,7 @@
if(rp->ttl < minttl)
rp->ttl = minttl;
rp->auth = 1;
- } else if(rp->type == Tns && inmyarea(rp->host->name))
+ } else if(rp->type == Tns && inmyarea(rp->host->name, nil))
rp->auth = 1;
} else if(area){
/* no outside spoofing */
@@ -707,7 +707,7 @@
next = rp->next;
rp->next = nil;
if(rp->type == Tall || rp->type == Topt || !rrsupported(rp->type)
- || cfg.cachedb && !rp->db && inmyarea(rp->owner->name))
+ || cfg.cachedb && !rp->db && inmyarea(rp->owner->name, nil))
rrfree(rp);
else
rrattach1(rp, auth);
--- a/sys/src/cmd/ndb/dnarea.c
+++ b/sys/src/cmd/ndb/dnarea.c
@@ -26,17 +26,22 @@
* true if a name is in our area
*/
Area*
-inmyarea(char *name)
+inmyarea(char *name, Area **delegation)
{
Area *s, *d;
s = nameinarea(name, owned);
- if(s == nil)
+ if(s == nil){
+ if(delegation)
+ *delegation = nil;
return nil;
+ }
d = nameinarea(name, delegated);
- if(d && d->len > s->len)
+ if(delegation)
+ *delegation = d;
+ if(d != nil && d->len > s->len)
return nil;
- return s; /* name is in owned area `s' and not in a delegated subarea */
+ return s; /* name is in owned area `s' and not in a delegated subarea `d' */
}
/*
--- a/sys/src/cmd/ndb/dnnotify.c
+++ b/sys/src/cmd/ndb/dnnotify.c
@@ -26,7 +26,7 @@
return;
/* is it something we care about? */
- a = inmyarea(repp->qd->owner->name);
+ a = inmyarea(repp->qd->owner->name, nil);
if(a == nil)
return;
--- a/sys/src/cmd/ndb/dnresolve.c
+++ b/sys/src/cmd/ndb/dnresolve.c
@@ -403,7 +403,7 @@
* if the domain name is within an area of ours,
* we should have found its data in memory by now.
*/
- area = inmyarea(dp->name);
+ area = inmyarea(dp->name, nil);
if (area || strncmp(dp->name, "local#", 6) == 0)
return nil;
--- a/sys/src/cmd/ndb/dns.h
+++ b/sys/src/cmd/ndb/dns.h
@@ -489,7 +489,7 @@
extern Area *owned;
void addarea(RR *rp, Ndbtuple *t);
void freeareas(Area**);
-Area* inmyarea(char*);
+Area* inmyarea(char*, Area**);
/* dblookup.c */
int baddelegation(RR*, RR*, uchar*);
--- a/sys/src/cmd/ndb/dnserver.c
+++ b/sys/src/cmd/ndb/dnserver.c
@@ -14,7 +14,7 @@
{
char tname[32], *cp;
DN *nsdp;
- Area *myarea;
+ Area *myarea, *delegation;
RR *rp, *neg;
repp->id = reqp->id;
@@ -49,7 +49,7 @@
return;
}
- myarea = inmyarea(repp->qd->owner->name);
+ myarea = inmyarea(repp->qd->owner->name, &delegation);
if(myarea){
if(repp->qd->type == Tixfr || repp->qd->type == Taxfr){
if(debug)
@@ -64,9 +64,15 @@
} else {
if(cfg.nonrecursive
|| cfg.localrecursive && !localip(srcip)){
- /* we don't recurse and we're not authoritative */
- setercode(repp, Rrefused);
- return;
+ if(delegation == nil){
+ /*
+ * we don't recurse and we're not authoritative
+ * nor lies the domain in a delegated sub area.
+ */
+ setercode(repp, Rrefused);
+ return;
+ }
+ neg = nil;
} else {
repp->flags |= Fcanrec;
if(reqp->flags & Frecurse){
--
⑨