Main Site Documentation

SPI Communication - Extra clock pulse



I am having an issue with the SPI communication on a G400D. I am communicating to an IO Expander, MCP23S17. Attached is a screen capture of my issue.

I have a dedicated GPIO pin for the chip select (blue on screen capture) and send over 16bits of register address followed by 16 bits of data (8bits actual data, 8 bits ignored) (yellow trace on screen capture)

I had this working correctly, but suddenly I am seeing an extra clock pulse(GREEN trace) before some of my messages.

It seems to be completely at random and if that extra clock pulse is not there, I can set the desired bit on my IO expander.
What could be causing this issue?

        ushort[] Motor_IOCONFIG = new ushort[] { 0x400A };// I/O Configuration Register
        ushort[] Motor_IODIRA = new ushort[] { 0x4000 }; // I/O Direction Register A
        ushort[] Motor_IODIRB = new ushort[] { 0x4010 };// I/O Direction Register B
        ushort[] Motor_GPPUB = new ushort[] { 0x4016 };// Pull Up Resistor Configuration for port B
        ushort[] Motor_GPIOB = new ushort[] { 0x4019 };// Port Register reflect the value on the port B
        ushort[] Motor_GPPUA = new ushort[] { 0x4006 };  // Pull Up Resistor Configuration for port A
        ushort[] Motor_GPIOA = new ushort[] { 0x4009 };
        ushort[] GPINTENA = new ushort[] { 0x4002 };   // Controls Interrupt-On-Change for each pin 
        ushort[] DEFVALA = new ushort[] { 0x4003 };

        ushort[] IOCON_Data = new ushort[] { 0xA2 };
        ushort[] DIR_Input_Data = new ushort[] { 0xFF };
        ushort[] DIR_Output_Data = new ushort[] { 0x00 };
        ushort[] PU_EN_Data = new ushort[] { 0xFF };
        ushort[] PU_DIS_Data = new ushort[] { 0x00 };
        //ushort[] PORTA_Status = new ushort[] {0x00};


        Motor_IOExpander_Reset.Write(false);    // Reset IO Expander 

        MotorControlSPI.WriteRead(Motor_IOCONFIG, SPI_DataReceived);   // IO Expander IO Configuration Register Address
        MotorControlSPI.WriteRead(IOCON_Data, SPI_DataReceived);       // IO Expander IO Configuration Data

        Motor_IOExpander_CS.Write(false);           // PortA Direction
        MotorControlSPI.WriteRead(Motor_IODIRA, SPI_DataReceived);     // Pins set as Output
        MotorControlSPI.WriteRead(DIR_Output_Data, SPI_DataReceived);

        Motor_IOExpander_CS.Write(false);           // PortB Direction 
        MotorControlSPI.WriteRead(Motor_IODIRB, SPI_DataReceived);     // Pins set as Inputs
        MotorControlSPI.WriteRead(DIR_Input_Data, SPI_DataReceived);

        PORTA_Status[0] = (ushort)PORTA_VALUES(PORTA_Status[0], "YRESET", "DISABLE");
        PORTA_Status[0] = (ushort)PORTA_VALUES(PORTA_Status[0], "YSLEEPN", "DISABLE");
        MotorControlSPI.WriteRead(Motor_GPIOA, SPI_DataReceived);
        MotorControlSPI.WriteRead(PORTA_Status, SPI_DataReceived);


Strange! Would adding a pull down resistor on the pin fixe it?


i think it’s signal integrity. If you look at the trace, there is an increase in jitter of your yellow signal line too. Can you zoom in on the problem time and show more detail there?

None of these should matter if you manage CS line correctly though, they should be ignoring any spurious clock pulses if they are not the active device on the bus. You’re doing two write-read operations within one CS operation - as a first step, I’d break those into autonomous operations, or at least explore doing a single transaction (as you obviously don’t need any data from the first) so you don’t risk the interpreter jumping on your timing, but the bigger question is, should you even be doing the CS pulses yourself? Just check the archive here, and neither example manually does that…