The Serial Peripheral Interface (SPI) communications protocol is used to send and receive data between integrated circuits.
The SPI function in MMBasic acts as the master (ie, MMBasic generates the clock).
The syntax of the function is:
received_data = SPI( rx, tx, clk, data_to_send, speed, mode, bits )
Data_to_send, speed, mode and bits are all optional. If not required they can be represented by either empty space between the commas or left off the end of the list.
‘rx’ is the pin number for the data input (MISO)
‘tx’ is the pin number for the data output (MOSI)
‘clk’ is the pin number for the clock generated by MMBasic (CLK)
‘data_to_send’ is optional and is an integer representing the data byte to send over the output pin. If it is not specified the ‘tx’ pin will be held low.
‘speed’ is optional and is the speed of the clock. It is a single letter either H, M or L where H is 3 MHz, M is 500 KHz and L is 50 KHz. Default is H.
‘mode’ is optional and is a single numeric digit representing the transmission mode – see Transmission Format below. The default mode is 3.
‘bits’ is optional and represents the number of bits to send/receive. Range is 1 to 23 (this limit is defined by how many bits can be stored in a floating point number). The default is 8.
The SPI function will return the data received during the transaction as an integer. Note that a single SPI transaction will send data while simultaneously receiving data from the slave (which is often discarded).
Using all the defaults:
A = SPI(11, 12, 13)
Specifying the data to be sent:
A = SPI(11, 12, 13, &hE4)
Setting the mode but using the defaults for data to send and speed:
A = SPI(11, 12, 13, , , 2)
An example specifying everything including a 12 bit data transfer:
A = SPI(11, 12, 13, &hE4, M, 2, 12)
The most significant bit is sent and received first. The format of the transmission can be specified by the ‘mode’ as follows:
Mode 0. CPOL 0, CPHA 0 – Clock is active high, data is captured on the rising edge and output on the falling edge
Mode 1. CPOL 0, CPHA 1 – Clock is active high, data is captured on the falling edge and output on the rising edge
Mode 2. CPOL 1, CPHA 0 – Clock is active low, data is captured on the falling edge and output on the rising edge
Mode 3. CPOL 1, CPHA 1 – Clock is active low, data is captured on the rising edge and output on the falling edge
Before invoking this function the ‘rx’ pin must be configured as an input using the SETPIN command and the ‘tx’ and ‘clk’ pins must be configured as outputs (either normal or open collector) again using the SETPIN command. The clock pin should also be set to the correct polarity (using the PIN function) before the SETPIN command so that it starts as inactive.
The SPI enable signal is often used to select a slave and “prime” it for data transfer. This signal is not generated by this function and (if required) should be generated using the PIN function on another pin.
The SPI function does not “take control” of the I/O pins like the serial and I2C protocols and the PIN command will continue to operate as normal on them. Also, because the I/O pins can be changed between function calls it is possible to communicate with many different SPI slaves on different I/O pins.
The following example will send the command &h80 and receive two bytes from the slave SPI device. Because the mode, speed and number of bits are not specified the defaults are used.
‘ set rx pin as a digital input
SETPIN 18, 2
‘ set tx pin as an output
SETPIN 19, 8
‘ set clk pin high then set it as an output
PIN(20) = 1 : SETPIN 20, 8
‘ pin 11 will be used as the enable signal
PIN(11) = 1 : SETPIN 11, 8
‘ assert the enable line (active low)
PIN(11) = 0
‘ send the command and ignore the return
junk = SPI(18, 19, 20, &h80)
‘ get the first byte from the slave
byte1 = SPI(18, 19, 20)
‘ get the second byte from the slave
byte2 = SPI(18, 19, 20)
‘ deselect the slave
PIN(11) = 1
Information from Geoff Graham http://geoffg.net