def RR.new_from_string(rrstring)
rrstring = rrstring.gsub(/(\?<!\\);.*/o, '')
matches = (/#{@@RR_REGEX}/xo).match(rrstring)
unless matches
raise "#{rrstring} did not match RR pattern. Please report this to the author!"
end
name = matches[1]
ttl = matches[2].to_i || 0
rrclass = matches[3] || ''
rrtype = matches[4] || ''
rdata = matches[5] || ''
rdata.gsub!(/\s+$/o, '') if rdata
if rrtype =~/^TYPE\d+/o
rrtype = Dnsruby::Types.typesbyval(Dnsruby::Types::typesbyname(rrtype))
end
if rrclass =~/^CLASS\d+/o
rrclass = Dnsruby::Classes.classesbyval(Dnsruby::Classes::classesbyname(rrclass))
end
if rrtype == '' && rrclass == 'ANY'
rrtype = 'ANY'
rrclass = 'IN'
elsif rrclass == ''
rrclass = 'IN'
end
if rrtype == ''
rrtype = 'ANY'
end
unless %w(NAPTR TXT).include?(rrtype)
if rdata
rdata.gsub!('(', '')
rdata.gsub!(')', '')
end
end
test_length = ->(hexdump, rdlength) do
if hexdump.length != rdlength * 2
raise "#{rdata} is inconsistent; length should be #{rdlength * 2} but is #{hexdump.length}."
end
end
pack_rdata = ->(regex) do
rdata =~ regex
matches = regex.match(rdata)
rdlength = matches[1].to_i
hexdump = matches[2].gsub(/\s*/, '')
test_length.(hexdump, rdlength)
packed_rdata = [hexdump].pack('H*')
[packed_rdata, rdlength]
end
if implemented_rrs.include?(rrtype) && rdata !~/^\s*\\#/o
return _get_subclass(name, rrtype, rrclass, ttl, rdata)
elsif implemented_rrs.include?(rrtype)
packed_rdata, rdlength = pack_rdata.(/\\#\s+(\d+)\s+(.*)$/o)
return new_from_data(name, rrtype, rrclass, ttl, rdlength, packed_rdata, 0)
elsif rdata =~ /\s*\\#\s+\d+\s+/o
regex = /\\#\s+(\d+)\s+(.*)$/o
raise 'Expected RFC3597 representation of RDATA' unless rdata =~ regex
packed_rdata, rdlength = pack_rdata.(regex)
return new_from_data(name, rrtype, rrclass, ttl, rdlength, packed_rdata, 0)
else
return _get_subclass(name, rrtype, rrclass, ttl, '')
end
end