]> Cypherpunks.ru repositories - gostls13.git/blob - src/net/dnsconfig_unix_test.go
cmd/compile/internal/inline: score call sites exposed by inlines
[gostls13.git] / src / net / dnsconfig_unix_test.go
1 // Copyright 2013 The Go Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style
3 // license that can be found in the LICENSE file.
4
5 //go:build unix
6
7 package net
8
9 import (
10         "errors"
11         "io/fs"
12         "os"
13         "reflect"
14         "strings"
15         "testing"
16         "time"
17 )
18
19 var dnsReadConfigTests = []struct {
20         name string
21         want *dnsConfig
22 }{
23         {
24                 name: "testdata/resolv.conf",
25                 want: &dnsConfig{
26                         servers:    []string{"8.8.8.8:53", "[2001:4860:4860::8888]:53", "[fe80::1%lo0]:53"},
27                         search:     []string{"localdomain."},
28                         ndots:      5,
29                         timeout:    10 * time.Second,
30                         attempts:   3,
31                         rotate:     true,
32                         unknownOpt: true, // the "options attempts 3" line
33                 },
34         },
35         {
36                 name: "testdata/domain-resolv.conf",
37                 want: &dnsConfig{
38                         servers:  []string{"8.8.8.8:53"},
39                         search:   []string{"localdomain."},
40                         ndots:    1,
41                         timeout:  5 * time.Second,
42                         attempts: 2,
43                 },
44         },
45         {
46                 name: "testdata/search-resolv.conf",
47                 want: &dnsConfig{
48                         servers:  []string{"8.8.8.8:53"},
49                         search:   []string{"test.", "invalid."},
50                         ndots:    1,
51                         timeout:  5 * time.Second,
52                         attempts: 2,
53                 },
54         },
55         {
56                 name: "testdata/search-single-dot-resolv.conf",
57                 want: &dnsConfig{
58                         servers:  []string{"8.8.8.8:53"},
59                         search:   []string{},
60                         ndots:    1,
61                         timeout:  5 * time.Second,
62                         attempts: 2,
63                 },
64         },
65         {
66                 name: "testdata/empty-resolv.conf",
67                 want: &dnsConfig{
68                         servers:  defaultNS,
69                         ndots:    1,
70                         timeout:  5 * time.Second,
71                         attempts: 2,
72                         search:   []string{"domain.local."},
73                 },
74         },
75         {
76                 name: "testdata/invalid-ndots-resolv.conf",
77                 want: &dnsConfig{
78                         servers:  defaultNS,
79                         ndots:    0,
80                         timeout:  5 * time.Second,
81                         attempts: 2,
82                         search:   []string{"domain.local."},
83                 },
84         },
85         {
86                 name: "testdata/large-ndots-resolv.conf",
87                 want: &dnsConfig{
88                         servers:  defaultNS,
89                         ndots:    15,
90                         timeout:  5 * time.Second,
91                         attempts: 2,
92                         search:   []string{"domain.local."},
93                 },
94         },
95         {
96                 name: "testdata/negative-ndots-resolv.conf",
97                 want: &dnsConfig{
98                         servers:  defaultNS,
99                         ndots:    0,
100                         timeout:  5 * time.Second,
101                         attempts: 2,
102                         search:   []string{"domain.local."},
103                 },
104         },
105         {
106                 name: "testdata/openbsd-resolv.conf",
107                 want: &dnsConfig{
108                         ndots:    1,
109                         timeout:  5 * time.Second,
110                         attempts: 2,
111                         lookup:   []string{"file", "bind"},
112                         servers:  []string{"169.254.169.254:53", "10.240.0.1:53"},
113                         search:   []string{"c.symbolic-datum-552.internal."},
114                 },
115         },
116         {
117                 name: "testdata/single-request-resolv.conf",
118                 want: &dnsConfig{
119                         servers:       defaultNS,
120                         ndots:         1,
121                         singleRequest: true,
122                         timeout:       5 * time.Second,
123                         attempts:      2,
124                         search:        []string{"domain.local."},
125                 },
126         },
127         {
128                 name: "testdata/single-request-reopen-resolv.conf",
129                 want: &dnsConfig{
130                         servers:       defaultNS,
131                         ndots:         1,
132                         singleRequest: true,
133                         timeout:       5 * time.Second,
134                         attempts:      2,
135                         search:        []string{"domain.local."},
136                 },
137         },
138         {
139                 name: "testdata/linux-use-vc-resolv.conf",
140                 want: &dnsConfig{
141                         servers:  defaultNS,
142                         ndots:    1,
143                         useTCP:   true,
144                         timeout:  5 * time.Second,
145                         attempts: 2,
146                         search:   []string{"domain.local."},
147                 },
148         },
149         {
150                 name: "testdata/freebsd-usevc-resolv.conf",
151                 want: &dnsConfig{
152                         servers:  defaultNS,
153                         ndots:    1,
154                         useTCP:   true,
155                         timeout:  5 * time.Second,
156                         attempts: 2,
157                         search:   []string{"domain.local."},
158                 },
159         },
160         {
161                 name: "testdata/openbsd-tcp-resolv.conf",
162                 want: &dnsConfig{
163                         servers:  defaultNS,
164                         ndots:    1,
165                         useTCP:   true,
166                         timeout:  5 * time.Second,
167                         attempts: 2,
168                         search:   []string{"domain.local."},
169                 },
170         },
171 }
172
173 func TestDNSReadConfig(t *testing.T) {
174         origGetHostname := getHostname
175         defer func() { getHostname = origGetHostname }()
176         getHostname = func() (string, error) { return "host.domain.local", nil }
177
178         for _, tt := range dnsReadConfigTests {
179                 want := *tt.want
180                 if len(want.search) == 0 {
181                         want.search = dnsDefaultSearch()
182                 }
183                 conf := dnsReadConfig(tt.name)
184                 if conf.err != nil {
185                         t.Fatal(conf.err)
186                 }
187                 conf.mtime = time.Time{}
188                 if !reflect.DeepEqual(conf, &want) {
189                         t.Errorf("%s:\ngot: %+v\nwant: %+v", tt.name, conf, want)
190                 }
191         }
192 }
193
194 func TestDNSReadMissingFile(t *testing.T) {
195         origGetHostname := getHostname
196         defer func() { getHostname = origGetHostname }()
197         getHostname = func() (string, error) { return "host.domain.local", nil }
198
199         conf := dnsReadConfig("a-nonexistent-file")
200         if !os.IsNotExist(conf.err) {
201                 t.Errorf("missing resolv.conf:\ngot: %v\nwant: %v", conf.err, fs.ErrNotExist)
202         }
203         conf.err = nil
204         want := &dnsConfig{
205                 servers:  defaultNS,
206                 ndots:    1,
207                 timeout:  5 * time.Second,
208                 attempts: 2,
209                 search:   []string{"domain.local."},
210         }
211         if !reflect.DeepEqual(conf, want) {
212                 t.Errorf("missing resolv.conf:\ngot: %+v\nwant: %+v", conf, want)
213         }
214 }
215
216 var dnsDefaultSearchTests = []struct {
217         name string
218         err  error
219         want []string
220 }{
221         {
222                 name: "host.long.domain.local",
223                 want: []string{"long.domain.local."},
224         },
225         {
226                 name: "host.local",
227                 want: []string{"local."},
228         },
229         {
230                 name: "host",
231                 want: nil,
232         },
233         {
234                 name: "host.domain.local",
235                 err:  errors.New("errored"),
236                 want: nil,
237         },
238         {
239                 // ensures we don't return []string{""}
240                 // which causes duplicate lookups
241                 name: "foo.",
242                 want: nil,
243         },
244 }
245
246 func TestDNSDefaultSearch(t *testing.T) {
247         origGetHostname := getHostname
248         defer func() { getHostname = origGetHostname }()
249
250         for _, tt := range dnsDefaultSearchTests {
251                 getHostname = func() (string, error) { return tt.name, tt.err }
252                 got := dnsDefaultSearch()
253                 if !reflect.DeepEqual(got, tt.want) {
254                         t.Errorf("dnsDefaultSearch with hostname %q and error %+v = %q, wanted %q", tt.name, tt.err, got, tt.want)
255                 }
256         }
257 }
258
259 func TestDNSNameLength(t *testing.T) {
260         origGetHostname := getHostname
261         defer func() { getHostname = origGetHostname }()
262         getHostname = func() (string, error) { return "host.domain.local", nil }
263
264         var char63 = ""
265         for i := 0; i < 63; i++ {
266                 char63 += "a"
267         }
268         longDomain := strings.Repeat(char63+".", 5) + "example"
269
270         for _, tt := range dnsReadConfigTests {
271                 conf := dnsReadConfig(tt.name)
272                 if conf.err != nil {
273                         t.Fatal(conf.err)
274                 }
275
276                 suffixList := tt.want.search
277                 if len(suffixList) == 0 {
278                         suffixList = dnsDefaultSearch()
279                 }
280
281                 var shortestSuffix int
282                 for _, suffix := range suffixList {
283                         if shortestSuffix == 0 || len(suffix) < shortestSuffix {
284                                 shortestSuffix = len(suffix)
285                         }
286                 }
287
288                 // Test a name that will be maximally long when prefixing the shortest
289                 // suffix (accounting for the intervening dot).
290                 longName := longDomain[len(longDomain)-254+1+shortestSuffix:]
291                 if longName[0] == '.' || longName[1] == '.' {
292                         longName = "aa." + longName[3:]
293                 }
294                 for _, fqdn := range conf.nameList(longName) {
295                         if len(fqdn) > 254 {
296                                 t.Errorf("got %d; want less than or equal to 254", len(fqdn))
297                         }
298                 }
299
300                 // Now test a name that's too long for suffixing.
301                 unsuffixable := "a." + longName[1:]
302                 unsuffixableResults := conf.nameList(unsuffixable)
303                 if len(unsuffixableResults) != 1 {
304                         t.Errorf("suffixed names %v; want []", unsuffixableResults[1:])
305                 }
306
307                 // Now test a name that's too long for DNS.
308                 tooLong := "a." + longDomain
309                 tooLongResults := conf.nameList(tooLong)
310                 if tooLongResults != nil {
311                         t.Errorf("suffixed names %v; want nil", tooLongResults)
312                 }
313         }
314 }