github.com/moqsien/xraycore@v1.8.5/app/dns/dns_test.go (about) 1 package dns_test 2 3 import ( 4 "testing" 5 "time" 6 7 "github.com/google/go-cmp/cmp" 8 "github.com/miekg/dns" 9 "github.com/moqsien/xraycore/app/dispatcher" 10 . "github.com/moqsien/xraycore/app/dns" 11 "github.com/moqsien/xraycore/app/policy" 12 "github.com/moqsien/xraycore/app/proxyman" 13 _ "github.com/moqsien/xraycore/app/proxyman/outbound" 14 "github.com/moqsien/xraycore/app/router" 15 "github.com/moqsien/xraycore/common" 16 "github.com/moqsien/xraycore/common/errors" 17 "github.com/moqsien/xraycore/common/net" 18 "github.com/moqsien/xraycore/common/serial" 19 "github.com/moqsien/xraycore/core" 20 feature_dns "github.com/moqsien/xraycore/features/dns" 21 "github.com/moqsien/xraycore/proxy/freedom" 22 "github.com/moqsien/xraycore/testing/servers/udp" 23 ) 24 25 type staticHandler struct{} 26 27 func (*staticHandler) ServeDNS(w dns.ResponseWriter, r *dns.Msg) { 28 ans := new(dns.Msg) 29 ans.Id = r.Id 30 31 var clientIP net.IP 32 33 opt := r.IsEdns0() 34 if opt != nil { 35 for _, o := range opt.Option { 36 if o.Option() == dns.EDNS0SUBNET { 37 subnet := o.(*dns.EDNS0_SUBNET) 38 clientIP = subnet.Address 39 } 40 } 41 } 42 43 for _, q := range r.Question { 44 switch { 45 case q.Name == "google.com." && q.Qtype == dns.TypeA: 46 if clientIP == nil { 47 rr, _ := dns.NewRR("google.com. IN A 8.8.8.8") 48 ans.Answer = append(ans.Answer, rr) 49 } else { 50 rr, _ := dns.NewRR("google.com. IN A 8.8.4.4") 51 ans.Answer = append(ans.Answer, rr) 52 } 53 54 case q.Name == "api.google.com." && q.Qtype == dns.TypeA: 55 rr, _ := dns.NewRR("api.google.com. IN A 8.8.7.7") 56 ans.Answer = append(ans.Answer, rr) 57 58 case q.Name == "v2.api.google.com." && q.Qtype == dns.TypeA: 59 rr, _ := dns.NewRR("v2.api.google.com. IN A 8.8.7.8") 60 ans.Answer = append(ans.Answer, rr) 61 62 case q.Name == "facebook.com." && q.Qtype == dns.TypeA: 63 rr, _ := dns.NewRR("facebook.com. IN A 9.9.9.9") 64 ans.Answer = append(ans.Answer, rr) 65 66 case q.Name == "ipv6.google.com." && q.Qtype == dns.TypeA: 67 rr, err := dns.NewRR("ipv6.google.com. IN A 8.8.8.7") 68 common.Must(err) 69 ans.Answer = append(ans.Answer, rr) 70 71 case q.Name == "ipv6.google.com." && q.Qtype == dns.TypeAAAA: 72 rr, err := dns.NewRR("ipv6.google.com. IN AAAA 2001:4860:4860::8888") 73 common.Must(err) 74 ans.Answer = append(ans.Answer, rr) 75 76 case q.Name == "notexist.google.com." && q.Qtype == dns.TypeAAAA: 77 ans.MsgHdr.Rcode = dns.RcodeNameError 78 79 case q.Name == "hostname." && q.Qtype == dns.TypeA: 80 rr, _ := dns.NewRR("hostname. IN A 127.0.0.1") 81 ans.Answer = append(ans.Answer, rr) 82 83 case q.Name == "hostname.local." && q.Qtype == dns.TypeA: 84 rr, _ := dns.NewRR("hostname.local. IN A 127.0.0.1") 85 ans.Answer = append(ans.Answer, rr) 86 87 case q.Name == "hostname.localdomain." && q.Qtype == dns.TypeA: 88 rr, _ := dns.NewRR("hostname.localdomain. IN A 127.0.0.1") 89 ans.Answer = append(ans.Answer, rr) 90 91 case q.Name == "localhost." && q.Qtype == dns.TypeA: 92 rr, _ := dns.NewRR("localhost. IN A 127.0.0.2") 93 ans.Answer = append(ans.Answer, rr) 94 95 case q.Name == "localhost-a." && q.Qtype == dns.TypeA: 96 rr, _ := dns.NewRR("localhost-a. IN A 127.0.0.3") 97 ans.Answer = append(ans.Answer, rr) 98 99 case q.Name == "localhost-b." && q.Qtype == dns.TypeA: 100 rr, _ := dns.NewRR("localhost-b. IN A 127.0.0.4") 101 ans.Answer = append(ans.Answer, rr) 102 103 case q.Name == "Mijia\\ Cloud." && q.Qtype == dns.TypeA: 104 rr, _ := dns.NewRR("Mijia\\ Cloud. IN A 127.0.0.1") 105 ans.Answer = append(ans.Answer, rr) 106 } 107 } 108 w.WriteMsg(ans) 109 } 110 111 func TestUDPServerSubnet(t *testing.T) { 112 port := udp.PickPort() 113 114 dnsServer := dns.Server{ 115 Addr: "127.0.0.1:" + port.String(), 116 Net: "udp", 117 Handler: &staticHandler{}, 118 UDPSize: 1200, 119 } 120 121 go dnsServer.ListenAndServe() 122 time.Sleep(time.Second) 123 124 config := &core.Config{ 125 App: []*serial.TypedMessage{ 126 serial.ToTypedMessage(&Config{ 127 NameServers: []*net.Endpoint{ 128 { 129 Network: net.Network_UDP, 130 Address: &net.IPOrDomain{ 131 Address: &net.IPOrDomain_Ip{ 132 Ip: []byte{127, 0, 0, 1}, 133 }, 134 }, 135 Port: uint32(port), 136 }, 137 }, 138 ClientIp: []byte{7, 8, 9, 10}, 139 }), 140 serial.ToTypedMessage(&dispatcher.Config{}), 141 serial.ToTypedMessage(&proxyman.OutboundConfig{}), 142 serial.ToTypedMessage(&policy.Config{}), 143 }, 144 Outbound: []*core.OutboundHandlerConfig{ 145 { 146 ProxySettings: serial.ToTypedMessage(&freedom.Config{}), 147 }, 148 }, 149 } 150 151 v, err := core.New(config) 152 common.Must(err) 153 154 client := v.GetFeature(feature_dns.ClientType()).(feature_dns.Client) 155 156 ips, err := client.LookupIP("google.com", feature_dns.IPOption{ 157 IPv4Enable: true, 158 IPv6Enable: true, 159 FakeEnable: false, 160 }) 161 if err != nil { 162 t.Fatal("unexpected error: ", err) 163 } 164 165 if r := cmp.Diff(ips, []net.IP{{8, 8, 4, 4}}); r != "" { 166 t.Fatal(r) 167 } 168 } 169 170 func TestUDPServer(t *testing.T) { 171 port := udp.PickPort() 172 173 dnsServer := dns.Server{ 174 Addr: "127.0.0.1:" + port.String(), 175 Net: "udp", 176 Handler: &staticHandler{}, 177 UDPSize: 1200, 178 } 179 180 go dnsServer.ListenAndServe() 181 time.Sleep(time.Second) 182 183 config := &core.Config{ 184 App: []*serial.TypedMessage{ 185 serial.ToTypedMessage(&Config{ 186 NameServers: []*net.Endpoint{ 187 { 188 Network: net.Network_UDP, 189 Address: &net.IPOrDomain{ 190 Address: &net.IPOrDomain_Ip{ 191 Ip: []byte{127, 0, 0, 1}, 192 }, 193 }, 194 Port: uint32(port), 195 }, 196 }, 197 }), 198 serial.ToTypedMessage(&dispatcher.Config{}), 199 serial.ToTypedMessage(&proxyman.OutboundConfig{}), 200 serial.ToTypedMessage(&policy.Config{}), 201 }, 202 Outbound: []*core.OutboundHandlerConfig{ 203 { 204 ProxySettings: serial.ToTypedMessage(&freedom.Config{}), 205 }, 206 }, 207 } 208 209 v, err := core.New(config) 210 common.Must(err) 211 212 client := v.GetFeature(feature_dns.ClientType()).(feature_dns.Client) 213 214 { 215 ips, err := client.LookupIP("google.com", feature_dns.IPOption{ 216 IPv4Enable: true, 217 IPv6Enable: true, 218 FakeEnable: false, 219 }) 220 if err != nil { 221 t.Fatal("unexpected error: ", err) 222 } 223 224 if r := cmp.Diff(ips, []net.IP{{8, 8, 8, 8}}); r != "" { 225 t.Fatal(r) 226 } 227 } 228 229 { 230 ips, err := client.LookupIP("facebook.com", feature_dns.IPOption{ 231 IPv4Enable: true, 232 IPv6Enable: true, 233 FakeEnable: false, 234 }) 235 if err != nil { 236 t.Fatal("unexpected error: ", err) 237 } 238 239 if r := cmp.Diff(ips, []net.IP{{9, 9, 9, 9}}); r != "" { 240 t.Fatal(r) 241 } 242 } 243 244 { 245 _, err := client.LookupIP("notexist.google.com", feature_dns.IPOption{ 246 IPv4Enable: true, 247 IPv6Enable: true, 248 FakeEnable: false, 249 }) 250 if err == nil { 251 t.Fatal("nil error") 252 } 253 if r := feature_dns.RCodeFromError(err); r != uint16(dns.RcodeNameError) { 254 t.Fatal("expected NameError, but got ", r) 255 } 256 } 257 258 { 259 ips, err := client.LookupIP("ipv4only.google.com", feature_dns.IPOption{ 260 IPv4Enable: false, 261 IPv6Enable: true, 262 FakeEnable: false, 263 }) 264 if !errors.AllEqual(feature_dns.ErrEmptyResponse, errors.Cause(err)) { 265 t.Fatal("error: ", err) 266 } 267 if len(ips) != 0 { 268 t.Fatal("ips: ", ips) 269 } 270 } 271 272 dnsServer.Shutdown() 273 274 { 275 ips, err := client.LookupIP("google.com", feature_dns.IPOption{ 276 IPv4Enable: true, 277 IPv6Enable: true, 278 FakeEnable: false, 279 }) 280 if err != nil { 281 t.Fatal("unexpected error: ", err) 282 } 283 284 if r := cmp.Diff(ips, []net.IP{{8, 8, 8, 8}}); r != "" { 285 t.Fatal(r) 286 } 287 } 288 } 289 290 func TestPrioritizedDomain(t *testing.T) { 291 port := udp.PickPort() 292 293 dnsServer := dns.Server{ 294 Addr: "127.0.0.1:" + port.String(), 295 Net: "udp", 296 Handler: &staticHandler{}, 297 UDPSize: 1200, 298 } 299 300 go dnsServer.ListenAndServe() 301 time.Sleep(time.Second) 302 303 config := &core.Config{ 304 App: []*serial.TypedMessage{ 305 serial.ToTypedMessage(&Config{ 306 NameServers: []*net.Endpoint{ 307 { 308 Network: net.Network_UDP, 309 Address: &net.IPOrDomain{ 310 Address: &net.IPOrDomain_Ip{ 311 Ip: []byte{127, 0, 0, 1}, 312 }, 313 }, 314 Port: 9999, /* unreachable */ 315 }, 316 }, 317 NameServer: []*NameServer{ 318 { 319 Address: &net.Endpoint{ 320 Network: net.Network_UDP, 321 Address: &net.IPOrDomain{ 322 Address: &net.IPOrDomain_Ip{ 323 Ip: []byte{127, 0, 0, 1}, 324 }, 325 }, 326 Port: uint32(port), 327 }, 328 PrioritizedDomain: []*NameServer_PriorityDomain{ 329 { 330 Type: DomainMatchingType_Full, 331 Domain: "google.com", 332 }, 333 }, 334 }, 335 }, 336 }), 337 serial.ToTypedMessage(&dispatcher.Config{}), 338 serial.ToTypedMessage(&proxyman.OutboundConfig{}), 339 serial.ToTypedMessage(&policy.Config{}), 340 }, 341 Outbound: []*core.OutboundHandlerConfig{ 342 { 343 ProxySettings: serial.ToTypedMessage(&freedom.Config{}), 344 }, 345 }, 346 } 347 348 v, err := core.New(config) 349 common.Must(err) 350 351 client := v.GetFeature(feature_dns.ClientType()).(feature_dns.Client) 352 353 startTime := time.Now() 354 355 { 356 ips, err := client.LookupIP("google.com", feature_dns.IPOption{ 357 IPv4Enable: true, 358 IPv6Enable: true, 359 FakeEnable: false, 360 }) 361 if err != nil { 362 t.Fatal("unexpected error: ", err) 363 } 364 365 if r := cmp.Diff(ips, []net.IP{{8, 8, 8, 8}}); r != "" { 366 t.Fatal(r) 367 } 368 } 369 370 endTime := time.Now() 371 if startTime.After(endTime.Add(time.Second * 2)) { 372 t.Error("DNS query doesn't finish in 2 seconds.") 373 } 374 } 375 376 func TestUDPServerIPv6(t *testing.T) { 377 port := udp.PickPort() 378 379 dnsServer := dns.Server{ 380 Addr: "127.0.0.1:" + port.String(), 381 Net: "udp", 382 Handler: &staticHandler{}, 383 UDPSize: 1200, 384 } 385 386 go dnsServer.ListenAndServe() 387 time.Sleep(time.Second) 388 389 config := &core.Config{ 390 App: []*serial.TypedMessage{ 391 serial.ToTypedMessage(&Config{ 392 NameServers: []*net.Endpoint{ 393 { 394 Network: net.Network_UDP, 395 Address: &net.IPOrDomain{ 396 Address: &net.IPOrDomain_Ip{ 397 Ip: []byte{127, 0, 0, 1}, 398 }, 399 }, 400 Port: uint32(port), 401 }, 402 }, 403 }), 404 serial.ToTypedMessage(&dispatcher.Config{}), 405 serial.ToTypedMessage(&proxyman.OutboundConfig{}), 406 serial.ToTypedMessage(&policy.Config{}), 407 }, 408 Outbound: []*core.OutboundHandlerConfig{ 409 { 410 ProxySettings: serial.ToTypedMessage(&freedom.Config{}), 411 }, 412 }, 413 } 414 415 v, err := core.New(config) 416 common.Must(err) 417 418 client := v.GetFeature(feature_dns.ClientType()).(feature_dns.Client) 419 { 420 ips, err := client.LookupIP("ipv6.google.com", feature_dns.IPOption{ 421 IPv4Enable: false, 422 IPv6Enable: true, 423 FakeEnable: false, 424 }) 425 if err != nil { 426 t.Fatal("unexpected error: ", err) 427 } 428 429 if r := cmp.Diff(ips, []net.IP{{32, 1, 72, 96, 72, 96, 0, 0, 0, 0, 0, 0, 0, 0, 136, 136}}); r != "" { 430 t.Fatal(r) 431 } 432 } 433 } 434 435 func TestStaticHostDomain(t *testing.T) { 436 port := udp.PickPort() 437 438 dnsServer := dns.Server{ 439 Addr: "127.0.0.1:" + port.String(), 440 Net: "udp", 441 Handler: &staticHandler{}, 442 UDPSize: 1200, 443 } 444 445 go dnsServer.ListenAndServe() 446 time.Sleep(time.Second) 447 448 config := &core.Config{ 449 App: []*serial.TypedMessage{ 450 serial.ToTypedMessage(&Config{ 451 NameServers: []*net.Endpoint{ 452 { 453 Network: net.Network_UDP, 454 Address: &net.IPOrDomain{ 455 Address: &net.IPOrDomain_Ip{ 456 Ip: []byte{127, 0, 0, 1}, 457 }, 458 }, 459 Port: uint32(port), 460 }, 461 }, 462 StaticHosts: []*Config_HostMapping{ 463 { 464 Type: DomainMatchingType_Full, 465 Domain: "example.com", 466 ProxiedDomain: "google.com", 467 }, 468 }, 469 }), 470 serial.ToTypedMessage(&dispatcher.Config{}), 471 serial.ToTypedMessage(&proxyman.OutboundConfig{}), 472 serial.ToTypedMessage(&policy.Config{}), 473 }, 474 Outbound: []*core.OutboundHandlerConfig{ 475 { 476 ProxySettings: serial.ToTypedMessage(&freedom.Config{}), 477 }, 478 }, 479 } 480 481 v, err := core.New(config) 482 common.Must(err) 483 484 client := v.GetFeature(feature_dns.ClientType()).(feature_dns.Client) 485 486 { 487 ips, err := client.LookupIP("example.com", feature_dns.IPOption{ 488 IPv4Enable: true, 489 IPv6Enable: true, 490 FakeEnable: false, 491 }) 492 if err != nil { 493 t.Fatal("unexpected error: ", err) 494 } 495 496 if r := cmp.Diff(ips, []net.IP{{8, 8, 8, 8}}); r != "" { 497 t.Fatal(r) 498 } 499 } 500 501 dnsServer.Shutdown() 502 } 503 504 func TestIPMatch(t *testing.T) { 505 port := udp.PickPort() 506 507 dnsServer := dns.Server{ 508 Addr: "127.0.0.1:" + port.String(), 509 Net: "udp", 510 Handler: &staticHandler{}, 511 UDPSize: 1200, 512 } 513 514 go dnsServer.ListenAndServe() 515 time.Sleep(time.Second) 516 517 config := &core.Config{ 518 App: []*serial.TypedMessage{ 519 serial.ToTypedMessage(&Config{ 520 NameServer: []*NameServer{ 521 // private dns, not match 522 { 523 Address: &net.Endpoint{ 524 Network: net.Network_UDP, 525 Address: &net.IPOrDomain{ 526 Address: &net.IPOrDomain_Ip{ 527 Ip: []byte{127, 0, 0, 1}, 528 }, 529 }, 530 Port: uint32(port), 531 }, 532 Geoip: []*router.GeoIP{ 533 { 534 CountryCode: "local", 535 Cidr: []*router.CIDR{ 536 { 537 // inner ip, will not match 538 Ip: []byte{192, 168, 11, 1}, 539 Prefix: 32, 540 }, 541 }, 542 }, 543 }, 544 }, 545 // second dns, match ip 546 { 547 Address: &net.Endpoint{ 548 Network: net.Network_UDP, 549 Address: &net.IPOrDomain{ 550 Address: &net.IPOrDomain_Ip{ 551 Ip: []byte{127, 0, 0, 1}, 552 }, 553 }, 554 Port: uint32(port), 555 }, 556 Geoip: []*router.GeoIP{ 557 { 558 CountryCode: "test", 559 Cidr: []*router.CIDR{ 560 { 561 Ip: []byte{8, 8, 8, 8}, 562 Prefix: 32, 563 }, 564 }, 565 }, 566 { 567 CountryCode: "test", 568 Cidr: []*router.CIDR{ 569 { 570 Ip: []byte{8, 8, 8, 4}, 571 Prefix: 32, 572 }, 573 }, 574 }, 575 }, 576 }, 577 }, 578 }), 579 serial.ToTypedMessage(&dispatcher.Config{}), 580 serial.ToTypedMessage(&proxyman.OutboundConfig{}), 581 serial.ToTypedMessage(&policy.Config{}), 582 }, 583 Outbound: []*core.OutboundHandlerConfig{ 584 { 585 ProxySettings: serial.ToTypedMessage(&freedom.Config{}), 586 }, 587 }, 588 } 589 590 v, err := core.New(config) 591 common.Must(err) 592 593 client := v.GetFeature(feature_dns.ClientType()).(feature_dns.Client) 594 595 startTime := time.Now() 596 597 { 598 ips, err := client.LookupIP("google.com", feature_dns.IPOption{ 599 IPv4Enable: true, 600 IPv6Enable: true, 601 FakeEnable: false, 602 }) 603 if err != nil { 604 t.Fatal("unexpected error: ", err) 605 } 606 607 if r := cmp.Diff(ips, []net.IP{{8, 8, 8, 8}}); r != "" { 608 t.Fatal(r) 609 } 610 } 611 612 endTime := time.Now() 613 if startTime.After(endTime.Add(time.Second * 2)) { 614 t.Error("DNS query doesn't finish in 2 seconds.") 615 } 616 } 617 618 func TestLocalDomain(t *testing.T) { 619 port := udp.PickPort() 620 621 dnsServer := dns.Server{ 622 Addr: "127.0.0.1:" + port.String(), 623 Net: "udp", 624 Handler: &staticHandler{}, 625 UDPSize: 1200, 626 } 627 628 go dnsServer.ListenAndServe() 629 time.Sleep(time.Second) 630 631 config := &core.Config{ 632 App: []*serial.TypedMessage{ 633 serial.ToTypedMessage(&Config{ 634 NameServers: []*net.Endpoint{ 635 { 636 Network: net.Network_UDP, 637 Address: &net.IPOrDomain{ 638 Address: &net.IPOrDomain_Ip{ 639 Ip: []byte{127, 0, 0, 1}, 640 }, 641 }, 642 Port: 9999, /* unreachable */ 643 }, 644 }, 645 NameServer: []*NameServer{ 646 { 647 Address: &net.Endpoint{ 648 Network: net.Network_UDP, 649 Address: &net.IPOrDomain{ 650 Address: &net.IPOrDomain_Ip{ 651 Ip: []byte{127, 0, 0, 1}, 652 }, 653 }, 654 Port: uint32(port), 655 }, 656 PrioritizedDomain: []*NameServer_PriorityDomain{ 657 // Equivalent of dotless:localhost 658 {Type: DomainMatchingType_Regex, Domain: "^[^.]*localhost[^.]*$"}, 659 }, 660 Geoip: []*router.GeoIP{ 661 { // Will match localhost, localhost-a and localhost-b, 662 CountryCode: "local", 663 Cidr: []*router.CIDR{ 664 {Ip: []byte{127, 0, 0, 2}, Prefix: 32}, 665 {Ip: []byte{127, 0, 0, 3}, Prefix: 32}, 666 {Ip: []byte{127, 0, 0, 4}, Prefix: 32}, 667 }, 668 }, 669 }, 670 }, 671 { 672 Address: &net.Endpoint{ 673 Network: net.Network_UDP, 674 Address: &net.IPOrDomain{ 675 Address: &net.IPOrDomain_Ip{ 676 Ip: []byte{127, 0, 0, 1}, 677 }, 678 }, 679 Port: uint32(port), 680 }, 681 PrioritizedDomain: []*NameServer_PriorityDomain{ 682 // Equivalent of dotless: and domain:local 683 {Type: DomainMatchingType_Regex, Domain: "^[^.]*$"}, 684 {Type: DomainMatchingType_Subdomain, Domain: "local"}, 685 {Type: DomainMatchingType_Subdomain, Domain: "localdomain"}, 686 }, 687 }, 688 }, 689 StaticHosts: []*Config_HostMapping{ 690 { 691 Type: DomainMatchingType_Full, 692 Domain: "hostnamestatic", 693 Ip: [][]byte{{127, 0, 0, 53}}, 694 }, 695 { 696 Type: DomainMatchingType_Full, 697 Domain: "hostnamealias", 698 ProxiedDomain: "hostname.localdomain", 699 }, 700 }, 701 }), 702 serial.ToTypedMessage(&dispatcher.Config{}), 703 serial.ToTypedMessage(&proxyman.OutboundConfig{}), 704 serial.ToTypedMessage(&policy.Config{}), 705 }, 706 Outbound: []*core.OutboundHandlerConfig{ 707 { 708 ProxySettings: serial.ToTypedMessage(&freedom.Config{}), 709 }, 710 }, 711 } 712 713 v, err := core.New(config) 714 common.Must(err) 715 716 client := v.GetFeature(feature_dns.ClientType()).(feature_dns.Client) 717 718 startTime := time.Now() 719 720 { // Will match dotless: 721 ips, err := client.LookupIP("hostname", feature_dns.IPOption{ 722 IPv4Enable: true, 723 IPv6Enable: true, 724 FakeEnable: false, 725 }) 726 if err != nil { 727 t.Fatal("unexpected error: ", err) 728 } 729 730 if r := cmp.Diff(ips, []net.IP{{127, 0, 0, 1}}); r != "" { 731 t.Fatal(r) 732 } 733 } 734 735 { // Will match domain:local 736 ips, err := client.LookupIP("hostname.local", feature_dns.IPOption{ 737 IPv4Enable: true, 738 IPv6Enable: true, 739 FakeEnable: false, 740 }) 741 if err != nil { 742 t.Fatal("unexpected error: ", err) 743 } 744 745 if r := cmp.Diff(ips, []net.IP{{127, 0, 0, 1}}); r != "" { 746 t.Fatal(r) 747 } 748 } 749 750 { // Will match static ip 751 ips, err := client.LookupIP("hostnamestatic", feature_dns.IPOption{ 752 IPv4Enable: true, 753 IPv6Enable: true, 754 FakeEnable: false, 755 }) 756 if err != nil { 757 t.Fatal("unexpected error: ", err) 758 } 759 760 if r := cmp.Diff(ips, []net.IP{{127, 0, 0, 53}}); r != "" { 761 t.Fatal(r) 762 } 763 } 764 765 { // Will match domain replacing 766 ips, err := client.LookupIP("hostnamealias", feature_dns.IPOption{ 767 IPv4Enable: true, 768 IPv6Enable: true, 769 FakeEnable: false, 770 }) 771 if err != nil { 772 t.Fatal("unexpected error: ", err) 773 } 774 775 if r := cmp.Diff(ips, []net.IP{{127, 0, 0, 1}}); r != "" { 776 t.Fatal(r) 777 } 778 } 779 780 { // Will match dotless:localhost, but not expectIPs: 127.0.0.2, 127.0.0.3, then matches at dotless: 781 ips, err := client.LookupIP("localhost", feature_dns.IPOption{ 782 IPv4Enable: true, 783 IPv6Enable: true, 784 FakeEnable: false, 785 }) 786 if err != nil { 787 t.Fatal("unexpected error: ", err) 788 } 789 790 if r := cmp.Diff(ips, []net.IP{{127, 0, 0, 2}}); r != "" { 791 t.Fatal(r) 792 } 793 } 794 795 { // Will match dotless:localhost, and expectIPs: 127.0.0.2, 127.0.0.3 796 ips, err := client.LookupIP("localhost-a", feature_dns.IPOption{ 797 IPv4Enable: true, 798 IPv6Enable: true, 799 FakeEnable: false, 800 }) 801 if err != nil { 802 t.Fatal("unexpected error: ", err) 803 } 804 805 if r := cmp.Diff(ips, []net.IP{{127, 0, 0, 3}}); r != "" { 806 t.Fatal(r) 807 } 808 } 809 810 { // Will match dotless:localhost, and expectIPs: 127.0.0.2, 127.0.0.3 811 ips, err := client.LookupIP("localhost-b", feature_dns.IPOption{ 812 IPv4Enable: true, 813 IPv6Enable: true, 814 FakeEnable: false, 815 }) 816 if err != nil { 817 t.Fatal("unexpected error: ", err) 818 } 819 820 if r := cmp.Diff(ips, []net.IP{{127, 0, 0, 4}}); r != "" { 821 t.Fatal(r) 822 } 823 } 824 825 { // Will match dotless: 826 ips, err := client.LookupIP("Mijia Cloud", feature_dns.IPOption{ 827 IPv4Enable: true, 828 IPv6Enable: true, 829 FakeEnable: false, 830 }) 831 if err != nil { 832 t.Fatal("unexpected error: ", err) 833 } 834 835 if r := cmp.Diff(ips, []net.IP{{127, 0, 0, 1}}); r != "" { 836 t.Fatal(r) 837 } 838 } 839 840 endTime := time.Now() 841 if startTime.After(endTime.Add(time.Second * 2)) { 842 t.Error("DNS query doesn't finish in 2 seconds.") 843 } 844 } 845 846 func TestMultiMatchPrioritizedDomain(t *testing.T) { 847 port := udp.PickPort() 848 849 dnsServer := dns.Server{ 850 Addr: "127.0.0.1:" + port.String(), 851 Net: "udp", 852 Handler: &staticHandler{}, 853 UDPSize: 1200, 854 } 855 856 go dnsServer.ListenAndServe() 857 time.Sleep(time.Second) 858 859 config := &core.Config{ 860 App: []*serial.TypedMessage{ 861 serial.ToTypedMessage(&Config{ 862 NameServers: []*net.Endpoint{ 863 { 864 Network: net.Network_UDP, 865 Address: &net.IPOrDomain{ 866 Address: &net.IPOrDomain_Ip{ 867 Ip: []byte{127, 0, 0, 1}, 868 }, 869 }, 870 Port: 9999, /* unreachable */ 871 }, 872 }, 873 NameServer: []*NameServer{ 874 { 875 Address: &net.Endpoint{ 876 Network: net.Network_UDP, 877 Address: &net.IPOrDomain{ 878 Address: &net.IPOrDomain_Ip{ 879 Ip: []byte{127, 0, 0, 1}, 880 }, 881 }, 882 Port: uint32(port), 883 }, 884 PrioritizedDomain: []*NameServer_PriorityDomain{ 885 { 886 Type: DomainMatchingType_Subdomain, 887 Domain: "google.com", 888 }, 889 }, 890 Geoip: []*router.GeoIP{ 891 { // Will only match 8.8.8.8 and 8.8.4.4 892 Cidr: []*router.CIDR{ 893 {Ip: []byte{8, 8, 8, 8}, Prefix: 32}, 894 {Ip: []byte{8, 8, 4, 4}, Prefix: 32}, 895 }, 896 }, 897 }, 898 }, 899 { 900 Address: &net.Endpoint{ 901 Network: net.Network_UDP, 902 Address: &net.IPOrDomain{ 903 Address: &net.IPOrDomain_Ip{ 904 Ip: []byte{127, 0, 0, 1}, 905 }, 906 }, 907 Port: uint32(port), 908 }, 909 PrioritizedDomain: []*NameServer_PriorityDomain{ 910 { 911 Type: DomainMatchingType_Subdomain, 912 Domain: "google.com", 913 }, 914 }, 915 Geoip: []*router.GeoIP{ 916 { // Will match 8.8.8.8 and 8.8.8.7, etc 917 Cidr: []*router.CIDR{ 918 {Ip: []byte{8, 8, 8, 7}, Prefix: 24}, 919 }, 920 }, 921 }, 922 }, 923 { 924 Address: &net.Endpoint{ 925 Network: net.Network_UDP, 926 Address: &net.IPOrDomain{ 927 Address: &net.IPOrDomain_Ip{ 928 Ip: []byte{127, 0, 0, 1}, 929 }, 930 }, 931 Port: uint32(port), 932 }, 933 PrioritizedDomain: []*NameServer_PriorityDomain{ 934 { 935 Type: DomainMatchingType_Subdomain, 936 Domain: "api.google.com", 937 }, 938 }, 939 Geoip: []*router.GeoIP{ 940 { // Will only match 8.8.7.7 (api.google.com) 941 Cidr: []*router.CIDR{ 942 {Ip: []byte{8, 8, 7, 7}, Prefix: 32}, 943 }, 944 }, 945 }, 946 }, 947 { 948 Address: &net.Endpoint{ 949 Network: net.Network_UDP, 950 Address: &net.IPOrDomain{ 951 Address: &net.IPOrDomain_Ip{ 952 Ip: []byte{127, 0, 0, 1}, 953 }, 954 }, 955 Port: uint32(port), 956 }, 957 PrioritizedDomain: []*NameServer_PriorityDomain{ 958 { 959 Type: DomainMatchingType_Full, 960 Domain: "v2.api.google.com", 961 }, 962 }, 963 Geoip: []*router.GeoIP{ 964 { // Will only match 8.8.7.8 (v2.api.google.com) 965 Cidr: []*router.CIDR{ 966 {Ip: []byte{8, 8, 7, 8}, Prefix: 32}, 967 }, 968 }, 969 }, 970 }, 971 }, 972 }), 973 serial.ToTypedMessage(&dispatcher.Config{}), 974 serial.ToTypedMessage(&proxyman.OutboundConfig{}), 975 serial.ToTypedMessage(&policy.Config{}), 976 }, 977 Outbound: []*core.OutboundHandlerConfig{ 978 { 979 ProxySettings: serial.ToTypedMessage(&freedom.Config{}), 980 }, 981 }, 982 } 983 984 v, err := core.New(config) 985 common.Must(err) 986 987 client := v.GetFeature(feature_dns.ClientType()).(feature_dns.Client) 988 989 startTime := time.Now() 990 991 { // Will match server 1,2 and server 1 returns expected ip 992 ips, err := client.LookupIP("google.com", feature_dns.IPOption{ 993 IPv4Enable: true, 994 IPv6Enable: true, 995 FakeEnable: false, 996 }) 997 if err != nil { 998 t.Fatal("unexpected error: ", err) 999 } 1000 1001 if r := cmp.Diff(ips, []net.IP{{8, 8, 8, 8}}); r != "" { 1002 t.Fatal(r) 1003 } 1004 } 1005 1006 { // Will match server 1,2 and server 1 returns unexpected ip, then server 2 returns expected one 1007 ips, err := client.LookupIP("ipv6.google.com", feature_dns.IPOption{ 1008 IPv4Enable: true, 1009 IPv6Enable: false, 1010 FakeEnable: false, 1011 }) 1012 if err != nil { 1013 t.Fatal("unexpected error: ", err) 1014 } 1015 1016 if r := cmp.Diff(ips, []net.IP{{8, 8, 8, 7}}); r != "" { 1017 t.Fatal(r) 1018 } 1019 } 1020 1021 { // Will match server 3,1,2 and server 3 returns expected one 1022 ips, err := client.LookupIP("api.google.com", feature_dns.IPOption{ 1023 IPv4Enable: true, 1024 IPv6Enable: true, 1025 FakeEnable: false, 1026 }) 1027 if err != nil { 1028 t.Fatal("unexpected error: ", err) 1029 } 1030 1031 if r := cmp.Diff(ips, []net.IP{{8, 8, 7, 7}}); r != "" { 1032 t.Fatal(r) 1033 } 1034 } 1035 1036 { // Will match server 4,3,1,2 and server 4 returns expected one 1037 ips, err := client.LookupIP("v2.api.google.com", feature_dns.IPOption{ 1038 IPv4Enable: true, 1039 IPv6Enable: true, 1040 FakeEnable: false, 1041 }) 1042 if err != nil { 1043 t.Fatal("unexpected error: ", err) 1044 } 1045 1046 if r := cmp.Diff(ips, []net.IP{{8, 8, 7, 8}}); r != "" { 1047 t.Fatal(r) 1048 } 1049 } 1050 1051 endTime := time.Now() 1052 if startTime.After(endTime.Add(time.Second * 2)) { 1053 t.Error("DNS query doesn't finish in 2 seconds.") 1054 } 1055 }