STM32F04 als Slave - Wie Frame lesen?

Gast #4596141
Lesenswert?

Guten Abend zusammen,

folgendes Szenario: An einem STM32F04 (Slave) ist am SPI1 ein Arduino 
(Master) angeschlossen welcher mir 4 Bytes schickt, dieses Frame ist mit 
einem CS umschlossen. (Siehe Anhang)

Ich habe es nicht geschafft diese 4 Bytes 'a' 'b' 'c' 'd' korrekt zu 
empfangen. Ich empfange immer zufällige Daten. Den SPI-Mode habe ich 
mehrere Male überprüft, das sollte passen.

Verbunden wie folgt:
1
    Arduino Nano:    STM32F04:
2
SCK    13          PB3
3
MOSI   11          PB5
4
CS     10          PA15

Folgendes hatte ich versucht:
1. Per RXNE Interrupt auf ankommende Daten reagieren:
Der RXNE Interrupt hat regelmäßig ausgelöst auch wenn keine Daten 
geschickt wurden. Immer im Interval von rund 40µs (mit Logic Analayzer 
geprüft). Die 4 gelesenen Bytes waren immer zufällig.

2. Per External Interrupt auf Fallende Flanke des CS reagieren:
Ich habe versucht im Interrupt-Handler die vier Bytes zu lesen. Es 
scheint dann aber nichts im Datenregister zu liegen, er bleibt immer in 
der Schleife hängen.
1
extern "C" void EXTI15_10_IRQHandler(void)
2
{
3
  static uint8_t byte;
4
  if (EXTI_GetITStatus(EXTI_Line15) == SET)
5
  {
6
    GPIO_SetBits(GPIOA, GPIO_Pin_0);  // Fuer Logic Analyzer
7

8
    // Lese die vier Bytes
9
    for (int i = 0; i < 4; ++i)
10
    {
11
      while (SPI_I2S_GetFlagStatus(SPI1, SPI_I2S_FLAG_RXNE) == RESET);
12
      byte = SPI_I2S_ReceiveData(SPI1);
13
    }
14

15
    EXTI_ClearITPendingBit(EXTI_Line15);
16
    GPIO_ResetBits(GPIOA, GPIO_Pin_0);  // Fuer Logic Analyzer
17
  }
18
}

Konfiguriert habe ich SPI1 wie folgt (hier mit External Interrupt):
1
void init_SPI1(void) {
2

3
    GPIO_InitTypeDef GPIO_InitStruct;
4
  NVIC_InitTypeDef NVIC_InitStructure;
5
  EXTI_InitTypeDef EXTI_InitStruct;
6
  SPI_InitTypeDef SPI_InitStruct;
7

8
  // Clocks
9
  RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOB, ENABLE);
10
  RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOA, ENABLE);
11
  RCC_APB2PeriphClockCmd(RCC_APB2Periph_SPI1, ENABLE);
12
  RCC_APB2PeriphClockCmd(RCC_APB2Periph_SYSCFG, ENABLE);
13
  
14
  // GPIO
15
  GPIO_PinAFConfig(GPIOB, GPIO_PinSource3, GPIO_AF_SPI1);
16
  GPIO_PinAFConfig(GPIOB, GPIO_PinSource4, GPIO_AF_SPI1);
17
  GPIO_PinAFConfig(GPIOB, GPIO_PinSource5, GPIO_AF_SPI1);
18

19
  GPIO_InitStruct.GPIO_Pin = GPIO_Pin_3 | GPIO_Pin_5;
20
  GPIO_InitStruct.GPIO_Mode = GPIO_Mode_AF;
21
  GPIO_InitStruct.GPIO_PuPd = GPIO_PuPd_NOPULL;
22
  GPIO_InitStruct.GPIO_Speed = GPIO_Speed_50MHz;
23
  GPIO_Init(GPIOB, &GPIO_InitStruct);
24
  
25
  // Chip select
26
  GPIO_InitStruct.GPIO_Pin = GPIO_Pin_15;
27
  GPIO_InitStruct.GPIO_Mode = GPIO_Mode_IN;
28
  GPIO_InitStruct.GPIO_PuPd = GPIO_PuPd_UP;
29
  GPIO_InitStruct.GPIO_Speed = GPIO_Speed_25MHz;
30
  GPIO_Init(GPIOA, &GPIO_InitStruct);
31

32
  SYSCFG_EXTILineConfig(EXTI_PortSourceGPIOA, EXTI_PinSource15);
33

34
  EXTI_InitStruct.EXTI_Line = EXTI_Line15;
35
  EXTI_InitStruct.EXTI_Mode = EXTI_Mode_Interrupt;
36
  EXTI_InitStruct.EXTI_Trigger = EXTI_Trigger_Falling;
37
  EXTI_InitStruct.EXTI_LineCmd = ENABLE;
38
  EXTI_Init(&EXTI_InitStruct);
39

40
  NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);
41
  NVIC_InitStructure.NVIC_IRQChannel = EXTI15_10_IRQn;
42
  NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0;
43
  NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0;
44
  NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
45
  NVIC_Init(&NVIC_InitStructure);
46
  
47
  // SPI
48
  SPI_InitStruct.SPI_Direction = SPI_Direction_Rx;
49
  SPI_InitStruct.SPI_Mode = SPI_Mode_Slave;
50
  SPI_InitStruct.SPI_DataSize = SPI_DataSize_8b; 
51
  SPI_InitStruct.SPI_CPOL = SPI_CPOL_High;
52
  SPI_InitStruct.SPI_CPHA = SPI_CPHA_1Edge;     
53
  SPI_InitStruct.SPI_NSS = SPI_NSS_Soft | SPI_NSSInternalSoft_Reset;
54
  SPI_InitStruct.SPI_FirstBit = SPI_FirstBit_MSB;
55
  SPI_Init(SPI1, &SPI_InitStruct);
56

57
  SPI_Cmd(SPI1, ENABLE); 
58
}

Inzwischen habe ich wahrscheinlich Tomaten auf den Augen. Sieht jemand 
den Fehler? Hat jemand schon einmal den STM32 als Slave betrieben und 
nur Daten empfangen?
Angehängte Dateien:
Gast #4596155
Lesenswert?

holger schrieb:
> Ja, lass den STM das was der Arduino macht gleich mit
> erledigen. Dann sparst du dir die Datenübertragung.

Der Arduino ist aktuell nur zum Testen gedacht. Eigentlich ist ein ADC 
angebunden der Daten über SPI an den STM feuert.

Da ich schon Probleme hatte die Daten vom ADC abzuholen, habe ich mir 
mit dem Arduino was zum Testen gebastelt um die SPI Hardware als Slave 
in Betrieb zu nehmen.

Antwort schreiben

Bitte melde dich an, um einen Beitrag zu schreiben.

oder

Mit Google-Account einloggen

Die Registrierung ist kostenlos und dauert nur eine Minute.

Jetzt registrieren