Open jmadajian opened 4 years ago
I suspect this is an underlying issue with the Linux SPI driver on the Pi not supporting threewire- that seems to be the (albeit tenuous) conclusion found here: https://www.raspberrypi.org/forums/viewtopic.php?t=76043 and here: https://www.raspberrypi.org/forums/viewtopic.php?f=44&t=30052&p=262677
IE: there's nothing that can be done with py-spidev that can fix this.
The SPI driver DOES support Threewire mode and it works. People are telling bs.
This is because in threewire mode you can only read OR write. However, with xfer it tells the spidev device to do both. So it fails with an invalid argument error.
However, you should be able to call spi.readbytes
and spi.writebytes
without any error, right?
Problem is, that py-spidev has no nice api to "concatenate" SPI reads/writes without releasing the chip select. As i just stumbled upon this issue as well, I will try to write a PR.
Any API Naming suggestions? I really dislike the xfer xfer2 xfer3 etc kind of naming convention.
This works for me: https://github.com/KoWu/py-spidev/tree/threewire-xfer
Compile & Install with:
sudo apt install python3-setuptools libpython3.7-dev
git clone https://github.com/KoWu/py-spidev.git && cd py-spidev
git checkout threewire-xfer
make CFLAGS+=-DSPIDEV_SINGLE
sudo make install
Example usage, tested with an Raspberry PI 3B and an IIS2MDC:
>>> import spidev
>>> spi = spidev.SpiDev()
>>> spi.open(0, 2)
>>> spi.threewire = True
>>> spi.xfer([0x4f | 0x80, None])
[None, 64]
Searching Github for "threewire = True" returned four results, one of which uses the method @KoWu described. I'll try implementing it next week, but this looks like the answer. How about naming them simply spi.read and spi.write like MicroPython does?
So, I installed your code, which required that I change the first line of /home/pi/py-spidev/Makefile to python3 before executing sudo make install
. but now I get
Traceback (most recent call last): File "program.py", line 1342, in <module> spi.xfer([0x4f | 0x80, None]) TypeError: Non-Int/Long value in arguments: 3b6e90.
Traceback (most recent call last): File "program.py", line 1344, in <module> spi.xfer([0x00 | 0x80, 0x00]) OSError: [Errno 22] Invalid argument
Also, I used print(spidev.__file__)
to verify that spidev was being imported from the same directory as the installation.
Some options. Either you forgot to call make with the CFLAGS option or you forgot to checkout the specific branch. Or you are still using the wrong spidev module for some reason. Because there is no way that this error message is printed otherwise. Try to uninstall py-spidev completely and then try again.
That did help. While I'm still troubleshooting with "threewire=True", I did discover one error that is consistent. Whenever I run spi.open(0,N)
the code compiles, howerver spi.open(1,N)
produces the following:
Traceback (most recent call last):
File "program.py", line 4, in <module>
spi.threewire = True
OSError: [Errno 22] Invalid argument
Yes, because only spidev0 supports 3wire. Spi1 and 2 are "universal spi masters" (lower throughput and simpler) and do not Support it as far as i can tell from the BCM2835 datasheet.
However this isnt that bad, because as spi0 uses gpio for chip select anyway you could just increase the number of cs pins by using a device tree overlay (if this is the reason why you would want to use spi1)
Greetings py-spidev team,
When I set the flag spi.threewire=True I get a response similar to this one:
Traceback (most recent call last): File "program.py", line 1333, in <module> transferRead("MUXOUT", 0) File "program.py", line 132, in transferRead resp = spi.xfer2([regW, 0]) # responce from register OSError: [Errno 22] Invalid argument
I'm using the RPi to control multiple SPI devices. One of the devices communicates successfully with with spi.threewire=False (implying that the rest of my code/workflow is working), but another device shares the SI/SO signals and requires spi.threewire=True.
What do you suggest? Is this an issue with py-spidev?
(Note that the RPi 4B has the BCM2711, not BCM2835)
Thank you,
Jonathan
pi@raspberrypi:~ $ uname -a Linux raspberrypi 4.19.118-v7l+ #1311 SMP Mon Apr 27 14:26:42 BST 2020 armv7l GNU/Linux
pi@raspberrypi:~ $ cat /proc/cpuinfo | grep Model Model : Raspberry Pi 4 Model B Rev 1.2
pi@raspberrypi:~ $ cat /proc/cpuinfo | grep Revision Revision : c03112
pi@raspberrypi:~ $ modinfo spi-bcm2835 filename: /lib/modules/4.19.118-v7l+/kernel/drivers/spi/spi-bcm2835.ko license: GPL v2 author: Chris Boot <bootc@bootc.net> description: SPI controller driver for Broadcom BCM2835 srcversion: CC0CA8084657816640759C9 alias: of:N*T*Cbrcm,bcm2835-spiC* alias: of:N*T*Cbrcm,bcm2835-spi depends: intree: Y name: spi_bcm2835 vermagic: 4.19.118-v7l+ SMP mod_unload modversions ARMv7 p2v8
pi@raspberrypi:~ $ python3 Python 3.7.3 (default, Dec 20 2019, 18:57:59) [GCC 8.3.0] on linux Type "help", "copyright", "credits" or "license" for more information.