STM32F1 printf auf non blocking konfigurieren?

Gast #5030639
Hallo,

ich programmiere einen STM32F1 µController. Fürs printf benutze ich das 
https://github.com/cjlano/tinyprintf Bibliothek .

Ich habe den tinyprintf folgendermaßen konfiguriert.
1
init_printf(NULL, myputc);
2

3
void myputc(void* p, char c) {
4
  UNUSED(p);
5
  while ((USART3->SR & USART_FLAG_TC) == (uint16_t) RESET) {
6
  }
7
  USART_SendData(USART3, c);
8
}

Es funktioniert zwar wunderbar. Aber, wenn eine zeitkritische Aufgabe in 
ISR mit hohem Takt ca. 10kHz erledigt werden soll, wobei zeitgleich 
printf in der Mainschleife aufgerufen wird, wird diese ISR Funktion 
durch printf gestört. Ab und zu blockiert der printf die ISR Funktionen.

Weiß jemand zufällig wie man das lösen kann.

Viele Grüße aus Emmen.
Gast #5030671
Rufus Τ. F. schrieb:
> Vincent schrieb:
>> wird diese ISR Funktion durch printf gestört.
>
> Was soll da der Wirkmechanismus sein?
>
> Wird in der ISR auch auf UART3 zugegriffen?

Ne, In der ISR werden Hallsensor-Zustände eines BLDC Motors und 
Strommessung sowie einen Drehzahl-Regelkreis betrieben. Wenn der printf 
in der Mainschleife aufgerufen wird, wird der Regelkreis-Taktzyklus 
unterbrochen.
Gast #5030709
Rufus Τ. F. schrieb:
> Dann stimmt da irgendwas grundlegendes nicht.
>
> Was macht die Funktion UART_SendData?

der macht:
1
/**
2
  * @brief  Transmits single data through the USARTx peripheral.
3
  * @param  USARTx: Select the USART or the UART peripheral. 
4
  *   This parameter can be one of the following values:
5
  *   USART1, USART2, USART3, UART4 or UART5.
6
  * @param  Data: the data to transmit.
7
  * @retval None
8
  */
9
void USART_SendData(USART_TypeDef* USARTx, uint16_t Data)
10
{
11
  /* Check the parameters */
12
  assert_param(IS_USART_ALL_PERIPH(USARTx));
13
  assert_param(IS_USART_DATA(Data)); 
14
    
15
  /* Transmit Data */
16
  USARTx->DR = (Data & (uint16_t)0x01FF);
17
}
Gast #5030724
Also so, wie das hier gemacht ist, blockiert das printf keine 
Interrupts. Man müßte sich jetzt aber auch nochmal die Initialisierung 
des USART angucken, nicht daß da noch irgendwo irrtümlich ein Interrupt 
z.B. für "TX done" eingerichtet wurde. Oder für den RX-Zweig ein 
Interrupt. Also, gehen würde es dann immer noch, aber man müßte die 
Interruptprios dann schon richtig setzen.

Kannst ja mal spaßeshalber den Aufruf der send-usart-Routine 
auskommentieren und gucken, ob es dann geht.

Und was findet denn außer printf noch so in der Mainschleife statt?
Gast #5030747
Nop schrieb:
> Also so, wie das hier gemacht ist, blockiert das printf keine
> Interrupts. Man müßte sich jetzt aber auch nochmal die Initialisierung
> des USART angucken, nicht daß da noch irgendwo irrtümlich ein Interrupt
> z.B. für "TX done" eingerichtet wurde. Oder für den RX-Zweig ein
> Interrupt. Also, gehen würde es dann immer noch, aber man müßte die
> Interruptprios dann schon richtig setzen.
>
> Kannst ja mal spaßeshalber den Aufruf der send-usart-Routine
> auskommentieren und gucken, ob es dann geht.
auskommentiert, es läuft.

> Und was findet denn außer printf noch so in der Mainschleife statt?
Led togglen und noch Delay(100ms)

Ich hab die ISR Prioritäten alles auf 0 gesetzt, keine Verbesserung.
die UART NVIC Initialisierung:
1
void USART_Configuration(void) {
2
  USART_InitTypeDef USART_InitStructure;
3

4
  USART_InitStructure.USART_BaudRate = 115200;
5
  USART_InitStructure.USART_WordLength = USART_WordLength_8b;
6
  USART_InitStructure.USART_StopBits = USART_StopBits_1;
7
  USART_InitStructure.USART_Parity = USART_Parity_No;
8
  USART_InitStructure.USART_HardwareFlowControl =
9
  USART_HardwareFlowControl_None;
10
  USART_InitStructure.USART_Mode = USART_Mode_Rx | USART_Mode_Tx;
11

12
  /* Configure USART3 */
13
  USART_Init(USART3, &USART_InitStructure);
14
  USART_Cmd(USART3, ENABLE);
15
}
16

17
void NVIC_Configuration(void) {
18
  NVIC_InitTypeDef NVIC_InitStructure;
19

20
  NVIC_InitStructure.NVIC_IRQChannel = EXTI15_10_IRQn;
21
  NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
22
  NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0x0F;
23
  NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0x0F;
24
  NVIC_Init(&NVIC_InitStructure);
25

26
  /* Configure and enable ADC interrupt */
27
  NVIC_InitStructure.NVIC_IRQChannel = ADC1_2_IRQn;
28
  NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0x0F;
29
  NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0x0F;
30
  NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
31
  NVIC_Init(&NVIC_InitStructure);
32
}
33

34
void EXTI15_10_IRQHandler(void) {
35
  if (EXTI_GetITStatus(EXTI_Line10) != RESET) {
36
    /* Clear interrupt flag */
37
    EXTI_ClearITPendingBit(EXTI_Line10);
38

39
    HallIRQ_L();
40
  }
41
  if (EXTI_GetITStatus(EXTI_Line11) != RESET) {
42
    /* Clear interrupt flag */
43
    EXTI_ClearITPendingBit(EXTI_Line11);
44

45
    HallIRQ_L();
46
  }
47
  if (EXTI_GetITStatus(EXTI_Line12) != RESET) {
48
    /* Clear interrupt flag */
49
    EXTI_ClearITPendingBit(EXTI_Line12);
50

51
    HallIRQ_L();
52
  }
53

54
}
55

56
void ADC1_2_IRQHandler(void) {
57
  GPIOA->ODR ^= GPIO_Pin_2;
58
  /* Clear ADC1 JEOC pending interrupt bit */
59
  ADC_ClearITPendingBit(ADC1, ADC_IT_JEOC);
60

61
  ControlLoop();
62

63
  GPIOA->ODR ^= GPIO_Pin_2;
64

65
}
Gast #5030822
pegel schrieb:
> Vincent schrieb:
>> wenn eine zeitkritische Aufgabe in
>> ISR mit hohem Takt ca. 10kHz
>
> Meinst du den ADC?
Ja,
> Setz doch dessen Priorität mal höher.

ich habe die beiden (Preemption, Sub) Prioritäten auf 0x01. Keine 
Änderung.

Antwort schreiben

Eine eigene Frage? Dieser Thread ist über 9 Jahre alt. Stell sie in einem eigenen Thread – dort lesen mehr Leute mit, und sie wird öfter und schneller beantwortet.

Neuen Thread starten

Eine Lösung, Ergänzung oder Rückmeldung zu diesem Thread? Dann antworte hier.

Formatierung
  • [c]C-Code[/c]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] – Link zu einem Artikel
  • Verweis auf einen anderen Beitrag: Rechtsklick auf dessen Beitrags-ID (#8078628), „Adresse kopieren“, in den Text einfügen

Mehr zur Formatierung

Längeren Sourcecode als Anhang, nicht in den Text. JPG nur für Fotos und Scans; Zeichnungen und Screenshots als PNG oder GIF. Siehe Bildformate.

Schon registriert? Anmelden

Wird nicht angezeigt. Wir schicken dir einen Link; sobald du damit bestätigst, erscheint dein Beitrag.

Mit dem Abschicken legst du einen kostenlosen Account an und erkennst die Nutzungsbedingungen und die Datenschutzerklärung an.