stm32 6 step pwm信号生成

对于上升计数,Update刚刚发生时,CNT<CCRx
对于下降计数,Update刚刚发生时,CNT>CCRx


STM32 高级定时器 6-step PWM generation

0推荐

6-step PWM generation

When complementary outputs are used on a channel, preload bits are available on the OCxM, CCxE and CCxNE bits. The preload bits are transferred to the shadow bits at the COM commutation event. Thus you can program in advance the configuration for the next step and change the configuration of all the channels at the same time. COM can be generated by software by setting the COM bit in the TIMx_EGR register or by hardware (on TRGI rising edge).
A flag is set when the COM event occurs (COMIF bit in the TIMx_SR register), which can generate an interrupt (if the COMIE bit is set in the TIMx_DIER register) or a DMA request(if the COMDE bit is set in the TIMx_DIER register).

@file    TIM/6Steps/main.c

TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure;
TIM_OCInitTypeDef TIM_OCInitStructure;
TIM_BDTRInitTypeDef TIM_BDTRInitStructure;
uint16_t CCR1_Val = 32767;
uint16_t CCR2_Val = 24575;
uint16_t CCR3_Val = 16383;
uint16_t CCR4_Val = 8191;

/* Private function prototypes -----------------------------------------------*/
void RCC_Configuration(void);
void GPIO_Configuration(void);
void SysTick_Configuration(void);
void NVIC_Configuration(void);

/* Private functions ---------------------------------------------------------*/

/**
* @brief   Main program
* @param None
* @retval None
*/
int main(void)
{
/*!< At this stage the microcontroller clock setting is already configured,
       this is done through SystemInit() function which is called from startup
       file (startup_stm32f10x_xx.s) before to branch to application main.
       To reconfigure the default setting of SystemInit() function, refer to
       system_stm32f10x.c file
     */    
          
/* System Clocks Configuration */
RCC_Configuration();

/* NVIC Configuration */
NVIC_Configuration();

/* GPIO Configuration */
GPIO_Configuration();

/* SysTick Configuration */
SysTick_Configuration();

/*-----------------------------------------------------------------------------
The STM32F10x TIM1 peripheral offers the possibility to program in advance the
configuration for the next TIM1 outputs behaviour (step) and change the configuration of all the channels at the same time. This operation is possible when the COM (commutation) event is used.
The COM event can be generated by software by setting the COM bit in the TIM1_EGR register or by hardware (on TRC rising edge).
In this example, a software COM event is generated each 100 ms: using the Systick interrupt.
The TIM1 is configured in Timing Mode, each time a COM event occurs,
a new TIM1 configuration will be set in advance.
The following Table describes the TIM1 Channels states:
              -----------------------------------------------
             | Step1 | Step2 | Step3 | Step4 | Step5 | Step6 |
   ----------------------------------------------------------
|Channel1 |   1   |   0   |   0   |   0   |   0   |   1   |
   ----------------------------------------------------------
|Channel1N |   0   |   0   |   1   |   1   |   0   |   0   |
   ----------------------------------------------------------
   |Channel2 |   0   |   0   |   0   |   1   |   1   |   0   |
   ----------------------------------------------------------
|Channel2N |   1   |   1   |   0   |   0   |   0   |   0   |
   ----------------------------------------------------------
   |Channel3 |   0   |   1   |   1   |   0   |   0   |   0   |
   ----------------------------------------------------------
|Channel3N |   0   |   0   |   0   |   0   |   1   |   1   |
   ----------------------------------------------------------
-----------------------------------------------------------------------------*/

/* Time Base configuration */
TIM_TimeBaseStructure.TIM_Prescaler = 0;
TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up;
//Specifies the period value to be loaded into the active
//Auto-Reload Register at the next update event.
TIM_TimeBaseStructure.TIM_Period = 4095;
TIM_TimeBaseStructure.TIM_ClockDivision = 0; //Specifies the clock division.
TIM_TimeBaseStructure.TIM_RepetitionCounter = 0;

TIM_TimeBaseInit(TIM1, &TIM_TimeBaseStructure);

/* Channel 1, 2,3 and 4 Configuration in PWM mode */
TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_Timing;
TIM_OCInitStructure.TIM_OutputState = TIM_OutputState_Enable;
TIM_OCInitStructure.TIM_OutputNState = TIM_OutputNState_Enable;
//Specifies the pulse value to be loaded into the Capture Compare Register.
TIM_OCInitStructure.TIM_Pulse = 2047;
TIM_OCInitStructure.TIM_OCPolarity = TIM_OCPolarity_High;
TIM_OCInitStructure.TIM_OCNPolarity = TIM_OCNPolarity_High;
TIM_OCInitStructure.TIM_OCIdleState = TIM_OCIdleState_Set;
TIM_OCInitStructure.TIM_OCNIdleState = TIM_OCNIdleState_Set;

TIM_OC1Init(TIM1, &TIM_OCInitStructure);

TIM_OCInitStructure.TIM_Pulse = 1023;
TIM_OC2Init(TIM1, &TIM_OCInitStructure);

TIM_OCInitStructure.TIM_Pulse = 511;
TIM_OC3Init(TIM1, &TIM_OCInitStructure);

/* Automatic Output enable, Break, dead time and lock configuration*/
TIM_BDTRInitStructure.TIM_OSSRState = TIM_OSSRState_Enable; //运行模式下“关闭状态”选择 (Off-state selection for Run mode)
TIM_BDTRInitStructure.TIM_OSSIState = TIM_OSSIState_Enable;
TIM_BDTRInitStructure.TIM_LOCKLevel = TIM_LOCKLevel_OFF;
TIM_BDTRInitStructure.TIM_DeadTime = 1;
TIM_BDTRInitStructure.TIM_Break = TIM_Break_Enable;
TIM_BDTRInitStructure.TIM_BreakPolarity = TIM_BreakPolarity_High;   //刹车输入极性 (Break polarity)
TIM_BDTRInitStructure.TIM_AutomaticOutput = TIM_AutomaticOutput_Enable;//1:MOE(主输出使能)能被软件置’1’或在下一个更新事件被自动置’1’(如果刹车输入无效)。

TIM_BDTRConfig(TIM1, &TIM_BDTRInitStructure);

TIM_CCPreloadControl(TIM1, ENABLE);

TIM_ITConfig(TIM1, TIM_IT_COM, ENABLE);

/* TIM1 counter enable */
TIM_Cmd(TIM1, ENABLE);

/* Main Output Enable */
TIM_CtrlPWMOutputs(TIM1, ENABLE);

while (1)
{}
}

@file    TIM/6Steps/stm32f10x_it.c

/**
* @brief This function handles SysTick Handler.
* @param None
* @retval None
*/
void SysTick_Handler(void)
{
/* Generate TIM1 COM event by software */
TIM_GenerateEvent(TIM1, TIM_EventSource_COM);
}

/******************************************************************************/
/*            STM32F10x Peripherals Interrupt Handlers                        */
/******************************************************************************/

/**
* @brief This function handles TIM1 Trigger and commutation interrupts
*   requests.
* @param None
* @retval None
*/
#if defined (STM32F10X_LD_VL) || defined (STM32F10X_MD_VL)
void TIM1_TRG_COM_TIM17_IRQHandler(void)
#else
void TIM1_TRG_COM_IRQHandler(void)
#endif
{
   /* Clear TIM1 COM pending bit */
   TIM_ClearITPendingBit(TIM1, TIM_IT_COM);

if (step == 1)
{
    /* Next step: Step 2 Configuration ---------------------------- */
    /* Channel3 configuration */
    TIM_CCxCmd(TIM1, TIM_Channel_3, TIM_CCx_Disable);
    TIM_CCxNCmd(TIM1, TIM_Channel_3, TIM_CCxN_Disable);

    /* Channel1 configuration */
    TIM_SelectOCxM(TIM1, TIM_Channel_1, TIM_OCMode_PWM1);
    TIM_CCxCmd(TIM1, TIM_Channel_1, TIM_CCx_Enable);
    TIM_CCxNCmd(TIM1, TIM_Channel_1, TIM_CCxN_Disable);

    /* Channel2 configuration */
    TIM_SelectOCxM(TIM1, TIM_Channel_2, TIM_OCMode_PWM1 );
    TIM_CCxCmd(TIM1, TIM_Channel_2, TIM_CCx_Disable);
    TIM_CCxNCmd(TIM1, TIM_Channel_2, TIM_CCxN_Enable);
    step++;
}
else if (step == 2)
{
    /* Next step: Step 3 Configuration ---------------------------- */
    /* Channel2 configuration */
    TIM_SelectOCxM(TIM1, TIM_Channel_2, TIM_OCMode_PWM1);
    TIM_CCxCmd(TIM1, TIM_Channel_2, TIM_CCx_Disable);
    TIM_CCxNCmd(TIM1, TIM_Channel_2, TIM_CCxN_Enable);
   
    /* Channel3 configuration */
    TIM_SelectOCxM(TIM1, TIM_Channel_3, TIM_OCMode_PWM1);
    TIM_CCxCmd(TIM1, TIM_Channel_3, TIM_CCx_Enable);
     TIM_CCxNCmd(TIM1, TIM_Channel_3, TIM_CCxN_Disable);

    /* Channel1 configuration */
    TIM_CCxCmd(TIM1, TIM_Channel_1, TIM_CCx_Disable);
    TIM_CCxNCmd(TIM1, TIM_Channel_1, TIM_CCxN_Disable);
    step++;
}
else if (step == 3)
{
    /* Next step: Step 4 Configuration ---------------------------- */
    /* Channel3 configuration */
    TIM_SelectOCxM(TIM1, TIM_Channel_3, TIM_OCMode_PWM1);
    TIM_CCxCmd(TIM1, TIM_Channel_3, TIM_CCx_Enable);
    TIM_CCxNCmd(TIM1, TIM_Channel_3, TIM_CCxN_Disable);

    /* Channel2 configuration */
    TIM_CCxCmd(TIM1, TIM_Channel_2, TIM_CCx_Disable);
    TIM_CCxNCmd(TIM1, TIM_Channel_2, TIM_CCxN_Disable);

    /* Channel1 configuration */
    TIM_SelectOCxM(TIM1, TIM_Channel_1, TIM_OCMode_PWM1);
    TIM_CCxCmd(TIM1, TIM_Channel_1, TIM_CCx_Disable);
    TIM_CCxNCmd(TIM1, TIM_Channel_1, TIM_CCxN_Enable);
    step++;
}
else if (step == 4)
{
    /* Next step: Step 5 Configuration ---------------------------- */
    /* Channel3 configuration */
    TIM_CCxCmd(TIM1, TIM_Channel_3, TIM_CCx_Disable);
    TIM_CCxNCmd(TIM1, TIM_Channel_3, TIM_CCxN_Disable);

    /* Channel1 configuration */
    TIM_SelectOCxM(TIM1, TIM_Channel_1, TIM_OCMode_PWM1);
    TIM_CCxCmd(TIM1, TIM_Channel_1, TIM_CCx_Disable);
    TIM_CCxNCmd(TIM1, TIM_Channel_1, TIM_CCxN_Enable);

    /* Channel2 configuration */
    TIM_SelectOCxM(TIM1, TIM_Channel_2, TIM_OCMode_PWM1);
    TIM_CCxCmd(TIM1, TIM_Channel_2, TIM_CCx_Enable);
    TIM_CCxNCmd(TIM1, TIM_Channel_2, TIM_CCxN_Disable);
    step++;
}
else if (step == 5)
{
   /* Next step: Step 6 Configuration ---------------------------- */
    /* Channel3 configuration */
    TIM_SelectOCxM(TIM1, TIM_Channel_3, TIM_OCMode_PWM1);
    TIM_CCxCmd(TIM1, TIM_Channel_3, TIM_CCx_Disable);
    TIM_CCxNCmd(TIM1, TIM_Channel_3, TIM_CCxN_Enable);

   /* Channel1 configuration */
    TIM_CCxCmd(TIM1, TIM_Channel_1, TIM_CCx_Disable);
    TIM_CCxNCmd(TIM1, TIM_Channel_1, TIM_CCxN_Disable);

    /* Channel2 configuration */
    TIM_SelectOCxM(TIM1, TIM_Channel_2, TIM_OCMode_PWM1);
    TIM_CCxCmd(TIM1, TIM_Channel_2, TIM_CCx_Enable);
    TIM_CCxNCmd(TIM1, TIM_Channel_2, TIM_CCxN_Disable);
    step++;
}
else
{
    /* Next step: Step 1 Configuration ---------------------------- */
    /* Channel1 configuration */
    TIM_SelectOCxM(TIM1, TIM_Channel_1, TIM_OCMode_PWM1);
    TIM_CCxCmd(TIM1, TIM_Channel_1, TIM_CCx_Enable);
    TIM_CCxNCmd(TIM1, TIM_Channel_2, TIM_CCxN_Disable);

    /* Channel3 configuration */
    TIM_SelectOCxM(TIM1, TIM_Channel_3, TIM_OCMode_PWM1);
    TIM_CCxCmd(TIM1, TIM_Channel_3, TIM_CCx_Disable);
    TIM_CCxNCmd(TIM1, TIM_Channel_3, TIM_CCxN_Enable);

    /* Channel2 configuration */
    TIM_CCxCmd(TIM1, TIM_Channel_2, TIM_CCx_Disable);
    TIM_CCxNCmd(TIM1, TIM_Channel_2, TIM_CCxN_Disable);
    step = 1;
}
}

stm32对于三相电机控制的特点

电机控制
STM32增强型系列内嵌非常适合三相无刷电机控制的定时器和ADC,其高级PWM定时器提供:
■   6路PWM输出;
■   死区产生;
■   边沿对齐和中心对齐波形;
■   紧急故障停机,可与2路ADC同步及与其它定时器同步;
■   可编程的防范机制可以用于防止对寄存器的非法写入;
■   编码器输入接口;
■ 霍尔传感器接口;
■ 完整的矢量控制环:无传感器模式下为21us
双ADC结构允许双通道采样/保持,以实现12位精度、1 ms的转化。此双ADC结构为2个工作在非连续模式的独立的时序控制,具有多个触发源,并且每个通道的采样时间可编程。以上专门的外围电路与高性能 Cotex-M3内核的结合,可使完整的矢量控制环软件执行时间缩短为21 ms(无传感器模式、3相PMSM马达)。当电流采样频率为10 kHz时,CPU的工作负载低于25%,STM32可以执行应用中电机控制之外的其它任务。


感觉老外的代码就是清楚。

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值