1--TEST-- 2Multicast support: IPv6 receive options 3--SKIPIF-- 4<?php 5if (!extension_loaded('sockets')) { 6 die('skip sockets extension not available.'); 7} 8if (!defined('IPPROTO_IPV6')) { 9 die('skip IPv6 not available.'); 10} 11$s = socket_create(AF_INET6, SOCK_DGRAM, SOL_UDP); 12if ($s === false) { 13 die("skip unable to create socket"); 14} 15$br = socket_bind($s, '::', 3000); 16/* On Linux, there is no route ff00::/8 by default on lo, which makes it 17 * troublesome to send multicast traffic from lo, which we must since 18 * we're dealing with interface-local traffic... */ 19$so = socket_set_option($s, IPPROTO_IPV6, MCAST_JOIN_GROUP, array( 20 "group" => 'ff01::114', 21 "interface" => 0, 22)); 23if ($so === false) { 24 die('skip unable to join multicast group on any interface.'); 25} 26$r = socket_sendto($s, $m = "testing packet", strlen($m), 0, 'ff01::114', 3000); 27if ($r === false) { 28 die('skip unable to send multicast packet.'); 29} 30 31if (!defined("MCAST_JOIN_SOURCE_GROUP")) 32 die('skip source operations are unavailable'); 33 34$so = socket_set_option($s, IPPROTO_IPV6, MCAST_LEAVE_GROUP, array( 35 "group" => 'ff01::114', 36 "interface" => 0, 37)); 38$so = socket_set_option($s, IPPROTO_IPV6, MCAST_JOIN_SOURCE_GROUP, array( 39 "group" => 'ff01::114', 40 "interface" => 0, 41 "source" => '2001::dead:beef', 42)); 43if ($so === false) { 44 die('skip protocol independent multicast API is unavailable.'); 45} 46--FILE-- 47<?php 48include __DIR__."/mcast_helpers.php.inc"; 49$domain = AF_INET6; 50$level = IPPROTO_IPV6; 51$interface = 0; 52$mcastaddr = 'ff01::114'; 53$sblock = "?"; 54 55echo "creating send socket\n"; 56$sends1 = socket_create($domain, SOCK_DGRAM, SOL_UDP) or die("err"); 57var_dump($sends1); 58 59echo "creating receive socket\n"; 60$s = socket_create($domain, SOCK_DGRAM, SOL_UDP) or die("err"); 61var_dump($s); 62$br = socket_bind($s, '::0', 3000) or die("err"); 63var_dump($br); 64 65$so = socket_set_option($s, $level, MCAST_JOIN_GROUP, array( 66 "group" => $mcastaddr, 67 "interface" => $interface, 68)) or die("err"); 69var_dump($so); 70 71$r = socket_sendto($sends1, $m = "testing packet", strlen($m), 0, $mcastaddr, 3000); 72var_dump($r); 73checktimeout($s, 500); 74$r = socket_recvfrom($s, $str, 2000, 0, $from, $fromPort); 75var_dump($r, $str, $from); 76$sblock = $from; 77 78$r = socket_sendto($sends1, $m = "initial packet", strlen($m), 0, $mcastaddr, 3000); 79var_dump($r); 80 81$i = 0; 82checktimeout($s, 500); 83while (($str = socket_read($s, 3000)) !== FALSE) { 84 $i++; 85 echo "$i> ", $str, "\n"; 86 87if ($i == 1) { 88 echo "leaving group\n"; 89 $so = socket_set_option($s, $level, MCAST_LEAVE_GROUP, array( 90 "group" => $mcastaddr, 91 "interface" => $interface, 92 )); 93 var_dump($so); 94 $r = socket_sendto($sends1, $m = "ignored mcast packet", strlen($m), 0, $mcastaddr, 3000); 95 var_dump($r); 96 $r = socket_sendto($sends1, $m = "unicast packet", strlen($m), 0, "::1", 3000); 97 var_dump($r); 98} 99if ($i == 2) { 100 echo "re-joining group\n"; 101 $so = socket_set_option($s, $level, MCAST_JOIN_GROUP, array( 102 "group" => $mcastaddr, 103 "interface" => $interface, 104 )); 105 var_dump($so); 106 $r = socket_sendto($sends1, $m = "mcast packet", strlen($m), 0, $mcastaddr, 3000); 107 var_dump($r); 108} 109if ($i == 3) { 110 echo "blocking source\n"; 111 $so = socket_set_option($s, $level, MCAST_BLOCK_SOURCE, array( 112 "group" => $mcastaddr, 113 "interface" => $interface, 114 "source" => $sblock, 115 )); 116 var_dump($so); 117 $r = socket_sendto($sends1, $m = "ignored packet (blocked source)", strlen($m), 0, $mcastaddr, 3000); 118 var_dump($r); 119 $r = socket_sendto($sends1, $m = "unicast packet", strlen($m), 0, "::1", 3000); 120 var_dump($r); 121} 122if ($i == 4) { 123 echo "unblocking source\n"; 124 $so = socket_set_option($s, $level, MCAST_UNBLOCK_SOURCE, array( 125 "group" => $mcastaddr, 126 "interface" => $interface, 127 "source" => $sblock, 128 )); 129 var_dump($so); 130 $r = socket_sendto($sends1, $m = "mcast packet", strlen($m), 0, $mcastaddr, 3000); 131 var_dump($r); 132} 133if ($i == 5) { 134 echo "leaving group\n"; 135 $so = socket_set_option($s, $level, MCAST_LEAVE_GROUP, array( 136 "group" => $mcastaddr, 137 "interface" => $interface, 138 )); 139 var_dump($so); 140 $r = socket_sendto($sends1, $m = "ignored mcast packet", strlen($m), 0, $mcastaddr, 3000); 141 var_dump($r); 142 $r = socket_sendto($sends1, $m = "unicast packet", strlen($m), 0, "::1", 3000); 143 var_dump($r); 144} 145if ($i == 6) { 146 echo "joining source group\n"; 147 $so = socket_set_option($s, $level, MCAST_JOIN_SOURCE_GROUP, array( 148 "group" => $mcastaddr, 149 "interface" => $interface, 150 "source" => $sblock, 151 )); 152 var_dump($so); 153 $r = socket_sendto($sends1, $m = "mcast packet from desired source", strlen($m), 0, $mcastaddr, 3000); 154 var_dump($r); 155} 156if ($i == 7) { 157 echo "leaving source group\n"; 158 $so = socket_set_option($s, $level, MCAST_LEAVE_SOURCE_GROUP, array( 159 "group" => $mcastaddr, 160 "interface" => $interface, 161 "source" => $sblock, 162 )); 163 var_dump($so); 164 $r = socket_sendto($sends1, $m = "ignored mcast packet", strlen($m), 0, $mcastaddr, 3000); 165 var_dump($r); 166 $r = socket_sendto($sends1, $m = "unicast packet", strlen($m), 0, "::1", 3000); 167 var_dump($r); 168} 169if ($i == 8) { 170 /*echo "joining source group\n"; 171 $so = socket_set_option($s, $level, MCAST_JOIN_SOURCE_GROUP, array( 172 "group" => $mcastaddr, 173 "interface" => $interface, 174 "source" => $sblock, 175 )); 176 var_dump($so);*/ 177 break; 178} 179 180} 181--EXPECTF-- 182creating send socket 183resource(%d) of type (Socket) 184creating receive socket 185resource(%d) of type (Socket) 186bool(true) 187bool(true) 188int(14) 189int(14) 190string(14) "testing packet" 191string(%d) "%s" 192int(14) 1931> initial packet 194leaving group 195bool(true) 196int(20) 197int(14) 1982> unicast packet 199re-joining group 200bool(true) 201int(12) 2023> mcast packet 203blocking source 204bool(true) 205int(31) 206int(14) 2074> unicast packet 208unblocking source 209bool(true) 210int(12) 2115> mcast packet 212leaving group 213bool(true) 214int(20) 215int(14) 2166> unicast packet 217joining source group 218bool(true) 219int(32) 2207> mcast packet from desired source 221leaving source group 222bool(true) 223int(20) 224int(14) 2258> unicast packet 226