How do you plan to solve it?
//init SPI(GPIO config, SPI handle config(sclk speed, duplex setting etc), enable spi peripheral
// in main, wait for button press, send a data, while(busy); disable spi.
// on slave side, toggle led in spi interrupt(RXNE Flag)
/*Paste your code here*/
/* Master Side */
#include "../drivers/Inc/stm32f401xx.h"
void delay(void) {
for (uint32_t i = 0; i < 500000 / 2; i++);
}
void GPIO_ButtonInit(void) {
GPIO_Handle_t GPIOBtn;
GPIOBtn.pGPIOx = GPIOC;
GPIOBtn.GPIO_PinConfig.GPIO_PinNumber = GPIO_PIN_NUM_13;
GPIOBtn.GPIO_PinConfig.GPIO_PinMode = GPIO_MODE_IN;
GPIOBtn.GPIO_PinConfig.GPIO_PinSpeed = GPIO_SPEED_HIGH;
GPIOBtn.GPIO_PinConfig.GPIO_PinPuPdControl = GPIO_NO_PUPD;
GPIO_Init(&GPIOBtn);
}
void SPI2_GPIOInit(void) {
GPIO_Handle_t SPI2Pins;
SPI2Pins.pGPIOx = GPIOB;
SPI2Pins.GPIO_PinConfig.GPIO_PinMode = GPIO_MODE_ALTFN;
SPI2Pins.GPIO_PinConfig.GPIO_PinAltFundMode = 5;
SPI2Pins.GPIO_PinConfig.GPIO_PinOPType = GPIO_OP_TYPE_PP;
SPI2Pins.GPIO_PinConfig.GPIO_PinPuPdControl = GPIO_NO_PUPD;
SPI2Pins.GPIO_PinConfig.GPIO_PinSpeed = GPIO_SPEED_HIGH;
SPI2Pins.GPIO_PinConfig.GPIO_PinNumber = GPIO_PIN_NUM_13; // SCLK
GPIO_Init(&SPI2Pins);
SPI2Pins.GPIO_PinConfig.GPIO_PinNumber = GPIO_PIN_NUM_15; // MOSI
GPIO_Init(&SPI2Pins);
SPI2Pins.GPIO_PinConfig.GPIO_PinNumber = GPIO_PIN_NUM_12; // NSS
GPIO_Init(&SPI2Pins);
// MISO omitted — master not receiving anything here
}
void SPI2_Init(void) {
SPI_Handle_t SPI2handle;
SPI2handle.pSPIx = SPI2;
SPI2handle.SPIConfig.SPI_BusConfig = SPI_BUS_CONFIG_FD;
SPI2handle.SPIConfig.SPI_DeviceMode = SPI_DEVICE_MODE_MASTER;
SPI2handle.SPIConfig.SPI_SclkSpeed = SPI_SCLK_SPEED_DIV8;
SPI2handle.SPIConfig.SPI_DFF = SPI_DFF_8BITS;
SPI2handle.SPIConfig.SPI_CPOL = SPI_CPOL_LOW;
SPI2handle.SPIConfig.SPI_CPHA = SPI_CPHA_LOW;
SPI2handle.SPIConfig.SPI_SSM = SPI_SSM_DI;
SPI_Init(&SPI2handle);
}
int main(void) {
uint8_t toggle_cmd = 0xAB; // arbitrary command byte, slave just needs any byte
GPIO_ButtonInit();
SPI2_GPIOInit();
SPI2_Init();
SPI_SSOEConfig(SPI2, ENABLE);
while (1) {
while (GPIO_ReadFromInputPin(GPIOC, GPIO_PIN_NUM_13)); // wait for press
delay(); // debounce
SPI_PeripheralControl(SPI2, ENABLE);
SPI_SendData(SPI2, &toggle_cmd, 1);
while (SPI_GetFlagStatus(SPI2, SPI_BUSY_FLAG));
SPI_PeripheralControl(SPI2, DISABLE);
}
return 0;
}
/* slave side *\
// LED on PA5 (onboard Nucleo LED)
void GPIO_LEDInit(void) {
GPIO_Handle_t GPIOA_LED;
GPIOA_LED.pGPIOx = GPIOA;
GPIOA_LED.GPIO_PinConfig.GPIO_PinNumber = GPIO_PIN_NUM_5;
GPIOA_LED.GPIO_PinConfig.GPIO_PinMode = GPIO_MODE_OUT;
GPIOA_LED.GPIO_PinConfig.GPIO_PinSpeed = GPIO_SPEED_HIGH;
GPIOA_LED.GPIO_PinConfig.GPIO_PinOPType = GPIO_OP_TYPE_PP;
GPIOA_LED.GPIO_PinConfig.GPIO_PinPuPdControl = GPIO_NO_PUPD;
GPIO_Init(&GPIOA_LED);
}
void SPI2_GPIOInit(void) {
GPIO_Handle_t SPI2Pins;
SPI2Pins.pGPIOx = GPIOB;
SPI2Pins.GPIO_PinConfig.GPIO_PinMode = GPIO_MODE_ALTFN;
SPI2Pins.GPIO_PinConfig.GPIO_PinAltFundMode = 5;
SPI2Pins.GPIO_PinConfig.GPIO_PinOPType = GPIO_OP_TYPE_PP;
SPI2Pins.GPIO_PinConfig.GPIO_PinPuPdControl = GPIO_NO_PUPD;
SPI2Pins.GPIO_PinConfig.GPIO_PinSpeed = GPIO_SPEED_HIGH;
SPI2Pins.GPIO_PinConfig.GPIO_PinNumber = GPIO_PIN_NUM_13; // SCLK
GPIO_Init(&SPI2Pins);
SPI2Pins.GPIO_PinConfig.GPIO_PinNumber = GPIO_PIN_NUM_15; // MOSI
GPIO_Init(&SPI2Pins);
SPI2Pins.GPIO_PinConfig.GPIO_PinNumber = GPIO_PIN_NUM_12; // NSS
GPIO_Init(&SPI2Pins);
// MISO omitted — slave not sending anything back
}
void SPI2_Init(void) {
SPI_Handle_t SPI2handle;
SPI2handle.pSPIx = SPI2;
SPI2handle.SPIConfig.SPI_BusConfig = SPI_BUS_CONFIG_FD;
SPI2handle.SPIConfig.SPI_DeviceMode = SPI_DEVICE_MODE_SLAVE; // <-- slave
SPI2handle.SPIConfig.SPI_DFF = SPI_DFF_8BITS;
SPI2handle.SPIConfig.SPI_CPOL = SPI_CPOL_LOW;
SPI2handle.SPIConfig.SPI_CPHA = SPI_CPHA_LOW;
SPI2handle.SPIConfig.SPI_SSM = SPI_SSM_DI;
// Note: no SclkSpeed for slave — slave doesn't generate the clock
SPI_Init(&SPI2handle);
}
// SPI2 IRQ handler — fires when a byte is received (RXNE)
void SPI2_IRQHandler(void) {
// Call your driver's IRQ handler if it exists, or handle inline:
// SPI_IRQHandling(&SPI2handle); // stub — depends on your driver
// Toggle LED on every received byte
GPIO_ToggleOutputPin(GPIOA, GPIO_PIN_NUM_5);
}
int main(void) {
GPIO_LEDInit();
SPI2_GPIOInit();
SPI2_Init();
// Enable RXNE interrupt on SPI2
SPI_IRQInterruptConfig(IRQ_NO_SPI2, ENABLE);
// Enable SPI peripheral — slave stays enabled, waiting
SPI_PeripheralControl(SPI2, ENABLE);
while (1) {
// Nothing here — everything handled in IRQ
}
return 0;
}
Add a photo of your hardware showing the output.
