硬汉嵌入式论坛

 找回密码
 立即注册
查看: 6149|回复: 2
收起左侧

[TIMER] STM32H7实现单个定时器中不同通道配置不同频率PWM的方法

[复制链接]

1万

主题

6万

回帖

10万

积分

管理员

Rank: 9Rank: 9Rank: 9

积分
106675
QQ
发表于 2018-8-16 01:20:52 | 显示全部楼层 |阅读模式
说明:感觉这种方式实用价值不大,因为要每次都进入中断里面更新CCR比较捕获寄存器。

不如用户自己搞个定时器中断,在中断里面直接操作IO即可,简单省事。

调用函数HAL_TIM_OC_Init,HAL_TIM_OC_ConfigChannel和HAL_TIM_OC_Start_IT即可实现

官方例子里面是测试了4路,我这里用示波器测试了前两路效果:


PA.08 (TIM1_Channel1)
PA.09 (TIM1_Channel2)
PA.10 (TIM1_Channel3)
PE.14 (TIM1_Channel4)


77.png


实现的代码如下:
  1. /* Private typedef -----------------------------------------------------------*/
  2. /* Private define ------------------------------------------------------------*/
  3. /* Private macro -------------------------------------------------------------*/
  4. /* Private variables ---------------------------------------------------------*/
  5. __IO uint32_t uhCCR1_Val = 40960;
  6. __IO uint32_t uhCCR2_Val = 20480;
  7. __IO uint32_t uhCCR3_Val = 10240;
  8. __IO uint32_t uhCCR4_Val = 5120;

  9. uint32_t uhCapture = 0;

  10. /* Timer handler declaration */
  11. TIM_HandleTypeDef    TimHandle;

  12. /* Timer Output Compare Configuration Structure declaration */
  13. TIM_OC_InitTypeDef sConfig;

  14. /* Counter Prescaler value */
  15. uint32_t uwPrescalerValue = 0;

  16. /* Private function prototypes -----------------------------------------------*/
  17. static void SystemClock_Config(void);
  18. static void Error_Handler(void);
  19. static void CPU_CACHE_Enable(void);
  20. /* Private functions ---------------------------------------------------------*/

  21. /**
  22.   * @brief  Main program.
  23.   * @param  None
  24.   * @retval None
  25.   */
  26. int main(void)
  27. {
  28.   /* Enable the CPU Cache */
  29.   CPU_CACHE_Enable();
  30.        
  31.   /* STM32H7xx HAL library initialization:
  32.        - Systick timer is configured by default as source of time base, but user
  33.          can eventually implement his proper time base source (a general purpose
  34.          timer for example or other time source), keeping in mind that Time base
  35.          duration should be kept 1ms since PPP_TIMEOUT_VALUEs are defined and
  36.          handled in milliseconds basis.
  37.        - Set NVIC Group Priority to 4
  38.        - Low Level Initialization
  39.      */
  40.   HAL_Init();

  41.   /* Configure the system clock to 400 MHz */
  42.   SystemClock_Config();

  43.   /* Configure LED2 */
  44.   BSP_LED_Init(LED2);


  45.    /*##-1- Configure the TIM peripheral #######################################*/
  46.   /* ---------------------------------------------------------------------------
  47.   TIM1 Configuration: Output Compare Toggle Mode:

  48.   To get TIM1 counter clock at 20 MHz, the prescaler is computed as follows:
  49.   Prescaler = (TIM1CLK / TIM1 counter clock) - 1
  50.   Prescaler = (SystemCoreClock /2*20000000) - 1

  51.   CC1 update rate = TIM1 counter clock / uhCCR1_Val
  52.                   = 20 MHz/40961 = 488.269 Hz
  53.   ==> So the TIM1 Channel 1 generates a periodic signal with a frequency equal
  54.       to 244.13 Hz.

  55.   CC2 update rate = TIM1 counter clock / uhCCR2_Val
  56.                   = 20 MHz/20480 = 976.56 Hz
  57.   ==> So the TIM1 Channel 2 generates a periodic signal with a frequency equal
  58.       to 488.28 Hz.

  59.   CC3 update rate = TIM1 counter clock / uhCCR3_Val
  60.                   = 20 MHz/10240 = 1953.1 Hz
  61.   ==> So the TIM1 Channel 3 generates a periodic signal with a frequency equal
  62.       to 976.56 Hz.

  63.   CC4 update rate = TIM1 counter clock / uhCCR4_Val
  64.                   = 20 MHz/5120 = 3906.25 Hz
  65.   ==> So the TIM1 Channel 4 generates a periodic signal with a frequency equal
  66.       to 1953.12 Hz.


  67.   --------------------------------------------------------------------------- */

  68.   /* Compute the prescaler value to have TIM1 counter clock equal to 20 MHz */
  69.   uwPrescalerValue = (uint32_t)((SystemCoreClock / 40000000) - 1);
  70.   
  71.   TimHandle.Instance = TIM1;
  72.   
  73.   TimHandle.Init.Period        = 65535;
  74.   TimHandle.Init.Prescaler     = uwPrescalerValue;
  75.   TimHandle.Init.ClockDivision = 0;
  76.   TimHandle.Init.CounterMode   = TIM_COUNTERMODE_UP;
  77.   if(HAL_TIM_OC_Init(&TimHandle) != HAL_OK)
  78.   {
  79.     /* Initialization Error */
  80.     Error_Handler();
  81.   }
  82.   
  83.   /*##-2- Configure the Output Compare channels ##############################*/
  84.   /* Common configuration for all channels */
  85.   sConfig.OCMode     = TIM_OCMODE_TOGGLE;
  86.   sConfig.OCPolarity = TIM_OCPOLARITY_LOW;

  87.   /* Output Compare Toggle Mode configuration: Channel1 */
  88.   sConfig.Pulse = uhCCR1_Val;  
  89.   if(HAL_TIM_OC_ConfigChannel(&TimHandle, &sConfig, TIM_CHANNEL_1) != HAL_OK)
  90.   {
  91.     /* Configuration Error */
  92.     Error_Handler();
  93.   }
  94.   
  95.   /* Output Compare Toggle Mode configuration: Channel2 */
  96.   sConfig.Pulse = uhCCR2_Val;
  97.   if(HAL_TIM_OC_ConfigChannel(&TimHandle, &sConfig, TIM_CHANNEL_2) != HAL_OK)
  98.   {
  99.     /* Configuration Error */
  100.     Error_Handler();
  101.   }
  102.   
  103.   /* Output Compare Toggle Mode configuration: Channel3 */
  104.   sConfig.Pulse = uhCCR3_Val;
  105.   if(HAL_TIM_OC_ConfigChannel(&TimHandle, &sConfig, TIM_CHANNEL_3) != HAL_OK)
  106.   {
  107.     /* Configuration Error */
  108.     Error_Handler();
  109.   }
  110.   
  111.   /* Output Compare Toggle Mode configuration: Channel4 */
  112.   sConfig.Pulse = uhCCR4_Val;
  113.   if(HAL_TIM_OC_ConfigChannel(&TimHandle, &sConfig, TIM_CHANNEL_4) != HAL_OK)
  114.   {
  115.     /* Configuration Error */
  116.     Error_Handler();
  117.   }

  118.   /*##-3- Start signals generation #######################################*/
  119.   /* Start channel 1 in Output compare mode */
  120.   if(HAL_TIM_OC_Start_IT(&TimHandle, TIM_CHANNEL_1) != HAL_OK)
  121.   {
  122.     /* Starting Error */
  123.     Error_Handler();
  124.   }
  125.   /* Start channel 2 in Output compare mode */
  126.   if(HAL_TIM_OC_Start_IT(&TimHandle, TIM_CHANNEL_2) != HAL_OK)
  127.   {
  128.     /* Starting Error */
  129.     Error_Handler();
  130.   }
  131.   /* Start channel 3 in Output compare mode */
  132.   if(HAL_TIM_OC_Start_IT(&TimHandle, TIM_CHANNEL_3) != HAL_OK)
  133.   {
  134.     /* Starting Error */
  135.     Error_Handler();
  136.   }
  137.   /* Start channel 4 in Output compare mode */
  138.   if(HAL_TIM_OC_Start_IT(&TimHandle, TIM_CHANNEL_4) != HAL_OK)
  139.   {
  140.     /* Starting Error */
  141.     Error_Handler();
  142.   }

  143.   while (1)
  144.   {}
  145. }

  146. /**
  147.   * @brief  Output Compare callback in non blocking mode
  148.   * @param  htim : TIM OC handle
  149.   * @retval None
  150.   */
  151. void HAL_TIM_OC_DelayElapsedCallback(TIM_HandleTypeDef *htim)
  152. {
  153.   /* TIM1_CH1 toggling with frequency = 244.13 Hz */
  154.   if(htim->Channel == HAL_TIM_ACTIVE_CHANNEL_1)
  155.   {
  156.     uhCapture = HAL_TIM_ReadCapturedValue(htim, TIM_CHANNEL_1);
  157.     /* Set the Capture Compare Register value */
  158.     __HAL_TIM_SET_COMPARE(&TimHandle, TIM_CHANNEL_1, (uhCapture + uhCCR1_Val));
  159.   }
  160.   
  161.   /* TIM1_CH2 toggling with frequency = 488.28 Hz */
  162.   if(htim->Channel == HAL_TIM_ACTIVE_CHANNEL_2)
  163.   {
  164.     uhCapture = HAL_TIM_ReadCapturedValue(htim, TIM_CHANNEL_2);
  165.     /* Set the Capture Compare Register value */
  166.     __HAL_TIM_SET_COMPARE(&TimHandle, TIM_CHANNEL_2, (uhCapture + uhCCR2_Val));   
  167.   }
  168.   
  169.   /* TIM1_CH3 toggling with frequency = 976.56 Hz */
  170.   if(htim->Channel == HAL_TIM_ACTIVE_CHANNEL_3)
  171.   {
  172.     uhCapture = HAL_TIM_ReadCapturedValue(htim, TIM_CHANNEL_3);
  173.     /* Set the Capture Compare Register value */
  174.     __HAL_TIM_SET_COMPARE(&TimHandle, TIM_CHANNEL_3, (uhCapture + uhCCR3_Val));
  175.   }
  176.   
  177.   /* TIM1_CH4 toggling with frequency = 1953.12 Hz */
  178.   if(htim->Channel == HAL_TIM_ACTIVE_CHANNEL_4)
  179.   {
  180.     uhCapture = HAL_TIM_ReadCapturedValue(htim, TIM_CHANNEL_4);
  181.     /* Set the Capture Compare Register value */
  182.     __HAL_TIM_SET_COMPARE(&TimHandle, TIM_CHANNEL_4, (uhCapture + uhCCR4_Val));
  183.   }
  184. }
复制代码







评分

参与人数 1金币 +10 收起 理由
朱日天 + 10

查看全部评分

回复

使用道具 举报

0

主题

4

回帖

4

积分

新手上路

积分
4
发表于 2020-3-26 23:53:10 | 显示全部楼层
管理员, 我玩这个demo出现了两个问题,
1. 就是不知道为什么, 我只使能了CCR4中断 HAL_TIM_OC_Start_IT(&htim2,TIM_CHANNEL_4);  但是我看SR寄存器为啥是0x1f?, 而且即使在这句话前面加上__HAL_TIM_CLEAR_FLAG(&htim2,TIM_FLAG_UPDATE|TIM_FLAG_CC1|TIM_FLAG_CC2|TIM_FLAG_CC3|TIM_FLAG_CC4);  问题仍然存在
2. 感觉我的中断只能进一次似的;而且cubeide仿真跟容易挂掉, 各种莫名其妙,
以上求解答, 谢谢

/* 定时器回调函�???  */
void HAL_TIM_OC_DelayElapsedCallback(TIM_HandleTypeDef *htim)
{
        uint32_t uhCapture;

        if(htim->Instance == TIM2)
        {
                if(htim->Channel == HAL_TIM_ACTIVE_CHANNEL_1)                //1ms
                {
                        //timerEvent();
                }
                if(htim->Channel == HAL_TIM_ACTIVE_CHANNEL_2)                //10ms
                {

                }
                if(htim->Channel == HAL_TIM_ACTIVE_CHANNEL_3)                //100ms
                {

                }
                if(htim->Channel == HAL_TIM_ACTIVE_CHANNEL_4)                //1000ms
                {
                        LED0_Turn();
//                        uhCapture = HAL_TIM_ReadCapturedValue(&htim2, HAL_TIM_ACTIVE_CHANNEL_4);
//                        __HAL_TIM_SET_COMPARE(&htim2,HAL_TIM_ACTIVE_CHANNEL_1,(uhCapture+1000));
                }
        }
}
回复

使用道具 举报

1万

主题

6万

回帖

10万

积分

管理员

Rank: 9Rank: 9Rank: 9

积分
106675
QQ
 楼主| 发表于 2020-3-27 00:29:04 | 显示全部楼层
爱吃饭 发表于 2020-3-26 23:53
管理员, 我玩这个demo出现了两个问题,
1. 就是不知道为什么, 我只使能了CCR4中断 HAL_TIM_OC_Start_IT ...

你用MDK跑原始的例子正常吗,我这个是早前使用ST的NUCLEO板子测试的,没问题。
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

QQ|小黑屋|Archiver|手机版|硬汉嵌入式论坛

GMT+8, 2024-4-29 08:23 , Processed in 0.291124 second(s), 40 queries .

Powered by Discuz! X3.4 Licensed

Copyright © 2001-2023, Tencent Cloud.

快速回复 返回顶部 返回列表