LINUX.ORG.RU

stm32, тест, непонятка с чтением состояния пина

 


0

1

добрый день

исходные данные:
stm32vldiscovery
STM32VL-Discovery-template
- No CubeX

набросал тест «помограть» с «кнопкой»
- синий св.диод моргает ~ 1Гц
- зеленый св.диод - меняет состояние по нажатию на кнопку

есть непонимание: код чтения пина кнопки «тормозит», точнее
- если код «чтения» заремить - то син.св.диод переключается «правильно», прим. 1Гц
- если код «включить», то син.св.диод переключается прим. в 2 раза медленнее

понятное дело, где-то тупой косяк, швыряйтесь наздоровье. спасибо

main.c

#include "stm32f10x.h"

#define TIMER_CNT 0xFFFFE

#define LED_B_SET (GPIO_SetBits  (GPIOC, GPIO_Pin_8))
#define LED_B_CLR (GPIO_ResetBits(GPIOC, GPIO_Pin_8))
#define LED_G_SET (GPIO_SetBits  (GPIOC, GPIO_Pin_9))
#define LED_G_CLR (GPIO_ResetBits(GPIOC, GPIO_Pin_9))

////////////////////////////////////////////////////////////////////////////////
void RCC_init()
////////////////////////////////////////////////////////////////////////////////
{
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOC, ENABLE); // enable clocking on Port C
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE);
}
////////////////////////////////////////////////////////////////////////////////
void Setup(void)
////////////////////////////////////////////////////////////////////////////////
{
GPIO_InitTypeDef GPIOC_init_params;

RCC_init();

//
// 2 LED pin's
//
GPIOC_init_params.GPIO_Pin = GPIO_Pin_8 | GPIO_Pin_9; // Blue LED PC[8], Green LED PC[9]
GPIOC_init_params.GPIO_Speed = GPIO_Speed_10MHz;
GPIOC_init_params.GPIO_Mode  = GPIO_Mode_Out_PP;  // Push-pull output
GPIO_Init        (GPIOC, &GPIOC_init_params);

//
// Button
//
GPIOC_init_params.GPIO_Pin   = GPIO_Pin_0;        // user button PA0
GPIOC_init_params.GPIO_Speed = GPIO_Speed_10MHz;  // 10-50 по барабану
GPIOC_init_params.GPIO_Mode  = GPIO_Mode_IPD;     // GPIO_Mode_IPD - PD connect GND
GPIO_Init        (GPIOA, &GPIOC_init_params);     //
}
////////////////////////////////////////////////////////////////////////////////
int main(void)
////////////////////////////////////////////////////////////////////////////////
{
int cnt = TIMER_CNT;
int flag_time = 0;
int flag_btn  = 0;

while(1)
  {
  if(!cnt--)
    {
    flag_time = 1;
    cnt       = TIMER_CNT;
    }

  if(flag_time)
    {
    flag_time = 0;

    if(GPIO_ReadInputDataBit(GPIOC, GPIO_Pin_8))    { LED_B_CLR; } // invert Blue Led
    else                                            { LED_B_SET; }

    if(flag_btn)
      {
      flag_btn = 0;

      if(GPIO_ReadInputDataBit(GPIOC, GPIO_Pin_9))  { LED_G_CLR; } // invert Green Led
      else                                          { LED_G_SET; }
      }   // if(flag_btn)
    }     // if(flag_time)

  //
  // читаем пин-кнопку
  //
  if(GPIO_ReadInputDataBit(GPIOA, GPIO_Pin_0))
    {
    flag_btn = 1;
    } //*/
  }     // while()
}
////////////////////////////////////////////////////////////////////////////////

★★★★★

Когда инвертируешь выходной сигнал, нужно читать не вход, а выход. Что-то типа GPIO_ReadOutputDataBit().

Beewek ★★★
()

Ты не кошерно выдержку времени реализуешь. Выдержка времени должна быть привязана либо к системному таймеру (systick) либо к обычному таймеру. Это чисто по теории.

Теперь конкретно по твоей проблеме. Видимо она в том, что тебе нужно код чтения кнопки засунуть внутрь if(flag_time), а то он выполняется на каждой итерации цикла while и оттягивает тебе время, естественно.

James_Holden ★★★★
()

То есть попробуй вот так

#include "stm32f10x.h"

#define TIMER_CNT 0xFFFFE

#define LED_B_SET (GPIO_SetBits  (GPIOC, GPIO_Pin_8))
#define LED_B_CLR (GPIO_ResetBits(GPIOC, GPIO_Pin_8))
#define LED_G_SET (GPIO_SetBits  (GPIOC, GPIO_Pin_9))
#define LED_G_CLR (GPIO_ResetBits(GPIOC, GPIO_Pin_9))

////////////////////////////////////////////////////////////////////////////////
void RCC_init()
////////////////////////////////////////////////////////////////////////////////
{
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOC, ENABLE); // enable clocking on Port C
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE);
}
////////////////////////////////////////////////////////////////////////////////
void Setup(void)
////////////////////////////////////////////////////////////////////////////////
{
GPIO_InitTypeDef GPIOC_init_params;

RCC_init();

//
// 2 LED pin's
//
GPIOC_init_params.GPIO_Pin = GPIO_Pin_8 | GPIO_Pin_9; // Blue LED PC[8], Green LED PC[9]
GPIOC_init_params.GPIO_Speed = GPIO_Speed_10MHz;
GPIOC_init_params.GPIO_Mode  = GPIO_Mode_Out_PP;  // Push-pull output
GPIO_Init        (GPIOC, &GPIOC_init_params);

//
// Button
//
GPIOC_init_params.GPIO_Pin   = GPIO_Pin_0;        // user button PA0
GPIOC_init_params.GPIO_Speed = GPIO_Speed_10MHz;  // 10-50 по барабану
GPIOC_init_params.GPIO_Mode  = GPIO_Mode_IPD;     // GPIO_Mode_IPD - PD connect GND
GPIO_Init        (GPIOA, &GPIOC_init_params);     //
}
////////////////////////////////////////////////////////////////////////////////
int main(void)
////////////////////////////////////////////////////////////////////////////////
{
int cnt = TIMER_CNT;
int flag_time = 0;
int flag_btn  = 0;

while(1)
  {
  if(!cnt--)
    {
    flag_time = 1;
    cnt       = TIMER_CNT;
    }

  if(flag_time)
    {
    flag_time = 0;

    if(GPIO_ReadInputDataBit(GPIOC, GPIO_Pin_8))    { LED_B_CLR; } // invert Blue Led
    else                                            { LED_B_SET; }

    if(flag_btn)
      {
      flag_btn = 0;

      if(GPIO_ReadInputDataBit(GPIOC, GPIO_Pin_9))  { LED_G_CLR; } // invert Green Led
      else                                          { LED_G_SET; }
      }   // if(flag_btn)

  //
  // читаем пин-кнопку
  //
  if(GPIO_ReadInputDataBit(GPIOA, GPIO_Pin_0))
    {
    flag_btn = 1;
    } //*/

    }     // if(flag_time)

  }     // while()
}
////////////////////////////////////////////////////////////////////////////////
James_Holden ★★★★
()
Ответ на: комментарий от James_Holden

Но так будет видимо другая проблема - придется кнопку долго держать, она будет медленно опрашиваться.

А чтобы это нормально решить - надо как я в первом ответе писал, привязывать задержку к таймеру.

James_Holden ★★★★
()
Последнее исправление: James_Holden (всего исправлений: 1)
Ответ на: комментарий от James_Holden

надо как я в первом ответе писал, привязывать задержку к таймеру

а я как привязал задержку?! почти как к таймеру :о)

это-ж был тестовый набросок... посмотреть, что-да как...

sunjob ★★★★★
() автор топика
Последнее исправление: sunjob (всего исправлений: 2)
Ответ на: комментарий от James_Holden

привязывать задержку к таймеру.

тут какая фигня-то? под «мандариной» подобный подход работает и особо задержек-то и нет никаких... дай, думаю, катану и тут... ага, не проканало :о)

sunjob ★★★★★
() автор топика
Последнее исправление: sunjob (всего исправлений: 1)
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.