0

I'm trying to communicate raspi and due with SPI. Raspi is master and due is slave. I can send bytes from raspi to due via SPI with no problem. But what I need on DUE side is , when I received the data from Raspi I send a new data to Raspi from DUE. Here are my codes;

Raspi QT wiring pi (master)

#include <wiringPiSPI.h>
#include <QDebug>
#define SPI_CHANNEL 0
#define SPI_CLOCK_SPEED 500000

int main(int argc, char *argv[])
{
    QApplication a(argc, argv);
    MainWindow w;
    w.show();
    int fd = wiringPiSPISetupMode(SPI_CHANNEL, SPI_CLOCK_SPEED, 0); // Starting SPI
    if (fd == -1) {
        qDebug() << "Failed to init SPI communication.\n";
        return -1;
    }
    qDebug() << "SPI communication successfully setup.\n";


    unsigned char buf[2] = { 1, 2 }; // Char for sending to DUE
    wiringPiSPIDataRW(SPI_CHANNEL, buf, 2); // Sending and receiving data
    qDebug() << "Data returned: " << buf[0] << buf[1] << "\n";
    return a.exec();
}

Arduino DUE codes(slave)

void setup() {
Serial.begin(250000);
//SPI serial recieve
REG_PMC_PCER0 |= PMC_PCER0_PID24;      // Power up SPI clock
REG_SPI0_WPMR = 0<<SPI_WPMR_WPEN;   //Unlock user interface for SPI

//Instance SPI0, MISO: PA25, (MISO), MOSI: PA26, (MOSI), SCLK: PA27, (SCLK), NSS: PA28, (NPCS0)
REG_PIOA_ABSR |= PIO_ABSR_P25;    // Transfer Pin control from PIO to SPI
REG_PIOA_PDR |= PIO_PDR_P25;        // Set MISO pin to an output

REG_PIOA_ABSR |= PIO_ABSR_P26;    // Transfer Pin control from PIO to SPI
REG_PIOA_PDR |= 0<<PIO_PDR_P26;  // Set MOSI pin to an input

REG_PIOA_ABSR |= PIO_ABSR_P27;     // Transfer Pin control from PIO to SPI
REG_PIOA_PDR |= 0<<PIO_PDR_P27;   // Set SCLK pin to an input

REG_PIOA_ABSR |= PIO_ABSR_P28;     // Transfer Pin control from PIO to SPI
REG_PIOA_PDR |= 0<<PIO_PDR_P28;   // Set NSS pin to an input

REG_SPI0_CR = 1;   // Enable SPI
REG_SPI0_MR = 0;   // Slave mode
// Receive Data Register Full Interrupt
SPI0->SPI_IER = SPI_IER_RDRF;
NVIC_EnableIRQ(SPI0_IRQn);

SPI0->SPI_CSR[0] = SPI_CSR_NCPHA|SPI_CSR_BITS_8_BIT;
}

void SPI0_Handler()
{    
  byte c = SPI0->SPI_RDR;
  SPI0->SPI_TDR = c;
}

With these codes I can send chars from Raspberry to DUE successfully but can only receive "0 0" from DUE. But If I connect the MOSI and MISO pins together on Raspberry pi I cant successfully receive/return "1 2"

EDIT : I changed the arduino DUE with arduino MEGA and use the "SLAVE" sketch on gammon... GAMMON SLAVE SKETCH Of course no change on raspberry side and everything works succesfully. So the problem is on DUE side....

bladekel
  • 37
  • 7

1 Answers1

0

I check the due datasheet. The register has some error. You can try this:

void setup() {
    Serial.begin(115200);
    while(!Serial);

    //SPI serial recieve
    REG_PMC_PCER0 |= PMC_PCER0_PID24;       // Power up SPI clock
    REG_SPI0_WPMR = 0<<SPI_WPMR_WPEN;       //Unlock user interface for SPI

    //Instance SPI0, MISO: PA25, (MISO), MOSI: PA26, (MOSI), SCLK: PA27, (SCLK), NSS: PA28, (NPCS0)
    REG_PIOA_ABSR &= ~PIO_ABSR_P25;         // Transfer Pin control from PIO to SPI
    REG_PIOA_PDR |= PIO_PDR_P25;            // disable pio to control this pin (MOSI)

    REG_PIOA_ABSR &= ~PIO_ABSR_P26;         // Transfer Pin control from PIO to SPI
    REG_PIOA_PDR |= PIO_PDR_P26;            // disable pio to control this pin (MOSI)

    REG_PIOA_ABSR &= ~PIO_ABSR_P27;         // Transfer Pin control from PIO to SPI
    REG_PIOA_PDR |= PIO_PDR_P27;            // disable pio to control this pin (SCLK)

    REG_PIOA_ABSR &= ~PIO_ABSR_P28;         // Transfer Pin control from PIO to SPI
    REG_PIOA_PDR |= PIO_PDR_P28;            //disable pio to control this pin (NSS)

    REG_SPI0_CR = 1;                        // Enable SPI
    REG_SPI0_MR = 0;                        // Slave mode

    SPI0->SPI_IER = SPI_IER_RDRF;           //Receive Data Register Full Interrupt
    NVIC_EnableIRQ(SPI0_IRQn);

    SPI0->SPI_CSR[0] = SPI_CSR_NCPHA|SPI_CSR_BITS_8_BIT;    // Shift on falling edge and transfer 8 bits.
    Serial.println("START");
}

bool flag=false;
uint16_t DataReceived;
void SPI0_Handler()
{
    uint32_t status = SPI0->SPI_SR;
    if (status & SPI_SR_RDRF){
        DataReceived = SPI0->SPI_RDR & SPI_RDR_RD_Msk;
        flag=true;
    }
    if (status & SPI_SR_TDRE) {
        SPI0->SPI_TDR = (uint16_t)DataReceived;
    }
}

void loop() {
    if(flag){
        flag=false;
        Serial.println(DataReceived);
    }
}
Etao
  • 1