mikrocontroller.net

Forum: Mikrocontroller und Digitale Elektronik FreeRTOS auf stm32F103 spring falsch bei NVIC lesen


Autor: Philipp (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo,
ich habe auf einem STM32F103RB nun FreeRTOS aufgesetzt und alles 
angepasst und es kommt beim start zu folgender stelle ...
portBASE_TYPE xPortStartScheduler( void )
{
  /* Make PendSV, CallSV and SysTick the same priroity as the kernel. */
  *(portNVIC_SYSPRI2) |= portNVIC_PENDSV_PRI;
  *(portNVIC_SYSPRI2) |= portNVIC_SYSTICK_PRI;

  /* Start the timer that generates the tick ISR.  Interrupts are disabled
  here already. */
  prvSetupTimerInterrupt();

  /* Initialise the critical nesting count ready for the first task. */
  uxCriticalNesting = 0;

  /* Start the first task. */
  vPortStartFirstTask();

  /* Should not get here! */
  return 0;
}


Bei vPortStartFirstTask liest er von der Adress 0xE000ED08 und spring 
jedoch wieder zu der zuvor bereits aufgerufenen Funktion 
prvSetupTimerInterrupt.
void vPortStartFirstTask( void )
{
    __asm volatile(
    
    " ldr r0, =0xE000ED08   \n" /* Use the NVIC offset register to locate the stack. */
    " ldr r0, [r0]       \n"
    " ldr r0, [r0]       \n"
    " msr msp, r0      \n" /* Set the msp back to the start of the stack. */
    " svc 0          \n" /* System call to start first task. */
    );
}

void prvSetupTimerInterrupt( void )
{
  /* Configure SysTick to interrupt at the requested rate. */
  *(portNVIC_SYSTICK_LOAD) = ( configCPU_CLOCK_HZ / configTICK_RATE_HZ ) - 1UL;
  *(portNVIC_SYSTICK_CTRL) = portNVIC_SYSTICK_CLK | portNVIC_SYSTICK_INT | portNVIC_SYSTICK_ENABLE;
}

Diese Schleife läuft dann ewig. Wo liegt der Fehler bzw. was habe ich 
vergessen zu konfigurieren? Irgendwie kommt der Stack durcheinander oder 
...

Philipp

Autor: Philipp (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Ich habe nun den Stack angesehen und er springt dann zu 
DEFAULT_ISR_HANDLER SVCHandler. Im Callstack ist zu sehen, daß er ca. 
15x zur main zurückkehrt und alles nochmals ausführt.

Autor: A. K. (prx)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Letzthin hatten wir hier mal den Fall, da passten die Namen der Handler 
im Startup-Code nicht zu den entsprechenden Namen im Code.

Jedenfalls sollte der SVCHandler vom FreeRTOS zum tragen kommen, sonst 
wird das garantiert nix.

Autor: A. K. (prx)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Die aktuelle Version des ARM CMSIS Standards für Cortex-M3 definiert 
sämtliche Vektoren im Startupcode. Ein Handler muss folglich exakt den 
Namen verwenden, der dafür vorgesehen ist, sonst wird er ignoriert. 
FreeRTOS tut das nicht, folglich wird dessen SVC Handler in Verbindung 
mit einem CMSIS-konformen Startupcode ingnoriert.

ST verwendete in der Lib V2 eine davon abweichende inkompatible Technik. 
Dort werden die Vektoren als C-Tabelle im File stm32f10x_vector.c 
definiert. FreeRTOS bezieht sich darauf und verwendet eine modifizierte 
Version dieser Tabelle, die direkt auf den vPortSVCHandler verweist.

Welche Entwicklungsumgebung verwendest du?

Autor: Philipp (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Also der ASM Code löst ja eigentlich den Call aus mit "svc 0" oder? Was 
ich nicht ganz verstehe ist, was soll dann eigenlich in der SVC 
Interrupt Routine passieren. Es soll doch der erste Task gestartet 
werden.

Autor: A. K. (prx)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Philipp schrieb:

> Also der ASM Code löst ja eigentlich den Call aus mit "svc 0" oder? Was
> ich nicht ganz verstehe ist, was soll dann eigenlich in der SVC
> Interrupt Routine passieren. Es soll doch der erste Task gestartet
> werden.

Yep, aber nur wenn du auch im richtigen SVC Handler landest. Ich gehe 
davon aus, dass du aufgrund des eben beschriebenen Problems statt dessen 
in einem Dummy-Handler landest.

Autor: Philipp (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Ich habe Rowley mal in Verwendung. Ich versuche noch herauszufinden, was 
optimal ist. Bin zwar seit vielen Jahren Keil Fan, aber da der Assistent 
nicht mal ein lauffähiges Demo erzeugen konnte, versuche ich gerade die 
Rowley.

Autor: Philipp (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Also im Startup ist er definiert mit " .word SVCHandler" und in der 
stm32f10x_it.c steht "void SVCHandler(void)", also müßte es doch 
funktionieren.

Autor: A. K. (prx)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Ich verwende ebenfalls Rowley (V2), aber kein FreeRTOS. Von Haus aus 
kriegst du bei Rowley einen eigenen CMSIS-konformen Startup-Code. 
Folglich muss der SVC Handler so heissen wie dort vorgesehen, also 
SVCHandler.

Probier mal, den Handler vom FreeRTOS entsprechend unzubenennen. Müsste 
mit -DvPortSVCHandler=SVCHandler möglich sein (rebuild all).

Für andere Interrupts, beispielsweise vUart... gilt das analog.

Alternativ kannst du dem Rowley beibringen, auf seinen Startup-Code zu 
verzichten und den im FreeRTOS verwenden. Aber frag micht jetzt nicht 
wie das geht, hab's noch nicht probiert. Ich halte mich lieber ans 
CMSIS.

Autor: A. K. (prx)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Na super, hab's grad nochmal kontrolliert. Das Chaos setzt sich fort, 
denn in Rowley heisst das Symbol SVCHandler, im CMSIS statt dessen 
SVC_Handler.

Wobei Rowley immerhin konsequent ist. CMSIS verteilt die Unterstriche 
ziemlich frei von Logik.

Autor: Philipp (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Also das FreeRTOS hat keine Definition für einen SVCHandler oder 
ähnliches - oder ich finde es nicht.

Da mir das nach mehreren Tagen nun auch schon zu blöd wird eine Frage. 
Was verwendest du denn als OS bzw. ist das von Rowley gut?

Philipp

Autor: A. K. (prx)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Philipp schrieb:

> Also das FreeRTOS hat keine Definition für einen SVCHandler oder
> ähnliches - oder ich finde es nicht.

Wirf mal einen Blick in ./Source/portable/GCC/ARM_CM3/port.c und suche 
die "Exception handlers". Das sind diejenigen, die aufgerufen werden 
sollten.

Wenn du dort vorneweg für diese Handler sowas wie
 #define falscherName richtigerName
schreibst, dann sollten auch mit Rowley-Startupcode die richtigen 
Handler aufgerufen werden. Die richtigen Namen findest du in 
Project/System Files/STM32F10x_Startup.s.

Wenn du den Code aus den Demos vom FreeRTOS verwendest, einschliesslich 
dessen Startup(!), denn passt es ohne Modifikation vom port.c, denn dort 
ist ggf. crt0_STM32x.c dafür zuständig. Aber dann musst du 
sicherstellen, dass der Rowley-Startupcode nicht greift.

Autor: Philipp (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Vielen Dank, super für deine Hilfe. Es geht (Hurra). Man braucht oft nur 
jemanden, der einem die Tomaten von den Augen nimmt :-)

Na dann kanns ja los gehn ...


Philipp

Autor: A. K. (prx)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Update: Es gibt bei Rowley mittlerweile zwei alternative CPU Support 
Packages für STM32.

STMicroelectronics STM32F10x CPU Support Package (1.11):
Das ist die oben skizzierte Version, möglicherweise Rowleys Eigenbau, 
jedenfalls die mit den nicht ganz zu CMSIS passenden Vektoren.

STMicroelectronics STM32 CPU Support Package (2.0):
Zu CMSIS passende Version.

Antwort schreiben

Die Angabe einer E-Mail-Adresse ist freiwillig. Wenn Sie automatisch per E-Mail über Antworten auf Ihren Beitrag informiert werden möchten, melden Sie sich bitte an.

Wichtige Regeln - erst lesen, dann posten!

  • Groß- und Kleinschreibung verwenden
  • Längeren Sourcecode nicht im Text einfügen, sondern als Dateianhang

Formatierung (mehr Informationen...)

  • [c]C-Code[/c]
  • [avrasm]AVR-Assembler-Code[/avrasm]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] - Link zu Artikel
  • Verweis auf anderen Beitrag einfügen: Rechtsklick auf Beitragstitel,
    "Adresse kopieren", und in den Text einfügen




Bild automatisch verkleinern, falls nötig
Bitte das JPG-Format nur für Fotos und Scans verwenden!
Zeichnungen und Screenshots im PNG- oder
GIF-Format hochladen. Siehe Bildformate.
Hinweis: der ursprüngliche Beitrag ist mehr als 6 Monate alt.
Bitte hier nur auf die ursprüngliche Frage antworten,
für neue Fragen einen neuen Beitrag erstellen.

Mit dem Abschicken bestätigst du, die Nutzungsbedingungen anzuerkennen.