Graham F.
Graham F.

Reputation: 107

Python io module's TextIOWrapper or BuffereRWPair functions are not playing nicely with pySerial

I'm writing a serial adapter for some scientific hardware whose command set uses UTF-8 character encodings. All responses from the hardware are terminated with a carriage return (u'\r'). I would like to able to use pySerial's readline() function with an EOL character specified, so I have this setup, ala this thread:

import serial
import io

ser = serial.Serial(port='COM10', baudrate=128000)
sio = io.TextIOWrapper(io.BufferedRWPair(ser, ser, 1), encoding='utf-8', newline=u'\r')

ser.open()

# these commands move to coordintes (25000, 0, 25000)
cmd = 'M\x80\x1a\x06\x00\x00\x00\x00\x00\x80\x1a\x06\x00'
ucmd = u'M\x80\x1a\x06\x00\x00\x00\x00\x00\x80\x1a\x06\x00'

#this works
ser.write(cmd)
print sio.readline()

#this does not
sio.write(ucmd)
sio.flush()
print sio.readline()

Strangely, the first command string (non-unicode using pySerial directly) elicits the correct behavior from the hardware. The second (unicode via Python's io module) causes it to move erratically and then hang. Why would this be? Sending unicode command strings to the hardware does work IF the command string is only a couple of a characters. Once you start sending bytes with hex(ord(byte)) values > 0x7F (outside ASCII range), then you start running intro trouble. I can work around this problem without too much trouble, but would like to know what is going on. Thanks!

Upvotes: 3

Views: 3044

Answers (1)

SiHa
SiHa

Reputation: 8411

From io docs:

BufferedRWPair does not attempt to synchronize accesses to its underlying raw streams. You should not pass it the same object as reader and writer; use BufferedRandom instead.

I'm guessing that's your problem, as you are passing same object ser as reader and writer. BufferendRandom doesn't look like it quite fits the bill either.

So is your problem with serial that it hangs waiting for the EOL?

Upvotes: 2

Related Questions