Ϫf0dZddlmZddlmZmZmZddlmZGddZ GddejZ d Z Gd d Z dd Zy )z Resolver implementation for querying successive authoritative servers to lookup a record, starting from the root nameservers. @author: Jp Calderone todo:: robustify it documentation )defer)commondnserror)FailureceZdZdZdZy)_DummyControllerz A do-nothing DNS controller. This is useful when all messages received will be responses to previously issued queries. Anything else received will be ignored. cyN)selfargss 4/usr/lib/python3/dist-packages/twisted/names/root.pymessageReceivedz _DummyController.messageReceiveds N)__name__ __module__ __qualname____doc__rr rrr r s   rr c6eZdZdZd dZdZdZdZdZdZ y) Resolverao L{Resolver} implements recursive lookup starting from a specified list of root servers. @ivar hints: See C{hints} parameter of L{__init__} @ivar _maximumQueries: See C{maximumQueries} parameter of L{__init__} @ivar _reactor: See C{reactor} parameter of L{__init__} @ivar _resolverFactory: See C{resolverFactory} parameter of L{__init__} Nctjj|||_||_||_|ddlm}||_y)a @param hints: A L{list} of L{str} giving the dotted quad representation of IP addresses of root servers at which to begin resolving names. @type hints: L{list} of L{str} @param maximumQueries: An optional L{int} giving the maximum number of queries which will be attempted to resolve a single name. @type maximumQueries: L{int} @param reactor: An optional L{IReactorTime} and L{IReactorUDP} provider to use to bind UDP ports and manage timeouts. @type reactor: L{IReactorTime} and L{IReactorUDP} provider @param resolverFactory: An optional callable which accepts C{reactor} and C{servers} arguments and returns an instance that provides a C{queryUDP} method. Defaults to L{twisted.names.client.Resolver}. @type resolverFactory: callable Nrr) r ResolverBase__init__hints_maximumQueries_reactortwisted.names.clientr_resolverFactory)r rmaximumQueriesreactorresolverFactorys rrzResolver.__init__+s?* $$T* -  " H /rc`|jDcgc]}|tjfc}Scc}w)z Return a list of two-tuples representing the addresses of the root servers, as defined by C{self.hints}. )rrPORT)r ips r_rootszResolver._rootsHs$ *.42SXX444s+c|j||j}|j|g|}|r|j|j|S)a Issue one query and return a L{Deferred} which fires with its response. @param query: The query to issue. @type query: L{dns.Query} @param servers: The servers which might have an answer for this query. @type servers: L{list} of L{tuple} of L{str} and L{int} @param timeout: A timeout on how long to wait for the response. @type timeout: L{tuple} of L{int} @param filter: A flag indicating whether to filter the results. If C{True}, the returned L{Deferred} will fire with a three-tuple of lists of L{twisted.names.dns.RRHeader} (like the return value of the I{lookup*} methods of L{IResolver}. IF C{False}, the result will be a L{Message} instance. @type filter: L{bool} @return: A L{Deferred} which fires with the response or a timeout error. @rtype: L{Deferred} )serversr")r rqueryUDP addCallback filterAnswers)r queryr)timeoutfilterrds r_queryzResolver._queryOsG2  ! !'4== ! I JJw (  MM!// *rc|d}|jtj||||j||jS)z Implement name lookup by recursively discovering the authoritative server for the name and then asking it, starting at one of the servers in C{self.hints}. ) -)_discoverAuthorityrQueryr'r)r nameclstyper.s r_lookupzResolver._lookupnsE ?%G&& IIdD# & w@T@T  rc|dkrttjdS|j|||d}|j |j |||dz |S)a# Issue a query to a server and follow a delegation if necessary. @param query: The query to issue. @type query: L{dns.Query} @param servers: The servers which might have an answer for this query. @type servers: L{list} of L{tuple} of L{str} and L{int} @param timeout: A C{tuple} of C{int} giving the timeout to use for this query. @param queriesLeft: A C{int} giving the number of queries which may yet be attempted to answer this query before the attempt will be abandoned. @return: A L{Deferred} which fires with a three-tuple of lists of L{twisted.names.dns.RRHeader} giving the response, or with a L{Failure} if there is a timeout or response error. rz"Query limit reached without resultFr4)rr ResolverErrorr2r+_discoveredAuthority)r r-r)r. queriesLeftr1s rr8zResolver._discoverAuthority|sX. ! 5../STU U KKw 7 d//qQrc|jtjk7r*tj |j|Si|j D]-}j |jgj|/fd}t}j}d} |j|| ||jj} | ||jk(rnjtjt|jjj!} fd} | j#| | S| jjk(r#|j |j$|j&fS| j(j|vrt+j,d| j(j}0i} |j&D]Q} | jtj.k(s!| j(j1| | jj<Sg}g}|j$D]z} | jtj2k(s!| j(jj}|| vr%|j| |tj4fj|j|||rj|S|rBj7|d} d}| j#|| j#fd| Stt+j,dS) as Interpret the response to a query, checking for error codes and following delegations if necessary. @param response: The L{Message} received in response to issuing C{query}. @type response: L{Message} @param query: The L{dns.Query} which was issued. @type query: L{dns.Query}. @param timeout: The timeout to use if another query is indicated by this response. @type timeout: L{tuple} of L{int} @param queriesLeft: A C{int} giving the number of queries which may yet be attempted to answer this query before the attempt will be abandoned. @return: A L{Failure} indicating a response error, a three-tuple of lists of L{twisted.names.dns.RRHeader} giving the response to C{query} or a L{Deferred} which will fire with one of those. cd}j|gD]E}|j|k(s|j|k(r|cS|jtjk(sD|}G|Sr )getr;r<rCNAME)r:r<r;cnamerecordrecordss rfindAnswerOrCNamez8Resolver._discoveredAuthority..findAnswerOrCNames[E!++dB/ '::${{d*%  1 &  'LrNc>|\}}}|jd|||fSNr)insert)resultsanswers authority additionalpreviouss r cbResolvedz1Resolver._discoveredAuthority..cbResolveds*9@6Jq(3 'J??rzCycle in CNAME processingrcH|\}}}|djjSrK)payload dottedQuad)rMrNrOrPs r getOneAddressz4Resolver._discoveredAuthority..getOneAddresss'18.Jqz))4466rcTj|tjfgdz S)Nr4)r8rr%)hintrAr-r r.s rz/Resolver._discoveredAuthority..s+T44T388,-w arz/Stuck at response without answers or delegation)rCoderOKrexceptionForCoderN setdefaultr:appendsetaddr<r;r8r9strr'r+rOrPrTrr?ArUNSr% lookupAddress)r responser-r.rAanswerrIseenr:rGr1rR addressesrrrtrapsnsrVrQrHs` ``` @@rr@zResolver._discoveredAuthoritys. >>SVV #@400@JK K&& ?F   v{{B / 6 6v > ? uzz HHTNH&tUZZCF~5::%// #d)UZZC # A@ MM*-H * (((*<*Q>QRR>>&&$.--.IJJ~~**EJ %% BBww#%%*,***?*?*A "'',,' B$$ %Bww#&& ZZ__))?LL)B-!:;LL$  % **5%+N N ""58W5A 7 MM- ( MM  H##$UV r) NN) rrrrrr'r2r=r8r@r rrrr s&0:5>  .placeholder..s'7wq$'7'D'Dr)r+)rrqdeferredr:s``r placeholderz$makePlaceholder..placeholdersDErr )rrr:rss`` rmakePlaceholderrts rceZdZdZdZdZy)DeferredResolvercHg|_|j|jyr )waitingr+gotRealResolver)r resolverDeferreds rrzDeferredResolver.__init__s $$T%9%9:rc|j}|j|_|j|_|D]}|j|yr )rx__dict__ __class__callback)r resolverwr1s rryz DeferredResolver.gotRealResolvers@ LL )) !++ !A JJx  !rc|jds|dvrF|jjtjt |jd|St |)Nlookup) getHostByNamer-) startswithrxr^rDeferredrtAttributeError)r r:s r __getattr__zDeferredResolver.__getattr__%sP ??8 $0J(J LL   0 1"4<<#3T: :T""rN)rrrrryrr rrrvrvs;!#rrvNc$tdDcgc]}ttd|z}}|Dcgc]}|jd|z}}t j |d}fd}|j |t|Scc}wcc}w)a Lookup the root nameserver addresses using the given resolver Return a Resolver which will eventually become a C{root.Resolver} instance that has references to all the root servers that we were able to look up. @param resolver: The resolver instance which will be used to lookup the root nameserver addresses. @type resolver: L{twisted.internet.interfaces.IResolverSimple} @param resolverFactory: An optional callable which returns a resolver instance. It will passed as the C{resolverFactory} argument to L{Resolver.__init__}. @type resolverFactory: callable @return: A L{DeferredResolver} which will be dynamically replaced with L{Resolver} when the root nameservers have been looked up. az%s.root-servers.netT) consumeErrorscVt|Dcgc] }|ds |dc}Scc}w)Nrr4)rr#r)reser#s r buildResolverz bootstrap..buildResolverDs-!$-A!1Q4-  -s &&)rangechrordrr DeferredListr+rv)rr#idomainsr1Lrs ` r bootstrapr,s(+0)4Qs3s8a< 4G4DKLq   5 9 :LAL 1D1A MM- A 5Ls BB r )rtwisted.internetr twisted.namesrrrtwisted.python.failurerr rrrtrvrr rrrsK #,,*  nv""nb##&r