1、基于芯片创建呼吸灯项目
基于rtthread studio 可以帮助我们创建好底层驱动,我们只需要做简单配置
2、配置pwm 设备
基于芯片生成的项目默认只打开了 uart 和 pin的驱动,对于其它硬件驱动需要自行配置;
对于pwm和设备的驱动分为四步,官方在board.h 中也已经给出;
2.1、第一步 设置rtthreadseting:
官方给出sep1;
STEP 1, open pwm driver framework support in the RT-Thread Settings file
打开我们的RT-Thread Settings file 找到组件下的设备并打开pwm开关;
2.2、sep2:设置宏定义
STEP 2, define macro related to the pwm such as #define BSP_USING_PWM1
在board.h中设置宏定义,这个需要根据自己所使用的tim定时器来确定,pwm1 d对应 tim1;
2.3:sep3 cubemx 配置tim定时器;
* STEP 3, copy your pwm timer init function from stm32xxxx_hal_msp.c generated by stm32cubemx to the end if board.c file
such as void HAL_TIM_Base_MspInit(TIM_HandleTypeDef* htim_base) and void HAL_TIM_MspPostInit(TIM_HandleTypeDef* htim
打开项目下的Cube MX Settings
配置pE9 为TIM1 的 CH1;
然后打开tim1 定时器的设置;将 ch1 设置为比较输出:
然后保存并生成代码:
然后将 项目目录cubemx下的 stm32l4xx_hal_msp.c
中的三个函数复制到board.c的末尾;
/**
* @brief TIM_OC MSP Initialization
* This function configures the hardware resources used in this example
* @param htim_oc: TIM_OC handle pointer
* @retval None
*/
void HAL_TIM_OC_MspInit(TIM_HandleTypeDef* htim_oc)
{
if(htim_oc->Instance==TIM1)
{
/* USER CODE BEGIN TIM1_MspInit 0 */
/* USER CODE END TIM1_MspInit 0 */
/* Peripheral clock enable */
__HAL_RCC_TIM1_CLK_ENABLE();
/* USER CODE BEGIN TIM1_MspInit 1 */
/* USER CODE END TIM1_MspInit 1 */
}
}
void HAL_TIM_MspPostInit(TIM_HandleTypeDef* htim)
{
GPIO_InitTypeDef GPIO_InitStruct = {0};
if(htim->Instance==TIM1)
{
/* USER CODE BEGIN TIM1_MspPostInit 0 */
/* USER CODE END TIM1_MspPostInit 0 */
__HAL_RCC_GPIOE_CLK_ENABLE();
/**TIM1 GPIO Configuration
PE9 ------> TIM1_CH1
*/
GPIO_InitStruct.Pin = GPIO_PIN_9;
GPIO_InitStruct.Mode = GPIO_MODE_AF_PP;
GPIO_InitStruct.Pull = GPIO_NOPULL;
GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW;
GPIO_InitStruct.Alternate = GPIO_AF1_TIM1;
HAL_GPIO_Init(GPIOE, &GPIO_InitStruct);
/* USER CODE BEGIN TIM1_MspPostInit 1 */
/* USER CODE END TIM1_MspPostInit 1 */
}
}
/**
* @brief TIM_OC MSP De-Initialization
* This function freeze the hardware resources used in this example
* @param htim_oc: TIM_OC handle pointer
* @retval None
*/
void HAL_TIM_OC_MspDeInit(TIM_HandleTypeDef* htim_oc)
{
if(htim_oc->Instance==TIM1)
{
/* USER CODE BEGIN TIM1_MspDeInit 0 */
/* USER CODE END TIM1_MspDeInit 0 */
/* Peripheral clock disable */
__HAL_RCC_TIM1_CLK_DISABLE();
/* USER CODE BEGIN TIM1_MspDeInit 1 */
/* USER CODE END TIM1_MspDeInit 1 */
}
}
复制完之后; 打开drivers 里的 drv_pwm.c 找到 stm32_hw_pwm_init这个函数,在TIM初始化之前初始化以下时钟引脚。
在图里所示的位置调用这个函数
第三步就完成了:
2.4、sep 4 :配置config文件;
* STEP 4, modify your stm32xxxx_hal_config.h file to support pwm peripherals. define macro related to the peripherals
* such as #define HAL_TIM_MODULE_ENABLED
找到driver 目录下的 stm32xxx_hal_config.h 文件,定义宏 #define HAL_TIM_MODULE_ENABLED
3、重新编译项目
如果cubemx 目录下出现报错,点击排除构建:
运行查看设备: pwm1
新建文件编写测试应用函数控制 pwm :代码如下
#include <rtthread.h>
#include <rtdevice.h>
#define PWM_DEV_NAME "pwm1" /* PWM设 备 名 称 */
#define PWM_DEV_CHANNEL 1 /* PWM通 道 */
struct rt_device_pwm *pwm_dev; /* PWM设 备 句 柄 */
static int pwm_led_sample(int argc, char *argv[])
{
rt_uint32_t period, pulse, dir;
period = 500000; /* 周 期 为0.5ms, 单 位 为 纳 秒ns */
dir = 1; /* PWM脉 冲 宽 度 值 的 增 减 方 向 */
pulse = 0; /* PWM脉 冲 宽 度 值, 单 位 为 纳 秒ns */
/* 查 找 设 备 */
pwm_dev = (struct rt_device_pwm *)rt_device_find(PWM_DEV_NAME);
if (pwm_dev == RT_NULL)
{
rt_kprintf("pwm sample run failed! can't find %s device!\n", PWM_DEV_NAME);
return RT_ERROR;
}
/* 设 置PWM周 期 和 脉 冲 宽 度 默 认 值 */
rt_pwm_set(pwm_dev, PWM_DEV_CHANNEL, period, pulse);
/* 使 能 设 备 */
rt_pwm_enable(pwm_dev, PWM_DEV_CHANNEL);
while (1)
{
rt_thread_mdelay(50);
if (dir)
{
pulse += 5000; /* 从0值 开 始 每 次 增 加5000ns */
}
else
{
pulse -= 5000; /* 从 最 大 值 开 始 每 次 减 少5000ns */
}
if (pulse >= period)
{
dir = 0;
}
if (0 == pulse)
{
dir = 1;
}
/* 设 置PWM周 期 和 脉 冲 宽 度 */
rt_pwm_set(pwm_dev, PWM_DEV_CHANNEL, period, pulse);
}
}
/* 导 出 到 msh 命 令 列 表 中 */
MSH_CMD_EXPORT(pwm_led_sample, pwm sample);
运行 pwm_led_sample 指令,观察led 灯运行效果: