github.com/roboticscm/goman@v0.0.0-20210203095141-87c07b4a0a55/src/net/port_unix.go (about) 1 // Copyright 2009 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 // Read system port mappings from /etc/services 8 9 package net 10 11 import "sync" 12 13 // services contains minimal mappings between services names and port 14 // numbers for platforms that don't have a complete list of port numbers 15 // (some Solaris distros). 16 var services = map[string]map[string]int{ 17 "tcp": {"http": 80}, 18 } 19 var servicesError error 20 var onceReadServices sync.Once 21 22 func readServices() { 23 var file *file 24 if file, servicesError = open("/etc/services"); servicesError != nil { 25 return 26 } 27 for line, ok := file.readLine(); ok; line, ok = file.readLine() { 28 // "http 80/tcp www www-http # World Wide Web HTTP" 29 if i := byteIndex(line, '#'); i >= 0 { 30 line = line[0:i] 31 } 32 f := getFields(line) 33 if len(f) < 2 { 34 continue 35 } 36 portnet := f[1] // "80/tcp" 37 port, j, ok := dtoi(portnet, 0) 38 if !ok || port <= 0 || j >= len(portnet) || portnet[j] != '/' { 39 continue 40 } 41 netw := portnet[j+1:] // "tcp" 42 m, ok1 := services[netw] 43 if !ok1 { 44 m = make(map[string]int) 45 services[netw] = m 46 } 47 for i := 0; i < len(f); i++ { 48 if i != 1 { // f[1] was port/net 49 m[f[i]] = port 50 } 51 } 52 } 53 file.close() 54 } 55 56 // goLookupPort is the native Go implementation of LookupPort. 57 func goLookupPort(network, service string) (port int, err error) { 58 onceReadServices.Do(readServices) 59 60 switch network { 61 case "tcp4", "tcp6": 62 network = "tcp" 63 case "udp4", "udp6": 64 network = "udp" 65 } 66 67 if m, ok := services[network]; ok { 68 if port, ok = m[service]; ok { 69 return 70 } 71 } 72 return 0, &AddrError{"unknown port", network + "/" + service} 73 }