From c83ea03c635387e8bd0f50f62c6e6ff7895c82df Mon Sep 17 00:00:00 2001 From: Matthias Schiffer Date: Sun, 13 May 2012 03:24:51 +0200 Subject: Allow more query types --- mdns-resolver | 90 +++++++++++++++++++++++++++++++---------------------------- 1 file changed, 48 insertions(+), 42 deletions(-) diff --git a/mdns-resolver b/mdns-resolver index e00d68c..608232d 100755 --- a/mdns-resolver +++ b/mdns-resolver @@ -6,11 +6,11 @@ require 'net/dns' require 'net/dns/packet' ### Config ### -domain = 'mesh.ffhl' -port = 53 -ttl = 600 -ns = ['mesh.ffhl. 3600 IN NS paul.ffhl.'] -soa = 'mesh.ffhl. 0 IN SOA paul.ffhl. freifunk\.luebeck.asta.uni-luebeck.de. 1 3600 180 600 60' +$domain = 'mesh.ffhl' +$port = 53 +$ttl = 0 +$ns = ['mesh.ffhl. 3600 IN NS paul.ffhl.'] +$soa = 'mesh.ffhl. 0 IN SOA paul.ffhl. freifunk\.luebeck.asta.uni-luebeck.de. 1 3600 180 600 60' ### Config end ### @@ -36,6 +36,19 @@ module Net end end +def soaRecord + record = Net::DNS::RR::SOA.new $soa + return Net::DNS::RR::SOA.new(:name => record.name, + :ttl => record.ttl, + :mname => record.mname, + :rname => record.rname, + :refresh => record.refresh, + :retry => record.retry, + :expire => record.expire, + :minimum => record.minimum, + :serial => Time.now.to_i) +end + run = true @@ -46,7 +59,7 @@ sock.setsockopt Socket::Option.bool(:INET6, :IPV6, :V6ONLY, false) sock.setsockopt Socket::Option.bool(:INET, :IP, :PKTINFO, true) sock.setsockopt Socket::Option.bool(:INET6, :IPV6, :RECVPKTINFO, true) -sock.bind('::', port) +sock.bind('::', $port) while run do data, sendaddr, rflags, *controls = sock.recvmsg @@ -73,52 +86,45 @@ while run do packet.question.each do |q| next unless q.qClass.to_i == Net::DNS::IN - - host, qdomain = q.qName.split('.', 2) - next unless qdomain == domain+'.' - begin - if q.qType.to_i == Net::DNS::A + if q.qName == $domain+'.' and (q.qType.to_i == Net::DNS::SOA or q.qType.to_i == Net::DNS::ANY) + packet.answer << soaRecord + else + host, qdomain = q.qName.split('.', 2) + next unless qdomain == $domain+'.' + + begin addresses = Set.new - Socket.getaddrinfo(host+'.local.', nil, :INET).each { |addr| addresses << addr[3] } - - addresses.each do |addr| - packet.answer << Net::DNS::RR::A.new(:name => q.qName, - :ttl => ttl, - :cls => Net::DNS::IN, - :type => Net::DNS::A, - :address => addr) + Socket.getaddrinfo(host+'.local.', nil).each { |addr| addresses << [addr[0], addr[3]] } + + if q.qType.to_i == Net::DNS::A or q.qType.to_i == Net::DNS::ANY + addresses.each do |addr| + packet.answer << Net::DNS::RR::A.new(:name => q.qName, + :ttl => $ttl, + :cls => Net::DNS::IN, + :type => Net::DNS::A, + :address => addr[1]) if addr[0] == "AF_INET" + end end - elsif q.qType.to_i == Net::DNS::AAAA - addresses = Set.new - Socket.getaddrinfo(host+'.local.', nil, :INET6).each { |addr| addresses << addr[3] } - - addresses.each do |addr| - packet.answer << Net::DNS::RR::AAAA.new(:name => q.qName, - :ttl => ttl, - :cls => Net::DNS::IN, - :type => Net::DNS::AAAA, - :address => addr) + if q.qType.to_i == Net::DNS::AAAA or q.qType.to_i == Net::DNS::ANY + addresses.each do |addr| + packet.answer << Net::DNS::RR::AAAA.new(:name => q.qName, + :ttl => $ttl, + :cls => Net::DNS::IN, + :type => Net::DNS::AAAA, + :address => addr[1]) if addr[0] == "AF_INET6" + end end + rescue + packet.header.rCode = Net::DNS::Header::RCode::NAME end - rescue - packet.header.rCode = Net::DNS::Header::RCode::NAME end end if packet.answer.empty? - record = Net::DNS::RR::SOA.new(soa) - packet.authority = [Net::DNS::RR::SOA.new(:name => record.name, - :ttl => record.ttl, - :mname => record.mname, - :rname => record.rname, - :refresh => record.refresh, - :retry => record.retry, - :expire => record.expire, - :minimum => record.minimum, - :serial => Time.now.to_i)] + packet.authority = [soaRecord] else - ns.each { |line| packet.authority << Net::DNS::RR::NS.new(line) } + $ns.each { |line| packet.authority << Net::DNS::RR::NS.new(line) } end sock.sendmsg(packet.data, 0, sendaddr, pktinfo) -- cgit v1.2.3