Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Updates for python3 compatibility #500

Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
50 changes: 26 additions & 24 deletions rosserial_python/src/rosserial_python/SerialClient.py
Original file line number Diff line number Diff line change
Expand Up @@ -39,13 +39,13 @@
import threading
import sys
import multiprocessing
import StringIO
import io
import errno
import signal
import socket
import struct
import time
from Queue import Queue
from queue import Queue

from serial import Serial, SerialException, SerialTimeoutException

Expand Down Expand Up @@ -132,7 +132,7 @@ def __init__(self, topic_info, parent):

def callback(self, msg):
""" Forward message to serial device. """
data_buffer = StringIO.StringIO()
data_buffer = io.BytesIO()
msg.serialize(data_buffer)
self.parent.send(self.id, data_buffer.getvalue())

Expand Down Expand Up @@ -167,7 +167,7 @@ def unregister(self):

def callback(self, req):
""" Forward request to serial device. """
data_buffer = StringIO.StringIO()
data_buffer = io.BytesIO()
req.serialize(data_buffer)
self.response = None
if self.parent.send(self.id, data_buffer.getvalue()) >= 0:
Expand Down Expand Up @@ -209,7 +209,7 @@ def handlePacket(self, data):
# call service proxy
resp = self.proxy(req)
# serialize and publish
data_buffer = StringIO.StringIO()
data_buffer = io.BytesIO()
resp.serialize(data_buffer)
self.parent.send(self.id, data_buffer.getvalue())

Expand Down Expand Up @@ -368,8 +368,8 @@ def __init__(self, port=None, baud=57600, timeout=5.0, fix_pyserial_for_test=Fal

# hydro introduces protocol ver2 which must match node_handle.h
# The protocol version is sent as the 2nd sync byte emitted by each end
self.protocol_ver1 = '\xff'
self.protocol_ver2 = '\xfe'
self.protocol_ver1 = b'\xff'
self.protocol_ver2 = b'\xfe'
self.protocol_ver = self.protocol_ver2

self.publishers = dict() # id:Publishers
Expand Down Expand Up @@ -409,15 +409,15 @@ def requestTopics(self):
self.port.flushInput()

# request topic sync
self.write_queue.put("\xff" + self.protocol_ver + "\x00\x00\xff\x00\x00\xff")
self.write_queue.put(b"\xff" + self.protocol_ver + b"\x00\x00\xff\x00\x00\xff")

def txStopRequest(self, signal, frame):
""" send stop tx request to arduino when receive SIGINT(Ctrl-c)"""
if not self.fix_pyserial_for_test:
with self.read_lock:
self.port.flushInput()

self.write_queue.put("\xff" + self.protocol_ver + "\x00\x00\xff\x0b\x00\xf4")
self.write_queue.put(b"\xff" + self.protocol_ver + b"\x00\x00\xff\x0b\x00\xf4")

# tx_stop_request is x0b
rospy.loginfo("Send tx stop request")
Expand Down Expand Up @@ -479,7 +479,7 @@ def run(self):
flag = [0, 0]
read_step = 'syncflag'
flag[0] = self.tryRead(1)
if (flag[0] != '\xff'):
if (flag[0] != b'\xff'):
continue

# Find protocol version.
Expand All @@ -488,7 +488,7 @@ def run(self):
if flag[1] != self.protocol_ver:
self.sendDiagnostics(diagnostic_msgs.msg.DiagnosticStatus.ERROR, ERROR_MISMATCHED_PROTOCOL)
rospy.logerr("Mismatched protocol version in packet (%s): lost sync or rosserial_python is from different ros release than the rosserial client" % repr(flag[1]))
protocol_ver_msgs = {'\xff': 'Rev 0 (rosserial 0.4 and earlier)', '\xfe': 'Rev 1 (rosserial 0.5+)', '\xfd': 'Some future rosserial version'}
protocol_ver_msgs = {b'\xff': 'Rev 0 (rosserial 0.4 and earlier)', b'\xfe': 'Rev 1 (rosserial 0.5+)', b'\xfd': 'Some future rosserial version'}
if flag[1] in protocol_ver_msgs:
found_ver_msg = 'Protocol version of client is ' + protocol_ver_msgs[flag[1]]
else:
Expand All @@ -499,23 +499,24 @@ def run(self):
# Read message length.
read_step = 'message length'
msg_len_bytes = self.tryRead(2)
msg_length, = struct.unpack("<h", msg_len_bytes)
msg_length, = struct.unpack("<H", msg_len_bytes)

# Read message length checksum.
read_step = 'message length checksum'
msg_len_chk = self.tryRead(1)
msg_len_checksum = sum(map(ord, msg_len_bytes)) + ord(msg_len_chk)
msg_len_chk_bytes = self.tryRead(1)
msg_len_chk, = struct.unpack("<B", msg_len_chk_bytes)
msg_len_checksum = sum(msg_len_bytes) + msg_len_chk

# Validate message length checksum.
if msg_len_checksum % 256 != 255:
rospy.loginfo("wrong checksum for msg length, length %d" %(msg_length))
rospy.loginfo("chk is %d" % ord(msg_len_chk))
rospy.loginfo("chk is %d" % msg_len_chk)
continue

# Read topic id (2 bytes)
read_step = 'topic id'
topic_id_header = self.tryRead(2)
topic_id, = struct.unpack("<h", topic_id_header)
topic_id, = struct.unpack("<H", topic_id_header)

# Read serialized message data.
read_step = 'data'
Expand All @@ -529,8 +530,9 @@ def run(self):

# Reada checksum for topic id and msg
read_step = 'data checksum'
chk = self.tryRead(1)
checksum = sum(map(ord, topic_id_header) ) + sum(map(ord, msg)) + ord(chk)
chk_bytes = self.tryRead(1)
chk, = struct.unpack("<B", chk_bytes)
checksum = sum(topic_id_header) + sum(msg) + chk

# Validate checksum.
if checksum % 256 == 255:
Expand Down Expand Up @@ -679,7 +681,7 @@ def handleTimeRequest(self, data):
""" Respond to device with system time. """
t = Time()
t.data = rospy.Time.now()
data_buffer = StringIO.StringIO()
data_buffer = io.BytesIO()
t.serialize(data_buffer)
self.send( TopicInfo.ID_TIME, data_buffer.getvalue() )
self.lastsync = rospy.Time.now()
Expand Down Expand Up @@ -716,7 +718,7 @@ def handleParameterRequest(self, data):
resp.floats =param
if t == str:
resp.strings = param
data_buffer = StringIO.StringIO()
data_buffer = io.BytesIO()
resp.serialize(data_buffer)
self.send(TopicInfo.ID_PARAMETER_REQUEST, data_buffer.getvalue())

Expand Down Expand Up @@ -761,9 +763,9 @@ def _send(self, topic, msg):
#modified frame : header(2 bytes) + msg_len(2 bytes) + msg_len_chk(1 byte) + topic_id(2 bytes) + msg(x bytes) + msg_topic_id_chk(1 byte)
# second byte of header is protocol version
msg_len_checksum = 255 - ( ((length&255) + (length>>8))%256 )
msg_checksum = 255 - ( ((topic&255) + (topic>>8) + sum([ord(x) for x in msg]))%256 )
data = "\xff" + self.protocol_ver + chr(length&255) + chr(length>>8) + chr(msg_len_checksum) + chr(topic&255) + chr(topic>>8)
data = data + msg + chr(msg_checksum)
msg_checksum = 255 - ( ((topic&255) + (topic>>8) + sum(msg))%256 )
data = b"\xff" + self.protocol_ver + struct.pack("<BBBBB", length&255, length>>8, msg_len_checksum, topic&255, topic>>8)
data = data + msg + struct.pack("<B", msg_checksum)
self._write(data)
return length

Expand All @@ -781,7 +783,7 @@ def processWriteQueue(self):
if isinstance(data, tuple):
topic, msg = data
self._send(topic, msg)
elif isinstance(data, basestring):
elif isinstance(data, bytes):
self._write(data)
else:
rospy.logerr("Trying to write invalid data type: %s" % type(data))
Expand Down
2 changes: 1 addition & 1 deletion rosserial_python/src/rosserial_python/__init__.py
Original file line number Diff line number Diff line change
@@ -1 +1 @@
from SerialClient import *
from rosserial_python.SerialClient import *