在Python中接收UDPv6多播

时间:2015-07-12 10:58:36

标签: python linux udp ipv6 contiki

使用Python接收UDPv6数据包时遇到问题。数据包来自使用6LBR的SLIP接口和Beagleboard上的整个运行,但事实并非如此。 Tcpdump可以毫无问题地捕获数据包:

10:17:32.220009 IP6 (hlim 64, next-header UDP (17) payload length: 21)
fe80::200:0:0:3.3000 > ff02::1.3000: [udp sum ok] UDP, length 13
0x0000:  6000 0000 0015 1140 fe80 0000 0000 0000  `......@........
0x0010:  0200 0000 0000 0003 ff02 0000 0000 0000  ................
0x0020:  0000 0000 0000 0001 0bb8 0bb8 0015 f9fe  ................
0x0030:  4d65 7373 6167 6520 3537 3236 00         Message.5726.

但是,我无法使用Python接收数据包:

MYPORT = 3000
MYGROUP_6 = 'ff02::1%eth0'

import time
import struct
import socket
import sys

def main():

    addrinfo = socket.getaddrinfo(MYGROUP_6, None)[0]
    print(addrinfo)
    s = socket.socket(socket.AF_INET6, socket.SOCK_DGRAM)
    s.bind(('', MYPORT))
    while True:
        data, sender = s.recvfrom(150)
        print (str(sender) + '  ' + repr(data))

if __name__ == '__main__':
    main()

另一方面,当我生成本地多播时,相同的代码能够接收数据包。数据包的Tcpdump输出,可以接收:

10:29:37.301406 IP6 (hlim 3, next-header UDP (17) payload length: 30)
fe80::c03a:f9ff:fe3d:9b30.56963 > ff02::1.3000: [udp sum ok] UDP, length 22
    0x0000:  6000 0000 001e 1103 fe80 0000 0000 0000  `...............
    0x0010:  c03a f9ff fe3d 9b30 ff02 0000 0000 0000  .:...=.0........
    0x0020:  0000 0000 0000 0001 de83 0bb8 001e 20ca  ................
    0x0030:  3134 3336 3639 3639 3737 2e33 3030 3532  1436696977.30052
    0x0040:  3164 7570 6100                           1dupa.

为什么呢?如何使用python捕获第一个数据包?

ARM Linux ip配置:

debian@arm:~$ sudo ifconfig
eth0      Link encap:Ethernet  HWaddr c2:3a:f9:3d:9b:30  
          inet addr:192.168.1.206  Bcast:192.168.1.255  Mask:255.255.255.0
          inet6 addr: fe80::c03a:f9ff:fe3d:9b30/64 Scope:Link
          UP BROADCAST RUNNING MULTICAST DYNAMIC  MTU:1500  Metric:1
          RX packets:261457 errors:0 dropped:0 overruns:0 frame:0
          TX packets:568962 errors:0 dropped:0 overruns:0 carrier:0
          collisions:0 txqueuelen:1000 
          RX bytes:28323386 (27.0 MiB)  TX bytes:71483396 (68.1 MiB)

Contiki节点的IP配置:

MAC 00:00:00:00:00:00:00:03 Contiki-2.7-7-g9698ca5 started. 
Node id is set to 3.
nullmac nullrdc, channel check rate 128 Hz, radio channel 26
Tentative link-local IPv6 address fe80:0000:0000:0000:0200:0000:0000:0003
Starting 'Unicast sender example process'
IPv6 addresses: bbbb::200:0:0:3
Sending unicast to ff02::1

1 个答案:

答案 0 :(得分:0)

您忘记加入多播组。您的进程绑定到端口3000上的通配符地址。带有该目标端口号的任何数据包都会传递到您的进程,但您实际上并没有要求操作系统将进程订阅到多播组,因此没有数据包到达那里的原因(除非它是在本地创建的)。

要将系统订阅到多播服装,请执行以下操作:

# Get the interface index for eth0
interface_index = socket.if_nametoindex("eth0")

# Create the JOIN option data
mc_addr = ipaddress.IPv6Address('ff02::1')
join_data = struct.pack('16sI', mc_addr.packed, interface_index)

# And join the group
sock.setsockopt(socket.IPPROTO_IPV6, socket.IPV6_JOIN_GROUP, join_data)