我有一个文件mc_send.py,它发送mcast消息,并从收到mcast消息的程序mc_recv.py收回单播消息。 mcast工作,但是当收到单播消息时,会出现一个奇怪的错误:ValueError: maximum length of data to be read cannot be negative
错误在此文件mc_send.py中的第14行:
我在windows7上使用python2.7.2和pyqt4 v4.9这几个小时都在挣扎,但找不到我做错了什么。该程序基于pyqt4的广播示例。
""" to see all ports on windows: netstat -ap udp | find "4545" """
from PyQt4 import QtCore, QtGui, QtNetwork
unicast_addr = "127.0.0.1"
unicast_port = 45455
mcast_addr = "239.255.43.21"
mcast_port = 45454
class Sender(QtGui.QDialog):
def processPendingDatagrams(self):
while self.udpServer.hasPendingDatagrams():
datagram, host, port = self.udpServer.readDatagram(self.udpSocket.pendingDatagramSize())
print "got msg:", datagram
def __init__(self, parent=None):
super(Sender, self).__init__(parent)
self.groupAddress = QtNetwork.QHostAddress(mcast_addr)
self.unicastAddress = QtNetwork.QHostAddress(unicast_addr)
self.statusLabel = QtGui.QLabel("Ready to multicast datagrams to group %s on port 45454" %
self.groupAddress.toString())
# setup socket for listening on incomming datagrams
self.udpServer = QtNetwork.QUdpSocket(self)
self.udpServer.bind(unicast_port)
self.udpServer.readyRead.connect(self.processPendingDatagrams)
self.startButton = QtGui.QPushButton("&Start")
self.quitButton = QtGui.QPushButton("&Quit")
buttonBox = QtGui.QDialogButtonBox()
buttonBox.addButton(self.startButton, QtGui.QDialogButtonBox.ActionRole)
buttonBox.addButton(self.quitButton, QtGui.QDialogButtonBox.RejectRole)
self.timer = QtCore.QTimer(self)
self.udpSocket = QtNetwork.QUdpSocket(self)
self.messageNo = 1
self.startButton.clicked.connect(self.startSending)
self.quitButton.clicked.connect(self.close)
self.timer.timeout.connect(self.send_mc_msg)
mainLayout = QtGui.QVBoxLayout()
mainLayout.addWidget(self.statusLabel)
mainLayout.addWidget(buttonBox)
self.setLayout(mainLayout)
self.setWindowTitle("WSim")
def startSending(self):
self.startButton.setEnabled(False)
self.timer.start(1000)
def send_mc_msg(self):
self.udpSocket.writeDatagram("hello %d" %(self.messageNo), self.groupAddress, mcast_port)
self.messageNo += 1
if __name__ == '__main__':
import sys
app = QtGui.QApplication(sys.argv)
sender = Sender()
sender.show()
sys.exit(sender.exec_())
同样发送单播响应的多播接收器看起来像这样mc_recv.py:
from PyQt4 import QtGui, QtNetwork
mcast_addr = "239.255.43.21"
mcast_port = 45454
answer_addr = "127.0.0.1"
answer_port = 45455
class Receiver(QtGui.QDialog):
def __init__(self, parent=None):
super(Receiver, self).__init__(parent)
self.groupAddress = QtNetwork.QHostAddress(mcast_addr)
self.udpSocket = QtNetwork.QUdpSocket(self)
self.udpSocket.bind(mcast_port, QtNetwork.QUdpSocket.ReuseAddressHint)
self.udpSocket.joinMulticastGroup(self.groupAddress)
self.udpSocket.readyRead.connect(self.processPendingDatagrams)
# Use this socket to send unicast messages to back
self.answerSocket = QtNetwork.QUdpSocket(self)
self.answerAddress = QtNetwork.QHostAddress(answer_addr)
quitButton = QtGui.QPushButton("&Quit")
quitButton.clicked.connect(self.close)
buttonLayout = QtGui.QHBoxLayout()
buttonLayout.addStretch(1)
buttonLayout.addWidget(quitButton)
buttonLayout.addStretch(1)
self.statusLabel = QtGui.QLabel("Listening for multicasted messages on %s" % mcast_addr)
mainLayout = QtGui.QVBoxLayout()
mainLayout.addWidget(self.statusLabel)
mainLayout.addLayout(buttonLayout)
self.setLayout(mainLayout)
self.setWindowTitle("mrecv")
def processPendingDatagrams(self):
"""receive and decode multicast messages and send a response message on the return address"""
while self.udpSocket.hasPendingDatagrams():
datagram, host, port = self.udpSocket.readDatagram(self.udpSocket.pendingDatagramSize())
self.statusLabel.setText("received mcast msg '%s'" % datagram)
# send a response back to msend
self.answerSocket.writeDatagram("hi back", self.answerAddress, answer_port)
if __name__ == '__main__':
import sys
app = QtGui.QApplication(sys.argv)
receiver = Receiver()
receiver.show()
sys.exit(receiver.exec_())
答案 0 :(得分:0)
发现原因,令人尴尬的简单错误,写过self.udpSocket.pendingDatagramSize() 当我读数据时,而不是self.udpServer.pendingDatagramSize()...