arduino / arduino/ArduinoCore-sam
SPI Mode 3 on Due doesn't work properly with new APIs i.e. using SPI.beginTransaction(SPISettings)
- Dominant language
- HTML
- Stars
- 91
- Forks
- 112
- PR merge metrics
- No merged PRs in 30d
Description
When I try to set SPI in Mode 3 on Due the first write doesn't work all the time. Upon investigating more I observed that when Due is set in Mode 3 the clock polarity on the oscilloscope is wrong for the cases it doesn't work on the first write, it generates Mode 0 clock.
The issue can be reproduced by using the following sketch to write to an EEPROM, the write in the setup function doesn't write correct data when the Clock of Mode 0 is generated when the SPI_Mode is set to Mode 3. However, the data written in the loop is read correctly and printed on Serial monitor when the:
```
#include
// Using simple SPI APIs for Due
#define CSPin 4
#define CLKRate 16000000
void setup() {
pinMode(CSPin ,OUTPUT);
SPI.begin();
digitalWrite(CSPin,HIGH);
Serial.begin(9600);
Serial.println("SETUP");
SPI.beginTransaction(SPISettings(CLKRate, MSBFIRST, SPI_MODE3));
digitalWrite(CSPin,LOW);
SPI.transfer(6);
digitalWrite(CSPin,HIGH);
SPI.endTransaction();
delay(10000);
Serial.println("SETUP:WriteData");
SPI.beginTransaction(SPISettings(CLKRate, MSBFIRST, SPI_MODE3));
byte dataWrite[8] = {2, 0, 0, 1, 3, 8, 4, 6};
digitalWrite(CSPin,LOW);
for(int i = 0 ; i < 7;i++)
{
SPI.transfer(dataWrite[i]);
}
SPI.transfer(dataWrite[7]);
digitalWrite(CSPin,HIGH);
SPI.endTransaction();
delay(10000);
Serial.println("SETUP:ReadData");
SPI.beginTransaction(SPISettings(CLKRate, MSBFIRST, SPI_MODE3));
byte dataWrite1[8] = {3, 0, 0, 0, 0, 0, 0, 0};
byte readData[8];
digitalWrite(CSPin,LOW);
for(int j = 0 ; j < 7;j++)
{
readData[j] = SPI.transfer(dataWrite1[j]);
Serial.println(readData[j]);
}
readData[7] = SPI.transfer(dataWrite1[7]);
Serial.println(readData[7]);
digitalWrite(CSPin,HIGH);
SPI.endTransaction();
Serial.println("ExitingSetup");
}
void loop() {
// put your main code here, to run repeatedly:
// Set BitRate to 4 MHz
Serial.println("LOOP");
SPI.beginTransaction(SPISettings(CLKRate, MSBFIRST, SPI_MODE3));
digitalWrite(CSPin,LOW);
SPI.transfer(6);
digitalWrite(CSPin,HIGH);
SPI.endTransaction();
delay(1000);
SPI.beginTransaction(SPISettings(CLKRate, MSBFIRST, SPI_MODE3));
byte dataWrite[8] = {2, 0, 0, 1, 3, 6, 4, 5};
digitalWrite(CSPin,LOW);
for(int i = 0 ; i < 7;i++)
{
SPI.transfer(dataWrite[i]);
}
SPI.transfer(dataWrite[7]);
digitalWrite(CSPin,HIGH);
SPI.endTransaction();
delay(1000);
SPI.beginTransaction(SPISettings(CLKRate, MSBFIRST, SPI_MODE3));
byte dataWrite1[8] = {3, 0, 0, 0, 0, 0, 0, 0};
byte readData[8];
digitalWrite(CSPin,LOW);
for(int j = 0 ; j < 7;j++)
{
readData[j] = SPI.transfer(dataWrite1[j]);
Serial.println(readData[j]);
}
readData[7] = SPI.transfer(dataWrite1[7]);
Serial.println(readData[7]);
digitalWrite(CSPin,HIGH);
SPI.endTransaction();
delay(10000);
}
```
Contributor guide
No contributing guide indexed for this repository
Research direction
Start at the SPI.beginTransaction(SPISettings) path and reproduce the provided sketch on an Arduino Due while observing the clock signal. The work is done when SPI_MODE3 consistently produces Mode 3 clock polarity on the first write, including the setup transaction, and the EEPROM receives the correct data.
Written by the indexing model from the issue text.
Assessment
- Tech stack
- cpp
- Domain
- embedded-iot
- Issue type
- Bug
- Difficulty
- 4/5
- Estimated time
- 3-5 days
- Activity status
- Stale
- Clarity
- Mostly clear
- Newbie friendliness
- 35/100