rubydns 2.0.2 → 2.1.0

Sign up to get free protection for your applications and to get access to all the features.
data/README.md DELETED
@@ -1,167 +0,0 @@
1
- # RubyDNS
2
-
3
- RubyDNS is a high-performance DNS server which can be easily integrated into other projects or used as a stand-alone daemon. By default it uses rule-based pattern matching. Results can be hard-coded, computed, fetched from a remote DNS server or fetched from a local cache, depending on requirements.
4
-
5
- [![Build Status](https://travis-ci.org/socketry/rubydns.svg)](https://travis-ci.org/socketry/rubydns)
6
- [![Code Climate](https://codeclimate.com/github/socketry/rubydns.svg)](https://codeclimate.com/github/socketry/rubydns)
7
- [![Coverage Status](https://coveralls.io/repos/socketry/rubydns/badge.svg)](https://coveralls.io/r/socketry/rubydns)
8
- [![Gitter](https://badges.gitter.im/join.svg)](https://gitter.im/socketry/rubydns)
9
-
10
- [![RubyDNS Introduction](http://img.youtube.com/vi/B9ygq0xh3HQ/maxresdefault.jpg)](https://www.youtube.com/watch?v=B9ygq0xh3HQ&feature=youtu.be&hd=1 "RubyDNS Introduction")
11
-
12
- ## Installation
13
-
14
- Add this line to your application's Gemfile:
15
-
16
- gem 'rubydns'
17
-
18
- And then execute:
19
-
20
- $ bundle
21
-
22
- Or install it yourself as:
23
-
24
- $ gem install rubydns
25
-
26
- ## Usage
27
-
28
- There are [lots of examples available](examples/README.md) in the `examples/` directory.
29
-
30
- ### Basic DNS Server
31
-
32
- Here is the code from `examples/basic-dns.rb`:
33
-
34
- ```ruby
35
- #!/usr/bin/env ruby
36
- require 'rubydns'
37
-
38
- INTERFACES = [
39
- [:udp, "0.0.0.0", 5300],
40
- [:tcp, "0.0.0.0", 5300],
41
- ]
42
-
43
- IN = Resolv::DNS::Resource::IN
44
-
45
- # Use upstream DNS for name resolution.
46
- UPSTREAM = RubyDNS::Resolver.new([[:udp, "8.8.8.8", 53], [:tcp, "8.8.8.8", 53]])
47
-
48
- # Start the RubyDNS server
49
- RubyDNS::run_server(INTERFACES) do
50
- match(%r{test.local}, IN::A) do |transaction|
51
- transaction.respond!("10.0.0.80")
52
- end
53
-
54
- # Default DNS handler
55
- otherwise do |transaction|
56
- transaction.passthrough!(UPSTREAM)
57
- end
58
- end
59
- ```
60
-
61
- Start the server using `RUBYOPT=-w ./examples/basic-dns.rb`. You can then test it using dig:
62
-
63
- $ dig @localhost -p 5300 test.local
64
- $ dig @localhost -p 5300 google.com
65
-
66
- ### File Handle Limitations
67
-
68
- On some platforms (e.g. Mac OS X) the number of file descriptors is relatively low by default and should be increased by calling `ulimit -n 10000` before running tests or even before starting a server which expects a large number of concurrent incoming connections.
69
-
70
- ### Custom Servers
71
-
72
- It is possible to create and integrate your own custom servers, however this functionality has now moved to [`Async::DNS::Server`](https://github.com/socketry/async-dns).
73
-
74
- ```ruby
75
- class MyServer < Async::DNS::Server
76
- def process(name, resource_class, transaction)
77
- transaction.fail!(:NXDomain)
78
- end
79
- end
80
-
81
- Async::Reactor.run do
82
- task = MyServer.new.run
83
-
84
- # ... do other things, e.g. run specs/tests
85
-
86
- # Shut down the server manually if required, otherwise it will run indefinitely.
87
- # task.stop
88
- end
89
- ```
90
-
91
- This is the best way to integrate with other projects.
92
-
93
- ## Performance
94
-
95
- **Due to changes in the underlying code, there have been some very minor performance regressions. The numbers below will be updated in due course.**
96
-
97
- We welcome additional benchmarks and feedback regarding RubyDNS performance. To check the current performance results, consult the [travis build job output](https://travis-ci.org/ioquatix/rubydns).
98
-
99
- ### Server
100
-
101
- The performance is on the same magnitude as `bind9`. Some basic benchmarks resolving 1000 names concurrently, repeated 5 times, using `RubyDNS::Resolver` gives the following:
102
-
103
- user system total real
104
- RubyDNS::Server 4.280000 0.450000 4.730000 ( 4.854862)
105
- Bind9 4.970000 0.520000 5.490000 ( 5.541213)
106
-
107
- These benchmarks are included in the unit tests. To test bind9 performance, it must be installed and `which named` must return the executable.
108
-
109
- ### Resolver
110
-
111
- The `RubyDNS::Resolver` is highly concurrent and can resolve individual names as fast as the built in `Resolv::DNS` resolver. Because the resolver is asynchronous, when dealing with multiple names, it can work more efficiently:
112
-
113
- user system total real
114
- RubyDNS::Resolver 0.020000 0.010000 0.030000 ( 0.030507)
115
- Resolv::DNS 0.070000 0.010000 0.080000 ( 1.465975)
116
-
117
- These benchmarks are included in the unit tests.
118
-
119
- ### DNSSEC support
120
-
121
- DNSSEC is currently not supported and is [unlikely to be supported in the future](http://sockpuppet.org/blog/2015/01/15/against-dnssec/).
122
-
123
- ## Contributing
124
-
125
- 1. Fork it
126
- 2. Create your feature branch (`git checkout -b my-new-feature`)
127
- 3. Commit your changes (`git commit -am 'Add some feature'`)
128
- 4. Push to the branch (`git push origin my-new-feature`)
129
- 5. Create new Pull Request
130
-
131
- ### Desired Features
132
-
133
- * Support for more features of DNS such as zone transfer.
134
- * Support reverse records more easily.
135
- * Some kind of system level integration, e.g. registering a DNS server with the currently running system resolver.
136
-
137
- ## See Also
138
-
139
- The majority of this gem is now implemented by `async-dns`.
140
-
141
- - [async-io](https://github.com/socketry/async-io) — Asynchronous networking and sockets.
142
- - [async-dns](https://github.com/socketry/async-dns) — Asynchronous DNS resolver and server.
143
- - [async-rspec](https://github.com/socketry/async-rspec) — Shared contexts for running async specs.
144
-
145
- ## License
146
-
147
- Released under the MIT license.
148
-
149
- Copyright, 2017, by [Samuel G. D. Williams](http://www.codeotaku.com/samuel-williams).
150
-
151
- Permission is hereby granted, free of charge, to any person obtaining a copy
152
- of this software and associated documentation files (the "Software"), to deal
153
- in the Software without restriction, including without limitation the rights
154
- to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
155
- copies of the Software, and to permit persons to whom the Software is
156
- furnished to do so, subject to the following conditions:
157
-
158
- The above copyright notice and this permission notice shall be included in
159
- all copies or substantial portions of the Software.
160
-
161
- THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
162
- IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
163
- FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
164
- AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
165
- LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
166
- OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
167
- THE SOFTWARE.
data/Rakefile DELETED
@@ -1,6 +0,0 @@
1
- require "bundler/gem_tasks"
2
- require "rspec/core/rake_task"
3
-
4
- RSpec::Core::RakeTask.new(:test)
5
-
6
- task :default => :test
data/bin/rubydns-check DELETED
@@ -1,374 +0,0 @@
1
- #!/usr/bin/env ruby
2
- # Copyright, 2009, 2012, by Samuel G. D. Williams. <http://www.codeotaku.com>
3
- #
4
- # Permission is hereby granted, free of charge, to any person obtaining a copy
5
- # of this software and associated documentation files (the "Software"), to deal
6
- # in the Software without restriction, including without limitation the rights
7
- # to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
8
- # copies of the Software, and to permit persons to whom the Software is
9
- # furnished to do so, subject to the following conditions:
10
- #
11
- # The above copyright notice and this permission notice shall be included in
12
- # all copies or substantial portions of the Software.
13
- #
14
- # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15
- # IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16
- # FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
17
- # AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
18
- # LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
19
- # OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
20
- # THE SOFTWARE.
21
-
22
- # Pulls down DNS data from old-dns
23
- # rd-dns-check -s old-dns.mydomain.com -d mydomain.com. -f old-dns.yml
24
-
25
- # Check data against old-dns
26
- # rd-dns-check -s old-dns.mydomain.com -d mydomain.com. -c old-dns.yml
27
-
28
- # Check data against new DNS server
29
- # rd-dns-check -s 10.0.0.36 -d mydomain.com. -c old-dns.yml
30
-
31
- require 'yaml'
32
- require 'optparse'
33
- require 'set'
34
-
35
- class DNSRecord
36
- def initialize(arr)
37
- @record = arr
38
- normalize
39
- end
40
-
41
- def normalize
42
- @record[0] = @record[0].downcase
43
- @record[1] = @record[1].upcase
44
- @record[2] = @record[2].upcase
45
- @record[3] = @record[3].downcase
46
- end
47
-
48
- def hostname
49
- @record[0]
50
- end
51
-
52
- def klass
53
- @record[1]
54
- end
55
-
56
- def type
57
- @record[2]
58
- end
59
-
60
- def value
61
- @record[3]
62
- end
63
-
64
- def is_address?
65
- ["A", "AAAA"].include?(type)
66
- end
67
-
68
- def is_cname?
69
- return type == "CNAME"
70
- end
71
-
72
- def to_s
73
- "#{hostname.ljust(50)} #{klass.rjust(4)} #{type.rjust(5)} #{value}"
74
- end
75
-
76
- def key
77
- "#{hostname}:#{klass}:#{type}".downcase
78
- end
79
-
80
- def to_a
81
- @record
82
- end
83
-
84
- def == other
85
- return @record == other.to_a
86
- end
87
- end
88
-
89
- def dig(dns_server, cmd, exclude = ["TXT", "HINFO", "SOA", "NS"])
90
- records = []
91
-
92
- IO.popen("dig @#{dns_server} +nottlid +nocmd +noall +answer " + cmd) do |p|
93
- p.each do |line|
94
- r = line.chomp.split(/\s/, 4)
95
-
96
- next if exclude.include?(r[2])
97
-
98
- records << DNSRecord.new(r)
99
- end
100
- end
101
-
102
- return records
103
- end
104
-
105
- def retrieve_records(dns_server, dns_root)
106
- return dig(dns_server, "#{dns_root} AXFR")
107
- end
108
-
109
- def resolve_hostname(dns_server, hostname)
110
- return dig(dns_server, "#{hostname} A").first
111
- end
112
-
113
- def resolve_address(dns_server, address)
114
- return dig(dns_server, "-x #{address}").first
115
- end
116
-
117
- def print_summary(records, errors, okay, &block)
118
- puts "[ Summary ]".center(72, "=")
119
- puts "Checked #{records.size} record(s). #{errors} errors."
120
- if errors == 0
121
- puts "Everything seemed okay."
122
- else
123
- puts "The following records are okay:"
124
- okay.each do |r|
125
- if block_given?
126
- yield r
127
- else
128
- puts "".rjust(12) + r.to_s
129
- end
130
- end
131
- end
132
- end
133
-
134
- # Resolve hostnames to IP address "A" or "AAAA" records.
135
- # Works through CNAME records in order to find out the final
136
- # address if possible. Checks for loops in CNAME records.
137
- def resolve_addresses(records)
138
- addresses = {}
139
- cnames = {}
140
-
141
- # Extract all hostname -> ip address mappings
142
- records.each do |r|
143
- if r.is_address?
144
- addresses[r.hostname] = r
145
- elsif r.is_cname?
146
- cnames[r.hostname] = r
147
- end
148
- end
149
-
150
- cnames.each do |hostname, r|
151
- q = r
152
- trail = []
153
- failed = false
154
-
155
- # Keep track of CNAME records to avoid loops
156
- while q.is_cname?
157
- trail << q
158
- q = cnames[q.value] || addresses[q.value]
159
-
160
- # Q could be nil at this point, which means there was no address record
161
- # Q could be already part of the trail, which means there was a loop
162
- if q == nil || trail.include?(q)
163
- failed = true
164
- break
165
- end
166
- end
167
-
168
- if failed
169
- q = trail.last
170
- puts "*** Warning: CNAME record #{hostname} does not point to actual address!"
171
- trail.each_with_index do |r, idx|
172
- puts idx.to_s.rjust(10) + ": " + r.to_s
173
- end
174
- end
175
-
176
- addresses[r.hostname] = q
177
- end
178
-
179
- return addresses, cnames
180
- end
181
-
182
- def check_reverse(records, dns_server)
183
- errors = 0
184
- okay = []
185
-
186
- puts "[ Checking Reverse Lookups ]".center(72, "=")
187
-
188
- records.each do |r|
189
- next unless r.is_address?
190
-
191
- sr = resolve_address(dns_server, r.value)
192
-
193
- if sr == nil
194
- puts "*** Could not resolve host"
195
- puts "".rjust(12) + r.to_s
196
- errors += 1
197
- elsif r.hostname != sr.value
198
- puts "*** Hostname does not match"
199
- puts "Primary: ".rjust(12) + r.to_s
200
- puts "Secondary: ".rjust(12) + sr.to_s
201
- errors += 1
202
- else
203
- okay << [r, sr]
204
- end
205
- end
206
-
207
- print_summary(records, errors, okay) do |r|
208
- puts "Primary:".rjust(12) + r[0].to_s
209
- puts "Secondary:".rjust(12) + r[1].to_s
210
- end
211
- end
212
-
213
- def ping_records(records)
214
- addresses, cnames = resolve_addresses(records)
215
-
216
- errors = 0
217
- okay = []
218
-
219
- puts "[ Pinging Records ]".center(72, "=")
220
-
221
- addresses.each do |hostname, r|
222
- ping = "ping -c 5 -t 5 -i 1 -o #{r.value} > /dev/null"
223
-
224
- system(ping)
225
-
226
- if $?.exitstatus == 0
227
- okay << r
228
- else
229
- puts "*** Could not ping host #{hostname.dump}: #{ping.dump}"
230
- puts "".rjust(12) + r.to_s
231
- errors += 1
232
- end
233
- end
234
-
235
- print_summary(records, errors, okay)
236
- end
237
-
238
- def query_records(primary, secondary_server)
239
- addresses, cnames = resolve_addresses(primary)
240
-
241
- okay = []
242
- errors = 0
243
-
244
- primary.each do |r|
245
- sr = resolve_hostname(secondary_server, r.hostname)
246
-
247
- if sr == nil
248
- puts "*** Could not resolve hostname #{r.hostname.dump}"
249
- puts "Primary: ".rjust(12) + r.to_s
250
-
251
- rsr = resolve_address(secondary_server, (addresses[r.value] || r).value)
252
- puts "Address: ".rjust(12) + rsr.to_s if rsr
253
-
254
- errors += 1
255
- elsif sr.value != r.value
256
- ra = addresses[r.value] if r.is_cname?
257
- sra = addresses[sr.value] if sr.is_cname?
258
-
259
- if (sra || sr).value != (ra || r).value
260
- puts "*** IP Address does not match"
261
- puts "Primary: ".rjust(12) + r.to_s
262
- puts "Resolved: ".rjust(12) + ra.to_s if ra
263
- puts "Secondary: ".rjust(12) + sr.to_s
264
- puts "Resolved: ".rjust(12) + sra.to_s if sra
265
- errors += 1
266
- end
267
- else
268
- okay << r
269
- end
270
- end
271
-
272
- print_summary(primary, errors, okay)
273
- end
274
-
275
- def check_records(primary, secondary)
276
- s = {}
277
- okay = []
278
- errors = 0
279
-
280
- secondary.each do |r|
281
- s[r.key] = r
282
- end
283
-
284
- puts "[ Checking Records ]".center(72, "=")
285
-
286
- primary.each do |r|
287
- sr = s[r.key]
288
-
289
- if sr == nil
290
- puts "*** Could not find record"
291
- puts "Primary: ".rjust(12) + r.to_s
292
- errors += 1
293
- elsif sr != r
294
- puts "*** Records are different"
295
- puts "Primary: ".rjust(12) + r.to_s
296
- puts "Secondary: ".rjust(12) + sr.to_s
297
- errors += 1
298
- else
299
- okay << r
300
- end
301
- end
302
-
303
- print_summary(primary, errors, okay)
304
- end
305
-
306
- OPTIONS = {
307
- :DNSServer => nil,
308
- :DNSRoot => ".",
309
- }
310
-
311
- ARGV.options do |o|
312
- script_name = File.basename($0)
313
-
314
- o.set_summary_indent(' ')
315
- o.banner = "Usage: #{script_name} [options]"
316
- o.define_head "This script is designed to test and check DNS servers."
317
-
318
- o.on("-s ns.my.domain.", "--server ns.my.domain.", String, "The DNS server to query.") { |host| OPTIONS[:DNSServer] = host }
319
- o.on("-d my.domain.", "--domain my.domain.", String, "The DNS zone to transfer/test.") { |host| OPTIONS[:DNSRoot] = host }
320
-
321
- o.on("-f output.yml", "--fetch output.yml", String, "Pull down a list of hosts. Filters TXT and HINFO records. DNS transfers must be enabled.") { |f|
322
- records = retrieve_records(OPTIONS[:DNSServer], OPTIONS[:DNSRoot])
323
-
324
- output = (f ? File.open(f, "w") : STDOUT)
325
-
326
- output.write(YAML::dump(records))
327
-
328
- puts "#{records.size} record(s) retrieved."
329
- }
330
-
331
- o.on("-c input.yml", "--check input.yml", String, "Check that the DNS server returns results as specified by the file.") { |f|
332
- input = (f ? File.open(f) : STDIN)
333
-
334
- master_records = YAML::load(input.read)
335
- secondary_records = retrieve_records(OPTIONS[:DNSServer], OPTIONS[:DNSRoot])
336
-
337
- check_records(master_records, secondary_records)
338
- }
339
-
340
- o.on("-q input.yml", "--query input.yml", String, "Query the remote DNS server with all hostnames in the given file, and checks the IP addresses are consistent.") { |f|
341
- input = (f ? File.open(f) : STDIN)
342
-
343
- master_records = YAML::load(input.read)
344
-
345
- query_records(master_records, OPTIONS[:DNSServer])
346
- }
347
-
348
- o.on("-p input.yml", "--ping input.yml", String, "Ping all hosts to check if they are available or not.") { |f|
349
- input = (f ? File.open(f) : STDIN)
350
-
351
- master_records = YAML::load(input.read)
352
-
353
- ping_records(master_records)
354
- }
355
-
356
- o.on("-r input.yml", "--reverse input.yml", String, "Check that all address records have appropriate reverse entries.") { |f|
357
- input = (f ? File.open(f) : STDIN)
358
-
359
- master_records = YAML::load(input.read)
360
-
361
- check_reverse(master_records, OPTIONS[:DNSServer])
362
- }
363
-
364
- o.separator ""
365
- o.separator "Help and Copyright information"
366
-
367
- o.on_tail("--copy", "Display copyright information") {
368
- puts "#{script_name}. Copyright (c) 2009, 2011 Samuel Williams. Released under the MIT license."
369
- puts "See http://www.oriontransfer.co.nz/ for more information."
370
- exit
371
- }
372
-
373
- o.on_tail("-h", "--help", "Show this help message.") { puts o; exit }
374
- end.parse!
data/examples/Gemfile DELETED
@@ -1,9 +0,0 @@
1
- source 'https://rubygems.org'
2
-
3
- gem 'rubydns', path: '../'
4
- gem "process-daemon"
5
- gem 'nokogiri'
6
-
7
- gem 'async-http'
8
-
9
- gem 'geoip'
data/examples/README.md DELETED
@@ -1,137 +0,0 @@
1
- # RubyDNS Examples
2
-
3
- This directory contains several examples of customized RubyDNS servers,
4
- intended to demonstrate how RubyDNS can be easily customized to specific
5
- needs.
6
-
7
- ## FlakeyDNS (flakey-dns.rb)
8
-
9
- A DNS server that selectively drops queries based on the requested domain name. Queries for domains that match specified regular expressions (like 'microsoft.com' or 'sco.com') return NXDomain, while all other queries are passed to upstream resolvers.
10
-
11
- By default this server will listen for UDP requests on port 5300 and does not need to be started as root.
12
-
13
- To start the server, ensure that you're in the examples subdirectory and type
14
-
15
- bundle
16
- bundle exec ./flakey-dns.rb start
17
-
18
- To see it in action you can then query some domains. For example,
19
-
20
- dig @localhost -p 5300 slashdot.org -t A
21
- dig @localhost -p 5300 www.hackernews.com -t A
22
-
23
- give the correct results. But
24
-
25
- dig @localhost -p 5300 microsoft.com -t A
26
- dig @localhost -p 5300 www.microsoft.com -t A
27
- dig @localhost -p 5300 www.microsoft.com
28
-
29
- all give an NXDomain result.
30
-
31
- ## FortuneDNS (fortune-dns.rb)
32
-
33
- A DNS server that allows a client to generate fortunes and fetch them with subsequent requests. The server
34
- 'remembers' the fortunes it generates, and can serve them to future requests. The reason for this is because most fortunes won't fit over UDP (maximum size 512 bytes) and the client will request the same fortune via TCP.
35
-
36
- You will need to have the `fortune` app installed on your system. It comes installed by default on
37
- most Linux distributions, and can be installed on a Mac with Homebrew by typing:
38
-
39
- # Homebrew
40
- brew install fortune
41
- # MacPorts
42
- sudo port install fortune
43
- # Arch Linux
44
- sudo pacman -S fortune-mod
45
-
46
- By default this server will listen for UDP and TCP requests on port 53, and needs to be started as root. It
47
- assumes the existence of a user 'daemon', as whom the process will run. If such a user doesn't exist on your
48
- system, you will need to either create such a user or update the script to use a user that exists on your
49
- system.
50
-
51
- To start the server, ensure that you're in the examples subdirectory and type
52
-
53
- bundle
54
- sudo bundle exec ./fortune-dns.rb start
55
-
56
- To create a new fortune type
57
-
58
- dig @localhost fortune -t TXT
59
-
60
- This will result in an DNS answer that looks something like this:
61
-
62
- fortune. 0 IN TXT "Text Size: 714 Byte Size: 714"
63
- fortune. 0 IN CNAME 32bf3bf2b0a2255f2df00ed9e95c8185.fortune.
64
-
65
- Take the CNAME from this result and query it. For our example this would be:
66
-
67
- dig @localhost 32bf3bf2b0a2255f2df00ed9e95c8185.fortune -t TXT
68
-
69
- And your answer will be a fortune.
70
-
71
- You can also generate a 'short' fortune by typing the following:
72
-
73
- dig @localhost short.fortune -t TXT
74
-
75
- or view the fortune stats with:
76
-
77
- dig @localhost stats.fortune -t TXT
78
-
79
- ## GeoIPDNS (geoip-dns.rb)
80
-
81
- A sample DNS daemon that demonstrates how to use RubyDNS to build responses
82
- that vary based on the geolocation of the requesting peer. Clients of this
83
- server who request A records will get an answer IP address based on the
84
- continent of the client IP address.
85
-
86
- Please note that use of this example requires that the peer have a public
87
- IP address. IP addresses on private networks or the localhost IP (127.0.0.1)
88
- cannot be resolved to a location, and so will always yield the unknown result.
89
-
90
- This daemon requires the file downloaded from
91
- [MaxMind](http://geolite.maxmind.com/download/geoip/database/GeoLiteCountry/GeoIP.dat.gz)
92
- For more information on the GeoIP library, please click [here](http://www.maxmind.com/en/geolite)
93
- or [here](https://github.com/cjheath/geoip). This file should be unzipped and placed in the
94
- examples root directory, i.e. `examples/GeoLiteCountry.dat`.
95
-
96
- By default this server will listen for UDP requests on port 5300 and does not need to be started as root.
97
-
98
- To start the server, ensure that you're in the examples subdirectory and type
99
-
100
- bundle
101
- sudo bundle exec ./geoip-dns.rb start
102
-
103
- To see the behavior, run a DNS query against the server where you are running the GeoIPDNS
104
- daemon. Depending on the continent to which the client machine's IP address is mapped,
105
- you will receive a different IP address in the answer section:
106
-
107
- Africa - 1.1.1.1
108
- Antarctica - 1.1.2.1
109
- Asia - 1.1.3.1
110
- Europe - 1.1.4.1
111
- North America - 1.1.5.1
112
- Oceania - 1.1.6.1
113
- South America - 1.1.7.1
114
-
115
- ## WikipediaDNS (wikipedia-dns.rb)
116
-
117
- A DNS server that queries Wikipedia and returns summaries for specifically crafted queries.
118
-
119
- By default this server will listen for UDP and TCP requests on port 53, and needs to be started as root. It
120
- assumes the existence of a user 'daemon', as whom the process will run. If such a user doesn't exist on your
121
- system, you will need to either create such a user or update the script to use a user that exists on your
122
- system.
123
-
124
- To start the server, ensure that you're in the examples subdirectory and type
125
-
126
- bundle
127
- sudo bundle exec ./wikipedia-dns.rb start
128
-
129
- To query Wikipedia, pick a term - say, 'helium' - and make a DNS query like
130
-
131
- dig @localhost helium.wikipedia -t TXT
132
-
133
- The answer section should contain the summary for this topic from Wikipedia
134
-
135
- helium.wikipedia. 86400 IN TXT "Helium is a chemical element with symbol He and atomic number 2. It is a colorless, odorless, tasteless, non-toxic, inert, monatomic gas that heads the noble gas group in the periodic table. Its boiling and melting points are the lowest among the elements" " and it exists only as a gas except in extreme conditions."
136
-
137
- Long blocks of text cannot be easily replied in DNS as they must be chunked into segments at most 255 bytes. Long replies must be sent back using TCP.