cdnsrfc1035

Writing more than 255 characters of data in a TXT or SPF record


While hand-writing DNS messages from scratch, I am able to send out TXT records upto 255 chars with this pseudo C code:

char use_this[1024];
memset(use_this, 0, 1024); 
use_this[0] = len;
for (int i = 0; i < len; i++){
        use_this[i + 1] = txt_record[i];
}

It goes out the wire OK. However when it comes to TXT or SPF strings with > 255 chars, I am lost, and need help!

   |###[ DNS Resource Record ]###
   |  rrname    = 'bbc.com.'
   |  type      = SPF
   |  rclass    = IN
   |  ttl       = 748
   |  rdlen     = 334
   |  rdata     = '\xdav=spf1 ip4:212.58.224.0/19 ip4:132.185.0.0/16 ip4:78.136.53.80/28 ip4:78.136.14.192/27 ip4:78.136.19.8/29 ip4:89.234.10.72/29 ip4:74.112.66.33 ip4:208.251.80.51 ip4:89.202.185.0/24 ip4:207.159.133.98 ip4:207.159.133.99r include:msgfocus.com include:cmail1.com include:mktomail.com include:servers.mcsv.net include:redsnapper.net ?all'
  ns        = None

For a 336 chars long string should it be: [255][chars0:255] + [81][255:] or, [336][chars<>], or something else obvious that I missed?

We can have TXT / SPF records larger than 255 characters, but not more than 255 characters in a single string. Looking for pointers on how to write a long record (of multiple strings) so I can send it out via the underlying socket. thanks!


Solution

  • You can't return a text fragment longer than 255 bytes these are not allowed by the DNS format.

    SPF allows splitting the record into fragments. according to https://www.rfc-editor.org/rfc/rfc7208#section-3.3 you can split the string at any position as the fragment boundaries are not syntactically significant, most humans will split between clauses, but there is no requirement to do so.

    When returning multiple text fragments just concatenate them same as is done for domain names. The RFC is silent on splits that cut the signature "v=spf1 " so keep the first segment at no less than 7 bytes in length.

    [length1-byte] "string of length1" [length2-byte] "string-of-length2"

    Multiple fragments may be used even when the total length is less than 255.

    Be sure to include the length bytes in the calculation of rdlen