STM8 Discovery Setting Flag using Button

Thread Starter

Amorphous

Joined Oct 16, 2015
10
Hi,

I am making a project where in I am connecting few LEDs with my STM8 Discovery Board (PA3, PD3, PD4) and setting the mode using the on-board button (PB7). The issue I am facing is that I am able to toggle to Flag = 2 (with for loops for phasing the 3 LEDs) but the button becomes unresponsive after that. I need to be able to go back to Flag 0 and Flag 1.

I am a beginner so there is a lot of hit & trial that I have done but the code is doing what it is supposed to do except this part. Would appreciate any guidance on this pls.

TIA!

IAR STM8 Code:
#include "STM8S.h"
 
 
void clock_setup(void);
void GPIO_setup(void);
void ADC1_setup(void);
void TIM2_setup(void);
void Key_scan(void);
 

unsigned int A0 = 0x0000;

int i = 0;
 

int flag = 0;

void delay_ms(long n)
{
  while(n--> 0);
}
 
void main()
{
  
   clock_setup();
   GPIO_setup();
   ADC1_setup();
   TIM2_setup();
   //ITC_setup();
 
  
   while(TRUE)
   {
    
    Key_scan();
      
  
   }

}
 
void clock_setup(void)
{
   CLK_DeInit();
                
   CLK_HSECmd(DISABLE);
   CLK_LSICmd(DISABLE);
   CLK_HSICmd(ENABLE);
   while(CLK_GetFlagStatus(CLK_FLAG_HSIRDY) == FALSE);
                
   CLK_ClockSwitchCmd(ENABLE);
   CLK_HSIPrescalerConfig(CLK_PRESCALER_HSIDIV1);
   CLK_SYSCLKConfig(CLK_PRESCALER_CPUDIV1);
                
   CLK_ClockSwitchConfig(CLK_SWITCHMODE_AUTO, CLK_SOURCE_HSI,
   DISABLE, CLK_CURRENTCLOCKSTATE_ENABLE);
                
   CLK_PeripheralClockConfig(CLK_PERIPHERAL_SPI, DISABLE);
   CLK_PeripheralClockConfig(CLK_PERIPHERAL_I2C, DISABLE);
   CLK_PeripheralClockConfig(CLK_PERIPHERAL_ADC, ENABLE);
   CLK_PeripheralClockConfig(CLK_PERIPHERAL_AWU, DISABLE);
   CLK_PeripheralClockConfig(CLK_PERIPHERAL_UART1, DISABLE);
   CLK_PeripheralClockConfig(CLK_PERIPHERAL_TIMER1, DISABLE);
   CLK_PeripheralClockConfig(CLK_PERIPHERAL_TIMER2, ENABLE);
   CLK_PeripheralClockConfig(CLK_PERIPHERAL_TIMER4, DISABLE);
}
 
 
void GPIO_setup(void)
{
   GPIO_DeInit(GPIOB);
   GPIO_Init(GPIOB, GPIO_PIN_0, GPIO_MODE_IN_FL_NO_IT);
                
   GPIO_DeInit(GPIOA);
   GPIO_Init(GPIOA, GPIO_PIN_3, GPIO_MODE_OUT_PP_HIGH_FAST);
                
   GPIO_DeInit(GPIOD);
   GPIO_Init(GPIOD, GPIO_PIN_3, GPIO_MODE_OUT_PP_HIGH_FAST);
   GPIO_Init(GPIOD, GPIO_PIN_4, GPIO_MODE_OUT_PP_HIGH_FAST);

  
   GPIO_DeInit(GPIOB);
   GPIO_Init(GPIOB, GPIO_PIN_7, GPIO_MODE_IN_FL_NO_IT);
  
}
 

void TIM2_setup(void)
{
      TIM2_DeInit();
      TIM2_TimeBaseInit(TIM2_PRESCALER_32, 1000);
      TIM2_OC1Init(TIM2_OCMODE_PWM1, TIM2_OUTPUTSTATE_ENABLE, 1000,
                   TIM2_OCPOLARITY_LOW);
      TIM2_OC2Init(TIM2_OCMODE_PWM1, TIM2_OUTPUTSTATE_ENABLE, 1000,
                   TIM2_OCPOLARITY_LOW);
      TIM2_OC3Init(TIM2_OCMODE_PWM1, TIM2_OUTPUTSTATE_ENABLE, 1000,
                   TIM2_OCPOLARITY_LOW);
      TIM2_Cmd(ENABLE);
}

 
void ADC1_setup(void)
{
   ADC1_DeInit();         
                
   ADC1_Init(ADC1_CONVERSIONMODE_CONTINUOUS,
             ADC1_CHANNEL_0,
             ADC1_PRESSEL_FCPU_D18,
             ADC1_EXTTRIG_GPIO,
             DISABLE,
             ADC1_ALIGN_RIGHT,
             ADC1_SCHMITTTRIG_CHANNEL0,
             DISABLE);
                                                                                  
   ADC1_Cmd(ENABLE);
}
 
void Key_scan(void)
{
 
  if(GPIO_ReadInputPin(GPIOB, GPIO_PIN_7) == 0)
  {
    do
    {
    }while(GPIO_ReadInputPin(GPIOB, GPIO_PIN_7) == 0);
    //delay(10000);
    delay_ms(1000);
    
    if(flag > 2)
    {
      flag = 0;
    
    }
    else
    {
     flag = flag + 1;
    }       
  }
 
       if (flag == 0)
     {
       TIM2_SetCompare1(0);
       TIM2_SetCompare2(0);
       TIM2_SetCompare3(0);
     }
    
     if (flag == 1)
     {
        ADC1_StartConversion();
       while(ADC1_GetFlagStatus(ADC1_FLAG_EOC) == FALSE);
                                
       A0 = 200 * ADC1_GetConversionValue();
    
       ADC1_ClearFlag(ADC1_FLAG_EOC);
      
       delay_ms(50);
       TIM2_SetCompare1(A0);
       TIM2_SetCompare2(A0);
       TIM2_SetCompare3(A0);
       delay_ms(50);       
          
    }
    
    if (flag == 2)
     {
          {
       for(i = 0; i < 3000; i += 1)
          {
              TIM2_SetCompare1(i);
              delay_ms(100);
          }
                
          delay_ms(10);
      
          for(i = 0; i < 3000; i += 1)
          {
              TIM2_SetCompare2(i);
              delay_ms(100);
          }
          delay_ms(10);
                  
          
          for(i = 0; i < 3000; i += 1)
          {
              TIM2_SetCompare3(i);
              delay_ms(100);
          }
          delay_ms(10);
          
          for(i = 3000; i > 0; i -= 1)
          {
              TIM2_SetCompare1(i);
              delay_ms(100);
          }
          delay_ms(10);
          
          for(i = 3000; i > 0; i -= 1)
          {
              TIM2_SetCompare2(i);
              delay_ms(100);
          }
          delay_ms(10);
          
          for(i = 3000; i > 0; i -= 1)
          {
              TIM2_SetCompare3(i);
              delay_ms(100);
          }
          delay_ms(10);
      
    }
 
      }

 
}
 

MrChips

Joined Oct 2, 2009
30,706
You have a Key_scan( ) function with a whole bunch of delays.

I would suggest that you start off by drawing a flowchart without looking at what you have written in the code.
Program design comes first. Writing code is secondary.
 

Thread Starter

Amorphous

Joined Oct 16, 2015
10
You have a Key_scan( ) function with a whole bunch of delays.

I would suggest that you start off by drawing a flowchart without looking at what you have written in the code.
Program design comes first. Writing code is secondary.
If I remove all delays in the function, the button runs as expected but I am not able to phase the LEDs the way I require. I need a very slow LED phasing (like here :
), is there another way of doing this without using delays?

Thanks a lot!
 
Top