SPI Bus in Python
-
@Lazar-Demin As I was seeing previously writebytes followed by readbytes causes too much delay between the read and write transaction and de-asserts chip-select causing loss of the read result. I assume keeping the clock and cs going and populating rx_buffer during the write should be a good solution, actually I belive xfer should be modified to populate rx_buffer anyway since a lot of SPI devices have an echo functionality where the MISO echoes MOSI to tell the driver that the chip is acknowledging data coming in.
My suggestion:
Replace this line with read equivalent size of the xfer or xfer2 write buffer so that data read in from the kernel driver actually reflects whatever the SPI slave is placing on the MISO during the write. Passing read length of 0 seems like a waste. Simply pass it the length of the write buffer, so that we get actual data rather than malloc noise.
Also not sure the purpose of this line, why should the driver populate xfer struct with read_buffer data ? As long is data is read correctly during the full-duplex xfer we should be fine.
Another read
A third read makes the full duplex limitation and need for mediatek special xfer3 clear. So the ioctl explicitly needs to null the xfer tx buffer pointer during the 2 read bytes for this to work.xfer3 would a possible solution once I get the onion toolchain going and can actually compile the python-spidev. Any assistance and mods from your side to implement the patch would be awesome.
-
@Tisham-Dhar Yeah, the de-assertion of the CS line complicates things.
Regarding setting up the Toolchain, take a look at the instructions in our Build System ReadMe. It will likely take the least amount of time if you use the Docker method on a Linux system.
-
@Lazar-Demin the docker make takes a tonne of time and crashes and only seems to work 1/2 decent on a native Linux host instead of a VM on Windows host.
Would you have steps to compile a custom spidev outside of the feeds/onion/python-spidev ? This would be really useful in getting more contributions. I believe the toolchain is the biggest hurdle.
Perhaps run a CI which regularly builds the toolchain and docker snapshots for easier pull.
-
@Tisham-Dhar Yeah, we use a pretty powerful Linux server to build the firmware. You'll notice in our Build System readme that we recommend running Docker on a Linux sytem.
Don't really have instructions to build python-spidev outside of the build system. The CI is a good idea, we'll look into it and see how we can fit that into our road map.
-
@Lazar-Demin I successfully staged and built python-spidev in isolation like this:
make package/python-spidev/{clean,compile,install} V=s
With a very handy tip from OpenWRT here.
This does not take tonnes of time compared to "make world" and is super useful for focusing my contribution. I will fork your python-spidev, patch it with xfer3 , update git link in feed to point to my fork and hack it till it works.
Anyone else is welcome to help me out and join the fun @Maximilian-Gerhardt
Regards,
-
@Tisham-Dhar Ah I misunderstood what you meant by "compile a custom spidev outside of the feeds/onion/python-spidev"
Yes, what you're doing is a good idea.
I would also suggest looking into theUSE_SOURCE_DIR
flag, it allows you to use/compile a local copy of the package source code. More info here.
-
I have started a fork an have been making Python signature commits to it. The core xfer3 logic is currently a TODO. If @Lazar-Demin can review and suggest an implementation it will be much appreciated.
-
@Tisham-Dhar the core logic can follow this function here: https://github.com/OnionIoT/omega2-lmic-lorawan/blob/master/native-spi.cpp#L110
Essentially it does two distinct transfers, one for writing and one immediately afterward for reading.
-
EDIT Sep 22, 2023: Updating below commands so Python3 version of spidev module is installed, as Python2 is now legacy
@Tisham-Dhar I've gone ahead and implemented a working half-duplex transmission function! Version 4.0.1 of
python3-spidev
features a newxfer3
function.Getting the Latest Version of
python3-spidev
If you don't have it installed already:
opkg update opkg install python3-light python3-spidev
If you have it installed, you'll need to upgrade:
opkg update opkg upgrade python3-spidev
To use the new function:
values = spi.xfer3([<list of bytes to write>], <number of bytes to read>)
This will write all of the bytes from the list in the first argument and will then immediately read the number of bytes specified by the second argument.
The function will return a list of the bytes that were read.
An Example
Instead of using
spi.xfer([0x80,0xD9,0x00,0x00])
Try
values = spi.xfer3([0x80,0xD9], 2)
More Details
More details can be found in our python-spidev github repo readme
Let me know how it goes!
-
@Lazar-Demin Is this still just for python 2??? is there a python 3 version??
-
@Juan-Pablo-Jimenez A python3 version is now available as well! See https://github.com/OnionIoT/python-spidev#installation-on-omega2
-
@Lazar-Demin I cannot install version for python3.. it says "Unknown package 'python3-spidev'"
-
@Pablo-Fonovich Which firmware version are you running?
I ask because python3-spidev is published in the new package repo. Try upgrading your firmware to v0.3.0 or higher and trying again.
-
@Lazar-Demin Oh thanks! i had updated to the latest stable. I'm trying right now.
-
@Lazar-Demin That worked! thanks.. are gpio and serial packages available for pyhton3?
-
@Pablo-Fonovich you can get a list of available python3 packages by running:
opkg opkg list | grep python3
You can also install
python3-pip
to install Python packages, see this guide for more details.
-
@Lazar-Demin , thanks, i've already knew that... but i cannot find any gpio module for python3, nor can i find a serial module for python3.. Are they available?
-
@Lazar-Demin Hey, sorry to continue this after this long. but i started with a second device, isntalled python3-pip, but command line says pip3 not found.. what could be happening?
-
@Lazar-Demin In fact, i can see pip3 binary in /usr/bin/, but running it, even with full absolute path, returns not found error
-
Maybe take a look at Lazar's recent response
https://community.onion.io/topic/3591/python3-modules-for-gpio-and-serial-port/9