Forum: Mikrocontroller und Digitale Elektronik HAL driver STM32F103 wie Zustandsänderung an Taster erfassen


von Jörg K (Gast)


Lesenswert?

Hallo,

ich versuche gerad zuverlässig eine Zustandsänderung an einem Pin
des STM32F103 zu erfassen.

also

nur wenn sich der Zustand von 1 auf low ändert soll eine
Variable getoggelt werden

aktuell versuche ich es wie folgt:

void get_reset_switch_state(void)
{
    if ((rst_swt == 1) && (HAL_GPIO_ReadPin(GPIOB, GPIO_PIN_4) == 1))
    {
      rst_swt_new = rst_swt;// do nothing no level change since last 
time on input pin
    }
    else if((rst_swt == 0) && (HAL_GPIO_ReadPin(GPIOB, GPIO_PIN_4) == 
1))
    {
      rst_swt_new = 1;
    }
    else if((rst_swt == 1) && (HAL_GPIO_ReadPin(GPIOB, GPIO_PIN_4) == 
0))
    {
      rst_swt_new = 0;
    }
    else if((rst_swt == 0) && (HAL_GPIO_ReadPin(GPIOB, GPIO_PIN_4) == 
0))
    {
      rst_swt_new = rst_swt;// do nothing no level change since last 
time on input pin
    }
    else
    {
     rst_swt_new = 0; // default case for what everest
    }
    rst_swt = rst_swt_new; // next state (new) becomes current state;
}

das klappt aber nicht zuverlässig....
das muss doch einfacher gehen?
oder?

von ich (Gast)


Lesenswert?

Warum pollst du überhaupt? Nehme -sofern möglich, doch einen Interrupt!
Zudem musst du das Prellen des Tasters beachten!

Grüße
ich

von Jörg K (Gast)


Lesenswert?

ich schrieb:
> Warum pollst du überhaupt? Nehme -sofern möglich, doch einen Interrupt!
> Zudem musst du das Prellen des Tasters beachten!
>
> Grüße
> ich

Ok welche Interrupt stehen mir da zur Verfügung?... ich bin noch nicht 
so firm
in der HAL lib.

von Mampf F. (mampf) Benutzerseite


Lesenswert?

Jörg K schrieb:
> Ok welche Interrupt stehen mir da zur Verfügung?... ich bin noch nicht
> so firm
> in der HAL lib.

Google mal nach EXTI HAL :)

von Jörg K (Gast)


Lesenswert?

Mampf F. schrieb:
> Jörg K schrieb:
>> Ok welche Interrupt stehen mir da zur Verfügung?... ich bin noch nicht
>> so firm
>> in der HAL lib.
>
> Google mal nach EXTI HAL :)

ok hab mir jetzt einen Interrupt für den pin von CubeMX generieren 
lassen:

void EXTI4_IRQHandler(void)
{
  /* USER CODE BEGIN EXTI4_IRQn 0 */
  HAL_GPIO_TogglePin(GPIOA, GPIO_PIN_0);
  /* USER CODE END EXTI4_IRQn 0 */
  HAL_GPIO_EXTI_IRQHandler(GPIO_PIN_4);
  /* USER CODE BEGIN EXTI4_IRQn 1 */

  /* USER CODE END EXTI4_IRQn 1 */
}

ist als External Interrupt Mode with Rising edge trigger detection
konfiguriert...

irgendwie geht das noch nicht ganz richtig...
kann es sein, dass mein Taster nicht entprellt wird?
vermutlich... wie geht das mit der HAL lib möglichst elegant?
oder ist der pin gelegentlich floating? hmmh
VG

von Harry L. (mysth)


Lesenswert?

Für normale Tasten-Abfragen braucht man keinen Interrupt - bzw. wenn, 
dann einen Timer-Interrupt, der max. alle 10ms die Tasten pollt.

Der direkte Interrupt ist wegen Prellen sogar eher kontraproduktiv.

: Bearbeitet durch User
von Jörg K (Gast)


Lesenswert?

Jörg K schrieb:
> Mampf F. schrieb:
>> Jörg K schrieb:
>>> Ok welche Interrupt stehen mir da zur Verfügung?... ich bin noch nicht
>>> so firm
>>> in der HAL lib.
>>
>> Google mal nach EXTI HAL :)
>
> ok hab mir jetzt einen Interrupt für den pin von CubeMX generieren
> lassen:
>
> void EXTI4_IRQHandler(void)
> {
>   /* USER CODE BEGIN EXTI4_IRQn 0 */
>   HAL_GPIO_TogglePin(GPIOA, GPIO_PIN_0);
>   /* USER CODE END EXTI4_IRQn 0 */
>   HAL_GPIO_EXTI_IRQHandler(GPIO_PIN_4);
>   /* USER CODE BEGIN EXTI4_IRQn 1 */
>
>   /* USER CODE END EXTI4_IRQn 1 */
> }
>
> ist als External Interrupt Mode with Rising edge trigger detection
> konfiguriert...
>
> irgendwie geht das noch nicht ganz richtig...
> kann es sein, dass mein Taster nicht entprellt wird?
> vermutlich... wie geht das mit der HAL lib möglichst elegant?
> oder ist der pin gelegentlich floating? hmmh
> VG


ok schon gleich einen schritt weitergekommen --> hab an dem Pin den 
Pullup aktivert... nun schaut die Sache schon ziemlich gut aus :)

mal sehen, ob da doch noch ein paar Fallstricke kommen ;)

von pegel (Gast)


Lesenswert?

HAL_GPIO_EXTI_Callback ist die Funktion, die dafür gedacht ist.

von Jörg K (Gast)


Lesenswert?

pegel schrieb:
> HAL_GPIO_EXTI_Callback ist die Funktion, die dafür gedacht ist.

muss das Tastenentprellen dann nicht auch noch gemacht werden?

VG

von Jörg K (Gast)


Lesenswert?

Jörg K schrieb:
> pegel schrieb:
>> HAL_GPIO_EXTI_Callback ist die Funktion, die dafür gedacht ist.
>
> muss das Tastenentprellen dann nicht auch noch gemacht werden?
>
> VG

und dann noch eine andere Sache, wie kann ich es machen,
dass eine Variable, die in

main.c

deklariert wurde
auch in der
stm32f1xx_it.c
sichtbar ist.
und gesetzt werden kann

volatile?
extern?
hä?

von Nico W. (nico_w)


Lesenswert?

getter-Funktion?
Kommt drauf an.

von Jörg K (Gast)


Lesenswert?

Jörg K schrieb:
> und dann noch eine andere Sache, wie kann ich es machen,
> dass eine Variable, die in
>
> main.c
>
> deklariert wurde
> auch in der
> stm32f1xx_it.c
> sichtbar ist.
> und gesetzt werden kann
>
> volatile?
> extern?
> hä?

ok frage selbst beantwortet:

in der main direkt deklarieren und
in der stm32f1xx_it.c
mit dem Zusatz extern
damit der weiß, die Variable gibt es schon anderswo ;)

von pegel (Gast)


Lesenswert?

Der Interrupt ist gut wenn ein klares Signal am Pin zu erwarten ist.
Für eine Taste würde ich HAL_Delay benutzen, das entprellt auf einfache 
Art.
Ist ein Timer Interrupt, der alle x ms den Tastenzustand abfragen kann.

von pegel (Gast)


Lesenswert?

Jörg K schrieb:
> in der main direkt deklarieren und
> in der stm32f1xx_it.c

Ich habe mir angewöhnt die HAL Funktionen zu nutzen und dabei die 
anderen c/h-Dateien möglichst in Ruhe zu lassen.

Die HAL Lib Beispiele sind auch so aufgebaut.

In diesen Fall sieh dir das GPIO_EXTI Beipielprojekt an. Der µC spielt 
dabei keine Rolle, kann auch für einen anderen sein.

von Jörg K (Gast)


Lesenswert?

Danke soweit für eure Hilfe hier....

meine Basisfunktionalität habe ich schon am Laufen...

nun würde ich gerne den Wert eine Variable
nicht flüchtig speichern,
also wenn die Versorgungsspannung weg ist, soll der
Wert erhalten bleiben, bzw. im Init aus dem Speicher gelesen werden
(a la..... oh ich schau mal nach, was der letzte betriebszustand war...

Kann ich das im Flash ablegen?
gibt es da schon nette Funktionen für?

VG

von pegel (Gast)


Lesenswert?

Hast du eine Stützbatterie dran? Dann geht das auch im RAM.

von Jörg K (Gast)


Lesenswert?

pegel schrieb:
> Hast du eine Stützbatterie dran? Dann geht das auch im RAM.

nö keine Batterie vorhanden...

von pegel (Gast)


Lesenswert?

In dem Fall verweise ich wieder auf ein Beispiel aus der Lib.

EEPROM_Emulation

von Jörg K (Gast)


Lesenswert?

pegel schrieb:
> In dem Fall verweise ich wieder auf ein Beispiel aus der Lib.
>
> EEPROM_Emulation

ich finde diese sch Beispiel im Netz nicht arrghhh

von DraconiX (Gast)


Lesenswert?

Jörg K schrieb:
> pegel schrieb:
>> In dem Fall verweise ich wieder auf ein Beispiel aus der Lib.
>>
>> EEPROM_Emulation
>
> ich finde diese sch Beispiel im Netz nicht arrghhh

Aus der Lib und nicht dem Netz.

von pegel (Gast)


Lesenswert?

STM32Cube_FW_F1_V1.6.0/Projects/STM32F103RB-Nucleo/Applications/EEPROM/E 
EPROM_Emulation

von pegel (Gast)


Lesenswert?

Da die Flash Größe und Pages vom µC Abhängig ist, musst du in diesem 
Fall die eeprom.h anpassen.

von W.S. (Gast)


Lesenswert?

Jörg K schrieb:
> ich versuche gerad zuverlässig eine Zustandsänderung an einem Pin
> des STM32F103 zu erfassen.

Herrjemine, ist denn sowas derart schwer???

Wenn du nicht weißt, wie man sich eine sinnvolle Infrastruktur in seinem 
µC schafft, dann guck die die Quellen der ollen Lernbetty an. Ich hatte 
damal alles sowas dort vorgeturnt.

Siehe auch das da:
https://www.mikrocontroller.net/attachment/316790/STM32F103C8T6.ZIP
Dort ist zwar keine Tastenentprellung drin, aber eine 
STM32F103-Infrastruktur.

Prinzip für die Tasten:
- Timertick einrichten, alle 1 ms .. 10 ms
- im Timertick betreffende Pins geeignet abfragen
- abgefragte Pins entprellen.
- aus den entprellten Ergebnissen Events generieren, die du dann zwecks 
Abarbeitung in eine Event-Warteschlange einfüllen kannst. (diese 
entkoppelt den Timetick-Interrupt von den Abarbeitungen)
- in der Grundschleife von main die Event-Warteschlange leeren und 
abarbeiten lassen.

W.S.

Beitrag #5222951 wurde von einem Moderator gelöscht.
Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.