blob: 5a87d1d13d4406bb93c270705966a920cd5fe89c [file] [log] [blame]
Tim Windelschmidt6d33a432025-02-04 14:34:25 +01001// Copyright The Monogon Project Authors.
2// SPDX-License-Identifier: Apache-2.0
3
Jan Schär4a180222024-07-29 16:32:54 +02004package dns
5
6import (
7 "testing"
8)
9
10func TestIsSubDomain(t *testing.T) {
11 cases := []struct {
12 parent, child string
13 expected bool
14 }{
15 {".", ".", true},
16 {".", "test.", true},
17 {"example.com.", "example.com.", true},
18 {"example.com.", "www.example.com.", true},
19 {"example.com.", "xample.com.", false},
20 {"example.com.", "www.axample.com.", false},
21 {"example.com.", "wwwexample.com.", false},
22 {"example.com.", `www\.example.com.`, false},
23 {"example.com.", `www\\.example.com.`, true},
24 }
25 for _, c := range cases {
26 if IsSubDomain(c.parent, c.child) != c.expected {
27 t.Errorf("IsSubDomain(%q, %q): expected %v", c.parent, c.child, c.expected)
28 }
29 }
30}
31
32func TestSplitLastLabel(t *testing.T) {
33 cases := []struct {
34 name, rest, label string
35 }{
36 {"", "", ""},
37 {".", "", ""},
38 {"com.", "", "com"},
39 {"www.example.com", "www.example.", "com"},
40 {"www.example.com.", "www.example.", "com"},
41 {`www.example\.com.`, "www.", `example\.com`},
42 {`www.example\\.com.`, `www.example\\.`, "com"},
43 }
44 for _, c := range cases {
45 rest, label := SplitLastLabel(c.name)
46 if rest != c.rest || label != c.label {
47 t.Errorf("SplitLastLabel(%q) = (%q, %q), expected (%q, %q)", c.name, rest, label, c.rest, c.label)
48 }
49 }
50}
51
52func TestParseReverse(t *testing.T) {
53 cases := []struct {
54 name string
55 ip string
56 bits int
57 extra bool
58 }{
59 {"example.", "invalid IP", 0, false},
60 {"0.10.200.255.in-addr.arpa.", "255.200.10.0", 32, false},
61 {"7.6.45.123.in-addr.arpa.", "123.45.6.7", 32, false},
62 {"6.45.123.in-addr.arpa.", "123.45.6.0", 24, false},
63 {"45.123.in-addr.arpa.", "123.45.0.0", 16, false},
64 {"123.in-addr.arpa.", "123.0.0.0", 8, false},
65 {"in-addr.arpa.", "0.0.0.0", 0, false},
66 {"8.7.6.45.123.in-addr.arpa.", "123.45.6.7", 32, true}, // too many fields
67 {".6.45.123.in-addr.arpa.", "123.45.6.0", 24, true}, // empty field
68 {"7.06.45.123.in-addr.arpa.", "123.45.0.0", 16, true}, // leading 0
69 {"7.256.45.123.in-addr.arpa.", "123.45.0.0", 16, true}, // number too large
70 {"a6.45.123.in-addr.arpa.", "123.45.0.0", 16, true}, // invalid character
71 {`7\.6.45.123.in-addr.arpa.`, "123.45.0.0", 16, true}, // escaped .
72 {"0.6.45.123in-addr.arpa.", "invalid IP", 0, false}, // missing .
73 {
74 "0.1.2.3.4.5.6.7.8.9.a.b.c.d.e.f.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.ip6.arpa.",
75 "::fedc:ba98:7654:3210",
76 128,
77 false,
78 },
79 {
80 "1.2.3.4.5.6.7.8.9.a.b.c.d.e.f.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.ip6.arpa.",
81 "::fedc:ba98:7654:3210",
82 124,
83 false,
84 },
85 {
86 "2.3.4.5.6.7.8.9.a.b.c.d.e.f.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.ip6.arpa.",
87 "::fedc:ba98:7654:3200",
88 120,
89 false,
90 },
91 {
92 "3.4.5.6.7.8.9.a.b.c.d.e.f.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.ip6.arpa.",
93 "::fedc:ba98:7654:3000",
94 116,
95 false,
96 },
97 {
98 "2.ip6.arpa.",
99 "2000::",
100 4,
101 false,
102 },
103 {
104 "ip6.arpa.",
105 "::",
106 0,
107 false,
108 },
109 {
110 "0.0.1.2.3.4.5.6.7.8.9.a.b.c.d.e.f.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.ip6.arpa.", // too long
111 "::fedc:ba98:7654:3210",
112 128,
113 true,
114 },
115 {
116 "01.2.3.4.5.6.7.8.9.a.b.c.d.e.f.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.ip6.arpa.", // missing dot
117 "::fedc:ba98:7654:3200",
118 120,
119 true,
120 },
121 {
122 "001.2.3.4.5.6.7.8.9.a.b.c.d.e.f.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.ip6.arpa.", // missing dot
123 "::fedc:ba98:7654:3200",
124 120,
125 true,
126 },
127 {
128 `0.1\.2.3.4.5.6.7.8.9.a.b.c.d.e.f.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.ip6.arpa.`, // escaped dot
129 "::fedc:ba98:7654:3000",
130 116,
131 true,
132 },
133 {
134 "g.1.2.3.4.5.6.7.8.9.a.b.c.d.e.f.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.ip6.arpa.", // invalid character
135 "::fedc:ba98:7654:3210",
136 124,
137 true,
138 },
139 }
140 for _, c := range cases {
141 ip, bits, extra := ParseReverse(c.name)
142 if ip.String() != c.ip || bits != c.bits || extra != c.extra {
143 t.Errorf("ParseReverse(%q) = (%s, %v, %v), expected (%s, %v, %v)", c.name, ip, bits, extra, c.ip, c.bits, c.extra)
144 }
145 }
146}
147
148func BenchmarkParseReverseIPv4(b *testing.B) {
149 for i := 0; i < b.N; i++ {
150 ParseReverse("7.6.45.123.in-addr.arpa.")
151 }
152}
153
154func BenchmarkParseReverseIPv6(b *testing.B) {
155 for i := 0; i < b.N; i++ {
156 ParseReverse("0.1.2.3.4.5.6.7.8.9.a.b.c.d.e.f.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.ip6.arpa.")
157 }
158}