I'm trying to figure out why my SPI device isn't responding as expected. So I hooked up my logic analyzer and am a bit confused by the results.
I'm seeing what appears to be random pulses on the chip select/slave select line (CS in the images below). The pulses happen in random locations with random counts. Always matching either a falling edge or rising edge in the CLK line.
Logic Analyser Screen Capture 1 Logic Analyser Screen Capture 2
The code I'm running is part of a library, but I've pulled it all out for a minimum functional example:
#include <SPI.h>
#define DC_PIN 9
#define CS_PIN 10
#define BUSY_PIN 7
int IfInit(void) {
pinMode(CS_PIN, OUTPUT);
SPI.begin();
SPI.beginTransaction(SPISettings(2000000, MSBFIRST, SPI_MODE0));
return 0;
}
void SpiTransfer(unsigned char data) {
digitalWrite(CS_PIN, LOW);
SPI.transfer(data);
digitalWrite(CS_PIN, HIGH);
}
int Init() {
if (IfInit() != 0) {
return -1;
}
SendCommand(0x01); //POWER_SETTING
SendData(0x03); // VDS_EN, VDG_EN
SendData(0x00); // VCOM_HV, VGHL_LV[1], VGHL_LV[0]
SendData(0x2b); // VDH
SendData(0x2b); // VDL
SendData(0xff); // VDHR
SendCommand(0x06); //BOOSTER_SOFT_START
SendData(0x17);
SendData(0x17);
SendData(0x17); //07 0f 17 1f 27 2F 37 2f
SendCommand(0x04); //POWER_ON
WaitUntilIdle();
SendCommand(0x00); //PANEL_SETTING
SendData(0xbf); // KW-BF KWR-AF BWROTP 0f
SendData(0x0b);
SendCommand(0x30); //PLL_CONTROL
SendData(0x3c); // 3A 100HZ 29 150Hz 39 200HZ 31 171HZ
return 0;
}
void SendCommand(unsigned char command) {
// digitalWrite(DC_PIN, LOW);
SpiTransfer(command);
}
void SendData(unsigned char data) {
// digitalWrite(DC_PIN, HIGH);
SpiTransfer(data);
}
void WaitUntilIdle(void) {
while(digitalRead(BUSY_PIN) == 0) { //0: busy, 1: idle
delay(100);
}
}
void setup() {
pinMode(CS_PIN, OUTPUT);
digitalWrite(CS_PIN, HIGH);
Serial.begin(9600);
Serial.println("Start");
if (Init() != 0) {
Serial.println("init failed");
return;
}
Serial.print("init success");
}
void loop() {
}
I've tried on two different ATMEGA chips (same Arduino Uno board), same results. I've also tried with the device disconnected. Again same results. I've also tried changing the pin used for the CS, still didn't change anything.
Anyone have some insight as to what might be causing this, and/or what can be done to stop it?
2 Answers 2
I shortened the leads between my arduino board and the device from 15 inches down to ~5 inches and the issue disappeared.
I would have to guess that it was some RF interference.
-
Interesting. A possible alternative would have been to slow down SPI. However that doesn't totally explain the glitches on SS.02/07/2018 04:57:40Commented Feb 7, 2018 at 4:57
See my page about SPI.
Pin 10 of the Arduino is the SS line - so does this mean you have to use it for the peripheral SS line? Or should it be kept high? The answer (from the Atmega documentation) is that the SS line (pin 10) must be configured as an output (regardless of what value is on it). If configured as an output the Arduino ignores the value on that line, and thus the SPI hardware will not be put into slave mode.
Since the value on pin 10 is ignored, providing it is set as an output, then it can also be used as the SS line for your first, or only, slave. You could then use other pins (eg. 5, 6, 7, 8, 9) to control other slaves.
For you to successfully make an SPI master then pin 10 on your Uno must be configured as an output, regardless of whether or not you actually use pin 10 for SS. Under the circumstances, you may as well use pin 10 for SS if you are going to make it an output anyway.
This issue persists when using pin 10 as the SS.
I tried your code with my Uno (no device connected) and had no such problems. Sounds like an electrical issue to me.
-
This issue persists when using pin 10 as the SS.Mazaryk– Mazaryk02/07/2018 00:11:55Commented Feb 7, 2018 at 0:11
-
See amended reply. I cannot reproduce that issue with your code.02/07/2018 02:38:59Commented Feb 7, 2018 at 2:38
-
Interesting. That definitely suggests it's an issue specific to my setup. Thanks.Mazaryk– Mazaryk02/07/2018 03:25:28Commented Feb 7, 2018 at 3:25
SPI.begin()
afterSPI.beginTransaction
is the wrong order to do things.SPI.begin()
should be done first.