Hardware Reference
In-Depth Information
digitalWrite(8, (blink = !blink)); // Blink LED life check
delay(1000);
}// End loop
byte transferSPI(byte dataToSend) {
digitalWrite(10, LOW); // Turn the slave select on
delay(1); // The slave takes a moment to respond to the slave select line falling
dataToReceive = SPI.transfer(dataToSend); // Begin full-duplex data transfer
digitalWrite(10, HIGH); // Turn the slave select off
Serial.write(dataToSend); // Echo sent data
Serial.println();
Serial.write(dataToReceive); // Display byte received
Serial.println();
}// End transferSPI
Verifying the Code
The code in Listing 10-1 needs to be uploaded to a single Arduino that will be designated as master. The SPI functionality
is handled by the library, and with only the SPI.begin() used, the default settings are all used from the Arduino. To verify
that the code is working properly, set up the LED to pin 8 and connect the MOSI pin 11 to the MISO pin 13, creating a
data loopback. The SS and SCK can be left alone for this test. The master connected to itself should echo the characters
sent through the serial connection. As it shifts a byte out normally to a slave, it shifts a byte in. This process is held in
lockstep by the SCK, which normally causes the slave to simultaneously send and receive a bit until the whole byte is
swapped. When plugged into itself, the master will expect a bit from the slave every time it sends one. Once you have
verified that the Arduino can properly send and receive data, it is ready integrate the slave into the SPI setup.
Interrupting Vectors
In order to respond to the incoming data from the master, the slave will need to react very quickly to the SS going
low. The SS pin could be constantly polled in the loop, but this would take a lot of time, and as the code grows in
complexity, it would become altogether impossible for the slave to react quickly enough. To achieve the proper
response time to the master's control, an internal interrupt needs to be implemented. The Arduino has several
interrupt vectors that each has a specific trigger. Generally, both the SREG and the specific interrupt must be set.
The simplest way to manipulate the SREG is to use the built-in commands cli(); and sei(); . cli(); turns global
interrupts off, and sei(); turns them on. When they are on, any enabled interrupts will be followed and make
use of the code within an attached ISR (interrupt service routine) function. When an interrupt occurs, the current
instruction will complete and the code that was running will stop and wait for the interrupt to finish. When working
with new code in an interrupt, it may be helpful to do something observable in the main loop—that is, to have a
simple method to verify that the interrupt is exiting properly and the loop is proceeding.
When designing code that includes interrupts, you need to take special care to determine if other code in the
program will fail while the interrupt is running. This may include code that itself is time sensitive or perhaps shares
a global variable with the interrupt, whereby data loss would occur by following the interrupt. In these cases it is best
to turn interrupts off until the code has executed. This can be accomplished by the command cli(); . Remember
the interrupts need to be turned back on after the critical code has executed to be used again later. This, again, is
accomplished by using the sei(); command. When multiprocessing, the behavior of other devices must also be
accounted for. The fact that interrupts are turned off on one device does not prevent the remaining devices from acting
as normal. With SPI, this could be handled through a software layer protocol. Simply have the slave echo the first byte
back to the master before the master continues transmission. This will tell the master that the slave is ready and listening.
The SPI interrupt vector is called when the SREG and SPI interrupt enable are on and the SPI interrupt flag is
set by the SS line going low. These registers are explained in the next section in detail. When these three conditions
 
Search WWH ::




Custom Search