I have a proprietary device that is connected to my computer with a USB cable.
I have been unable to successfully read (or write, or both?) when running the code on my Xubuntu installation.
Note: The same logic works pretty much flawlessly on both Windows (tested on 7, 8 and 10) and Mac (tested on Yosemite and Mojave).
Here is the code I'm trying to run (hardcoded some values for simplicity):
ser = serial.Serial('/dev/ttyACM0', 500000, timeout = 0.03, write_timeout = 0.015)
ser.write(bytes([248, 40, 0]))
ser.flush()
reply = ser.read(40)
Current behaviour
The device is running some code that responds to the packets that it receives. In this initial packet, my Python code is requesting a full copy of the device's state, which it receives in a whopping 40 bytes array.
On Linux, the following is returned instead of the requested 40 bytes:
[248, 13, 10, 40, 13, 10, 0, 13, 10]
What I find interesting is that it returns the exact same bytes that I tried writing, with 13 and 10 in between them.
Expected behaviour On both Mac and Windows, something like this is returned (contents are not that important):
[71, 89, 65, 32, 1, 4, 50, 0, 27, 0, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 238, 1, 255, 255, 136, 1, 255, 255, 255, 255]
The expected behaviour is the same as the behaviour on Mac and Windows.
Extra info
Running on Python 3.5.
I'm using the exact same USB device and cable.
I've tried all ports on the computer.
The code is exactly the same on all operating systems, with only the port name being different due to the nature of said OSs.
The serial port is confirmed to be device I need (I print the name) and is confirmed to be open (I print out the serial object).
I've played around with timeouts and baudrates, but to no avail.
I've tried exchanging the read with a
if(ser.in_waiting): reply = ser.read()
but nothing really changes.I have verified that the device is on port
/dev/ttyACM0
.I have added permissions to that port after encountering a OSError: [Errno 13] Permission denied: '/dev/ttyACM0' error.
Permissions were added by using both
sudo chmod 666 /dev/ttyACM0
andsudo usermod -aG dialout $USER
after reading some solutions on here.I have experimented with
time.sleep()
.[EDIT] Tried out the suggestions given by @michael-o. No luck.
Some other SO questions I've researched and tried, in no particular order:
Any info/ideas will be greatly appreciated!
[EDIT2] The problem has become even weirder. Here's what I tried today:
First, I programmed an Arduino on a Windows machine to constantly print a number and to blink the LED if it receives anything. Then I tested on the Linux machine and everything worked great.
Then, we programmed our hardware to do the same - constantly print a number and blink the LED if it receives anything.
Even though the logic is the same, it still fails to read or write anything to it. I even tried using GtkTerm to just inspect what is being communicated between the device and the computer. Nothing.
However! Sending "X" to the device triggers a small custom-made terminal that has some built-in commands, like "S" for stress testing and such.
The important command here is "E", which exits the terminal. If this is done (in GtkTerm), the device suddenly starts printing that number mentioned earlier. The intuition here was that on Linux (or at least in GtkTerm), "X" is sent to the device for whatever reason. So we tried exiting that custom terminal.
This unfortunately didn't in Python. It still continues receiving the same packet as described before.
So... we are stuck. But it seems like it is a firmware issue bundled with some weird quirks of the operating system. Will update if we ever figure it out.