Pythons套接字,recvfrom()无法在Rasperry Pi

时间:2016-10-10 22:01:45

标签: python sockets

我想与一个Art-Net节点(它是一个网络小工具,用于将UDP Art-Net数据包转换为DMX输出,用于舞台和电影照明)与树莓派,在raspbian上运行python。

下面的代码有两个问题,一个与pi有关: 在我的Windows计算机上运行代码时,一切正常。 当运行相同的代码时(除了更改socket.bind的ip地址),代码发送ArtPoll数据包,网络中的节点使用ArtPollReply回复,但这些数据包不会被python脚本接收。代码挂起在"数据,addr = self.sock.recvfrom(4096)"但没有什么是接收的(有接收的数据包,计算机同时接收这些数据包)。

网络配置没问题,我检查了一切。我还检查了另一个artnet python的东西,它有效 - 所以网络接口本身没有问题。

这是整个演示代码,应该演示问题。

import socket
import struct
import threading
import time

class PollThread(threading.Thread):      
def __init__(self, artnet):
    threading.Thread.__init__(self)
    self.artnet = artnet

def run(self):
    while self.artnet.running:
        #break
        time.sleep(3)
        print self.artnet.nodes_ip
        self.artnet.ArtPoll()
    print "EXIT POLL THREAD"

class ArtNet(threading.Thread):
    nodes_ip = []
    nodes_data = []
    running = True
    def __init__(self):
        threading.Thread.__init__(self)
        self.pollthread = PollThread(self)
        ip = "10.0.0.2"
        self.header_artpoll = self.set_Header_ArtPoll()
        #open socket
        try:      
            self.sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)                    
        except socket.error, msg:
            print 'Failed to create socket. Error code: ' + str(msg[0]) + ' , Error message : ' + msg[1]
        print '[INFO] Socket Created %s' % ip
        self.sock.setsockopt(socket.SOL_SOCKET, socket.SO_BROADCAST, 1)         #Enable Broadcast
        self.sock.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)         #Diable Port blocking when reuse this port
        self.sock.bind((ip, 6454))

    def run(self):
        self.pollthread.start()
        while self.running:
            print "RECEIVING...."
            data, addr = self.sock.recvfrom(4096)
            print "RECEIVED DATA!"
            print addr
            opcode = struct.unpack('<H', data[8:10])[0]
            if opcode == 0x2000:
                self.HandleArtPollReply(addr[0], data)
                #self.artnet_handler.ArtPollReply() 
            if opcode == 0x2100:
                self.HandleArtPollReply(addr[0], data)
        print "EXIT ARTNET THREAD"

    def set_Header_ArtPoll(self):
        header = []
       header.append("Art-Net\x00")                                        #ID
        header.append(struct.pack('<H', 0x2000))                            #OpCode
        header.append(struct.pack('>H', 14))                                #ProtVer
        header.append(struct.pack('>H', 0b00000000))                        #TalkToMe
        header.append(chr(0xe0))                                            #Priority
        header = "".join(header)
        return header

    def HandleArtPollReply(self, ip, data):
        self.nodes_ip.append(ip)
        self.nodes_data.append(data)

    def ArtPoll(self):         
        self.nodes_ip = []
        self.nodes_data = []
        self.sock.sendto(self.header_artpoll, ('<broadcast>', 6454))
        self.sock.sendto(self.header_artpoll, ('10.255.255.255', 6454))
        self.sock.sendto(self.header_artpoll, ('2.255.255.255', 6454))

if __name__ == '__main__':
    artnet = ArtNet()
    artnet.start()
    s = raw_input()
    artnet.sock.close()
    artnet.running = False
    print "MIAN EXIT"

编辑: 现在我还有其他信息:如果我绑定到&#39;&#39;,一切正常,也就是pi。

self.sock.bind(('', 6454))

在评论中,我得到了使用

的建议
self.sock.bind((socket.INADDR_ANY, 6454))

抛出错误:

self.sock.bind((socket.INADDR_ANY, 6454))
File "C:\Python27\lib\socket.py", line 228, in meth
return getattr(self._sock,name)(*args)
TypeError: coercing to Unicode: need string or buffer, int found

在第一次运行中对我有用,但它可以是,我必须在系统上使用多个接口来执行不同的任务 - 所以我可以使用基于ip的绑定到接口来区分他们提供的服务。 编辑结束

第二个问题是,我不知道如何关闭ArtNet()类,因为当我这样做时,线程会挂起&#34;数据,addr = self.sock.recvfrom(4096)& #34;等待数据。所以我必须打破这个命令。我的想法是将一些数据发送到机器以解除阻塞......

编辑: 我已经使用了这个self.sock.close(),并且线程在close()

之后继续运行

0 个答案:

没有答案