I am having some issues passing more than one byte of information acorss the SPI. I have already looked at Gammon Forum : Electronics : Microprocessors : SPI - Serial Peripheral Interface - for Arduino, and tried the example where he makes SPI transmit anything, using a structure and templates. That doesn't make sense to me.
What i need is something that passes a command to the slaves, then the slave receives this command, and performs one of the prescribed actions. in paricular i want the master to send a command to read digital pins 22-49, and the slave will read those pins, compiling the results.
I based my code on an example "How to make an SPI slave" on the Gammon website.
The code works, but it can only transmit one byte of information, whereas i would like to transmit a long....
Any help is very much appreciated.
Master code:
//Master
#include <SPI.h>
int SS_one = 36; //slave select on pin 36
int SS_two = 38;
int SS_three = 40;
void setup (void)
{
Serial.begin (115200);
Serial.println ();
pinMode(SS_one, OUTPUT); //assigning slave select one
digitalWrite(SS_one, HIGH);
pinMode(SS_two, OUTPUT); //assigning slave select two
digitalWrite(SS_two, HIGH);
pinMode(SS_three, OUTPUT); //assigning slave select three
digitalWrite(SS_three, HIGH);
digitalWrite(SS, HIGH); // ensure SS stays high for now
// Put SCK, MOSI, SS pins into output mode
// also put SCK, MOSI into LOW state, and SS into HIGH state.
// Then put SPI hardware into Master mode and turn SPI on
SPI.begin ();
// Slow down the master a bit
SPI.setClockDivider(SPI_CLOCK_DIV8);
} // end of setup
byte transferAndWait ( int what)
{
int a = SPI.transfer (what);
delayMicroseconds (2000);
return a;
} // end of transferAndWait
void loop (void)
{
int a;
int aa;
int aaa;
//adding stuff, command a
// enable Slave Select
digitalWrite(SS_one, LOW); //enabling slave, to read data
transferAndWait ('a'); // add command
transferAndWait (0);
a = transferAndWait (0);
// disable Slave Select
digitalWrite(SS_one, HIGH);
Serial.println ("Slave Status:1:");
Serial.println (a, DEC);
delay(500);
// enable Slave Select
digitalWrite(SS_two, LOW); //Slave 2 ADD
transferAndWait ('a'); // add command
transferAndWait (0);
aa = transferAndWait (0);
// disable Slave Select
digitalWrite(SS_two, HIGH);
Serial.println ("Slave Status:2:");
Serial.println (aa, DEC);
delay(500);
digitalWrite(SS_three, LOW); //Slave 3 add
transferAndWait ('a'); // add command
transferAndWait (0);
aaa = transferAndWait (0);
// disable Slave Select
digitalWrite(SS_three, HIGH);
Serial.println ("Slave Status:3:");
Serial.println (aaa);
Slave
//Slave
#include <SPI.h>
#include "Wire.h" //wire class, for serial communication
//Global Variables, to be changed by programer
int SLAVE_ID = 2; //Slave Is, change this while programming the boards, to corrispond to their address in the verifier
volatile byte command = 0;
void setup (void)
{
// have to send on master in, *slave out*
pinMode(MISO, OUTPUT);
// turn on SPI in slave mode
SPCR |= _BV(SPE);
// turn on interrupts
SPCR |= _BV(SPIE);
Serial.begin(9600);
} // end of setup
// SPI interrupt routine
ISR (SPI_STC_vect)
{
long c = SPDR;
//data.select = SPDR;
long d = 0;
switch (command)
{
// no command? then this is the command
case 0:
command = c;
SPDR = 0;
break;
// add to incoming byte, return result
case 'a':
d = check_pins_2(0);
SPDR = d;
break;
// subtract from incoming byte, return result
case 's':
SPDR = c - 8; // subtract 8
break;
} // end of switch
} // end of interrupt service routine (ISR) SPI_STC_vect
void loop (void)
{
// if SPI not active, clear current command
if (digitalRead (SS) == HIGH)
{
command = 0;
Serial.print ("no longer reading");
}
Serial.println(check_pins_2(0), DEC);
} // end of loop
int check_pins_2 (int whatever)
{
int ABSOLUTE_VALUE =0;
for(int pinNum = 22; pinNum <= 49; pinNum++) //this while looper will cycle through the lower and upper pins, scanning and reporting the state of each pin, printing across the serial communication port.
{
int myPin = pinNum;
pinMode(myPin, INPUT);
if (digitalRead(myPin) == true) //if the pin is high
{
ABSOLUTE_VALUE += ( myPin); //add to absolute_value
}
//ABSOLUTE_VALUE += (SLAVE_ID*160) + 1;
return ABSOLUTE_VALUE;
}