The attached patch fixes this.

Note well that it does it in such a way that it is backwards compatible, but
also allows callers to see the strings as an array. I need this.

RFC1035 says "semantics of the text depends on the domain where it is found",
and the DNS-SD draft says mDNS TXT responses contain key/value pairs, where
each key/value pair is a <character-string> from the TXT rdata.

RFC1035:

  3.3.14. TXT RDATA format

      +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
      /                   TXT-DATA                    /
      +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+

  where:

  TXT-DATA        One or more <character-string>s.

  TXT RRs are used to hold descriptive text.  The semantics of the text
  depends on the domain where it is found.

Reproduce this with packet collected from wild:

  require 'resolv.rb'
  require 'pp'

  data = "\000\000\000\000\000\003\000\003\000\000\000\000\025Sam Roberts\342\200\231s Music\005_daap\004_tcp\005local\000\000!\000\001\300\f\000\020\000\001\300\"\000\f\000\001\300\f\000!\000\001\000\000\000;\000\021\000\000\000\000\016i\010ensemble\300-\300\f\000\020\000\001\000\000\000;\000\224\ttxtvers=1\016Version=196608\023iTSh Version=131073\027Machine ID=9C5AC2725708\034Database ID=681233690CC1C418\"Machine Name=Sam Roberts\342\200\231s Music\016Password=false\300\"\000\f\000\001\000\000\034\037\000\002\300\f"

  msg = Resolv::DNS::Message.decode(data)

  pp msg

  txtanswer = msg.answer[1]
  txtrr = txtanswer[2]

  pp txtrr.data
  pp txtrr.datas


Changelog:

  resolv.rb dies on TXT records with multiple strings

Patch:


Index: resolv.rb
===================================================================
RCS file: /src/ruby/lib/resolv.rb,v
retrieving revision 1.17.2.8
diff -u -r1.17.2.8 resolv.rb
--- resolv.rb	29 Jan 2005 05:22:35 -0000	1.17.2.8
+++ resolv.rb	5 Feb 2005 03:11:52 -0000
@@ -1266,6 +1266,14 @@
           return d
         end
 
+        def get_strings
+          strings = []
+          until @index == @limit
+            strings << get_string
+          end
+          strings
+        end
+
         def get_name
           return Name.new(self.get_labels)
         end
@@ -1511,14 +1519,21 @@
         def initialize(data)
           @data = data
         end
-        attr_reader :data
+
+        def data
+          @data.join
+        end
+
+        def datas
+          @data
+        end
 
         def encode_rdata(msg)
           msg.put_string(@data)
         end
 
         def self.decode_rdata(msg)
-          data = msg.get_string
+          data = msg.get_strings
           return self.new(data)
         end
       end