github.com/c0deoo1/golang1.5@v0.0.0-20220525150107-c87c805d4593/src/net/lookup_unix.go (about) 1 // Copyright 2011 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 // +build darwin dragonfly freebsd linux netbsd openbsd solaris 6 7 package net 8 9 import "sync" 10 11 var onceReadProtocols sync.Once 12 13 // readProtocols loads contents of /etc/protocols into protocols map 14 // for quick access. 15 func readProtocols() { 16 if file, err := open("/etc/protocols"); err == nil { 17 for line, ok := file.readLine(); ok; line, ok = file.readLine() { 18 // tcp 6 TCP # transmission control protocol 19 if i := byteIndex(line, '#'); i >= 0 { 20 line = line[0:i] 21 } 22 f := getFields(line) 23 if len(f) < 2 { 24 continue 25 } 26 if proto, _, ok := dtoi(f[1], 0); ok { 27 if _, ok := protocols[f[0]]; !ok { 28 protocols[f[0]] = proto 29 } 30 for _, alias := range f[2:] { 31 if _, ok := protocols[alias]; !ok { 32 protocols[alias] = proto 33 } 34 } 35 } 36 } 37 file.close() 38 } 39 } 40 41 // lookupProtocol looks up IP protocol name in /etc/protocols and 42 // returns correspondent protocol number. 43 func lookupProtocol(name string) (int, error) { 44 onceReadProtocols.Do(readProtocols) 45 proto, found := protocols[name] 46 if !found { 47 return 0, &AddrError{Err: "unknown IP protocol specified", Addr: name} 48 } 49 return proto, nil 50 } 51 52 func lookupHost(host string) (addrs []string, err error) { 53 order := systemConf().hostLookupOrder(host) 54 if order == hostLookupCgo { 55 if addrs, err, ok := cgoLookupHost(host); ok { 56 return addrs, err 57 } 58 // cgo not available (or netgo); fall back to Go's DNS resolver 59 order = hostLookupFilesDNS 60 } 61 return goLookupHostOrder(host, order) 62 } 63 64 func lookupIP(host string) (addrs []IPAddr, err error) { 65 order := systemConf().hostLookupOrder(host) 66 if order == hostLookupCgo { 67 if addrs, err, ok := cgoLookupIP(host); ok { 68 return addrs, err 69 } 70 // cgo not available (or netgo); fall back to Go's DNS resolver 71 order = hostLookupFilesDNS 72 } 73 return goLookupIPOrder(host, order) 74 } 75 76 func lookupPort(network, service string) (int, error) { 77 port, err, ok := cgoLookupPort(network, service) 78 if !ok { 79 port, err = goLookupPort(network, service) 80 } 81 return port, err 82 } 83 84 func lookupCNAME(name string) (string, error) { 85 cname, err, ok := cgoLookupCNAME(name) 86 if !ok { 87 cname, err = goLookupCNAME(name) 88 } 89 return cname, err 90 } 91 92 func lookupSRV(service, proto, name string) (string, []*SRV, error) { 93 var target string 94 if service == "" && proto == "" { 95 target = name 96 } else { 97 target = "_" + service + "._" + proto + "." + name 98 } 99 cname, rrs, err := lookup(target, dnsTypeSRV) 100 if err != nil { 101 return "", nil, err 102 } 103 srvs := make([]*SRV, len(rrs)) 104 for i, rr := range rrs { 105 rr := rr.(*dnsRR_SRV) 106 srvs[i] = &SRV{Target: rr.Target, Port: rr.Port, Priority: rr.Priority, Weight: rr.Weight} 107 } 108 byPriorityWeight(srvs).sort() 109 return cname, srvs, nil 110 } 111 112 func lookupMX(name string) ([]*MX, error) { 113 _, rrs, err := lookup(name, dnsTypeMX) 114 if err != nil { 115 return nil, err 116 } 117 mxs := make([]*MX, len(rrs)) 118 for i, rr := range rrs { 119 rr := rr.(*dnsRR_MX) 120 mxs[i] = &MX{Host: rr.Mx, Pref: rr.Pref} 121 } 122 byPref(mxs).sort() 123 return mxs, nil 124 } 125 126 func lookupNS(name string) ([]*NS, error) { 127 _, rrs, err := lookup(name, dnsTypeNS) 128 if err != nil { 129 return nil, err 130 } 131 nss := make([]*NS, len(rrs)) 132 for i, rr := range rrs { 133 nss[i] = &NS{Host: rr.(*dnsRR_NS).Ns} 134 } 135 return nss, nil 136 } 137 138 func lookupTXT(name string) ([]string, error) { 139 _, rrs, err := lookup(name, dnsTypeTXT) 140 if err != nil { 141 return nil, err 142 } 143 txts := make([]string, len(rrs)) 144 for i, rr := range rrs { 145 txts[i] = rr.(*dnsRR_TXT).Txt 146 } 147 return txts, nil 148 } 149 150 func lookupAddr(addr string) ([]string, error) { 151 ptrs, err, ok := cgoLookupPTR(addr) 152 if !ok { 153 ptrs, err = goLookupPTR(addr) 154 } 155 return ptrs, err 156 }