Trouble with SPI communication using an Arduino Mega :(

Hello People,

I am a desperate programmer trying to establish an SPI communication between my Arduino Mega 2560 and a PIC based device. I need to send my data as fletcher checksum and have implemented the coding for the same. Everything except the SPI bit seems to be working. I’ve gone through numerous blogs and I am still not able to put my finger on where am going wrong. My coding is as follows. Any help or suggestions will be highly appreciated.

Many thanks
Lallisan.

Coding:

#include <SPI.h>

const int slaveselect = 26;
byte tx_buf[9]; // [ Addr, len, d0, d1, … c0, c1, dummy]
uint8_t total_len = 2;

void setup() {
// put your setup code here, to run once:
Serial.begin(115200);
digitalWrite(slaveselect, HIGH);
pinMode(slaveselect, OUTPUT); //SS
pinMode(52, OUTPUT); //SCLK
pinMode(50, OUTPUT); //MOSI
SPI.begin();
Serial.println(“SPI communication has begun”);
}

uint16_t fletcher16( uint8_t const *data, size_t bytes )
{
uint16_t sum1 = 0xff, sum2 = 0xff;

while (bytes) {
size_t tlen = bytes > 20 ? 20 : bytes;
bytes -= tlen;
do {
sum2 += sum1 += data++;
} while (–tlen);
sum1 = (sum1 & 0xff) + (sum1 >> 8);
sum2 = (sum2 & 0xff) + (sum2 >> 8);
}
/
Second reduction step to reduce sums to 8 bits */
sum1 = (sum1 & 0xff) + (sum1 >> 8);
sum2 = (sum2 & 0xff) + (sum2 >> 8);
return sum2 << 8 | sum1;
}

void fletcher_sum_data(uint8_t id, uint8_t address, uint8_t len, int32_t value)
{
int i;
tx_buf[0] = address;
tx_buf[1] = len;
while (len–)
{
tx_buf[total_len++] = value & 0xff;
value = value >> 8;
}

uint16_t csum;
uint8_t c0, c1, f0, f1;

csum = fletcher16( tx_buf, total_len); // total_len so far
f0 = csum & 0xff;
f1 = (csum >> 8) & 0xff;
c0 = 0xff - (( f0 + f1) % 0xff);
c1 = 0xff - (( f0 + c0 ) % 0xff);
tx_buf[total_len++] = c0;
tx_buf[total_len++] = c1;
tx_buf[total_len++] = ‘D’; // Dummy byte
// total_len now includes c0, c1 and dummy.
/for (i = 0; i < total_len; i++)
{
Serial.println(tx_buf
);*
_ }*/_
}
void loop() {

  • // put your main code here, to run repeatedly:*
  • int data;*
  • int received_data;*
  • int ch_no = 0;*
  • int data_address = 0xC0;*
  • int data_length = 2;*
  • int data_value = 40;*
  • fletcher_sum_data(ch_no, data_address, data_length, data_value);*
  • for (data = 0; data < total_len; data++)*
  • {*
  • Serial.print("transmitted data: ");*
  • Serial.println(tx_buf[data]);*
  • digitalWrite(slaveselect, LOW);*
  • received_data = SPI.transfer(tx_buf[data]);*
  • Serial.println(received_data);*
  • digitalWrite(slaveselect, HIGH);*
  • delay(1000);*
  • }*
    }

D50 is not MOSI. That is D51.

D50 - MISO (input) D51 - MOSI (output) D52 - SCK (output) D53 - SS (output)

Hi SurferTim

Thanks for you response. I have given the connections correctly but have messed up while commenting.. I have given the MOSI connection on D51 and it still doesnt work!

This is not just a bad comment. D50 should be an input. pinMode(50, OUTPUT); //MOSI

Have you tried inserting a small delay between setting the slave select LOW and the SPI.transfer call? Do you have an o-scope or a digital signal analyzer?

I don't have a scope with me right now however I had connected one yesterday when I was at work but couldn't see any transmission. I do have a debug UART port in the slave PIC device for reading the slave output data and have connected it to TX2 and RX2 in the Mega. But its always returning either 0 ro -1!

Were you seeing anything on the SCK and MOSI lines?

Don’t call pinMode on MOSI, MISO, or SCK. SPI.begin does that for you. Let it handle those lines. All you need to worry about is SS.

And please put your code in code tags so it doesn’t turn into italics and smileys.

Hi I can't see anything in either SCLK or MOSI lines! just popped into work to connect it in scope.

Sounds like you have a hardware fail. There should be signals on the SCK and MOSI lines when the SPI.transfer() function is called. Any other time there will be nothing (no signals) on those lines.

Oh okay! I have an arduino Uno with me as well.. Let me wire it up and see the outputs there! Thank you very much for your time and help :)

You really don't need to wire it to anything. The SCK and MOSI will still have signals during the transfer even if there is no slave device connected, but there will not be any signals on the MISO line.