Home | History | Annotate | Download | only in net
      1 // Copyright 2015 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 package net
      6 
      7 import (
      8 	"bytes"
      9 	"internal/syscall/windows"
     10 	"sort"
     11 	"testing"
     12 )
     13 
     14 func TestWindowsInterfaces(t *testing.T) {
     15 	aas, err := adapterAddresses()
     16 	if err != nil {
     17 		t.Fatal(err)
     18 	}
     19 	ift, err := Interfaces()
     20 	if err != nil {
     21 		t.Fatal(err)
     22 	}
     23 	for i, ifi := range ift {
     24 		aa := aas[i]
     25 		if len(ifi.HardwareAddr) != int(aa.PhysicalAddressLength) {
     26 			t.Errorf("got %d; want %d", len(ifi.HardwareAddr), aa.PhysicalAddressLength)
     27 		}
     28 		if ifi.MTU > 0x7fffffff {
     29 			t.Errorf("%s: got %d; want less than or equal to 1<<31 - 1", ifi.Name, ifi.MTU)
     30 		}
     31 		if ifi.Flags&FlagUp != 0 && aa.OperStatus != windows.IfOperStatusUp {
     32 			t.Errorf("%s: got %v; should not include FlagUp", ifi.Name, ifi.Flags)
     33 		}
     34 		if ifi.Flags&FlagLoopback != 0 && aa.IfType != windows.IF_TYPE_SOFTWARE_LOOPBACK {
     35 			t.Errorf("%s: got %v; should not include FlagLoopback", ifi.Name, ifi.Flags)
     36 		}
     37 		if _, _, err := addrPrefixTable(aa); err != nil {
     38 			t.Errorf("%s: %v", ifi.Name, err)
     39 		}
     40 	}
     41 }
     42 
     43 type byAddrLen []IPNet
     44 
     45 func (ps byAddrLen) Len() int { return len(ps) }
     46 
     47 func (ps byAddrLen) Less(i, j int) bool {
     48 	if n := bytes.Compare(ps[i].IP, ps[j].IP); n != 0 {
     49 		return n < 0
     50 	}
     51 	if n := bytes.Compare(ps[i].Mask, ps[j].Mask); n != 0 {
     52 		return n < 0
     53 	}
     54 	return false
     55 }
     56 
     57 func (ps byAddrLen) Swap(i, j int) { ps[i], ps[j] = ps[j], ps[i] }
     58 
     59 var windowsAddrPrefixLenTests = []struct {
     60 	pfxs []IPNet
     61 	ip   IP
     62 	out  int
     63 }{
     64 	{
     65 		[]IPNet{
     66 			{IP: IPv4(172, 16, 0, 0), Mask: IPv4Mask(255, 255, 0, 0)},
     67 			{IP: IPv4(192, 168, 0, 0), Mask: IPv4Mask(255, 255, 255, 0)},
     68 			{IP: IPv4(192, 168, 0, 0), Mask: IPv4Mask(255, 255, 255, 128)},
     69 			{IP: IPv4(192, 168, 0, 0), Mask: IPv4Mask(255, 255, 255, 192)},
     70 		},
     71 		IPv4(192, 168, 0, 1),
     72 		26,
     73 	},
     74 	{
     75 		[]IPNet{
     76 			{IP: ParseIP("2001:db8::"), Mask: IPMask(ParseIP("ffff:ffff:ffff:ffff:ffff:ffff:ffff:fff0"))},
     77 			{IP: ParseIP("2001:db8::"), Mask: IPMask(ParseIP("ffff:ffff:ffff:ffff:ffff:ffff:ffff:fff8"))},
     78 			{IP: ParseIP("2001:db8::"), Mask: IPMask(ParseIP("ffff:ffff:ffff:ffff:ffff:ffff:ffff:fffc"))},
     79 		},
     80 		ParseIP("2001:db8::1"),
     81 		126,
     82 	},
     83 
     84 	// Fallback cases. It may happen on Windows XP or 2003 server.
     85 	{
     86 		[]IPNet{
     87 			{IP: IPv4(127, 0, 0, 0).To4(), Mask: IPv4Mask(255, 0, 0, 0)},
     88 			{IP: IPv4(10, 0, 0, 0).To4(), Mask: IPv4Mask(255, 0, 0, 0)},
     89 			{IP: IPv4(172, 16, 0, 0).To4(), Mask: IPv4Mask(255, 255, 0, 0)},
     90 			{IP: IPv4(192, 168, 255, 0), Mask: IPv4Mask(255, 255, 255, 0)},
     91 			{IP: IPv4zero, Mask: IPv4Mask(0, 0, 0, 0)},
     92 		},
     93 		IPv4(192, 168, 0, 1),
     94 		8 * IPv4len,
     95 	},
     96 	{
     97 		nil,
     98 		IPv4(192, 168, 0, 1),
     99 		8 * IPv4len,
    100 	},
    101 	{
    102 		[]IPNet{
    103 			{IP: IPv6loopback, Mask: IPMask(ParseIP("ffff:ffff:ffff:ffff:ffff:ffff:ffff:ffff"))},
    104 			{IP: ParseIP("2001:db8:1::"), Mask: IPMask(ParseIP("ffff:ffff:ffff:ffff:ffff:ffff:ffff:fff0"))},
    105 			{IP: ParseIP("2001:db8:2::"), Mask: IPMask(ParseIP("ffff:ffff:ffff:ffff:ffff:ffff:ffff:fff8"))},
    106 			{IP: ParseIP("2001:db8:3::"), Mask: IPMask(ParseIP("ffff:ffff:ffff:ffff:ffff:ffff:ffff:fffc"))},
    107 			{IP: IPv6unspecified, Mask: IPMask(ParseIP("::"))},
    108 		},
    109 		ParseIP("2001:db8::1"),
    110 		8 * IPv6len,
    111 	},
    112 	{
    113 		nil,
    114 		ParseIP("2001:db8::1"),
    115 		8 * IPv6len,
    116 	},
    117 }
    118 
    119 func TestWindowsAddrPrefixLen(t *testing.T) {
    120 	for i, tt := range windowsAddrPrefixLenTests {
    121 		sort.Sort(byAddrLen(tt.pfxs))
    122 		l := addrPrefixLen(tt.pfxs, tt.ip)
    123 		if l != tt.out {
    124 			t.Errorf("#%d: got %d; want %d", i, l, tt.out)
    125 		}
    126 		sort.Sort(sort.Reverse(byAddrLen(tt.pfxs)))
    127 		l = addrPrefixLen(tt.pfxs, tt.ip)
    128 		if l != tt.out {
    129 			t.Errorf("#%d: got %d; want %d", i, l, tt.out)
    130 		}
    131 	}
    132 }
    133