embeded/Cortex-M3 STM2024. 12. 13. 14:13

PWM 이랑 거의 비슷하다

TIM2를 사용할 거고, clock source - internal clock

prescaler는 6MHz로 작동해서 6000 으로 하여 1msec 주기의 tick을 사용한다.

Counter Period는 1000 으로 해서 1000 번의 tick이 모이면 (= 1초) timer interrupt가 발생하게 한다.

 

NVIC Settings에서 TIM2 global interrupt를 발생시키게 하고 프로젝트 갱신하고

 

아래의 함수들을 추가하면 끝

void HAL_TIM_PeriodElapsedCallback(TIM_HandleTypeDef *htim)
{
    static int pwm_val = 0;
    static int dir = 1;

    if(dir)
    {
        if(pwm_val < 10)
        {
            pwm_val++;
        }
        else
        {
            dir = 0;
            pwm_val--;
        }
    }
    else
    {
        if(pwm_val > 0)
        {
            pwm_val--;
        }
        else
        {
            dir = 1;
            pwm_val++;
        }
    }
    // printf("pwm_val[%d] dir[%d]\n", pwm_val, dir);
    htim3.Instance->CCR1 = pwm_val;
    htim3.Instance->CCR2 = pwm_val;
}

int main(void)
{
    /* USER CODE BEGIN 2 */
    HAL_TIM_Base_Start_IT(&htim2);
    /* USER CODE END 2 */
    /* Infinite loop */
    /* USER CODE BEGIN WHILE */
    while (1)
    {
        /* USER CODE END WHILE */
        /* USER CODE BEGIN 3 */
        HAL_Delay(10);
    }
    /* USER CODE END 3 */
}

[링크 : https://eteo.tistory.com/73]

Posted by 구차니
embeded/Cortex-M3 STM2024. 12. 13. 12:39

STM32F103RETx 에서 구현 함.

 

CubeIDE 에서 클럭은 12MHz XTAL로 들어오고 있고

TIM3를 사용해야 하니까 APB1 의 클럭을 보면 된다.

TIM1/TIM8은 APB2에 있네

 

APB1 Timer clocks는 6MHz

 

핀에서 TIM3_CH1 / TIM3_CH2 로 할당하고

Timers - TIM3 에 가서

clock source를 internal clock 으로 바꾸고

channel 1과 channel 2를 PWM Generation CH1/2로 지정해 준다.

그리고 prescaler를 5999 (6000-1) 으로 해주면 6MHz / 6000 이니 1msec 를 1tick으로 쓰고

counter Period를 0~9 까지 10을 묶어서 10msec 마다 1번의 pwm을 발생하게 한다

※ 다르게 표현하면 100Hz PWM clock 으로 지정된다.

그리고 PWM Generation Channel 1/2 에서 Pulse (16 bits value) 에는

counter Period 값을 분모로 하는 값을 지정하면 되고 "Pulse / Counter Period"로 Duty Rate이 지정된다.

 

그러면 50% duty로 100Hz의 PWM 파형이 생성된다.

 

약간의 꽁수로(?) 아래와 같이 해주면

50ms 마다 1씩 변화되어 20번의 증감을 통해 1초 주기로 점멸하는 LED가 생성된다.

50ms 마다 바꾸는 것도 다른 타이머를 이용하면 메인 쓰레드에서 안해도 되니 정확한 타이밍이 될 듯.

    static int pwm_val = 0;
    static int dir = 1;

    if(dir)
    {
      if(pwm_val < 10) pwm_val++;
      else
      {
        dir = 0;
        pwm_val--;
      }
    }
    else
    {
      if(pwm_val > 0) pwm_val--;
      else
      {
        dir = 1;
        pwm_val++;
      }
    }
    // printf("pwm_val[%d] dir[%d]\n", pwm_val, dir);
    htim3.Instance->CCR1 = pwm_val;
    htim3.Instance->CCR2 = pwm_val;
    HAL_Delay(50);

 

[링크 : https://pilimage.tistory.com/23]

'embeded > Cortex-M3 STM' 카테고리의 다른 글

STM32 timer 사용하기  (0) 2024.12.13
stm32 gpio ext interrupt 모드  (0) 2024.11.04
stm32f103 adc + dma  (0) 2024.11.04
stm32 adc 읽기(1개로 여러 개 채널)  (0) 2024.10.30
stm32 tim output compare(OC) mode  (0) 2024.07.12
Posted by 구차니
embeded/Cortex-M3 STM2024. 11. 4. 22:48

왜 안되나 했더니.. 다른 칩에서 계속 pull down 하고 있어서 버튼을 눌러도 올라가지 않았던...

 

cubeide 에서 특정 핀을 GPIO_EXT로 설정하고

 

External Interrupt Mode with ... 로 시작하는 녀석을 고른다.

필요하다면 falling edge 혹은 rising edge에서만도 잡을 수 있는데

 

둘 다 해두면 어떤 이벤트에서 인터럽트가 발생하는지 모르니, 결국에는 인터럽트 핸들러에서

해당 핀의 상태를 읽어서  판별을 해야하나? 조금 복잡한 문제가 발생할 듯 하다.

[링크 : https://blog.naver.com/micomcore/223281042436?]

 

그리고 NVIC 탭에서 해당 인터럽트를 활성화 해준다.

 

아래의 _weak 함수를 재정의 해서 사용하면 끝

GPIO_Pin은 핀 번호 별로 올라오니, 다른 포트의 같은 핀은 구분이 되지 않으니 유의

void HAL_GPIO_EXTI_Callback(uint16_t GPIO_Pin)
{
  printf("GPIO_Pin[%d]\n", GPIO_Pin);
}

'embeded > Cortex-M3 STM' 카테고리의 다른 글

STM32 timer 사용하기  (0) 2024.12.13
STM32 PWM 으로 LED 점진적으로 깜박이기  (0) 2024.12.13
stm32f103 adc + dma  (0) 2024.11.04
stm32 adc 읽기(1개로 여러 개 채널)  (0) 2024.10.30
stm32 tim output compare(OC) mode  (0) 2024.07.12
Posted by 구차니
embeded/Cortex-M3 STM2024. 11. 4. 14:12

4개의 아날로그 값을 읽어야 해서 고군분투(?) 했는데 

(설정은 아래대로)

 

+ 2024.11.06

Sampling time이 1.5Cycle로 할 경우 다른 채널이 막 섞이는 것 처럼 보인다.

71.5cycle로 하고(@12MHz) 문제없이 작동 확인

+

 

 

의외로 삽질을 한 부분은... "Continuous Conversion Mode"

이걸 켜고 4개 rank에 대해서 dma로 읽으니

1 2 3 4

2 3 4 1

3 4 1 2

식으로 데이터가 하나씩 (조금은 랜덤하게) 밀리는 현상이 발생한다.

 

Sampling Time은 어느 문서에서는 86cycle 이런식으로 길게 하라는데

혹시나 해서 시스템 클럭을 낮게 했는데도 1.5Cycle에서 큰 문제가 없어 보이니, 장기적으로 테스트 해봐야 알 듯.

 

 

[링크 : https://www.st.com/content/dam/kms/Contents/Reflibrary/ADC_Firmware_guide_Mode_and_Feature.pdf]

[링크 : https://www.st.com/content/dam/kms/Contents/Reflibrary/ADC_Firmware_guide_Timer_and_ADC.pdf]

 

84 cycle

[링크 : https://m.blog.naver.com/kiss103007/223043132332]

[링크 : https://blog.naver.com/nextstone/223369997849]

 

+

STM32F4 시리즈는 F1 과는 또 다른 듯?

[링크 : https://m.blog.naver.com/eziya76/221473392732]

 

[링크 : https://www.st.com/resource/en/application_note/an3116-stm32s-adc-modes-and-their-applications-stmicroelectronics.pdf]

Posted by 구차니
embeded/Cortex-M3 STM2024. 10. 30. 19:35

ADC는 3개인데

읽을 핀은 4개라서 어떻게 해야 하나

 

[링크 : https://m.blog.naver.com/gauya/220232257331]

[링크 : https://github.com/sweesineng/STM32_ADC_MultiCh_SingleConv_Polling?tab=readme-ov-file]

 

'embeded > Cortex-M3 STM' 카테고리의 다른 글

stm32 gpio ext interrupt 모드  (0) 2024.11.04
stm32f103 adc + dma  (0) 2024.11.04
stm32 tim output compare(OC) mode  (0) 2024.07.12
stm32 reset 없이 JTAG 붙이기  (0) 2023.07.19
STM32H/STM32G 시리즈 시리얼 포트 데이터 order  (0) 2022.08.29
Posted by 구차니
embeded/Cortex-M3 STM2024. 7. 12. 17:30

timer 설명에 설정값에 따라 GPIO 출력이 바뀌게 되는게 가능한건 알고 있었는데

그걸 어떻게 써먹나 어따 써먹다 이런게 안떠올라서 잊고 있던걸 구현된 코드를 처음으로 봄 -_-

 

IP로 구현된 통신이 아닌

GPIO를 통해 정확한 시간 간격에 오가야 한다면

타이머 값이 매치되면 값이 바뀌는게 가장 정확할 수 밖에 없겠구나 싶어진다.

 

[링크 : https://m.blog.naver.com/eziya76/221461279858]

[링크 : https://m.blog.naver.com/eziya76/222712447615]

[링크 : https://eteo.tistory.com/159]

Posted by 구차니
embeded/Cortex-M3 STM2023. 7. 19. 19:19

stm32를 찾아봐야 하나..

gdb 문법은 아닌듯 한데 stm32 전용 구문들이려나?

 

# custom.cfg
source [find interface/stlink-v2-1.cfg]
transport select "hla_swd"

source [find stm32f4x.cfg]

reset_config none

 

 

[링크 : https://www.openstm32.org/forumthread1967]

Posted by 구차니
embeded/Cortex-M3 STM2022. 8. 29. 10:37

STM32F는 이렇게 단순한데

 

검색한 내용중에 H와 G 시리즈가 걸려 나와서

STM32G로 검색해서 가장 위에 있던 STM32G030C6Tx로

프로젝트 구성해보니 내용이 많이 나온다. 눈에 띄는건.. MSB First 라는 항목

 

main.c는 아래와 같이 생성되었고

  /* USER CODE END USART1_Init 1 */
  huart1.Instance = USART1;
  huart1.Init.BaudRate = 115200;
  huart1.Init.WordLength = UART_WORDLENGTH_8B;
  huart1.Init.StopBits = UART_STOPBITS_1;
  huart1.Init.Parity = UART_PARITY_NONE;
  huart1.Init.Mode = UART_MODE_TX_RX;
  huart1.Init.HwFlowCtl = UART_HWCONTROL_NONE;
  huart1.Init.OverSampling = UART_OVERSAMPLING_16;
  huart1.Init.OneBitSampling = UART_ONE_BIT_SAMPLE_DISABLE;
  huart1.Init.ClockPrescaler = UART_PRESCALER_DIV1;
  huart1.AdvancedInit.AdvFeatureInit = UART_ADVFEATURE_DMADISABLEONERROR_INIT|UART_ADVFEATURE_MSBFIRST_INIT;
  huart1.AdvancedInit.DMADisableonRxError = UART_ADVFEATURE_DMA_DISABLEONRXERROR;
  huart1.AdvancedInit.MSBFirst = UART_ADVFEATURE_MSBFIRST_ENABLE;

 

Stm32g0xx_hal_uart.h를 따라가면 아래와 같이 먼가 있긴 하다.(귀찮아..)

#define UART_ADVFEATURE_NO_INIT                 0x00000000U          /*!< No advanced feature initialization       */
#define UART_ADVFEATURE_TXINVERT_INIT           0x00000001U          /*!< TX pin active level inversion            */
#define UART_ADVFEATURE_RXINVERT_INIT           0x00000002U          /*!< RX pin active level inversion            */
#define UART_ADVFEATURE_DATAINVERT_INIT         0x00000004U          /*!< Binary data inversion                    */
#define UART_ADVFEATURE_SWAP_INIT               0x00000008U          /*!< TX/RX pins swap                          */
#define UART_ADVFEATURE_RXOVERRUNDISABLE_INIT   0x00000010U          /*!< RX overrun disable                       */
#define UART_ADVFEATURE_DMADISABLEONERROR_INIT  0x00000020U          /*!< DMA disable on Reception Error           */
#define UART_ADVFEATURE_AUTOBAUDRATE_INIT       0x00000040U          /*!< Auto Baud rate detection initialization  */
#define UART_ADVFEATURE_MSBFIRST_INIT           0x00000080U          /*!< Most significant bit sent/received first */


#define USART_CR2_MSBFIRST_Pos       (19U)
#define USART_CR2_MSBFIRST_Msk       (0x1UL << USART_CR2_MSBFIRST_Pos)         /*!< 0x00080000 */
#define USART_CR2_MSBFIRST           USART_CR2_MSBFIRST_Msk                    /*!< Most Significant Bit First */


#define UART_ADVFEATURE_MSBFIRST_DISABLE    0x00000000U             /*!< Most significant bit sent/received
                                                                         first disable                      */
#define UART_ADVFEATURE_MSBFIRST_ENABLE     USART_CR2_MSBFIRST      /*!< Most significant bit sent/received
                                                                         first enable                       */

 

The USART can also communicate synchronously. It can operate as a SPI in Master or Slave mode with programmable clock polarity (CPOL) and phase (CPHA) and programmable data order with MSB or LSB first. The clock is output (in case of Master mode) or input (in case of Slave mode) on the CK pin. No clock pulses are provided during the start and stop bits. When the USART is configured in SPI slave mode, it supports the Transmit underrun error and the NSS hardware or software management.

[링크 : https://www.st.com/.../en.STM32G0-Peripheral-USART-interface-USART.pdf]

[링크 : https://www.st.com/.../en.STM32H7-Peripheral-USART_interface_USART.pdf]

'embeded > Cortex-M3 STM' 카테고리의 다른 글

stm32 tim output compare(OC) mode  (0) 2024.07.12
stm32 reset 없이 JTAG 붙이기  (0) 2023.07.19
stm32 wdg 최대 설정시간  (0) 2021.08.09
stm32 RST pull-up reset fail  (0) 2021.08.02
STM32 RDP(ReaD Protection)  (0) 2021.07.02
Posted by 구차니
embeded/Cortex-M3 STM2021. 8. 9. 17:02

stm32에서 와치독으로는 40 KHz의 RC 클럭이 들어간다.

 

그리고 prescaler는 4/8/16/32/64/128/256 뿐이고

 

다운카운터는 0~4095가 설정가능 범위

 

입력 클럭을 40k로 잡고 프리스케일러에 따른 클럭을 계산하고

타겟 시간을 2초로 잡아보면, 4095가 최대 값이니, prescaler는 16 이상으로 쓰면 가능!

 

미친척 하나씩 대입해보니 STM32에서 설정 가능한 와치독 최대 시간은 26초.

(그런데 와치독을 25초 가까이 쓸일이 있나 싶긴 한데...?)

[링크 : https://blog.naver.com/namunny/220393603436]

'embeded > Cortex-M3 STM' 카테고리의 다른 글

stm32 reset 없이 JTAG 붙이기  (0) 2023.07.19
STM32H/STM32G 시리즈 시리얼 포트 데이터 order  (0) 2022.08.29
stm32 RST pull-up reset fail  (0) 2021.08.02
STM32 RDP(ReaD Protection)  (0) 2021.07.02
stm32 uart echo  (0) 2021.02.04
Posted by 구차니
embeded/Cortex-M3 STM2021. 8. 2. 19:57

리셋핀에 강하게 외부에서 풀업이 걸려있을 경우

내부 리셋에 의해서 리셋이 되지 않는 문제가 발생하지 않는다.

 

어쩌면 HAL_SystemReset() 함수가 리셋핀을 조작해서 자기 자신이 스스로 LOW로 낮춤으로

물리적은 하드웨어 리셋을 구현해놨는데 외부에서 풀업이 걸려있으면 내릴수가 없으니

리셋이 안걸리는거 아닐려나?

 

 

 

[링크 : https://kaizen8501.tistory.com/26]

[링크 : https://community.st.com/s/question/0D53W000006EROWSA4]

[링크 : https://community.st.com/s/question/0D50X00009XkZUg/problem-with-nvicsystemreset]

'embeded > Cortex-M3 STM' 카테고리의 다른 글

STM32H/STM32G 시리즈 시리얼 포트 데이터 order  (0) 2022.08.29
stm32 wdg 최대 설정시간  (0) 2021.08.09
STM32 RDP(ReaD Protection)  (0) 2021.07.02
stm32 uart echo  (0) 2021.02.04
STM32CubeIDE / HAL register callbacks  (0) 2021.02.03
Posted by 구차니