chiark
/
gitweb
/
~mdw
/
adns
/ blobdiff
commit
grep
author
committer
pickaxe
?
search:
re
summary
|
shortlog
|
log
|
commit
|
commitdiff
|
tree
raw
|
inline
| side by side
Parse searchlist; beginnings of paying attention.
[adns]
/
src
/
reply.c
diff --git
a/src/reply.c
b/src/reply.c
index ceeaceeeb4d7390523c9b734ae46946515fc3d7f..c1ad342e1cb29f3a20c5f3bc93548afacbe74b56 100644
(file)
--- a/
src/reply.c
+++ b/
src/reply.c
@@
-3,7
+3,7
@@
* - main handling and parsing routine for received datagrams
*/
/*
* - main handling and parsing routine for received datagrams
*/
/*
- * This file is part of adns, which is Copyright (C) 1997
, 1998
Ian Jackson
+ * This file is part of adns, which is Copyright (C) 1997
-1999
Ian Jackson
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
@@
-33,6
+33,7
@@
void adns__procdgram(adns_state ads, const byte *dgram, int dglen,
int rrtype, rrclass, rdlength, rdstart;
int anstart, nsstart, arstart;
int ownermatched, l, nrrs;
int rrtype, rrclass, rdlength, rdstart;
int anstart, nsstart, arstart;
int ownermatched, l, nrrs;
+ unsigned long ttl, soattl;
const typeinfo *typei;
adns_query qu, nqu;
dns_rcode rcode;
const typeinfo *typei;
adns_query qu, nqu;
dns_rcode rcode;
@@
-111,22
+112,22
@@
void adns__procdgram(adns_state ads, const byte *dgram, int dglen,
break;
case rcode_formaterror:
adns__warn(ads,serv,qu,"server cannot understand our query (Format Error)");
break;
case rcode_formaterror:
adns__warn(ads,serv,qu,"server cannot understand our query (Format Error)");
- adns__query_fail(qu,adns_s_
serverfaulty
);
+ adns__query_fail(qu,adns_s_
rcodeformaterror
);
return;
case rcode_servfail:
return;
case rcode_servfail:
- adns__query_fail(qu,adns_s_servfail);
+ adns__query_fail(qu,adns_s_
rcode
servfail);
return;
case rcode_notimp:
adns__warn(ads,serv,qu,"server claims not to implement our query");
return;
case rcode_notimp:
adns__warn(ads,serv,qu,"server claims not to implement our query");
- adns__query_fail(qu,adns_s_notimplemented);
+ adns__query_fail(qu,adns_s_
rcode
notimplemented);
return;
case rcode_refused:
adns__warn(ads,serv,qu,"server refused our query");
return;
case rcode_refused:
adns__warn(ads,serv,qu,"server refused our query");
- adns__query_fail(qu,adns_s_refused);
+ adns__query_fail(qu,adns_s_r
coder
efused);
return;
default:
adns__warn(ads,serv,qu,"server gave unknown response code %d",rcode);
return;
default:
adns__warn(ads,serv,qu,"server gave unknown response code %d",rcode);
- adns__query_fail(qu,adns_s_r
eason
unknown);
+ adns__query_fail(qu,adns_s_r
code
unknown);
return;
}
return;
}
@@
-138,7
+139,7
@@
void adns__procdgram(adns_state ads, const byte *dgram, int dglen,
for (rri= 0; rri<ancount; rri++) {
rrstart= cbyte;
st= adns__findrr(qu,serv, dgram,dglen,&cbyte,
for (rri= 0; rri<ancount; rri++) {
rrstart= cbyte;
st= adns__findrr(qu,serv, dgram,dglen,&cbyte,
- &rrtype,&rrclass,&rdlength,&rdstart,
+ &rrtype,&rrclass,&
ttl, &
rdlength,&rdstart,
&ownermatched);
if (st) { adns__query_fail(qu,st); return; }
if (rrtype == -1) goto x_truncated;
&ownermatched);
if (st) { adns__query_fail(qu,st); return; }
if (rrtype == -1) goto x_truncated;
@@
-155,9
+156,12
@@
void adns__procdgram(adns_state ads, const byte *dgram, int dglen,
}
continue;
}
}
continue;
}
- if (rrtype == adns_r_cname &&
/* fixme - implement adns_qf_nocname */
+ if (rrtype == adns_r_cname &&
(qu->typei->type & adns__rrt_typemask) != adns_r_cname) {
(qu->typei->type & adns__rrt_typemask) != adns_r_cname) {
- if (!qu->cname_dgram) { /* Ignore second and subsequent CNAMEs */
+ if (qu->flags & adns_qf_cname_forbid) {
+ adns__query_fail(qu,adns_s_prohibitedcname);
+ return;
+ } else if (!qu->cname_dgram) { /* Ignore second and subsequent CNAMEs */
qu->cname_begin= rdstart;
qu->cname_dglen= dglen;
st= adns__parse_domain(ads,serv,qu, &qu->vb,
qu->cname_begin= rdstart;
qu->cname_dglen= dglen;
st= adns__parse_domain(ads,serv,qu, &qu->vb,
@@
-167,13
+171,14
@@
void adns__procdgram(adns_state ads, const byte *dgram, int dglen,
if (st) { adns__query_fail(qu,st); return; }
l= strlen(qu->vb.buf)+1;
qu->answer->cname= adns__alloc_interim(qu,l);
if (st) { adns__query_fail(qu,st); return; }
l= strlen(qu->vb.buf)+1;
qu->answer->cname= adns__alloc_interim(qu,l);
- if (!qu->answer->cname) { adns__query_fail(qu,adns_s_no
localmem
); return; }
+ if (!qu->answer->cname) { adns__query_fail(qu,adns_s_no
memory
); return; }
qu->cname_dgram= adns__alloc_mine(qu,dglen);
memcpy(qu->cname_dgram,dgram,dglen);
memcpy(qu->answer->cname,qu->vb.buf,l);
cname_here= 1;
qu->cname_dgram= adns__alloc_mine(qu,dglen);
memcpy(qu->cname_dgram,dgram,dglen);
memcpy(qu->answer->cname,qu->vb.buf,l);
cname_here= 1;
+ adns__update_expires(qu,ttl,now);
/* If we find the answer section truncated after this point we restart
* the query at the CNAME; if beforehand then we obviously have to use
* TCP. If there is no truncation we can use the whole answer if
/* If we find the answer section truncated after this point we restart
* the query at the CNAME; if beforehand then we obviously have to use
* TCP. If there is no truncation we can use the whole answer if
@@
-200,18
+205,13
@@
void adns__procdgram(adns_state ads, const byte *dgram, int dglen,
if (!wantedrrs) {
/* Oops, NODATA or NXDOMAIN or perhaps a referral (which would be a problem) */
if (!wantedrrs) {
/* Oops, NODATA or NXDOMAIN or perhaps a referral (which would be a problem) */
-
- if (rcode == rcode_nxdomain) {
- adns__query_fail(qu,adns_s_nxdomain);
- return;
- }
/* RFC2308: NODATA has _either_ a SOA _or_ _no_ NS records in authority section */
/* RFC2308: NODATA has _either_ a SOA _or_ _no_ NS records in authority section */
- foundsoa= 0; foundns= 0;
+ foundsoa= 0;
soattl= 0;
foundns= 0;
for (rri= 0; rri<nscount; rri++) {
rrstart= cbyte;
st= adns__findrr(qu,serv, dgram,dglen,&cbyte,
for (rri= 0; rri<nscount; rri++) {
rrstart= cbyte;
st= adns__findrr(qu,serv, dgram,dglen,&cbyte,
- &rrtype,&rrclass,&rdlength,&rdstart, 0);
+ &rrtype,&rrclass,&
ttl, &
rdlength,&rdstart, 0);
if (st) { adns__query_fail(qu,st); return; }
if (rrtype==-1) goto x_truncated;
if (rrclass != DNS_CLASS_IN) {
if (st) { adns__query_fail(qu,st); return; }
if (rrtype==-1) goto x_truncated;
if (rrclass != DNS_CLASS_IN) {
@@
-220,12
+220,20
@@
void adns__procdgram(adns_state ads, const byte *dgram, int dglen,
rrclass,DNS_CLASS_IN);
continue;
}
rrclass,DNS_CLASS_IN);
continue;
}
- if (rrtype == adns_r_soa_raw) { foundsoa= 1; break; }
+ if (rrtype == adns_r_soa_raw) { foundsoa= 1;
soattl= ttl;
break; }
else if (rrtype == adns_r_ns_raw) { foundns= 1; }
}
else if (rrtype == adns_r_ns_raw) { foundns= 1; }
}
+
+ if (rcode == rcode_nxdomain) {
+ /* We still wanted to look for the SOA so we could find the TTL. */
+ adns__update_expires(qu,soattl,now);
+ adns__query_fail(qu,adns_s_nxdomain);
+ return;
+ }
if (foundsoa || !foundns) {
/* Aha ! A NODATA response, good. */
if (foundsoa || !foundns) {
/* Aha ! A NODATA response, good. */
+ adns__update_expires(qu,soattl,now);
adns__query_fail(qu,adns_s_nodata);
return;
}
adns__query_fail(qu,adns_s_nodata);
return;
}
@@
-246,7
+254,7
@@
void adns__procdgram(adns_state ads, const byte *dgram, int dglen,
adns__query_fail(qu,adns_s_norecurse);
} else {
adns__diag(ads,serv,qu,"server claims to do recursion, but gave us a referral");
adns__query_fail(qu,adns_s_norecurse);
} else {
adns__diag(ads,serv,qu,"server claims to do recursion, but gave us a referral");
- adns__query_fail(qu,adns_s_
serverfaulty
);
+ adns__query_fail(qu,adns_s_
invalidresponse
);
}
return;
}
}
return;
}
@@
-254,7
+262,7
@@
void adns__procdgram(adns_state ads, const byte *dgram, int dglen,
/* Now, we have some RRs which we wanted. */
qu->answer->rrs.untyped= adns__alloc_interim(qu,qu->typei->rrsz*wantedrrs);
/* Now, we have some RRs which we wanted. */
qu->answer->rrs.untyped= adns__alloc_interim(qu,qu->typei->rrsz*wantedrrs);
- if (!qu->answer->rrs.untyped) { adns__query_fail(qu,adns_s_no
localmem
); return; }
+ if (!qu->answer->rrs.untyped) { adns__query_fail(qu,adns_s_no
memory
); return; }
typei= qu->typei;
cbyte= anstart;
typei= qu->typei;
cbyte= anstart;
@@
-268,16
+276,18
@@
void adns__procdgram(adns_state ads, const byte *dgram, int dglen,
pai.nsstart= nsstart;
pai.nscount= nscount;
pai.arcount= arcount;
pai.nsstart= nsstart;
pai.nscount= nscount;
pai.arcount= arcount;
+ pai.now= now;
for (rri=0, nrrs=0; rri<ancount; rri++) {
st= adns__findrr(qu,serv, dgram,dglen,&cbyte,
for (rri=0, nrrs=0; rri<ancount; rri++) {
st= adns__findrr(qu,serv, dgram,dglen,&cbyte,
- &rrtype,&rrclass,&rdlength,&rdstart,
+ &rrtype,&rrclass,&
ttl, &
rdlength,&rdstart,
&ownermatched);
assert(!st); assert(rrtype != -1);
if (rrclass != DNS_CLASS_IN ||
rrtype != (qu->typei->type & adns__rrt_typemask) ||
!ownermatched)
continue;
&ownermatched);
assert(!st); assert(rrtype != -1);
if (rrclass != DNS_CLASS_IN ||
rrtype != (qu->typei->type & adns__rrt_typemask) ||
!ownermatched)
continue;
+ adns__update_expires(qu,ttl,now);
st= typei->parse(&pai, rdstart,rdstart+rdlength, rrsdata+nrrs*typei->rrsz);
if (st) { adns__query_fail(qu,st); return; }
if (rdstart==-1) goto x_truncated;
st= typei->parse(&pai, rdstart,rdstart+rdlength, rrsdata+nrrs*typei->rrsz);
if (st) { adns__query_fail(qu,st); return; }
if (rdstart==-1) goto x_truncated;
@@
-300,7
+310,7
@@
void adns__procdgram(adns_state ads, const byte *dgram, int dglen,
if (!flg_tc) {
adns__diag(ads,serv,qu,"server sent datagram which points outside itself");
if (!flg_tc) {
adns__diag(ads,serv,qu,"server sent datagram which points outside itself");
- adns__query_fail(qu,adns_s_
serverfaulty
);
+ adns__query_fail(qu,adns_s_
invalidresponse
);
return;
}
qu->flags |= adns_qf_usevc;
return;
}
qu->flags |= adns_qf_usevc;
@@
-314,7
+324,7
@@
void adns__procdgram(adns_state ads, const byte *dgram, int dglen,
if (st) { adns__query_fail(qu,st); return; }
newquery= realloc(qu->query_dgram,qu->vb.used);
if (st) { adns__query_fail(qu,st); return; }
newquery= realloc(qu->query_dgram,qu->vb.used);
- if (!newquery) { adns__query_fail(qu,adns_s_no
localmem
); return; }
+ if (!newquery) { adns__query_fail(qu,adns_s_no
memory
); return; }
qu->query_dgram= newquery;
qu->query_dglen= qu->vb.used;
qu->query_dgram= newquery;
qu->query_dglen= qu->vb.used;