diff --git a/TODO b/TODO index 8b277fe..c862787 100644 --- a/TODO +++ b/TODO @@ -34,50 +34,3 @@ doesn't make sense to apply there. It probably shouldn't cache SOA records at all. Djbdns doesn't. ("dnscache does not cache SOA records", from http://cr.yp.to/djbdns/dnscache.html) - -### Zero-timeout RRs in subqueries - -Currently they make it appear that there are no available answers! - -E.g. this IN A query for maps.bpl.org. Note the zero-timeout A records -that come back from dns-lproof2. - - 1348086228 DNS: '#s(udp-address "127.0.0.1" 41127) asks '#s(udp-listener 5555) 44280 - 1348086228 : (list (question (domain '(#"maps" #"bpl" #"org") '(#"maps" #"bpl" #"org")) 'a 'in #f)) - 1348086228 dns-vm PID 114447 ((packet-relay #s(active-request #s(udp-address 127.0.0.1 41127) 44280))) started - 1348086228 DNS: (question (domain '(#"maps" #"bpl" #"org") '(#"maps" #"bpl" #"org")) 'a 'in #f) - 1348086228 dns-vm PID 114448 ((question-handler #s(question #(struct:domain (maps bpl org) (maps bpl org)) a in #f))) started - 1348086228 dns-vm PID 114449 ((network-query #s(question #(struct:domain (maps bpl org) (maps bpl org)) a in #f))) started - 1348086228 DNS: (question (domain '(#"dns-lproof1" #"bpl" #"org") '(#"dns-lproof1" #"bpl" #"org")) 'a 'in (ns-subq (question (domain '(#"maps" #"bpl" #"org") '(#"maps" #"bpl" #"org")) 'a 'in #f))) - 1348086228 dns-vm PID 114450 ((question-handler #s(question #(struct:domain (dns-lproof1 bpl org) (dns-lproof1 bpl org)) a in #s((ns-subq subquestion 1) #s(question #(struct:domain (maps bpl org) (maps bpl org)) a in #f))))) started - 1348086228 DNS: (answered-question (question (domain '(#"dns-lproof1" #"bpl" #"org") '(#"dns-lproof1" #"bpl" #"org")) 'a 'in (ns-subq (question (domain '(#"maps" #"bpl" #"org") '(#"maps" #"bpl" #"org")) 'a 'in #f))) (complete-answer (set (rr (domain '(#"dns-lproof1" #"bpl" #"org") '(#"dns-lproof1" #"bpl" #"org")) 'a 'in 9484 '#(192 80 65 2))) (set) (set))) - 1348086228 dns-vm PID 114450 ((question-handler #s(question #(struct:domain (dns-lproof1 bpl org) (dns-lproof1 bpl org)) a in #s((ns-subq subquestion 1) #s(question #(struct:domain (maps bpl org) (maps bpl org)) a in #f))))) garbage-collected - 1348086228 DNS: '(request network-query/allocate-query-id441781 allocate-query-id) - 1348086228 DNS: '(reply network-query/allocate-query-id441781 11080) - 1348086228 DNS: '#s(udp-handle dns-client) asks '#s(udp-address "192.80.65.2" 53) 11080 - 1348086228 : (list (question (domain '(#"maps" #"bpl" #"org") '(#"maps" #"bpl" #"org")) 'a 'in #f)) - 1348086228 DNS: '#s(set-timer (#s(udp-handle dns-client) 11080) 3000 relative) - 1348086231 DNS: '#s(timer-expired (#s(udp-handle dns-client) 11080) 1348086231475.239) - 1348086231 DNS: (question (domain '(#"dns-lproof2" #"bpl" #"org") '(#"dns-lproof2" #"bpl" #"org")) 'a 'in (ns-subq (question (domain '(#"maps" #"bpl" #"org") '(#"maps" #"bpl" #"org")) 'a 'in #f))) - 1348086231 DNS: '(release-query-id 11080) - 1348086231 dns-vm PID 114451 ((question-handler #s(question #(struct:domain (dns-lproof2 bpl org) (dns-lproof2 bpl org)) a in #s((ns-subq subquestion 1) #s(question #(struct:domain (maps bpl org) (maps bpl org)) a in #f))))) started - 1348086231 DNS: (answered-question (question (domain '(#"dns-lproof2" #"bpl" #"org") '(#"dns-lproof2" #"bpl" #"org")) 'a 'in (ns-subq (question (domain '(#"maps" #"bpl" #"org") '(#"maps" #"bpl" #"org")) 'a 'in #f))) (complete-answer (set (rr (domain '(#"dns-lproof2" #"bpl" #"org") '(#"dns-lproof2" #"bpl" #"org")) 'a 'in 9481 '#(216 236 248 2))) (set) (set))) - 1348086231 dns-vm PID 114451 ((question-handler #s(question #(struct:domain (dns-lproof2 bpl org) (dns-lproof2 bpl org)) a in #s((ns-subq subquestion 1) #s(question #(struct:domain (maps bpl org) (maps bpl org)) a in #f))))) garbage-collected - 1348086231 DNS: '(request network-query/allocate-query-id441790 allocate-query-id) - 1348086231 DNS: '(reply network-query/allocate-query-id441790 8847) - 1348086231 DNS: '#s(udp-handle dns-client) asks '#s(udp-address "216.236.248.2" 53) 8847 - 1348086231 : (list (question (domain '(#"maps" #"bpl" #"org") '(#"maps" #"bpl" #"org")) 'a 'in #f)) - 1348086231 DNS: '#s(set-timer (#s(udp-handle dns-client) 8847) 3000 relative) - 1348086231 DNS: '#s(udp-address "216.236.248.2" 53) answers '#s(udp-handle dns-client) - - 1348086231 : (dns-message 8847 'response 'query 'authoritative 'not-truncated 'no-recursion-desired 'no-recursion-available 'no-error (list (question (domain '(#"maps" #"bpl" #"org") '(#"maps" #"bpl" #"org")) 'a 'in #f)) (list (rr (domain '(#"maps" #"bpl" #"org") '(#"maps" #"bpl" #"org")) 'a 'in 0 '#(216 236 252 42)) (rr (domain '(#"maps" #"bpl" #"org") '(#"maps" #"bpl" #"org")) 'a 'in 0 '#(192 80 65 42))) '() '()) - 1348086231 DNS: (network-reply 'referral441777 (complete-answer (set (rr (domain '(#"maps" #"bpl" #"org") '(#"maps" #"bpl" #"org")) 'a 'in 0 '#(192 80 65 42)) (rr (domain '(#"maps" #"bpl" #"org") '(#"maps" #"bpl" #"org")) 'a 'in 0 '#(216 236 252 42))) (set) (set))) - 1348086231 DNS: '(release-query-id 8847) - 1348086231 dns-vm PID 114449 ((network-query #s(question #(struct:domain (maps bpl org) (maps bpl org)) a in #f))) garbage-collected - 1348086231 DNS: (answered-question (question (domain '(#"maps" #"bpl" #"org") '(#"maps" #"bpl" #"org")) 'a 'in #f) (complete-answer (set) (set) (set))) - 1348086231 DNS: (set-timer (list 'check-dns-expiry (domain '(#"maps" #"bpl" #"org") '(#"maps" #"bpl" #"org"))) 0 'relative) - 1348086231 dns-vm PID 114448 ((question-handler #s(question #(struct:domain (maps bpl org) (maps bpl org)) a in #f))) garbage-collected - 1348086231 DNS: '#s(udp-listener 5555) answers '#s(udp-address "127.0.0.1" 41127) - 1348086231 : (dns-message 44280 'response 'query 'non-authoritative 'not-truncated 'recursion-desired 'recursion-available 'no-error (list (question (domain '(#"maps" #"bpl" #"org") '(#"maps" #"bpl" #"org")) 'a 'in #f)) '() '() '()) - 1348086231 dns-vm PID 114447 ((packet-relay #s(active-request #s(udp-address 127.0.0.1 41127) 44280))) garbage-collected - 1348086231 DNS: (timer-expired (list 'check-dns-expiry (domain '(#"maps" #"bpl" #"org") '(#"maps" #"bpl" #"org"))) 1348086231532.27) diff --git a/proxy.rkt b/proxy.rkt index e6bd94b..6be200e 100644 --- a/proxy.rkt +++ b/proxy.rkt @@ -207,7 +207,7 @@ (endpoint #:subscriber (network-reply (wild) (wild)) #:state zone [(network-reply _ answer) - (let-values (((new-zone timers) (incorporate-complete-answer answer zone))) + (let-values (((new-zone timers) (incorporate-complete-answer answer zone #t))) (transition-and-set-timers new-zone timers))]) (endpoint #:subscriber (timer-expired (list 'check-dns-expiry (wild)) (wild)) #:state zone @@ -255,7 +255,7 @@ (delete-endpoint referral-id) (send-message (answered-question q #f)))] [(network-reply (== referral-id) ans) - (let-values (((new-zone ignored-timers) (incorporate-complete-answer ans zone))) + (let-values (((new-zone ignored-timers) (incorporate-complete-answer ans zone #f))) (when (log-level? (current-logger) 'debug) (log-debug (format "Referral ~v results in origin ~v:~n" referral-id zone-origin)) diff --git a/zonedb.rkt b/zonedb.rkt index ab9c1a1..e13e65a 100644 --- a/zonedb.rkt +++ b/zonedb.rkt @@ -75,7 +75,20 @@ ;; being non-expiring with an InfiniteLifetime. (define ((incorporate-rr base-time) resource0 db) (define expiry (if base-time - (+ base-time (rr-ttl resource0)) + (if (zero? (rr-ttl resource0)) + ;; We are definitely not caching this + ;; resource then, because we are not even + ;; called by incorporate-complete-answer in + ;; case of 0-TTL and the cache. This record + ;; is transient and used just for the current + ;; resolution. Storing it with a real 0-TTL + ;; would mean it immediately is ignored, + ;; which is silly, so store it with an + ;; infinite-lifetime instead. + (infinite-lifetime 0) + ;; Otherwise it has a normal TTL, which we + ;; honour. + (+ base-time (rr-ttl resource0))) (infinite-lifetime (rr-ttl resource0)))) (define resource (struct-copy rr resource0 [ttl 0])) (define name (rr-name resource)) @@ -89,8 +102,8 @@ [else ;; old record finite-lifetime but expiring after the new expiry: leave it alone db])) -;; Maybe CompiledZone -> (values CompiledZone Timers) -(define (incorporate-complete-answer ans db) +;; Maybe CompiledZone Boolean -> (values CompiledZone Timers) +(define (incorporate-complete-answer ans db is-cache?) (match ans [#f (values db (set))] @@ -98,8 +111,10 @@ (define now (current-inexact-seconds)) (for/fold ([db db] [timers (set)]) ([rr (in-sequences ns us ds)]) - (values ((incorporate-rr now) rr db) - (set-add timers (cons (rr-name rr) (rr-ttl rr)))))])) + (if (and is-cache? (zero? (rr-ttl rr))) ;; Do not *cache* 0-TTL RRs (RFC 1034 3.6) + (values db timers) + (values ((incorporate-rr now) rr db) + (set-add timers (cons (rr-name rr) (rr-ttl rr))))))])) ;; CompiledZone DomainName -> CompiledZone ;; Checks the given name to see if there are any expiring records, and