RTEMS SPI Implementations

William Busacker wbusacker at outlook.com
Thu Jan 31 04:28:20 UTC 2019

Hi all,

Told myself that in the new year I'd finally get around to working on the Raspberry Pi's BSP some more, but before I start I have a couple questions I'd like to have answered, particularly about SPI. Not sure if this belongs in the devel list, figured users was a good place to start.

Its been talked about before how the RPi SPI driver should be re-written at some point. Between the interrupt mis-handling, file descriptor bugs, and performance issues, I think there is enough cause to do a rewrite, but I'm not sure how exactly it should be done. Section 10 of the BSP and Driver guide blanket statements that the SPI bus drivers should use the SPI bus framework (dead link, likely lost in the cpukit move) and specifies that the API needs to be Linux user-space compatible. I understand the desire to be as linux-y as possible to make developing in RTEMS much more natural for those not used to real time systems, but in this case I'm not sure if it is the best move. Doubly so for the Raspberry Pi. (As I'm interested in the RPi in particular I'll be referencing that specific BSP forward)

Since the RPi is marketed as an "entry" device for hobby electronics, it is either a gateway device or is being upgraded to from an Arduino. Brand new users trying to learn about SPI online (Sparkfun's blog post being very popular) and people coming from Arduino will be used to the model of 8/16 bits being traded with cs active end point. Put data in buffer, send/receive, read back, or do it all at once with a single function call. Arduino handles this flow quite nicely; configure an SPISettings object, "begin" transactions, do as many .transfers() as you want then when you're done "end" transaction. Granted Arduino purposefully simplifies things, it still is very representative to what actually occurs in hardware and is easy for a newcomer to grasp. Linux's SPI user-space driver introduces ioctl which in and of itself is complex and then makes all interaction through a file descriptor, limiting the user to either read or write ability, not both at the same time.

For the RPi, the vast majority of SPI examples are either in Python (which does use spidev) or in C using either the wiringPi or BCM2835 libraries. Both the C libraries provide functionality more akin to Arduino's solution than the Linux kernel solution.

There are also issues in operational terms of spidev.
- Full duplex is impossible without digging into ioctl
- Everything must be synchronous (sitting in its own task can help mimic interrupts but may not be the best solution)
- spidev doesn't offer slave select polarity control

What I was thinking as an alternative is something close to how the BCM2835<https://www.airspayce.com/mikem/bcm2835/group__spi.html#ga0127eab1b6c3f8bf127bdac474fdc0f9> library controls SPI. The library can't be directly put into the RTEMS project since it relies on Linux for other things, but its general approach is something I feel is a much better solution than using spidev. It grants far more insight into what the bus is doing as well as much tighter control over the device. I realize this means more documentation (something I also plan on attempting to tackle for RPi at some point), but I think thats a worthy tradeoff. Especially since it seems spidev was designed to fit Unix's I'll-get-around-to-it-when-I-feel-like-it approach to device control, compared to an rtos's Its my bus and I need it now!

-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.rtems.org/pipermail/users/attachments/20190131/f9247bc9/attachment.html>

More information about the users mailing list