ARM Einstieg - 2 Fragen

#3263478
Lesenswert?

Hallo!

Versuche mich gerade nach dem AVR in die ARM-Welt einzuarbeiten. Habe 
mir dazu das günstige STM32F4-Discovery Board zugelegt. Hätte da jetzt 
mal zwei Fragen.

1. Kann man wie beim AVR Variablen(const) im FLASH ablegen und zur 
Laufzeit auslesen? Hintergrund ist es RAM zu sparen das ich für andere 
Zwecke bräuchte.

2. Bei der GPIO Konfiguration gibt es das "GPIO port bit set/reset 
register (GPIOx_BSRR)" und das "GPIO port output data register 
(GPIOx_ODR)". Eigentlich würde doch eins von den beiden reichen?! Gibt 
es ein Grund warum ST dort diese zwei Register "angelegt" hat?

Viele Grüße Deepdiver99
Gast #3263483
Lesenswert?

deep diver99 schrieb:
> Hallo!
>
> Versuche mich gerade nach dem AVR in die ARM-Welt einzuarbeiten. Habe
> mir dazu das günstige STM32F4-Discovery Board zugelegt. Hätte da jetzt
> mal zwei Fragen.
>
> 1. Kann man wie beim AVR Variablen(const) im FLASH ablegen und zur
> Laufzeit auslesen? Hintergrund ist es RAM zu sparen das ich für andere
> Zwecke bräuchte.

Problemlos.

> 2. Bei der GPIO Konfiguration gibt es das "GPIO port bit set/reset
> register (GPIOx_BSRR)" und das "GPIO port output data register
> (GPIOx_ODR)". Eigentlich würde doch eins von den beiden reichen?! Gibt
> es ein Grund warum ST dort diese zwei Register "angelegt" hat?

Atomic operation.

Steht aber alles im RM
#3263786
Lesenswert?

Und wie geht's mit dem dem Flash?

Das "Note: For atomic bit set/reset, the ODR bits can be individually 
set and reset by writing to the
GPIOx_BSRR register (x = A..I/)." hab ich gelesen. Trotzdem leuchtet mir 
nicht ein warum 2 Register dafür da sind, wenn man mit beiden das 
gleiche Ergebnis erreichen kann.
Gast #3263843
Lesenswert?

1)
static const


2)
Each I/O port bit is freely programmable, however the I/O port registers 
have to be accessed as 32-bit words, half-words or bytes. The purpose of 
the GPIOx_BSRR register is to allow atomic read/modify accesses to any 
of the GPIO registers.

In this way, there is no risk of an IRQ occurring between the read and 
the modify access.
Gast #3264189
Lesenswert?

deep diver99 schrieb:
> Noch ein Frage :-)
>
> Gibt es beim STM32F4 ein Input Capture Timer wie beim AVR mit dem ich
> die Takte zwischen zwei Signale einer externen Quelle messen kann?
> Bin aus dem ReferenzManual nicht so richtig schlau geworden.

Klar, gibt es...

Sogar noch besser als beim AVR, der STM32F4 kann beim capture event 
einen DMA Request erzeugen und den Counter ohne CPU 
Intervention/Interrupt lesen und im Speicher ablegen. Und das kann er 
sauschnell mehrmals hintereinander.
Hab's noch nicht gebraucht, aber mein Bauchgefühl sagt mir locker im 
zweistelligen MHz Bereich.

vgl. RM0090 (Doc ID 018909 Rev 4) S.371ff  -  14.3.6 Input capture mode
#3264210
Lesenswert?

So hatte ich das auch schon raus gelesen. Ist denn das Counter Register 
auch das Register was hoch gezählt wird? Das wäre nämlich ungünstig da 
ich dann ja nicht die genaue Taktanzahl bekomme durch den zeitlichen 
Versatz bei der Eventauslösung.
Bei den 32Bit Timern geht das auch nicht? Und mit DMA? Würde mir gerne 
den Overflow Interrupt sparen :-).
Gast #3264221
Lesenswert?

Ne, hab' mich unpräzise ausgedrückt.

Der jeweilige Zählerstand wird bei einem capture event in das 
entsprechende capture/compare Register transferiert und bleibt dort 
stehen bis zum nächsten capture event.
#3265584
Lesenswert?

deep diver99 (deepdiver99)
> 2. Bei der GPIO Konfiguration gibt es das "GPIO port bit set/reset
> register (GPIOx_BSRR)" und das "GPIO port output data register
> (GPIOx_ODR)". Eigentlich würde doch eins von den beiden reichen?! Gibt
> es ein Grund warum ST dort diese zwei Register "angelegt" hat?

Sinngemäß würde ich sagen, daß es das gleiche ist; trotzdem macht sowas 
niemand ohne Grund. Vermutlich geht's wie üblich um den durch das 
Schreiben gelatchte Bit (GPIO port output data register) einerseits und 
um den echten Port-Zustand (GPIO port bit set/reset register 
(GPIOx_BSRR))andererseits.
Manchmal ist der kognitive Zusammenhang den Chip-Designer im Kopf haben 
für SW-Schreiber nicht auf den ersten Blick sichtbar;-) Bin aber kein 
Experte für STM, ich kenn' nur AT91SAM.
Gast #3265741
Lesenswert?

deep diver99 schrieb:
> 2. Bei der GPIO Konfiguration gibt es das "GPIO port bit set/reset
> register (GPIOx_BSRR)" und das "GPIO port output data register
> (GPIOx_ODR)". Eigentlich würde doch eins von den beiden reichen?! Gibt
> es ein Grund warum ST dort diese zwei Register "angelegt" hat?

Der Hauptgrund wird wohl sein dass du so echte "bit set" und "bit reset" 
Funktionen hast . Stell dir mal folgendes vor, an deinm Port sind 16 
LEDs angeschlossen. Du willst nun LED0, LED1 ansteuern

GPIOx_ODR = 0x0003;  // Funktioniert wunder bar. Nun noch LED15 dazu...
GPIOx_ODR = 0x8000;  // Uupps nun leuchtet aber nur noch LED15

Also macht man üblicherweise:

GPIOx_ODR |= 0x8000;  // LED15 ansteurn, restliche LEDs belassen

Dies wird "read modify write" "rmw" genannt und dauert aber länger da 
nun gelesen, verodert und geschrieben werden muss

Hässlich wirds nun wenn dein TimerIrq regelmässig LED8 ansteuert und der 
IRq genau auftritt wenn der Read Part des "rmw" abgeschlossen ist. Das 
verodern bassiert dann auf alten Daten und die werden mit write 
geschrieben. Die LED8 aus dem Irq leuchtet also nicht. Die "rmw" sequenz 
ist also nicht "atomic".

Desshalb wird folgendes häufig angewendet:

Disable Irq
GPIOx_ODR |= 0x8000;  // LED15 ansteurn, restliche LEDs belassen
Enable Irq

Und nun wird das ganze nochmals länger und langsamer...

Moderne uC wie die STM32 bieten aber bessere Möglichkeiten, es können 
einzelne bits an den outputports gesetzt/gelöscht werden ohne die 
anderen zu beinflussen!

Du kannst also

GPIOx_BSRR = 0x0003;  // LED0, LED1 an
GPIOx_BSRR = 0x8000;  // LED15 noch dazu, LED0, LED1 beleiben an

Dein TimerIrq würde
GPIOx_BSRR = 0x0100;  // LED8 an

Löschen kannst du auf zwei verschiedne Arten
GPIOx_BSRR = 0x00030000;  // LED0, LED1 löschen, vorsicht muss im high 
word stenen
GPIOx_BRR = 0x8000;  // LED15 löschen

Das geht aber auch kombiniert
GPIOx_BSRR = 0x80000003;  // LED15 löschen, LED0 LED1 an

Fazit: Es gibt weniger Befehle und IO Operationen sind vereifacht.

Die Cortex M3/4 können das auch für das RAM machen, nennt sich "bit 
banding". Es gibt eine "Bitband Are"im Adressraum, welche das ganze 
interne SRAM bitweise ansprechen lässt. Somit lassen sich bit set bzw. 
bit clear befehle auf alle Variablen anwenden.

Cheers

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