Skip to content

Instantly share code, notes, and snippets.

@nraynaud
Created March 30, 2015 16:13
Show Gist options
  • Save nraynaud/75650aae6ebad2f97d77 to your computer and use it in GitHub Desktop.
Save nraynaud/75650aae6ebad2f97d77 to your computer and use it in GitHub Desktop.
STM32F4: receiving one shot of data on the SPI bus in receive only
#include <stm32f4xx.h>
#include "stm32f4xx_conf.h"
#include "stm32f4_discovery.h"
#include "math.h"
#include "arm_math.h"
volatile uint16_t counter = 0;
volatile uint16_t savedCounter = 0;
uint16_t parallelPins = GPIO_Pin_3 | GPIO_Pin_4 | GPIO_Pin_5 | GPIO_Pin_6 | GPIO_Pin_7 | GPIO_Pin_8 | GPIO_Pin_9 | GPIO_Pin_10;
void sendCounter();
__attribute__ ((noreturn)) void main(void) {
//enable FPU
SCB->CPACR |= 0b000000000111100000000000000000000UL;
STM_EVAL_LEDInit(LED3);
STM_EVAL_LEDInit(LED4);
STM_EVAL_LEDInit(LED5);
STM_EVAL_LEDInit(LED6);
STM_EVAL_LEDOff(LED3);
STM_EVAL_LEDOff(LED4);
STM_EVAL_LEDOff(LED5);
STM_EVAL_LEDOff(LED6);
RCC_APB1PeriphClockCmd(RCC_APB1Periph_SPI2, ENABLE);
RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOB, ENABLE);
RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOE, ENABLE);
GPIO_PinAFConfig(GPIOB, GPIO_PinSource12, GPIO_AF_SPI2);
GPIO_PinAFConfig(GPIOB, GPIO_PinSource13, GPIO_AF_SPI2);
GPIO_PinAFConfig(GPIOB, GPIO_PinSource14, GPIO_AF_SPI2);
GPIO_PinAFConfig(GPIOB, GPIO_PinSource15, GPIO_AF_SPI2);
GPIO_Init(GPIOB, &(GPIO_InitTypeDef) {
.GPIO_Pin = GPIO_Pin_12 | GPIO_Pin_13 | GPIO_Pin_15,
.GPIO_Mode = GPIO_Mode_AF,
.GPIO_Speed = GPIO_Speed_100MHz,
.GPIO_OType = GPIO_OType_PP,
.GPIO_PuPd = GPIO_PuPd_DOWN});
GPIO_Init(GPIOB, &(GPIO_InitTypeDef) {
.GPIO_Pin =GPIO_Pin_14,
.GPIO_Mode = GPIO_Mode_AF,
.GPIO_Speed = GPIO_Speed_100MHz,
.GPIO_OType = GPIO_OType_PP,
.GPIO_PuPd = GPIO_PuPd_NOPULL});
GPIO_Init(GPIOB, &(GPIO_InitTypeDef) {
.GPIO_Pin = GPIO_Pin_11,
.GPIO_Mode = GPIO_Mode_OUT,
.GPIO_Speed = GPIO_Speed_100MHz,
.GPIO_OType = GPIO_OType_PP});
GPIO_Init(GPIOE, &(GPIO_InitTypeDef) {
.GPIO_Pin = parallelPins,
.GPIO_Mode = GPIO_Mode_OUT,
.GPIO_Speed = GPIO_Speed_100MHz,
.GPIO_OType = GPIO_OType_PP});
SPI_I2S_DeInit(SPI2);
SPI_Init(SPI2, &(SPI_InitTypeDef) {
.SPI_Mode = SPI_Mode_Master,
.SPI_Direction = SPI_Direction_2Lines_RxOnly,
.SPI_DataSize = SPI_DataSize_8b,
.SPI_CPOL = SPI_CPOL_Low,
.SPI_CPHA = SPI_CPHA_1Edge,
.SPI_NSS = SPI_NSS_Soft,
.SPI_BaudRatePrescaler = SPI_BaudRatePrescaler_4,
.SPI_FirstBit = SPI_FirstBit_MSB,
.SPI_CRCPolynomial = 7
});
GPIO_SetBits(GPIOB, GPIO_Pin_11);
SPI_Cmd(SPI2, DISABLE);
SPI_TIModeCmd(SPI2, DISABLE);
STM_EVAL_PBInit(BUTTON_USER, BUTTON_MODE_EXTI);
savedCounter = 5;
counter = 5;
#pragma clang diagnostic push
#pragma clang diagnostic ignored "-Wmissing-noreturn"
while (1) {
sendCounter();
receiveCounter();
for (uint32_t i = 0; i < 10000; i++)
__asm__("");
}
#pragma clang diagnostic pop
}
void parallelData(uint16_t data) {
GPIO_ResetBits(GPIOE, parallelPins);
GPIO_SetBits(GPIOE, parallelPins & (data << 3));
for (uint32_t i = 0; i < 10000; i++)
__asm__("");
}
int readData() {
GPIO_ResetBits(GPIOB, GPIO_Pin_11);
for (uint32_t i = 0; i < 10000; i++)
__asm__("");
GPIO_SetBits(GPIOB, GPIO_Pin_11);
SPI_Cmd(SPI2, ENABLE);
/*while (!SPI_I2S_GetFlagStatus(SPI2, SPI_I2S_FLAG_BSY))
__asm__("");*/
while (!SPI_I2S_GetFlagStatus(SPI2, SPI_I2S_FLAG_RXNE))
__asm__("");
SPI_Cmd(SPI2, DISABLE);
return SPI_I2S_ReceiveData(SPI2);
}
void sendCounter() {
parallelData(counter);
}
void receiveCounter() {
STM_EVAL_LEDOff(LED3);
STM_EVAL_LEDOff(LED4);
STM_EVAL_LEDOff(LED5);
STM_EVAL_LEDOff(LED6);
int received = readData();
if (received == counter) {
STM_EVAL_LEDOn(LED3);
STM_EVAL_LEDOn(LED4);
}
else {
STM_EVAL_LEDOn(LED5);
if (SPI_I2S_GetFlagStatus(SPI2, SPI_I2S_FLAG_OVR))
STM_EVAL_LEDOn(LED6);
}
}
void EXTI0_IRQHandler(void) {
if (EXTI_GetITStatus(EXTI_Line0) != RESET) {
counter++;
sendCounter();
receiveCounter();
for (uint32_t i = 0; i < 10000; i++)
__asm__("");
EXTI_ClearITPendingBit(EXTI_Line0);
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment