pNet-DNS 0.0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (71) hide show
  1. data/README +68 -0
  2. data/lib/Net/DNS.rb +879 -0
  3. data/lib/Net/DNS/Header.rb +303 -0
  4. data/lib/Net/DNS/Nameserver.rb +601 -0
  5. data/lib/Net/DNS/Packet.rb +851 -0
  6. data/lib/Net/DNS/Question.rb +117 -0
  7. data/lib/Net/DNS/RR.rb +630 -0
  8. data/lib/Net/DNS/RR/A.rb +103 -0
  9. data/lib/Net/DNS/RR/AAAA.rb +147 -0
  10. data/lib/Net/DNS/RR/AFSDB.rb +114 -0
  11. data/lib/Net/DNS/RR/CERT.rb +191 -0
  12. data/lib/Net/DNS/RR/CNAME.rb +89 -0
  13. data/lib/Net/DNS/RR/DNAME.rb +84 -0
  14. data/lib/Net/DNS/RR/EID.rb +70 -0
  15. data/lib/Net/DNS/RR/HINFO.rb +108 -0
  16. data/lib/Net/DNS/RR/ISDN.rb +118 -0
  17. data/lib/Net/DNS/RR/LOC.rb +341 -0
  18. data/lib/Net/DNS/RR/MB.rb +92 -0
  19. data/lib/Net/DNS/RR/MG.rb +96 -0
  20. data/lib/Net/DNS/RR/MINFO.rb +109 -0
  21. data/lib/Net/DNS/RR/MR.rb +92 -0
  22. data/lib/Net/DNS/RR/MX.rb +124 -0
  23. data/lib/Net/DNS/RR/NAPTR.rb +182 -0
  24. data/lib/Net/DNS/RR/NIMLOC.rb +70 -0
  25. data/lib/Net/DNS/RR/NS.rb +100 -0
  26. data/lib/Net/DNS/RR/NSAP.rb +273 -0
  27. data/lib/Net/DNS/RR/NULL.rb +68 -0
  28. data/lib/Net/DNS/RR/OPT.rb +251 -0
  29. data/lib/Net/DNS/RR/PTR.rb +93 -0
  30. data/lib/Net/DNS/RR/PX.rb +131 -0
  31. data/lib/Net/DNS/RR/RP.rb +108 -0
  32. data/lib/Net/DNS/RR/RT.rb +115 -0
  33. data/lib/Net/DNS/RR/SOA.rb +195 -0
  34. data/lib/Net/DNS/RR/SPF.rb +46 -0
  35. data/lib/Net/DNS/RR/SRV.rb +153 -0
  36. data/lib/Net/DNS/RR/SSHFP.rb +190 -0
  37. data/lib/Net/DNS/RR/TKEY.rb +219 -0
  38. data/lib/Net/DNS/RR/TSIG.rb +358 -0
  39. data/lib/Net/DNS/RR/TXT.rb +162 -0
  40. data/lib/Net/DNS/RR/UNKNOWN.rb +76 -0
  41. data/lib/Net/DNS/RR/X25.rb +90 -0
  42. data/lib/Net/DNS/Resolver.rb +2090 -0
  43. data/lib/Net/DNS/Resolver/Recurse.rb +478 -0
  44. data/lib/Net/DNS/Update.rb +189 -0
  45. data/test/custom.txt +4 -0
  46. data/test/resolv.conf +4 -0
  47. data/test/tc_escapedchars.rb +498 -0
  48. data/test/tc_header.rb +91 -0
  49. data/test/tc_inet6.rb +169 -0
  50. data/test/tc_misc.rb +137 -0
  51. data/test/tc_online.rb +236 -0
  52. data/test/tc_packet.rb +174 -0
  53. data/test/tc_packet_unique_push.rb +126 -0
  54. data/test/tc_question.rb +49 -0
  55. data/test/tc_recurse.rb +69 -0
  56. data/test/tc_res_env.rb +59 -0
  57. data/test/tc_res_file.rb +55 -0
  58. data/test/tc_res_opt.rb +135 -0
  59. data/test/tc_resolver.rb +102 -0
  60. data/test/tc_rr-opt.rb +40 -0
  61. data/test/tc_rr-rrsort.rb +116 -0
  62. data/test/tc_rr-txt.rb +138 -0
  63. data/test/tc_rr-unknown.rb +95 -0
  64. data/test/tc_rr.rb +246 -0
  65. data/test/tc_tcp.rb +34 -0
  66. data/test/tc_tkey.rb +115 -0
  67. data/test/tc_update.rb +226 -0
  68. data/test/ts_netdns.rb +17 -0
  69. data/test/ts_offline.rb +32 -0
  70. data/test/ts_online.rb +33 -0
  71. metadata +119 -0
@@ -0,0 +1,478 @@
1
+ # The contents of this file are subject to the Mozilla
2
+ # Public Licence Version 1.1 (the "Licence"); you may
3
+ # not use this file except in compliance with the
4
+ # Licence. You may obtain a copy of the Licence at
5
+ # http://www.mozilla.org/MPL
6
+ # Software distributed under the Licence is distributed
7
+ # on an "AS IS" basis, WITHOUT WARRANTY OF ANY KIND,
8
+ # either express or implied. See the Licence of the
9
+ # specific language governing rights and limitations
10
+ # under the Licence.
11
+ # The Original Code is pNet::DNS.
12
+ # The Initial Developer of the Original Code is
13
+ # Nominet UK (www.nominet.org.uk). Portions created by
14
+ # Nominet UK are Copyright (c) Nominet UK 2006.
15
+ # All rights reserved.
16
+ module Net
17
+ module DNS
18
+ class Resolver
19
+ #= NAME
20
+ #
21
+ #Net::DNS::Resolver::Recurse - Perform recursive dns lookups
22
+ #
23
+ #= SYNOPSIS
24
+ #
25
+ # require 'Net/DNS'
26
+ # res = Net::DNS::Resolver::Recurse.new
27
+ #
28
+ #= DESCRIPTION
29
+ #
30
+ #This module is a sub class of Net::DNS::Resolver. So the methods for
31
+ #Net::DNS::Resolver still work for this module as well. There are just a
32
+ #couple methods added
33
+ #
34
+ #=head1 AUTHOR
35
+ #
36
+ #Rob Brown, bbb@cpan.org
37
+ #
38
+ #=head1 SEE ALSO
39
+ #
40
+ #L<Net::DNS::Resolver>,
41
+ #
42
+ #=head1 COPYRIGHT
43
+ #
44
+ #Copyright (c) 2002, Rob Brown. All rights reserved.
45
+ #Portions Copyright (c) 2005, Olaf M Kolkman.
46
+ #Ruby version Copyright (c) 2006, AlexD (Nominet UK)
47
+ #
48
+ #This module is free software; you can redistribute
49
+ #it and/or modify it under the same terms as Perl itself.
50
+ #
51
+ #Example lookup process:
52
+ #
53
+ #[root@box root]# dig +trace www.rob.com.au.
54
+ #
55
+ #; <<>> DiG 9.2.0 <<>> +trace www.rob.com.au.
56
+ #;; global options: printcmd
57
+ #. 507343 IN NS C.ROOT-SERVERS.NET.
58
+ #. 507343 IN NS D.ROOT-SERVERS.NET.
59
+ #. 507343 IN NS E.ROOT-SERVERS.NET.
60
+ #. 507343 IN NS F.ROOT-SERVERS.NET.
61
+ #. 507343 IN NS G.ROOT-SERVERS.NET.
62
+ #. 507343 IN NS H.ROOT-SERVERS.NET.
63
+ #. 507343 IN NS I.ROOT-SERVERS.NET.
64
+ #. 507343 IN NS J.ROOT-SERVERS.NET.
65
+ #. 507343 IN NS K.ROOT-SERVERS.NET.
66
+ #. 507343 IN NS L.ROOT-SERVERS.NET.
67
+ #. 507343 IN NS M.ROOT-SERVERS.NET.
68
+ #. 507343 IN NS A.ROOT-SERVERS.NET.
69
+ #. 507343 IN NS B.ROOT-SERVERS.NET.
70
+ #;; Received 436 bytes from 127.0.0.1#53(127.0.0.1) in 9 ms
71
+ # ;;; But these should be hard coded as the hints
72
+ #
73
+ # ;;; Ask H.ROOT-SERVERS.NET gave:
74
+ #au. 172800 IN NS NS2.BERKELEY.EDU.
75
+ #au. 172800 IN NS NS1.BERKELEY.EDU.
76
+ #au. 172800 IN NS NS.UU.NET.
77
+ #au. 172800 IN NS BOX2.AUNIC.NET.
78
+ #au. 172800 IN NS SEC1.APNIC.NET.
79
+ #au. 172800 IN NS SEC3.APNIC.NET.
80
+ #;; Received 300 bytes from 128.63.2.53#53(H.ROOT-SERVERS.NET) in 322 ms
81
+ # ;;; A little closer than before
82
+ #
83
+ # ;;; Ask NS2.BERKELEY.EDU gave:
84
+ #com.au. 259200 IN NS ns4.ausregistry.net.
85
+ #com.au. 259200 IN NS dns1.telstra.net.
86
+ #com.au. 259200 IN NS au2ld.CSIRO.au.
87
+ #com.au. 259200 IN NS audns01.syd.optus.net.
88
+ #com.au. 259200 IN NS ns.ripe.net.
89
+ #com.au. 259200 IN NS ns1.ausregistry.net.
90
+ #com.au. 259200 IN NS ns2.ausregistry.net.
91
+ #com.au. 259200 IN NS ns3.ausregistry.net.
92
+ #com.au. 259200 IN NS ns3.melbourneit.com.
93
+ #;; Received 387 bytes from 128.32.206.12#53(NS2.BERKELEY.EDU) in 10312 ms
94
+ # ;;; A little closer than before
95
+ #
96
+ # ;;; Ask ns4.ausregistry.net gave:
97
+ #com.au. 259200 IN NS ns1.ausregistry.net.
98
+ #com.au. 259200 IN NS ns2.ausregistry.net.
99
+ #com.au. 259200 IN NS ns3.ausregistry.net.
100
+ #com.au. 259200 IN NS ns4.ausregistry.net.
101
+ #com.au. 259200 IN NS ns3.melbourneit.com.
102
+ #com.au. 259200 IN NS dns1.telstra.net.
103
+ #com.au. 259200 IN NS au2ld.CSIRO.au.
104
+ #com.au. 259200 IN NS ns.ripe.net.
105
+ #com.au. 259200 IN NS audns01.syd.optus.net.
106
+ #;; Received 259 bytes from 137.39.1.3#53(ns4.ausregistry.net) in 606 ms
107
+ # ;;; Uh... yeah... I already knew this
108
+ # ;;; from what NS2.BERKELEY.EDU told me.
109
+ # ;;; ns4.ausregistry.net must have brain damage
110
+ #
111
+ # ;;; Ask ns1.ausregistry.net gave:
112
+ #rob.com.au. 86400 IN NS sy-dns02.tmns.net.au.
113
+ #rob.com.au. 86400 IN NS sy-dns01.tmns.net.au.
114
+ #;; Received 87 bytes from 203.18.56.41#53(ns1.ausregistry.net) in 372 ms
115
+ # ;;; Ah, much better. Something more useful.
116
+ #
117
+ # ;;; Ask sy-dns02.tmns.net.au gave:
118
+ #www.rob.com.au. 7200 IN A 139.134.5.123
119
+ #rob.com.au. 7200 IN NS sy-dns01.tmns.net.au.
120
+ #rob.com.au. 7200 IN NS sy-dns02.tmns.net.au.
121
+ #;; Received 135 bytes from 139.134.2.18#53(sy-dns02.tmns.net.au) in 525 ms
122
+ # ;;; FINALLY, THE ANSWER!
123
+ class Recurse < Resolver
124
+ attr_accessor :nameservers, :callback, :recurse
125
+ attr_reader :hints
126
+ #Initialize the hint servers. Recursive queries need a starting name
127
+ #server to work off of. This method takes a list of IP addresses to use
128
+ #as the starting servers. These name servers should be authoritative for
129
+ #the root (.) zone.
130
+ #
131
+ # res.hints=(ips)
132
+ #
133
+ #If no hints are passed, the default nameserver is asked for the hints.
134
+ #Normally these IPs can be obtained from the following location:
135
+ #
136
+ # ftp://ftp.internic.net/domain/named.root
137
+ #
138
+ def hints=(hints)
139
+ print ";; hints(#{hints.inspect})\n" if @debug
140
+ if (!hints && @nameservers)
141
+ @hints=(@nameservers)
142
+ else
143
+ @nameservers=(hints)
144
+ end
145
+ print ";; verifying (root) zone...\n" if @debug
146
+ # bind always asks one of the hint servers
147
+ # for who it thinks is authoritative for
148
+ # the (root) zone as a sanity check.
149
+ # Nice idea.
150
+
151
+ recurse=(1)
152
+ packet=query(".", "NS", "IN")
153
+
154
+ hints = Hash.new
155
+ if (packet)
156
+ if (ans = packet.answer)
157
+ # foreach my $rr (@ans)
158
+ ans.each do |rr|
159
+ if (rr.name =~ /^\.?$/ and
160
+ rr.type == "NS")
161
+ # Found root authority
162
+ server = rr.rdatastr.downcase
163
+ server.sub!(/\.$/,"")
164
+ print ";; FOUND HINT: #{server}\n" if @debug
165
+ hints[server] = []
166
+ end
167
+ end
168
+ # foreach my $rr ($packet->additional) {
169
+ packet.additional.each do |rr|
170
+ print ";; ADDITIONAL: ",rr.inspect,"\n" if @debug
171
+ if (server = rr.name.downcase)
172
+ if ( rr.type == "A")
173
+ #print ";; ADDITIONAL HELP: $server -> [".$rr->rdatastr."]\n" if $self->{'debug'};
174
+ if (hints[server]!=nil)
175
+ print ";; STORING IP: #{server} IN A ",rr.rdatastr,"\n" if @debug
176
+ hints[server]=rr.rdatastr
177
+ end
178
+ end
179
+ if ( rr.type == "AAAA")
180
+ #print ";; ADDITIONAL HELP: $server -> [".$rr->rdatastr."]\n" if $self->{'debug'};
181
+ if (hints[server])
182
+ print ";; STORING IP6: #{server} IN AAAA ",rr.rdatastr,"\n" if @debug
183
+ hints[server]=rr.rdatastr
184
+ end
185
+ end
186
+
187
+ end
188
+ end
189
+ end
190
+ # foreach my $server (keys %hints) {
191
+ hints.keys.each do |server|
192
+ if (!hints[server] || hints[server]==[])
193
+ # Wipe the servers without lookups
194
+ hints.delete(server)
195
+ end
196
+ end
197
+ @hints = hints
198
+ else
199
+ @hints = []
200
+ end
201
+ if (@hints.size > 0)
202
+ if (@debug)
203
+ print ";; USING THE FOLLOWING HINT IPS:\n";
204
+ # foreach my $ips (values %{ $self->{'hints'} }) {
205
+ @hints.values.each do |ips|
206
+ # foreach my $server (@{ $ips }) {
207
+ ips.each do |server|
208
+ print ";; #{server}\n";
209
+ end
210
+ end
211
+ end
212
+ else
213
+ warn "Server ["+(@nameservers)[0]+"] did not give answers"
214
+ end
215
+
216
+ # Disable recursion flag.
217
+ @recurse=(0)
218
+
219
+ # return $self->nameservers( map { @{ $_ } } values %{ $self->{'hints'} } );
220
+ @nameservers = @hints.values
221
+ return @nameservers
222
+ end
223
+
224
+
225
+ #This method is takes a code reference, which is then invoked each time a
226
+ #packet is received during the recursive lookup. For example to emulate
227
+ #dig's C<+trace> function:
228
+ #
229
+ # res.recursion_callback(Proc.new { |packet|
230
+ # print packet.additional.inspect
231
+ #
232
+ # print";; Received %d bytes from %s\n\n",
233
+ # packetanswersize,
234
+ # packet.answerfrom);
235
+ # })
236
+ #
237
+ def recursion_callback=(sub)
238
+ # if (sub && UNIVERSAL::isa(sub, 'CODE'))
239
+ @callback = sub
240
+ # end
241
+ end
242
+
243
+ def recursion_callback
244
+ return @callback
245
+ end
246
+
247
+
248
+ #
249
+ #This method is much like the normal query() method except it disables
250
+ #the recurse flag in the packet and explicitly performs the recursion.
251
+ #
252
+ # packet = res.query_dorecursion( "www.netscape.com.", "A")
253
+ #
254
+ #
255
+ def query_dorecursion(*args)
256
+
257
+ # Make sure the hint servers are initialized.
258
+ @hints=Hash.new unless @hints
259
+ @recurse=(0)
260
+ # Make sure the authority cache is clean.
261
+ # It is only used to store A and AAAA records of
262
+ # the suposedly authoritative name servers.
263
+ @authority_cache = Hash.new
264
+
265
+ # Obtain real question Net::DNS::Packet
266
+ query_packet = make_query_packet(args)
267
+
268
+ # Seed name servers with hints
269
+ return _dorecursion( query_packet, ".", @hints, 0)
270
+ end
271
+
272
+ def _dorecursion(query_packet, known_zone, known_authorities, depth)
273
+ cache = @authority_cache
274
+
275
+ # die "Recursion too deep, aborting..." if $depth > 255;
276
+ if ( depth > 255 )
277
+ print ";; _dorecursion() Recursion too deep, aborting...\n" if @debug
278
+ @errorstring="Recursion too deep, aborted"
279
+ return nil
280
+ end
281
+
282
+ known_zone.sub!(/\.*$/, ".")
283
+
284
+ # Get IPs from authorities
285
+ ns = []
286
+ # foreach my $ns (keys %{ $known_authorities }) {
287
+ known_authorities.keys.each do |ns_rec|
288
+ if (known_authorities[ns_rec] != nil && known_authorities[ns_rec] != [] )
289
+ cache[ns_rec] = known_authorities[ns_rec]
290
+ ns.push(cache[ns_rec])
291
+ elsif (cache[ns_rec]!=nil && cache[ns_rec]!=[])
292
+ known_authorities[ns_rec] = cache[ns_rec]
293
+ ns.push(cache[ns_rec])
294
+ end
295
+ end
296
+
297
+ if (ns.length == 0)
298
+ found_auth = 0
299
+ if (@debug)
300
+ print ";; _dorecursion() Failed to extract nameserver IPs:\n";
301
+ print known_authorities.inspect + cache.inspect + "\n"
302
+ end
303
+ # foreach my $ns (keys %{ $known_authorities }) {
304
+ known_authorities.keys.each do |ns_rec|
305
+ if (known_authorities[ns_rec]==nil || known_authorities[ns_rec]==[])
306
+ print ";; _dorecursion() Manual lookup for authority [#{ns_rec}]\n" if @debug
307
+
308
+ auth_packet=nil
309
+ ans=[]
310
+
311
+ # Don't query for V6 if its not there.
312
+ if (! @force_v4)
313
+ auth_packet = _dorecursion(make_query_packet([ns_rec,"AAAA"]), # packet
314
+ ".", # known_zone
315
+ @hints, # known_authorities
316
+ depth+1); # depth
317
+ ans = auth_packet.answer if auth_packet
318
+ end
319
+
320
+ auth_packet = _dorecursion(make_query_packet([ns_rec,"A"]), # packet
321
+ ".", # known_zone
322
+ @hints, # known_authorities
323
+ depth+1); # depth
324
+
325
+ ans.push(auth_packet.answer ) if auth_packet
326
+
327
+ if ( ans.length > 0 )
328
+ print ";; _dorecursion() Answers found for [#{ns_rec}]\n" if @debug
329
+ # foreach my $rr (@ans) {
330
+ ans.each do |rr_arr|
331
+ rr_arr.each do |rr|
332
+ print ";; RR:" + rr.inspect + "\n" if @debug
333
+ if (rr.type == "CNAME")
334
+ # Follow CNAME
335
+ server = rr.name.downcase
336
+ if (server)
337
+ server.sub!(/\.*$/, ".")
338
+ if (server == ns_rec)
339
+ cname = rr.rdatastr.downcase
340
+ cname.sub!(/\.*$/, ".")
341
+ print ";; _dorecursion() Following CNAME ns [#{ns_rec}] -> [#{cname}]\n" if @debug
342
+ known_authorities[cname] ||= []
343
+ known_authorities.delete[ns_rec]
344
+ next
345
+ end
346
+ end
347
+ elsif (rr.type == "A" || rr.type == "AAAA" )
348
+ server = rr.name.downcase
349
+ if (server)
350
+ server.sub!(/\.*$/, ".")
351
+ if (known_authorities[server]!=nil)
352
+ ip = rr.rdatastr
353
+ print ";; _dorecursion() Found ns: #{server} IN A #{ip}\n" if @debug
354
+ cache[server] = known_authorities[server]
355
+ cache[ns_rec].push(ip)
356
+ found_auth+=1
357
+ next
358
+ end
359
+ end
360
+ end
361
+ print ";; _dorecursion() Ignoring useless answer: " + rr.inspect + "\n" if @debug
362
+ end
363
+ end
364
+ else
365
+ print ";; _dorecursion() Could not find A records for [#{ns_rec}]\n" if @debug
366
+ end
367
+ end
368
+ end
369
+ if (found_auth > 0)
370
+ print ";; _dorecursion() Found #{found_auth} new NS authorities...\n" if @debug
371
+ return _dorecursion( query_packet, known_zone, known_authorities, depth+1)
372
+ end
373
+ print ";; _dorecursion() No authority information could be obtained.\n" if @debug
374
+ return nil
375
+ end
376
+
377
+ # Cut the deck of IPs in a random place.
378
+ print ";; _dorecursion() cutting deck of (" + ns.length.to_s + ") authorities...\n" if @debug
379
+ splitpos = rand(ns.length)
380
+ start = ns[0, splitpos]
381
+ endarr = ns[splitpos, ns.length - splitpos]
382
+ ns = endarr + start
383
+
384
+
385
+ ns.each do |levelns|
386
+ print ";; _dorecursion() Trying nameserver [#{levelns}]\n" if @debug
387
+ @nameservers=(levelns)
388
+
389
+ packet = send( query_packet )
390
+ if (packet)
391
+
392
+ if (@callback)
393
+ @callback.call(packet)
394
+ end
395
+
396
+ of = nil
397
+ print ";; _dorecursion() Response received from [" + @answerfrom + "]\n" if @debug
398
+ status = packet.header.rcode
399
+ authority = packet.authority
400
+ if (status)
401
+ if (status == "NXDOMAIN")
402
+ # I guess NXDOMAIN is the best we'll ever get
403
+ print ";; _dorecursion() returning NXDOMAIN\n" if @debug
404
+ return packet
405
+ elsif (packet.answer.length > 0)
406
+ print ";; _dorecursion() Answers were found.\n" if @debug
407
+ return packet
408
+ elsif (authority.length > 0)
409
+ auth = Hash.new
410
+ # foreach my $rr (@authority) {
411
+ authority.each do |rr|
412
+ if (rr.type =~ /^(NS|SOA)$/)
413
+ server = (rr.type == "NS" ? rr.nsdname : rr.mname).downcase
414
+ server.sub!(/\.*$/, ".")
415
+ of = rr.name.downcase
416
+ of.sub!(/\.*$/, ".")
417
+ print ";; _dorecursion() Received authority [#{of}] [" + rr.type() + "] [#{server}]\n" if @debug
418
+ if (of.length <= known_zone.length)
419
+ print ";; _dorecursion() Deadbeat name server did not provide new information.\n" if @debug
420
+ next
421
+ elsif (of =~ /#{known_zone}/)
422
+ print ";; _dorecursion() FOUND closer authority for [#{of}] at [#{server}].\n" if @debug
423
+ auth[server] ||= []
424
+ else
425
+ print ";; _dorecursion() Confused name server [" + @answerfrom + "] thinks [#{of}] is closer than [#{known_zone}]?\n" if @debug
426
+ last
427
+ end
428
+ else
429
+ print ";; _dorecursion() Ignoring NON NS entry found in authority section: " + rr.inspect + "\n" if @debug
430
+ end
431
+ end
432
+ # foreach my $rr ($packet->additional)
433
+ packet.additional.each do |rr|
434
+ if (rr.type == "CNAME")
435
+ # Store this CNAME into %auth too
436
+ server = rr.name.downcase
437
+ if (server)
438
+ server.sub!(/\.*$/, ".")
439
+ if (auth[server]!=nil && auth[server]!=[])
440
+ cname = rr.rdatastr.downcase
441
+ cname.sub!(/\.*$/, ".")
442
+ print ";; _dorecursion() FOUND CNAME authority: " + rr.string + "\n" if @debug
443
+ auth[cname] ||= []
444
+ auth[server] = auth[cname]
445
+ next
446
+ end
447
+
448
+ end
449
+ elsif (rr.type == "A" || rr.type == "AAAA")
450
+ server = rr.name.downcase
451
+ if (server)
452
+ server.sub!(/\.*$/, ".")
453
+ if (auth[server]!=nil)
454
+ print ";; _dorecursion() STORING: #{server} IN A " + rr.rdatastr + "\n" if @debug && rr.type == "A"
455
+ print ";; _dorecursion() STORING: #{server} IN AAAA " + rr.rdatastr + "\n" if @debug && rr.type == "AAAA"
456
+ auth[server].push(rr.rdatastr)
457
+ next
458
+ end
459
+ end
460
+ end
461
+ print ";; _dorecursion() Ignoring useless: " + rr.inspect + "\n" if @debug
462
+ end
463
+ if (of =~ /#{known_zone}/)
464
+ return _dorecursion( query_packet, of, auth, depth+1 )
465
+ else
466
+ return _dorecursion( query_packet, known_zone, known_authorities, depth+1 )
467
+ end
468
+ end
469
+ end
470
+ end
471
+ end
472
+
473
+ return nil
474
+ end
475
+ end
476
+ end
477
+ end
478
+ end