/** * @brief Set TIMx registers to their reset values. * @param TIMx Timer instance * @retval An ErrorStatus enumeration value: * - SUCCESS: TIMx registers are de-initialized * - ERROR: invalid TIMx instance */ ErrorStatus LL_TIM_DeInit(TIM_TypeDef *TIMx) { ErrorStatus result = SUCCESS; /* Check the parameters */ assert_param(IS_TIM_INSTANCE(TIMx)); if (TIMx == TIM2) { LL_APB1_GRP1_ForceReset(LL_APB1_GRP1_PERIPH_TIM2); LL_APB1_GRP1_ReleaseReset(LL_APB1_GRP1_PERIPH_TIM2); } #if defined(TIM3) else if (TIMx == TIM3) { LL_APB1_GRP1_ForceReset(LL_APB1_GRP1_PERIPH_TIM3); LL_APB1_GRP1_ReleaseReset(LL_APB1_GRP1_PERIPH_TIM3); } #endif /* TIM3 */ #if defined(TIM6) else if (TIMx == TIM6) { LL_APB1_GRP1_ForceReset(LL_APB1_GRP1_PERIPH_TIM6); LL_APB1_GRP1_ReleaseReset(LL_APB1_GRP1_PERIPH_TIM6); } #endif /* TIM6 */ #if defined(TIM7) else if (TIMx == TIM7) { LL_APB1_GRP1_ForceReset(LL_APB1_GRP1_PERIPH_TIM7); LL_APB1_GRP1_ReleaseReset(LL_APB1_GRP1_PERIPH_TIM7); } #endif /* TIM7 */ else if (TIMx == TIM21) { LL_APB2_GRP1_ForceReset(LL_APB2_GRP1_PERIPH_TIM21); LL_APB2_GRP1_ReleaseReset(LL_APB2_GRP1_PERIPH_TIM21); } #if defined(TIM22) else if (TIMx == TIM22) { LL_APB2_GRP1_ForceReset(LL_APB2_GRP1_PERIPH_TIM22); LL_APB2_GRP1_ReleaseReset(LL_APB2_GRP1_PERIPH_TIM22); } #endif /* TIM22 */ else { result = ERROR; } return result; }
/** * @brief Configure the TIMx time base unit. * @param TIMx Timer Instance * @param TIM_InitStruct pointer to a @ref LL_TIM_InitTypeDef structure (TIMx time base unit configuration data structure) * @retval An ErrorStatus enumeration value: * - SUCCESS: TIMx registers are de-initialized * - ERROR: not applicable */ ErrorStatus LL_TIM_Init(TIM_TypeDef *TIMx, LL_TIM_InitTypeDef *TIM_InitStruct) { uint32_t tmpcr1 = 0U; /* Check the parameters */ assert_param(IS_TIM_INSTANCE(TIMx)); assert_param(IS_LL_TIM_COUNTERMODE(TIM_InitStruct->CounterMode)); assert_param(IS_LL_TIM_CLOCKDIVISION(TIM_InitStruct->ClockDivision)); tmpcr1 = LL_TIM_ReadReg(TIMx, CR1); if (IS_TIM_COUNTER_MODE_SELECT_INSTANCE(TIMx)) { /* Select the Counter Mode */ MODIFY_REG(tmpcr1, (TIM_CR1_DIR | TIM_CR1_CMS), TIM_InitStruct->CounterMode); } if (IS_TIM_CLOCK_DIVISION_INSTANCE(TIMx)) { /* Set the clock division */ MODIFY_REG(tmpcr1, TIM_CR1_CKD, TIM_InitStruct->ClockDivision); } /* Write to TIMx CR1 */ LL_TIM_WriteReg(TIMx, CR1, tmpcr1); /* Set the Autoreload value */ LL_TIM_SetAutoReload(TIMx, TIM_InitStruct->Autoreload); /* Set the Prescaler value */ LL_TIM_SetPrescaler(TIMx, TIM_InitStruct->Prescaler); if (IS_TIM_REPETITION_COUNTER_INSTANCE(TIMx)) { /* Set the Repetition Counter value */ LL_TIM_SetRepetitionCounter(TIMx, TIM_InitStruct->RepetitionCounter); } /* Generate an update event to reload the Prescaler and the repetition counter value (if applicable) immediately */ LL_TIM_GenerateEvent_UPDATE(TIMx); return SUCCESS; }
/* * Set the period and pulse width for a PWM pin. * * Parameters * dev: Pointer to PWM device structure * pwm: PWM channel to set * period_cycles: Period (in timer count) * pulse_cycles: Pulse width (in timer count). * * return 0, or negative errno code */ static int pwm_stm32_pin_set(struct device *dev, u32_t pwm, u32_t period_cycles, u32_t pulse_cycles) { struct pwm_stm32_data *data = DEV_DATA(dev); TIM_HandleTypeDef *TimerHandle = &data->hpwm; TIM_OC_InitTypeDef sConfig; u32_t channel; bool counter_32b; if (period_cycles == 0 || pulse_cycles > period_cycles) { return -EINVAL; } /* configure channel */ channel = (pwm - 1)*CHANNEL_LENGTH; if (!IS_TIM_INSTANCE(PWM_STRUCT(dev)) || !IS_TIM_CHANNELS(channel)) { return -ENOTSUP; } #ifdef CONFIG_SOC_SERIES_STM32F1X /* FIXME: IS_TIM_32B_COUNTER_INSTANCE not available on * SMT32F1 Cube HAL since all timer counters are 16 bits */ counter_32b = 0; #else counter_32b = IS_TIM_32B_COUNTER_INSTANCE(PWM_STRUCT(dev)); #endif /* * The timer counts from 0 up to the value in the ARR register (16-bit). * Thus period_cycles cannot be greater than UINT16_MAX + 1. */ if (!counter_32b && (period_cycles > 0x10000)) { /* 16 bits counter does not support requested period * You might want to adapt PWM output clock to adjust * cycle durations to fit requested period into 16 bits * counter */ return -ENOTSUP; } /* Configure Timer IP */ TimerHandle->Instance = PWM_STRUCT(dev); TimerHandle->Init.Prescaler = data->pwm_prescaler; TimerHandle->Init.ClockDivision = 0; TimerHandle->Init.CounterMode = TIM_COUNTERMODE_UP; TimerHandle->Init.RepetitionCounter = 0; /* Set period value */ TimerHandle->Init.Period = period_cycles - 1; HAL_TIM_PWM_Init(TimerHandle); /* Configure PWM channel */ sConfig.OCMode = TIM_OCMODE_PWM1; sConfig.OCPolarity = TIM_OCPOLARITY_HIGH; sConfig.OCFastMode = TIM_OCFAST_DISABLE; sConfig.OCNPolarity = TIM_OCNPOLARITY_HIGH; sConfig.OCNIdleState = TIM_OCNIDLESTATE_RESET; sConfig.OCIdleState = TIM_OCIDLESTATE_RESET; /* Set the pulse value */ sConfig.Pulse = pulse_cycles; HAL_TIM_PWM_ConfigChannel(TimerHandle, &sConfig, channel); return HAL_TIM_PWM_Start(TimerHandle, channel); }