1package dns 2 3import ( 4 "bytes" 5 "encoding/base64" 6 "net" 7 "strconv" 8 "strings" 9) 10 11// A remainder of the rdata with embedded spaces, return the parsed string (sans the spaces) 12// or an error 13func endingToString(c *zlexer, errstr string) (string, *ParseError) { 14 var buffer bytes.Buffer 15 l, _ := c.Next() // zString 16 for l.value != zNewline && l.value != zEOF { 17 if l.err { 18 return buffer.String(), &ParseError{"", errstr, l} 19 } 20 switch l.value { 21 case zString: 22 buffer.WriteString(l.token) 23 case zBlank: // Ok 24 default: 25 return "", &ParseError{"", errstr, l} 26 } 27 l, _ = c.Next() 28 } 29 30 return buffer.String(), nil 31} 32 33// A remainder of the rdata with embedded spaces, split on unquoted whitespace 34// and return the parsed string slice or an error 35func endingToTxtSlice(c *zlexer, errstr string) ([]string, *ParseError) { 36 // Get the remaining data until we see a zNewline 37 l, _ := c.Next() 38 if l.err { 39 return nil, &ParseError{"", errstr, l} 40 } 41 42 // Build the slice 43 s := make([]string, 0) 44 quote := false 45 empty := false 46 for l.value != zNewline && l.value != zEOF { 47 if l.err { 48 return nil, &ParseError{"", errstr, l} 49 } 50 switch l.value { 51 case zString: 52 empty = false 53 if len(l.token) > 255 { 54 // split up tokens that are larger than 255 into 255-chunks 55 sx := []string{} 56 p, i := 0, 255 57 for { 58 if i <= len(l.token) { 59 sx = append(sx, l.token[p:i]) 60 } else { 61 sx = append(sx, l.token[p:]) 62 break 63 64 } 65 p, i = p+255, i+255 66 } 67 s = append(s, sx...) 68 break 69 } 70 71 s = append(s, l.token) 72 case zBlank: 73 if quote { 74 // zBlank can only be seen in between txt parts. 75 return nil, &ParseError{"", errstr, l} 76 } 77 case zQuote: 78 if empty && quote { 79 s = append(s, "") 80 } 81 quote = !quote 82 empty = true 83 default: 84 return nil, &ParseError{"", errstr, l} 85 } 86 l, _ = c.Next() 87 } 88 89 if quote { 90 return nil, &ParseError{"", errstr, l} 91 } 92 93 return s, nil 94} 95 96func (rr *A) parse(c *zlexer, o string) *ParseError { 97 l, _ := c.Next() 98 rr.A = net.ParseIP(l.token) 99 // IPv4 addresses cannot include ":". 100 // We do this rather than use net.IP's To4() because 101 // To4() treats IPv4-mapped IPv6 addresses as being 102 // IPv4. 103 isIPv4 := !strings.Contains(l.token, ":") 104 if rr.A == nil || !isIPv4 || l.err { 105 return &ParseError{"", "bad A A", l} 106 } 107 return slurpRemainder(c) 108} 109 110func (rr *AAAA) parse(c *zlexer, o string) *ParseError { 111 l, _ := c.Next() 112 rr.AAAA = net.ParseIP(l.token) 113 // IPv6 addresses must include ":", and IPv4 114 // addresses cannot include ":". 115 isIPv6 := strings.Contains(l.token, ":") 116 if rr.AAAA == nil || !isIPv6 || l.err { 117 return &ParseError{"", "bad AAAA AAAA", l} 118 } 119 return slurpRemainder(c) 120} 121 122func (rr *NS) parse(c *zlexer, o string) *ParseError { 123 l, _ := c.Next() 124 name, nameOk := toAbsoluteName(l.token, o) 125 if l.err || !nameOk { 126 return &ParseError{"", "bad NS Ns", l} 127 } 128 rr.Ns = name 129 return slurpRemainder(c) 130} 131 132func (rr *PTR) parse(c *zlexer, o string) *ParseError { 133 l, _ := c.Next() 134 name, nameOk := toAbsoluteName(l.token, o) 135 if l.err || !nameOk { 136 return &ParseError{"", "bad PTR Ptr", l} 137 } 138 rr.Ptr = name 139 return slurpRemainder(c) 140} 141 142func (rr *NSAPPTR) parse(c *zlexer, o string) *ParseError { 143 l, _ := c.Next() 144 name, nameOk := toAbsoluteName(l.token, o) 145 if l.err || !nameOk { 146 return &ParseError{"", "bad NSAP-PTR Ptr", l} 147 } 148 rr.Ptr = name 149 return slurpRemainder(c) 150} 151 152func (rr *RP) parse(c *zlexer, o string) *ParseError { 153 l, _ := c.Next() 154 mbox, mboxOk := toAbsoluteName(l.token, o) 155 if l.err || !mboxOk { 156 return &ParseError{"", "bad RP Mbox", l} 157 } 158 rr.Mbox = mbox 159 160 c.Next() // zBlank 161 l, _ = c.Next() 162 rr.Txt = l.token 163 164 txt, txtOk := toAbsoluteName(l.token, o) 165 if l.err || !txtOk { 166 return &ParseError{"", "bad RP Txt", l} 167 } 168 rr.Txt = txt 169 170 return slurpRemainder(c) 171} 172 173func (rr *MR) parse(c *zlexer, o string) *ParseError { 174 l, _ := c.Next() 175 name, nameOk := toAbsoluteName(l.token, o) 176 if l.err || !nameOk { 177 return &ParseError{"", "bad MR Mr", l} 178 } 179 rr.Mr = name 180 return slurpRemainder(c) 181} 182 183func (rr *MB) parse(c *zlexer, o string) *ParseError { 184 l, _ := c.Next() 185 name, nameOk := toAbsoluteName(l.token, o) 186 if l.err || !nameOk { 187 return &ParseError{"", "bad MB Mb", l} 188 } 189 rr.Mb = name 190 return slurpRemainder(c) 191} 192 193func (rr *MG) parse(c *zlexer, o string) *ParseError { 194 l, _ := c.Next() 195 name, nameOk := toAbsoluteName(l.token, o) 196 if l.err || !nameOk { 197 return &ParseError{"", "bad MG Mg", l} 198 } 199 rr.Mg = name 200 return slurpRemainder(c) 201} 202 203func (rr *HINFO) parse(c *zlexer, o string) *ParseError { 204 chunks, e := endingToTxtSlice(c, "bad HINFO Fields") 205 if e != nil { 206 return e 207 } 208 209 if ln := len(chunks); ln == 0 { 210 return nil 211 } else if ln == 1 { 212 // Can we split it? 213 if out := strings.Fields(chunks[0]); len(out) > 1 { 214 chunks = out 215 } else { 216 chunks = append(chunks, "") 217 } 218 } 219 220 rr.Cpu = chunks[0] 221 rr.Os = strings.Join(chunks[1:], " ") 222 223 return nil 224} 225 226func (rr *MINFO) parse(c *zlexer, o string) *ParseError { 227 l, _ := c.Next() 228 rmail, rmailOk := toAbsoluteName(l.token, o) 229 if l.err || !rmailOk { 230 return &ParseError{"", "bad MINFO Rmail", l} 231 } 232 rr.Rmail = rmail 233 234 c.Next() // zBlank 235 l, _ = c.Next() 236 rr.Email = l.token 237 238 email, emailOk := toAbsoluteName(l.token, o) 239 if l.err || !emailOk { 240 return &ParseError{"", "bad MINFO Email", l} 241 } 242 rr.Email = email 243 244 return slurpRemainder(c) 245} 246 247func (rr *MF) parse(c *zlexer, o string) *ParseError { 248 l, _ := c.Next() 249 name, nameOk := toAbsoluteName(l.token, o) 250 if l.err || !nameOk { 251 return &ParseError{"", "bad MF Mf", l} 252 } 253 rr.Mf = name 254 return slurpRemainder(c) 255} 256 257func (rr *MD) parse(c *zlexer, o string) *ParseError { 258 l, _ := c.Next() 259 name, nameOk := toAbsoluteName(l.token, o) 260 if l.err || !nameOk { 261 return &ParseError{"", "bad MD Md", l} 262 } 263 rr.Md = name 264 return slurpRemainder(c) 265} 266 267func (rr *MX) parse(c *zlexer, o string) *ParseError { 268 l, _ := c.Next() 269 i, e := strconv.ParseUint(l.token, 10, 16) 270 if e != nil || l.err { 271 return &ParseError{"", "bad MX Pref", l} 272 } 273 rr.Preference = uint16(i) 274 275 c.Next() // zBlank 276 l, _ = c.Next() // zString 277 rr.Mx = l.token 278 279 name, nameOk := toAbsoluteName(l.token, o) 280 if l.err || !nameOk { 281 return &ParseError{"", "bad MX Mx", l} 282 } 283 rr.Mx = name 284 285 return slurpRemainder(c) 286} 287 288func (rr *RT) parse(c *zlexer, o string) *ParseError { 289 l, _ := c.Next() 290 i, e := strconv.ParseUint(l.token, 10, 16) 291 if e != nil { 292 return &ParseError{"", "bad RT Preference", l} 293 } 294 rr.Preference = uint16(i) 295 296 c.Next() // zBlank 297 l, _ = c.Next() // zString 298 rr.Host = l.token 299 300 name, nameOk := toAbsoluteName(l.token, o) 301 if l.err || !nameOk { 302 return &ParseError{"", "bad RT Host", l} 303 } 304 rr.Host = name 305 306 return slurpRemainder(c) 307} 308 309func (rr *AFSDB) parse(c *zlexer, o string) *ParseError { 310 l, _ := c.Next() 311 i, e := strconv.ParseUint(l.token, 10, 16) 312 if e != nil || l.err { 313 return &ParseError{"", "bad AFSDB Subtype", l} 314 } 315 rr.Subtype = uint16(i) 316 317 c.Next() // zBlank 318 l, _ = c.Next() // zString 319 rr.Hostname = l.token 320 321 name, nameOk := toAbsoluteName(l.token, o) 322 if l.err || !nameOk { 323 return &ParseError{"", "bad AFSDB Hostname", l} 324 } 325 rr.Hostname = name 326 return slurpRemainder(c) 327} 328 329func (rr *X25) parse(c *zlexer, o string) *ParseError { 330 l, _ := c.Next() 331 if l.err { 332 return &ParseError{"", "bad X25 PSDNAddress", l} 333 } 334 rr.PSDNAddress = l.token 335 return slurpRemainder(c) 336} 337 338func (rr *KX) parse(c *zlexer, o string) *ParseError { 339 l, _ := c.Next() 340 i, e := strconv.ParseUint(l.token, 10, 16) 341 if e != nil || l.err { 342 return &ParseError{"", "bad KX Pref", l} 343 } 344 rr.Preference = uint16(i) 345 346 c.Next() // zBlank 347 l, _ = c.Next() // zString 348 rr.Exchanger = l.token 349 350 name, nameOk := toAbsoluteName(l.token, o) 351 if l.err || !nameOk { 352 return &ParseError{"", "bad KX Exchanger", l} 353 } 354 rr.Exchanger = name 355 return slurpRemainder(c) 356} 357 358func (rr *CNAME) parse(c *zlexer, o string) *ParseError { 359 l, _ := c.Next() 360 name, nameOk := toAbsoluteName(l.token, o) 361 if l.err || !nameOk { 362 return &ParseError{"", "bad CNAME Target", l} 363 } 364 rr.Target = name 365 return slurpRemainder(c) 366} 367 368func (rr *DNAME) parse(c *zlexer, o string) *ParseError { 369 l, _ := c.Next() 370 name, nameOk := toAbsoluteName(l.token, o) 371 if l.err || !nameOk { 372 return &ParseError{"", "bad DNAME Target", l} 373 } 374 rr.Target = name 375 return slurpRemainder(c) 376} 377 378func (rr *SOA) parse(c *zlexer, o string) *ParseError { 379 l, _ := c.Next() 380 ns, nsOk := toAbsoluteName(l.token, o) 381 if l.err || !nsOk { 382 return &ParseError{"", "bad SOA Ns", l} 383 } 384 rr.Ns = ns 385 386 c.Next() // zBlank 387 l, _ = c.Next() 388 rr.Mbox = l.token 389 390 mbox, mboxOk := toAbsoluteName(l.token, o) 391 if l.err || !mboxOk { 392 return &ParseError{"", "bad SOA Mbox", l} 393 } 394 rr.Mbox = mbox 395 396 c.Next() // zBlank 397 398 var ( 399 v uint32 400 ok bool 401 ) 402 for i := 0; i < 5; i++ { 403 l, _ = c.Next() 404 if l.err { 405 return &ParseError{"", "bad SOA zone parameter", l} 406 } 407 if j, err := strconv.ParseUint(l.token, 10, 32); err != nil { 408 if i == 0 { 409 // Serial must be a number 410 return &ParseError{"", "bad SOA zone parameter", l} 411 } 412 // We allow other fields to be unitful duration strings 413 if v, ok = stringToTTL(l.token); !ok { 414 return &ParseError{"", "bad SOA zone parameter", l} 415 416 } 417 } else { 418 v = uint32(j) 419 } 420 switch i { 421 case 0: 422 rr.Serial = v 423 c.Next() // zBlank 424 case 1: 425 rr.Refresh = v 426 c.Next() // zBlank 427 case 2: 428 rr.Retry = v 429 c.Next() // zBlank 430 case 3: 431 rr.Expire = v 432 c.Next() // zBlank 433 case 4: 434 rr.Minttl = v 435 } 436 } 437 return slurpRemainder(c) 438} 439 440func (rr *SRV) parse(c *zlexer, o string) *ParseError { 441 l, _ := c.Next() 442 i, e := strconv.ParseUint(l.token, 10, 16) 443 if e != nil || l.err { 444 return &ParseError{"", "bad SRV Priority", l} 445 } 446 rr.Priority = uint16(i) 447 448 c.Next() // zBlank 449 l, _ = c.Next() // zString 450 i, e1 := strconv.ParseUint(l.token, 10, 16) 451 if e1 != nil || l.err { 452 return &ParseError{"", "bad SRV Weight", l} 453 } 454 rr.Weight = uint16(i) 455 456 c.Next() // zBlank 457 l, _ = c.Next() // zString 458 i, e2 := strconv.ParseUint(l.token, 10, 16) 459 if e2 != nil || l.err { 460 return &ParseError{"", "bad SRV Port", l} 461 } 462 rr.Port = uint16(i) 463 464 c.Next() // zBlank 465 l, _ = c.Next() // zString 466 rr.Target = l.token 467 468 name, nameOk := toAbsoluteName(l.token, o) 469 if l.err || !nameOk { 470 return &ParseError{"", "bad SRV Target", l} 471 } 472 rr.Target = name 473 return slurpRemainder(c) 474} 475 476func (rr *NAPTR) parse(c *zlexer, o string) *ParseError { 477 l, _ := c.Next() 478 i, e := strconv.ParseUint(l.token, 10, 16) 479 if e != nil || l.err { 480 return &ParseError{"", "bad NAPTR Order", l} 481 } 482 rr.Order = uint16(i) 483 484 c.Next() // zBlank 485 l, _ = c.Next() // zString 486 i, e1 := strconv.ParseUint(l.token, 10, 16) 487 if e1 != nil || l.err { 488 return &ParseError{"", "bad NAPTR Preference", l} 489 } 490 rr.Preference = uint16(i) 491 492 // Flags 493 c.Next() // zBlank 494 l, _ = c.Next() // _QUOTE 495 if l.value != zQuote { 496 return &ParseError{"", "bad NAPTR Flags", l} 497 } 498 l, _ = c.Next() // Either String or Quote 499 if l.value == zString { 500 rr.Flags = l.token 501 l, _ = c.Next() // _QUOTE 502 if l.value != zQuote { 503 return &ParseError{"", "bad NAPTR Flags", l} 504 } 505 } else if l.value == zQuote { 506 rr.Flags = "" 507 } else { 508 return &ParseError{"", "bad NAPTR Flags", l} 509 } 510 511 // Service 512 c.Next() // zBlank 513 l, _ = c.Next() // _QUOTE 514 if l.value != zQuote { 515 return &ParseError{"", "bad NAPTR Service", l} 516 } 517 l, _ = c.Next() // Either String or Quote 518 if l.value == zString { 519 rr.Service = l.token 520 l, _ = c.Next() // _QUOTE 521 if l.value != zQuote { 522 return &ParseError{"", "bad NAPTR Service", l} 523 } 524 } else if l.value == zQuote { 525 rr.Service = "" 526 } else { 527 return &ParseError{"", "bad NAPTR Service", l} 528 } 529 530 // Regexp 531 c.Next() // zBlank 532 l, _ = c.Next() // _QUOTE 533 if l.value != zQuote { 534 return &ParseError{"", "bad NAPTR Regexp", l} 535 } 536 l, _ = c.Next() // Either String or Quote 537 if l.value == zString { 538 rr.Regexp = l.token 539 l, _ = c.Next() // _QUOTE 540 if l.value != zQuote { 541 return &ParseError{"", "bad NAPTR Regexp", l} 542 } 543 } else if l.value == zQuote { 544 rr.Regexp = "" 545 } else { 546 return &ParseError{"", "bad NAPTR Regexp", l} 547 } 548 549 // After quote no space?? 550 c.Next() // zBlank 551 l, _ = c.Next() // zString 552 rr.Replacement = l.token 553 554 name, nameOk := toAbsoluteName(l.token, o) 555 if l.err || !nameOk { 556 return &ParseError{"", "bad NAPTR Replacement", l} 557 } 558 rr.Replacement = name 559 return slurpRemainder(c) 560} 561 562func (rr *TALINK) parse(c *zlexer, o string) *ParseError { 563 l, _ := c.Next() 564 previousName, previousNameOk := toAbsoluteName(l.token, o) 565 if l.err || !previousNameOk { 566 return &ParseError{"", "bad TALINK PreviousName", l} 567 } 568 rr.PreviousName = previousName 569 570 c.Next() // zBlank 571 l, _ = c.Next() 572 rr.NextName = l.token 573 574 nextName, nextNameOk := toAbsoluteName(l.token, o) 575 if l.err || !nextNameOk { 576 return &ParseError{"", "bad TALINK NextName", l} 577 } 578 rr.NextName = nextName 579 580 return slurpRemainder(c) 581} 582 583func (rr *LOC) parse(c *zlexer, o string) *ParseError { 584 // Non zero defaults for LOC record, see RFC 1876, Section 3. 585 rr.Size = 0x12 // 1e2 cm (1m) 586 rr.HorizPre = 0x16 // 1e6 cm (10000m) 587 rr.VertPre = 0x13 // 1e3 cm (10m) 588 ok := false 589 590 // North 591 l, _ := c.Next() 592 i, e := strconv.ParseUint(l.token, 10, 32) 593 if e != nil || l.err || i > 90 { 594 return &ParseError{"", "bad LOC Latitude", l} 595 } 596 rr.Latitude = 1000 * 60 * 60 * uint32(i) 597 598 c.Next() // zBlank 599 // Either number, 'N' or 'S' 600 l, _ = c.Next() 601 if rr.Latitude, ok = locCheckNorth(l.token, rr.Latitude); ok { 602 goto East 603 } 604 if i, err := strconv.ParseUint(l.token, 10, 32); err != nil || l.err || i > 59 { 605 return &ParseError{"", "bad LOC Latitude minutes", l} 606 } else { 607 rr.Latitude += 1000 * 60 * uint32(i) 608 } 609 610 c.Next() // zBlank 611 l, _ = c.Next() 612 if i, err := strconv.ParseFloat(l.token, 64); err != nil || l.err || i < 0 || i >= 60 { 613 return &ParseError{"", "bad LOC Latitude seconds", l} 614 } else { 615 rr.Latitude += uint32(1000 * i) 616 } 617 c.Next() // zBlank 618 // Either number, 'N' or 'S' 619 l, _ = c.Next() 620 if rr.Latitude, ok = locCheckNorth(l.token, rr.Latitude); ok { 621 goto East 622 } 623 // If still alive, flag an error 624 return &ParseError{"", "bad LOC Latitude North/South", l} 625 626East: 627 // East 628 c.Next() // zBlank 629 l, _ = c.Next() 630 if i, err := strconv.ParseUint(l.token, 10, 32); err != nil || l.err || i > 180 { 631 return &ParseError{"", "bad LOC Longitude", l} 632 } else { 633 rr.Longitude = 1000 * 60 * 60 * uint32(i) 634 } 635 c.Next() // zBlank 636 // Either number, 'E' or 'W' 637 l, _ = c.Next() 638 if rr.Longitude, ok = locCheckEast(l.token, rr.Longitude); ok { 639 goto Altitude 640 } 641 if i, err := strconv.ParseUint(l.token, 10, 32); err != nil || l.err || i > 59 { 642 return &ParseError{"", "bad LOC Longitude minutes", l} 643 } else { 644 rr.Longitude += 1000 * 60 * uint32(i) 645 } 646 c.Next() // zBlank 647 l, _ = c.Next() 648 if i, err := strconv.ParseFloat(l.token, 64); err != nil || l.err || i < 0 || i >= 60 { 649 return &ParseError{"", "bad LOC Longitude seconds", l} 650 } else { 651 rr.Longitude += uint32(1000 * i) 652 } 653 c.Next() // zBlank 654 // Either number, 'E' or 'W' 655 l, _ = c.Next() 656 if rr.Longitude, ok = locCheckEast(l.token, rr.Longitude); ok { 657 goto Altitude 658 } 659 // If still alive, flag an error 660 return &ParseError{"", "bad LOC Longitude East/West", l} 661 662Altitude: 663 c.Next() // zBlank 664 l, _ = c.Next() 665 if l.token == "" || l.err { 666 return &ParseError{"", "bad LOC Altitude", l} 667 } 668 if l.token[len(l.token)-1] == 'M' || l.token[len(l.token)-1] == 'm' { 669 l.token = l.token[0 : len(l.token)-1] 670 } 671 if i, err := strconv.ParseFloat(l.token, 64); err != nil { 672 return &ParseError{"", "bad LOC Altitude", l} 673 } else { 674 rr.Altitude = uint32(i*100.0 + 10000000.0 + 0.5) 675 } 676 677 // And now optionally the other values 678 l, _ = c.Next() 679 count := 0 680 for l.value != zNewline && l.value != zEOF { 681 switch l.value { 682 case zString: 683 switch count { 684 case 0: // Size 685 exp, m, ok := stringToCm(l.token) 686 if !ok { 687 return &ParseError{"", "bad LOC Size", l} 688 } 689 rr.Size = exp&0x0f | m<<4&0xf0 690 case 1: // HorizPre 691 exp, m, ok := stringToCm(l.token) 692 if !ok { 693 return &ParseError{"", "bad LOC HorizPre", l} 694 } 695 rr.HorizPre = exp&0x0f | m<<4&0xf0 696 case 2: // VertPre 697 exp, m, ok := stringToCm(l.token) 698 if !ok { 699 return &ParseError{"", "bad LOC VertPre", l} 700 } 701 rr.VertPre = exp&0x0f | m<<4&0xf0 702 } 703 count++ 704 case zBlank: 705 // Ok 706 default: 707 return &ParseError{"", "bad LOC Size, HorizPre or VertPre", l} 708 } 709 l, _ = c.Next() 710 } 711 return nil 712} 713 714func (rr *HIP) parse(c *zlexer, o string) *ParseError { 715 // HitLength is not represented 716 l, _ := c.Next() 717 i, e := strconv.ParseUint(l.token, 10, 8) 718 if e != nil || l.err { 719 return &ParseError{"", "bad HIP PublicKeyAlgorithm", l} 720 } 721 rr.PublicKeyAlgorithm = uint8(i) 722 723 c.Next() // zBlank 724 l, _ = c.Next() // zString 725 if l.token == "" || l.err { 726 return &ParseError{"", "bad HIP Hit", l} 727 } 728 rr.Hit = l.token // This can not contain spaces, see RFC 5205 Section 6. 729 rr.HitLength = uint8(len(rr.Hit)) / 2 730 731 c.Next() // zBlank 732 l, _ = c.Next() // zString 733 if l.token == "" || l.err { 734 return &ParseError{"", "bad HIP PublicKey", l} 735 } 736 rr.PublicKey = l.token // This cannot contain spaces 737 decodedPK, decodedPKerr := base64.StdEncoding.DecodeString(rr.PublicKey) 738 if decodedPKerr != nil { 739 return &ParseError{"", "bad HIP PublicKey", l} 740 } 741 rr.PublicKeyLength = uint16(len(decodedPK)) 742 743 // RendezvousServers (if any) 744 l, _ = c.Next() 745 var xs []string 746 for l.value != zNewline && l.value != zEOF { 747 switch l.value { 748 case zString: 749 name, nameOk := toAbsoluteName(l.token, o) 750 if l.err || !nameOk { 751 return &ParseError{"", "bad HIP RendezvousServers", l} 752 } 753 xs = append(xs, name) 754 case zBlank: 755 // Ok 756 default: 757 return &ParseError{"", "bad HIP RendezvousServers", l} 758 } 759 l, _ = c.Next() 760 } 761 762 rr.RendezvousServers = xs 763 return nil 764} 765 766func (rr *CERT) parse(c *zlexer, o string) *ParseError { 767 l, _ := c.Next() 768 if v, ok := StringToCertType[l.token]; ok { 769 rr.Type = v 770 } else if i, err := strconv.ParseUint(l.token, 10, 16); err != nil { 771 return &ParseError{"", "bad CERT Type", l} 772 } else { 773 rr.Type = uint16(i) 774 } 775 c.Next() // zBlank 776 l, _ = c.Next() // zString 777 i, e := strconv.ParseUint(l.token, 10, 16) 778 if e != nil || l.err { 779 return &ParseError{"", "bad CERT KeyTag", l} 780 } 781 rr.KeyTag = uint16(i) 782 c.Next() // zBlank 783 l, _ = c.Next() // zString 784 if v, ok := StringToAlgorithm[l.token]; ok { 785 rr.Algorithm = v 786 } else if i, err := strconv.ParseUint(l.token, 10, 8); err != nil { 787 return &ParseError{"", "bad CERT Algorithm", l} 788 } else { 789 rr.Algorithm = uint8(i) 790 } 791 s, e1 := endingToString(c, "bad CERT Certificate") 792 if e1 != nil { 793 return e1 794 } 795 rr.Certificate = s 796 return nil 797} 798 799func (rr *OPENPGPKEY) parse(c *zlexer, o string) *ParseError { 800 s, e := endingToString(c, "bad OPENPGPKEY PublicKey") 801 if e != nil { 802 return e 803 } 804 rr.PublicKey = s 805 return nil 806} 807 808func (rr *CSYNC) parse(c *zlexer, o string) *ParseError { 809 l, _ := c.Next() 810 j, e := strconv.ParseUint(l.token, 10, 32) 811 if e != nil { 812 // Serial must be a number 813 return &ParseError{"", "bad CSYNC serial", l} 814 } 815 rr.Serial = uint32(j) 816 817 c.Next() // zBlank 818 819 l, _ = c.Next() 820 j, e1 := strconv.ParseUint(l.token, 10, 16) 821 if e1 != nil { 822 // Serial must be a number 823 return &ParseError{"", "bad CSYNC flags", l} 824 } 825 rr.Flags = uint16(j) 826 827 rr.TypeBitMap = make([]uint16, 0) 828 var ( 829 k uint16 830 ok bool 831 ) 832 l, _ = c.Next() 833 for l.value != zNewline && l.value != zEOF { 834 switch l.value { 835 case zBlank: 836 // Ok 837 case zString: 838 tokenUpper := strings.ToUpper(l.token) 839 if k, ok = StringToType[tokenUpper]; !ok { 840 if k, ok = typeToInt(l.token); !ok { 841 return &ParseError{"", "bad CSYNC TypeBitMap", l} 842 } 843 } 844 rr.TypeBitMap = append(rr.TypeBitMap, k) 845 default: 846 return &ParseError{"", "bad CSYNC TypeBitMap", l} 847 } 848 l, _ = c.Next() 849 } 850 return nil 851} 852 853func (rr *ZONEMD) parse(c *zlexer, o string) *ParseError { 854 l, _ := c.Next() 855 i, e := strconv.ParseUint(l.token, 10, 32) 856 if e != nil || l.err { 857 return &ParseError{"", "bad ZONEMD Serial", l} 858 } 859 rr.Serial = uint32(i) 860 861 c.Next() // zBlank 862 l, _ = c.Next() 863 i, e1 := strconv.ParseUint(l.token, 10, 8) 864 if e1 != nil || l.err { 865 return &ParseError{"", "bad ZONEMD Scheme", l} 866 } 867 rr.Scheme = uint8(i) 868 869 c.Next() // zBlank 870 l, _ = c.Next() 871 i, err := strconv.ParseUint(l.token, 10, 8) 872 if err != nil || l.err { 873 return &ParseError{"", "bad ZONEMD Hash Algorithm", l} 874 } 875 rr.Hash = uint8(i) 876 877 s, e2 := endingToString(c, "bad ZONEMD Digest") 878 if e2 != nil { 879 return e2 880 } 881 rr.Digest = s 882 return nil 883} 884 885func (rr *SIG) parse(c *zlexer, o string) *ParseError { return rr.RRSIG.parse(c, o) } 886 887func (rr *RRSIG) parse(c *zlexer, o string) *ParseError { 888 l, _ := c.Next() 889 tokenUpper := strings.ToUpper(l.token) 890 if t, ok := StringToType[tokenUpper]; !ok { 891 if strings.HasPrefix(tokenUpper, "TYPE") { 892 t, ok = typeToInt(l.token) 893 if !ok { 894 return &ParseError{"", "bad RRSIG Typecovered", l} 895 } 896 rr.TypeCovered = t 897 } else { 898 return &ParseError{"", "bad RRSIG Typecovered", l} 899 } 900 } else { 901 rr.TypeCovered = t 902 } 903 904 c.Next() // zBlank 905 l, _ = c.Next() 906 i, e := strconv.ParseUint(l.token, 10, 8) 907 if e != nil || l.err { 908 return &ParseError{"", "bad RRSIG Algorithm", l} 909 } 910 rr.Algorithm = uint8(i) 911 912 c.Next() // zBlank 913 l, _ = c.Next() 914 i, e1 := strconv.ParseUint(l.token, 10, 8) 915 if e1 != nil || l.err { 916 return &ParseError{"", "bad RRSIG Labels", l} 917 } 918 rr.Labels = uint8(i) 919 920 c.Next() // zBlank 921 l, _ = c.Next() 922 i, e2 := strconv.ParseUint(l.token, 10, 32) 923 if e2 != nil || l.err { 924 return &ParseError{"", "bad RRSIG OrigTtl", l} 925 } 926 rr.OrigTtl = uint32(i) 927 928 c.Next() // zBlank 929 l, _ = c.Next() 930 if i, err := StringToTime(l.token); err != nil { 931 // Try to see if all numeric and use it as epoch 932 if i, err := strconv.ParseUint(l.token, 10, 32); err == nil { 933 rr.Expiration = uint32(i) 934 } else { 935 return &ParseError{"", "bad RRSIG Expiration", l} 936 } 937 } else { 938 rr.Expiration = i 939 } 940 941 c.Next() // zBlank 942 l, _ = c.Next() 943 if i, err := StringToTime(l.token); err != nil { 944 if i, err := strconv.ParseUint(l.token, 10, 32); err == nil { 945 rr.Inception = uint32(i) 946 } else { 947 return &ParseError{"", "bad RRSIG Inception", l} 948 } 949 } else { 950 rr.Inception = i 951 } 952 953 c.Next() // zBlank 954 l, _ = c.Next() 955 i, e3 := strconv.ParseUint(l.token, 10, 16) 956 if e3 != nil || l.err { 957 return &ParseError{"", "bad RRSIG KeyTag", l} 958 } 959 rr.KeyTag = uint16(i) 960 961 c.Next() // zBlank 962 l, _ = c.Next() 963 rr.SignerName = l.token 964 name, nameOk := toAbsoluteName(l.token, o) 965 if l.err || !nameOk { 966 return &ParseError{"", "bad RRSIG SignerName", l} 967 } 968 rr.SignerName = name 969 970 s, e4 := endingToString(c, "bad RRSIG Signature") 971 if e4 != nil { 972 return e4 973 } 974 rr.Signature = s 975 976 return nil 977} 978 979func (rr *NSEC) parse(c *zlexer, o string) *ParseError { 980 l, _ := c.Next() 981 name, nameOk := toAbsoluteName(l.token, o) 982 if l.err || !nameOk { 983 return &ParseError{"", "bad NSEC NextDomain", l} 984 } 985 rr.NextDomain = name 986 987 rr.TypeBitMap = make([]uint16, 0) 988 var ( 989 k uint16 990 ok bool 991 ) 992 l, _ = c.Next() 993 for l.value != zNewline && l.value != zEOF { 994 switch l.value { 995 case zBlank: 996 // Ok 997 case zString: 998 tokenUpper := strings.ToUpper(l.token) 999 if k, ok = StringToType[tokenUpper]; !ok { 1000 if k, ok = typeToInt(l.token); !ok { 1001 return &ParseError{"", "bad NSEC TypeBitMap", l} 1002 } 1003 } 1004 rr.TypeBitMap = append(rr.TypeBitMap, k) 1005 default: 1006 return &ParseError{"", "bad NSEC TypeBitMap", l} 1007 } 1008 l, _ = c.Next() 1009 } 1010 return nil 1011} 1012 1013func (rr *NSEC3) parse(c *zlexer, o string) *ParseError { 1014 l, _ := c.Next() 1015 i, e := strconv.ParseUint(l.token, 10, 8) 1016 if e != nil || l.err { 1017 return &ParseError{"", "bad NSEC3 Hash", l} 1018 } 1019 rr.Hash = uint8(i) 1020 c.Next() // zBlank 1021 l, _ = c.Next() 1022 i, e1 := strconv.ParseUint(l.token, 10, 8) 1023 if e1 != nil || l.err { 1024 return &ParseError{"", "bad NSEC3 Flags", l} 1025 } 1026 rr.Flags = uint8(i) 1027 c.Next() // zBlank 1028 l, _ = c.Next() 1029 i, e2 := strconv.ParseUint(l.token, 10, 16) 1030 if e2 != nil || l.err { 1031 return &ParseError{"", "bad NSEC3 Iterations", l} 1032 } 1033 rr.Iterations = uint16(i) 1034 c.Next() 1035 l, _ = c.Next() 1036 if l.token == "" || l.err { 1037 return &ParseError{"", "bad NSEC3 Salt", l} 1038 } 1039 if l.token != "-" { 1040 rr.SaltLength = uint8(len(l.token)) / 2 1041 rr.Salt = l.token 1042 } 1043 1044 c.Next() 1045 l, _ = c.Next() 1046 if l.token == "" || l.err { 1047 return &ParseError{"", "bad NSEC3 NextDomain", l} 1048 } 1049 rr.HashLength = 20 // Fix for NSEC3 (sha1 160 bits) 1050 rr.NextDomain = l.token 1051 1052 rr.TypeBitMap = make([]uint16, 0) 1053 var ( 1054 k uint16 1055 ok bool 1056 ) 1057 l, _ = c.Next() 1058 for l.value != zNewline && l.value != zEOF { 1059 switch l.value { 1060 case zBlank: 1061 // Ok 1062 case zString: 1063 tokenUpper := strings.ToUpper(l.token) 1064 if k, ok = StringToType[tokenUpper]; !ok { 1065 if k, ok = typeToInt(l.token); !ok { 1066 return &ParseError{"", "bad NSEC3 TypeBitMap", l} 1067 } 1068 } 1069 rr.TypeBitMap = append(rr.TypeBitMap, k) 1070 default: 1071 return &ParseError{"", "bad NSEC3 TypeBitMap", l} 1072 } 1073 l, _ = c.Next() 1074 } 1075 return nil 1076} 1077 1078func (rr *NSEC3PARAM) parse(c *zlexer, o string) *ParseError { 1079 l, _ := c.Next() 1080 i, e := strconv.ParseUint(l.token, 10, 8) 1081 if e != nil || l.err { 1082 return &ParseError{"", "bad NSEC3PARAM Hash", l} 1083 } 1084 rr.Hash = uint8(i) 1085 c.Next() // zBlank 1086 l, _ = c.Next() 1087 i, e1 := strconv.ParseUint(l.token, 10, 8) 1088 if e1 != nil || l.err { 1089 return &ParseError{"", "bad NSEC3PARAM Flags", l} 1090 } 1091 rr.Flags = uint8(i) 1092 c.Next() // zBlank 1093 l, _ = c.Next() 1094 i, e2 := strconv.ParseUint(l.token, 10, 16) 1095 if e2 != nil || l.err { 1096 return &ParseError{"", "bad NSEC3PARAM Iterations", l} 1097 } 1098 rr.Iterations = uint16(i) 1099 c.Next() 1100 l, _ = c.Next() 1101 if l.token != "-" { 1102 rr.SaltLength = uint8(len(l.token) / 2) 1103 rr.Salt = l.token 1104 } 1105 return slurpRemainder(c) 1106} 1107 1108func (rr *EUI48) parse(c *zlexer, o string) *ParseError { 1109 l, _ := c.Next() 1110 if len(l.token) != 17 || l.err { 1111 return &ParseError{"", "bad EUI48 Address", l} 1112 } 1113 addr := make([]byte, 12) 1114 dash := 0 1115 for i := 0; i < 10; i += 2 { 1116 addr[i] = l.token[i+dash] 1117 addr[i+1] = l.token[i+1+dash] 1118 dash++ 1119 if l.token[i+1+dash] != '-' { 1120 return &ParseError{"", "bad EUI48 Address", l} 1121 } 1122 } 1123 addr[10] = l.token[15] 1124 addr[11] = l.token[16] 1125 1126 i, e := strconv.ParseUint(string(addr), 16, 48) 1127 if e != nil { 1128 return &ParseError{"", "bad EUI48 Address", l} 1129 } 1130 rr.Address = i 1131 return slurpRemainder(c) 1132} 1133 1134func (rr *EUI64) parse(c *zlexer, o string) *ParseError { 1135 l, _ := c.Next() 1136 if len(l.token) != 23 || l.err { 1137 return &ParseError{"", "bad EUI64 Address", l} 1138 } 1139 addr := make([]byte, 16) 1140 dash := 0 1141 for i := 0; i < 14; i += 2 { 1142 addr[i] = l.token[i+dash] 1143 addr[i+1] = l.token[i+1+dash] 1144 dash++ 1145 if l.token[i+1+dash] != '-' { 1146 return &ParseError{"", "bad EUI64 Address", l} 1147 } 1148 } 1149 addr[14] = l.token[21] 1150 addr[15] = l.token[22] 1151 1152 i, e := strconv.ParseUint(string(addr), 16, 64) 1153 if e != nil { 1154 return &ParseError{"", "bad EUI68 Address", l} 1155 } 1156 rr.Address = i 1157 return slurpRemainder(c) 1158} 1159 1160func (rr *SSHFP) parse(c *zlexer, o string) *ParseError { 1161 l, _ := c.Next() 1162 i, e := strconv.ParseUint(l.token, 10, 8) 1163 if e != nil || l.err { 1164 return &ParseError{"", "bad SSHFP Algorithm", l} 1165 } 1166 rr.Algorithm = uint8(i) 1167 c.Next() // zBlank 1168 l, _ = c.Next() 1169 i, e1 := strconv.ParseUint(l.token, 10, 8) 1170 if e1 != nil || l.err { 1171 return &ParseError{"", "bad SSHFP Type", l} 1172 } 1173 rr.Type = uint8(i) 1174 c.Next() // zBlank 1175 s, e2 := endingToString(c, "bad SSHFP Fingerprint") 1176 if e2 != nil { 1177 return e2 1178 } 1179 rr.FingerPrint = s 1180 return nil 1181} 1182 1183func (rr *DNSKEY) parseDNSKEY(c *zlexer, o, typ string) *ParseError { 1184 l, _ := c.Next() 1185 i, e := strconv.ParseUint(l.token, 10, 16) 1186 if e != nil || l.err { 1187 return &ParseError{"", "bad " + typ + " Flags", l} 1188 } 1189 rr.Flags = uint16(i) 1190 c.Next() // zBlank 1191 l, _ = c.Next() // zString 1192 i, e1 := strconv.ParseUint(l.token, 10, 8) 1193 if e1 != nil || l.err { 1194 return &ParseError{"", "bad " + typ + " Protocol", l} 1195 } 1196 rr.Protocol = uint8(i) 1197 c.Next() // zBlank 1198 l, _ = c.Next() // zString 1199 i, e2 := strconv.ParseUint(l.token, 10, 8) 1200 if e2 != nil || l.err { 1201 return &ParseError{"", "bad " + typ + " Algorithm", l} 1202 } 1203 rr.Algorithm = uint8(i) 1204 s, e3 := endingToString(c, "bad "+typ+" PublicKey") 1205 if e3 != nil { 1206 return e3 1207 } 1208 rr.PublicKey = s 1209 return nil 1210} 1211 1212func (rr *DNSKEY) parse(c *zlexer, o string) *ParseError { return rr.parseDNSKEY(c, o, "DNSKEY") } 1213func (rr *KEY) parse(c *zlexer, o string) *ParseError { return rr.parseDNSKEY(c, o, "KEY") } 1214func (rr *CDNSKEY) parse(c *zlexer, o string) *ParseError { return rr.parseDNSKEY(c, o, "CDNSKEY") } 1215func (rr *DS) parse(c *zlexer, o string) *ParseError { return rr.parseDS(c, o, "DS") } 1216func (rr *DLV) parse(c *zlexer, o string) *ParseError { return rr.parseDS(c, o, "DLV") } 1217func (rr *CDS) parse(c *zlexer, o string) *ParseError { return rr.parseDS(c, o, "CDS") } 1218 1219func (rr *RKEY) parse(c *zlexer, o string) *ParseError { 1220 l, _ := c.Next() 1221 i, e := strconv.ParseUint(l.token, 10, 16) 1222 if e != nil || l.err { 1223 return &ParseError{"", "bad RKEY Flags", l} 1224 } 1225 rr.Flags = uint16(i) 1226 c.Next() // zBlank 1227 l, _ = c.Next() // zString 1228 i, e1 := strconv.ParseUint(l.token, 10, 8) 1229 if e1 != nil || l.err { 1230 return &ParseError{"", "bad RKEY Protocol", l} 1231 } 1232 rr.Protocol = uint8(i) 1233 c.Next() // zBlank 1234 l, _ = c.Next() // zString 1235 i, e2 := strconv.ParseUint(l.token, 10, 8) 1236 if e2 != nil || l.err { 1237 return &ParseError{"", "bad RKEY Algorithm", l} 1238 } 1239 rr.Algorithm = uint8(i) 1240 s, e3 := endingToString(c, "bad RKEY PublicKey") 1241 if e3 != nil { 1242 return e3 1243 } 1244 rr.PublicKey = s 1245 return nil 1246} 1247 1248func (rr *EID) parse(c *zlexer, o string) *ParseError { 1249 s, e := endingToString(c, "bad EID Endpoint") 1250 if e != nil { 1251 return e 1252 } 1253 rr.Endpoint = s 1254 return nil 1255} 1256 1257func (rr *NIMLOC) parse(c *zlexer, o string) *ParseError { 1258 s, e := endingToString(c, "bad NIMLOC Locator") 1259 if e != nil { 1260 return e 1261 } 1262 rr.Locator = s 1263 return nil 1264} 1265 1266func (rr *GPOS) parse(c *zlexer, o string) *ParseError { 1267 l, _ := c.Next() 1268 _, e := strconv.ParseFloat(l.token, 64) 1269 if e != nil || l.err { 1270 return &ParseError{"", "bad GPOS Longitude", l} 1271 } 1272 rr.Longitude = l.token 1273 c.Next() // zBlank 1274 l, _ = c.Next() 1275 _, e1 := strconv.ParseFloat(l.token, 64) 1276 if e1 != nil || l.err { 1277 return &ParseError{"", "bad GPOS Latitude", l} 1278 } 1279 rr.Latitude = l.token 1280 c.Next() // zBlank 1281 l, _ = c.Next() 1282 _, e2 := strconv.ParseFloat(l.token, 64) 1283 if e2 != nil || l.err { 1284 return &ParseError{"", "bad GPOS Altitude", l} 1285 } 1286 rr.Altitude = l.token 1287 return slurpRemainder(c) 1288} 1289 1290func (rr *DS) parseDS(c *zlexer, o, typ string) *ParseError { 1291 l, _ := c.Next() 1292 i, e := strconv.ParseUint(l.token, 10, 16) 1293 if e != nil || l.err { 1294 return &ParseError{"", "bad " + typ + " KeyTag", l} 1295 } 1296 rr.KeyTag = uint16(i) 1297 c.Next() // zBlank 1298 l, _ = c.Next() 1299 if i, err := strconv.ParseUint(l.token, 10, 8); err != nil { 1300 tokenUpper := strings.ToUpper(l.token) 1301 i, ok := StringToAlgorithm[tokenUpper] 1302 if !ok || l.err { 1303 return &ParseError{"", "bad " + typ + " Algorithm", l} 1304 } 1305 rr.Algorithm = i 1306 } else { 1307 rr.Algorithm = uint8(i) 1308 } 1309 c.Next() // zBlank 1310 l, _ = c.Next() 1311 i, e1 := strconv.ParseUint(l.token, 10, 8) 1312 if e1 != nil || l.err { 1313 return &ParseError{"", "bad " + typ + " DigestType", l} 1314 } 1315 rr.DigestType = uint8(i) 1316 s, e2 := endingToString(c, "bad "+typ+" Digest") 1317 if e2 != nil { 1318 return e2 1319 } 1320 rr.Digest = s 1321 return nil 1322} 1323 1324func (rr *TA) parse(c *zlexer, o string) *ParseError { 1325 l, _ := c.Next() 1326 i, e := strconv.ParseUint(l.token, 10, 16) 1327 if e != nil || l.err { 1328 return &ParseError{"", "bad TA KeyTag", l} 1329 } 1330 rr.KeyTag = uint16(i) 1331 c.Next() // zBlank 1332 l, _ = c.Next() 1333 if i, err := strconv.ParseUint(l.token, 10, 8); err != nil { 1334 tokenUpper := strings.ToUpper(l.token) 1335 i, ok := StringToAlgorithm[tokenUpper] 1336 if !ok || l.err { 1337 return &ParseError{"", "bad TA Algorithm", l} 1338 } 1339 rr.Algorithm = i 1340 } else { 1341 rr.Algorithm = uint8(i) 1342 } 1343 c.Next() // zBlank 1344 l, _ = c.Next() 1345 i, e1 := strconv.ParseUint(l.token, 10, 8) 1346 if e1 != nil || l.err { 1347 return &ParseError{"", "bad TA DigestType", l} 1348 } 1349 rr.DigestType = uint8(i) 1350 s, e2 := endingToString(c, "bad TA Digest") 1351 if e2 != nil { 1352 return e2 1353 } 1354 rr.Digest = s 1355 return nil 1356} 1357 1358func (rr *TLSA) parse(c *zlexer, o string) *ParseError { 1359 l, _ := c.Next() 1360 i, e := strconv.ParseUint(l.token, 10, 8) 1361 if e != nil || l.err { 1362 return &ParseError{"", "bad TLSA Usage", l} 1363 } 1364 rr.Usage = uint8(i) 1365 c.Next() // zBlank 1366 l, _ = c.Next() 1367 i, e1 := strconv.ParseUint(l.token, 10, 8) 1368 if e1 != nil || l.err { 1369 return &ParseError{"", "bad TLSA Selector", l} 1370 } 1371 rr.Selector = uint8(i) 1372 c.Next() // zBlank 1373 l, _ = c.Next() 1374 i, e2 := strconv.ParseUint(l.token, 10, 8) 1375 if e2 != nil || l.err { 1376 return &ParseError{"", "bad TLSA MatchingType", l} 1377 } 1378 rr.MatchingType = uint8(i) 1379 // So this needs be e2 (i.e. different than e), because...??t 1380 s, e3 := endingToString(c, "bad TLSA Certificate") 1381 if e3 != nil { 1382 return e3 1383 } 1384 rr.Certificate = s 1385 return nil 1386} 1387 1388func (rr *SMIMEA) parse(c *zlexer, o string) *ParseError { 1389 l, _ := c.Next() 1390 i, e := strconv.ParseUint(l.token, 10, 8) 1391 if e != nil || l.err { 1392 return &ParseError{"", "bad SMIMEA Usage", l} 1393 } 1394 rr.Usage = uint8(i) 1395 c.Next() // zBlank 1396 l, _ = c.Next() 1397 i, e1 := strconv.ParseUint(l.token, 10, 8) 1398 if e1 != nil || l.err { 1399 return &ParseError{"", "bad SMIMEA Selector", l} 1400 } 1401 rr.Selector = uint8(i) 1402 c.Next() // zBlank 1403 l, _ = c.Next() 1404 i, e2 := strconv.ParseUint(l.token, 10, 8) 1405 if e2 != nil || l.err { 1406 return &ParseError{"", "bad SMIMEA MatchingType", l} 1407 } 1408 rr.MatchingType = uint8(i) 1409 // So this needs be e2 (i.e. different than e), because...??t 1410 s, e3 := endingToString(c, "bad SMIMEA Certificate") 1411 if e3 != nil { 1412 return e3 1413 } 1414 rr.Certificate = s 1415 return nil 1416} 1417 1418func (rr *RFC3597) parse(c *zlexer, o string) *ParseError { 1419 l, _ := c.Next() 1420 if l.token != "\\#" { 1421 return &ParseError{"", "bad RFC3597 Rdata", l} 1422 } 1423 1424 c.Next() // zBlank 1425 l, _ = c.Next() 1426 rdlength, e := strconv.ParseUint(l.token, 10, 16) 1427 if e != nil || l.err { 1428 return &ParseError{"", "bad RFC3597 Rdata ", l} 1429 } 1430 1431 s, e1 := endingToString(c, "bad RFC3597 Rdata") 1432 if e1 != nil { 1433 return e1 1434 } 1435 if int(rdlength)*2 != len(s) { 1436 return &ParseError{"", "bad RFC3597 Rdata", l} 1437 } 1438 rr.Rdata = s 1439 return nil 1440} 1441 1442func (rr *SPF) parse(c *zlexer, o string) *ParseError { 1443 s, e := endingToTxtSlice(c, "bad SPF Txt") 1444 if e != nil { 1445 return e 1446 } 1447 rr.Txt = s 1448 return nil 1449} 1450 1451func (rr *AVC) parse(c *zlexer, o string) *ParseError { 1452 s, e := endingToTxtSlice(c, "bad AVC Txt") 1453 if e != nil { 1454 return e 1455 } 1456 rr.Txt = s 1457 return nil 1458} 1459 1460func (rr *TXT) parse(c *zlexer, o string) *ParseError { 1461 // no zBlank reading here, because all this rdata is TXT 1462 s, e := endingToTxtSlice(c, "bad TXT Txt") 1463 if e != nil { 1464 return e 1465 } 1466 rr.Txt = s 1467 return nil 1468} 1469 1470// identical to setTXT 1471func (rr *NINFO) parse(c *zlexer, o string) *ParseError { 1472 s, e := endingToTxtSlice(c, "bad NINFO ZSData") 1473 if e != nil { 1474 return e 1475 } 1476 rr.ZSData = s 1477 return nil 1478} 1479 1480func (rr *URI) parse(c *zlexer, o string) *ParseError { 1481 l, _ := c.Next() 1482 i, e := strconv.ParseUint(l.token, 10, 16) 1483 if e != nil || l.err { 1484 return &ParseError{"", "bad URI Priority", l} 1485 } 1486 rr.Priority = uint16(i) 1487 c.Next() // zBlank 1488 l, _ = c.Next() 1489 i, e1 := strconv.ParseUint(l.token, 10, 16) 1490 if e1 != nil || l.err { 1491 return &ParseError{"", "bad URI Weight", l} 1492 } 1493 rr.Weight = uint16(i) 1494 1495 c.Next() // zBlank 1496 s, e2 := endingToTxtSlice(c, "bad URI Target") 1497 if e2 != nil { 1498 return e2 1499 } 1500 if len(s) != 1 { 1501 return &ParseError{"", "bad URI Target", l} 1502 } 1503 rr.Target = s[0] 1504 return nil 1505} 1506 1507func (rr *DHCID) parse(c *zlexer, o string) *ParseError { 1508 // awesome record to parse! 1509 s, e := endingToString(c, "bad DHCID Digest") 1510 if e != nil { 1511 return e 1512 } 1513 rr.Digest = s 1514 return nil 1515} 1516 1517func (rr *NID) parse(c *zlexer, o string) *ParseError { 1518 l, _ := c.Next() 1519 i, e := strconv.ParseUint(l.token, 10, 16) 1520 if e != nil || l.err { 1521 return &ParseError{"", "bad NID Preference", l} 1522 } 1523 rr.Preference = uint16(i) 1524 c.Next() // zBlank 1525 l, _ = c.Next() // zString 1526 u, e1 := stringToNodeID(l) 1527 if e1 != nil || l.err { 1528 return e1 1529 } 1530 rr.NodeID = u 1531 return slurpRemainder(c) 1532} 1533 1534func (rr *L32) parse(c *zlexer, o string) *ParseError { 1535 l, _ := c.Next() 1536 i, e := strconv.ParseUint(l.token, 10, 16) 1537 if e != nil || l.err { 1538 return &ParseError{"", "bad L32 Preference", l} 1539 } 1540 rr.Preference = uint16(i) 1541 c.Next() // zBlank 1542 l, _ = c.Next() // zString 1543 rr.Locator32 = net.ParseIP(l.token) 1544 if rr.Locator32 == nil || l.err { 1545 return &ParseError{"", "bad L32 Locator", l} 1546 } 1547 return slurpRemainder(c) 1548} 1549 1550func (rr *LP) parse(c *zlexer, o string) *ParseError { 1551 l, _ := c.Next() 1552 i, e := strconv.ParseUint(l.token, 10, 16) 1553 if e != nil || l.err { 1554 return &ParseError{"", "bad LP Preference", l} 1555 } 1556 rr.Preference = uint16(i) 1557 1558 c.Next() // zBlank 1559 l, _ = c.Next() // zString 1560 rr.Fqdn = l.token 1561 name, nameOk := toAbsoluteName(l.token, o) 1562 if l.err || !nameOk { 1563 return &ParseError{"", "bad LP Fqdn", l} 1564 } 1565 rr.Fqdn = name 1566 return slurpRemainder(c) 1567} 1568 1569func (rr *L64) parse(c *zlexer, o string) *ParseError { 1570 l, _ := c.Next() 1571 i, e := strconv.ParseUint(l.token, 10, 16) 1572 if e != nil || l.err { 1573 return &ParseError{"", "bad L64 Preference", l} 1574 } 1575 rr.Preference = uint16(i) 1576 c.Next() // zBlank 1577 l, _ = c.Next() // zString 1578 u, e1 := stringToNodeID(l) 1579 if e1 != nil || l.err { 1580 return e1 1581 } 1582 rr.Locator64 = u 1583 return slurpRemainder(c) 1584} 1585 1586func (rr *UID) parse(c *zlexer, o string) *ParseError { 1587 l, _ := c.Next() 1588 i, e := strconv.ParseUint(l.token, 10, 32) 1589 if e != nil || l.err { 1590 return &ParseError{"", "bad UID Uid", l} 1591 } 1592 rr.Uid = uint32(i) 1593 return slurpRemainder(c) 1594} 1595 1596func (rr *GID) parse(c *zlexer, o string) *ParseError { 1597 l, _ := c.Next() 1598 i, e := strconv.ParseUint(l.token, 10, 32) 1599 if e != nil || l.err { 1600 return &ParseError{"", "bad GID Gid", l} 1601 } 1602 rr.Gid = uint32(i) 1603 return slurpRemainder(c) 1604} 1605 1606func (rr *UINFO) parse(c *zlexer, o string) *ParseError { 1607 s, e := endingToTxtSlice(c, "bad UINFO Uinfo") 1608 if e != nil { 1609 return e 1610 } 1611 if ln := len(s); ln == 0 { 1612 return nil 1613 } 1614 rr.Uinfo = s[0] // silently discard anything after the first character-string 1615 return nil 1616} 1617 1618func (rr *PX) parse(c *zlexer, o string) *ParseError { 1619 l, _ := c.Next() 1620 i, e := strconv.ParseUint(l.token, 10, 16) 1621 if e != nil || l.err { 1622 return &ParseError{"", "bad PX Preference", l} 1623 } 1624 rr.Preference = uint16(i) 1625 1626 c.Next() // zBlank 1627 l, _ = c.Next() // zString 1628 rr.Map822 = l.token 1629 map822, map822Ok := toAbsoluteName(l.token, o) 1630 if l.err || !map822Ok { 1631 return &ParseError{"", "bad PX Map822", l} 1632 } 1633 rr.Map822 = map822 1634 1635 c.Next() // zBlank 1636 l, _ = c.Next() // zString 1637 rr.Mapx400 = l.token 1638 mapx400, mapx400Ok := toAbsoluteName(l.token, o) 1639 if l.err || !mapx400Ok { 1640 return &ParseError{"", "bad PX Mapx400", l} 1641 } 1642 rr.Mapx400 = mapx400 1643 return slurpRemainder(c) 1644} 1645 1646func (rr *CAA) parse(c *zlexer, o string) *ParseError { 1647 l, _ := c.Next() 1648 i, e := strconv.ParseUint(l.token, 10, 8) 1649 if e != nil || l.err { 1650 return &ParseError{"", "bad CAA Flag", l} 1651 } 1652 rr.Flag = uint8(i) 1653 1654 c.Next() // zBlank 1655 l, _ = c.Next() // zString 1656 if l.value != zString { 1657 return &ParseError{"", "bad CAA Tag", l} 1658 } 1659 rr.Tag = l.token 1660 1661 c.Next() // zBlank 1662 s, e1 := endingToTxtSlice(c, "bad CAA Value") 1663 if e1 != nil { 1664 return e1 1665 } 1666 if len(s) != 1 { 1667 return &ParseError{"", "bad CAA Value", l} 1668 } 1669 rr.Value = s[0] 1670 return nil 1671} 1672 1673func (rr *TKEY) parse(c *zlexer, o string) *ParseError { 1674 l, _ := c.Next() 1675 1676 // Algorithm 1677 if l.value != zString { 1678 return &ParseError{"", "bad TKEY algorithm", l} 1679 } 1680 rr.Algorithm = l.token 1681 c.Next() // zBlank 1682 1683 // Get the key length and key values 1684 l, _ = c.Next() 1685 i, e := strconv.ParseUint(l.token, 10, 8) 1686 if e != nil || l.err { 1687 return &ParseError{"", "bad TKEY key length", l} 1688 } 1689 rr.KeySize = uint16(i) 1690 c.Next() // zBlank 1691 l, _ = c.Next() 1692 if l.value != zString { 1693 return &ParseError{"", "bad TKEY key", l} 1694 } 1695 rr.Key = l.token 1696 c.Next() // zBlank 1697 1698 // Get the otherdata length and string data 1699 l, _ = c.Next() 1700 i, e1 := strconv.ParseUint(l.token, 10, 8) 1701 if e1 != nil || l.err { 1702 return &ParseError{"", "bad TKEY otherdata length", l} 1703 } 1704 rr.OtherLen = uint16(i) 1705 c.Next() // zBlank 1706 l, _ = c.Next() 1707 if l.value != zString { 1708 return &ParseError{"", "bad TKEY otherday", l} 1709 } 1710 rr.OtherData = l.token 1711 return nil 1712} 1713 1714func (rr *APL) parse(c *zlexer, o string) *ParseError { 1715 var prefixes []APLPrefix 1716 1717 for { 1718 l, _ := c.Next() 1719 if l.value == zNewline || l.value == zEOF { 1720 break 1721 } 1722 if l.value == zBlank && prefixes != nil { 1723 continue 1724 } 1725 if l.value != zString { 1726 return &ParseError{"", "unexpected APL field", l} 1727 } 1728 1729 // Expected format: [!]afi:address/prefix 1730 1731 colon := strings.IndexByte(l.token, ':') 1732 if colon == -1 { 1733 return &ParseError{"", "missing colon in APL field", l} 1734 } 1735 1736 family, cidr := l.token[:colon], l.token[colon+1:] 1737 1738 var negation bool 1739 if family != "" && family[0] == '!' { 1740 negation = true 1741 family = family[1:] 1742 } 1743 1744 afi, e := strconv.ParseUint(family, 10, 16) 1745 if e != nil { 1746 return &ParseError{"", "failed to parse APL family: " + e.Error(), l} 1747 } 1748 var addrLen int 1749 switch afi { 1750 case 1: 1751 addrLen = net.IPv4len 1752 case 2: 1753 addrLen = net.IPv6len 1754 default: 1755 return &ParseError{"", "unrecognized APL family", l} 1756 } 1757 1758 ip, subnet, e1 := net.ParseCIDR(cidr) 1759 if e1 != nil { 1760 return &ParseError{"", "failed to parse APL address: " + e1.Error(), l} 1761 } 1762 if !ip.Equal(subnet.IP) { 1763 return &ParseError{"", "extra bits in APL address", l} 1764 } 1765 1766 if len(subnet.IP) != addrLen { 1767 return &ParseError{"", "address mismatch with the APL family", l} 1768 } 1769 1770 prefixes = append(prefixes, APLPrefix{ 1771 Negation: negation, 1772 Network: *subnet, 1773 }) 1774 } 1775 1776 rr.Prefixes = prefixes 1777 return nil 1778} 1779