blob: a66250c844b43fe6763449b6016e8192c89d98ef [file] [log] [blame]
Dave Cheney08567312011-02-16 15:07:13 -05001// 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
5package net
6
7import (
Dave Cheney8b8b54a2011-04-11 10:39:21 +10008 "flag"
Mikio Harafca50822011-08-18 12:22:02 -04009 "os"
Alex Brainman6cf98a42011-02-17 12:00:02 +110010 "runtime"
Dave Cheney08567312011-02-16 15:07:13 -050011 "testing"
12)
13
Dave Cheney8b8b54a2011-04-11 10:39:21 +100014var multicast = flag.Bool("multicast", false, "enable multicast tests")
15
Mikio Harafca50822011-08-18 12:22:02 -040016var joinAndLeaveGroupUDPTests = []struct {
17 net string
18 laddr IP
19 gaddr IP
20 flags Flags
21 ipv6 bool
22}{
23 // cf. RFC 4727: Experimental Values in IPv4, IPv6, ICMPv4, ICMPv6, UDP, and TCP Headers
24 {"udp", IPv4zero, IPv4(224, 0, 0, 254), (FlagUp | FlagLoopback), false},
25 {"udp4", IPv4zero, IPv4(224, 0, 0, 254), (FlagUp | FlagLoopback), false},
26 {"udp", IPv6unspecified, ParseIP("ff0e::114"), (FlagUp | FlagLoopback), true},
27 {"udp6", IPv6unspecified, ParseIP("ff01::114"), (FlagUp | FlagLoopback), true},
28 {"udp6", IPv6unspecified, ParseIP("ff02::114"), (FlagUp | FlagLoopback), true},
29 {"udp6", IPv6unspecified, ParseIP("ff04::114"), (FlagUp | FlagLoopback), true},
30 {"udp6", IPv6unspecified, ParseIP("ff05::114"), (FlagUp | FlagLoopback), true},
31 {"udp6", IPv6unspecified, ParseIP("ff08::114"), (FlagUp | FlagLoopback), true},
32 {"udp6", IPv6unspecified, ParseIP("ff0e::114"), (FlagUp | FlagLoopback), true},
33}
34
35func TestJoinAndLeaveGroupUDP(t *testing.T) {
Alex Brainman6cf98a42011-02-17 12:00:02 +110036 if runtime.GOOS == "windows" {
37 return
38 }
Dave Cheney8b8b54a2011-04-11 10:39:21 +100039 if !*multicast {
40 t.Logf("test disabled; use --multicast to enable")
41 return
42 }
Dave Cheney90847a82011-02-18 13:48:13 -050043
Mikio Harafca50822011-08-18 12:22:02 -040044 for _, tt := range joinAndLeaveGroupUDPTests {
45 var (
46 ifi *Interface
47 found bool
48 )
49 if tt.ipv6 && (!supportsIPv6 || os.Getuid() != 0) {
50 continue
51 }
52 ift, err := Interfaces()
53 if err != nil {
54 t.Fatalf("Interfaces() failed: %v", err)
55 }
56 for _, x := range ift {
57 if x.Flags&tt.flags == tt.flags {
58 ifi = &x
59 break
60 }
61 }
62 if ifi == nil {
63 t.Logf("an appropriate multicast interface not found")
64 return
65 }
66 c, err := ListenUDP(tt.net, &UDPAddr{IP: tt.laddr})
67 if err != nil {
68 t.Fatal(err)
69 }
70 defer c.Close()
71 if err := c.JoinGroup(ifi, tt.gaddr); err != nil {
72 t.Fatal(err)
73 }
74 ifmat, err := ifi.MulticastAddrs()
75 if err != nil {
76 t.Fatalf("MulticastAddrs() failed: %v", err)
77 }
78 for _, ifma := range ifmat {
79 if ifma.(*IPAddr).IP.Equal(tt.gaddr) {
80 found = true
81 break
82 }
83 }
84 if !found {
85 t.Fatalf("%q not found in RIB", tt.gaddr.String())
86 }
87 if err := c.LeaveGroup(ifi, tt.gaddr); err != nil {
88 t.Fatal(err)
89 }
Dave Cheney08567312011-02-16 15:07:13 -050090 }
Dave Cheney08567312011-02-16 15:07:13 -050091}