Sou apenas um novato, se houver algum erro, aponte-o.
Índice
1. Diagrama de pinos do temporizador
1. Diagrama de pinos do temporizador
2. Enquadramento geral
Nota: Além das funções de captura de entrada e comparação de saída do temporizador geral, o temporizador avançado também adiciona saída complementar de zona morta programável, contador de repetições e funções de freio (quebra de circuito).Este artigo intercepta apenas a comparação de saída.diagrama de blocos.
Divido a estrutura do temporizador avançado em 4 partes: módulo base de tempo, registro de comparação, gerador de zona morta e controle de saída.
2.1 Módulo base de tempo
Existem 4 fontes de relógio temporizador avançado. Somente a fonte de relógio interno é apresentada aqui.
O quadro da unidade base de tempo é mostrado na figura
Divida isso em 4 partes: 1. Prescaler PSC, que pode atingir a divisão de frequência de 1-65536. 2. Contador CNT: três modos de contagem, modo de contagem crescente, modo de contagem decrescente e modo de contagem ascendente/descendente (alinhado ao centro). 3. Registro de recarga automática ARR e 4. Contador de repetição RCR
O que difere do temporizador básico aqui são os três modos de contagem e o contador de repetições.
Em termos leigos, o loop começa em 0 (ou o valor máximo) e conta para cima (ou para baixo). Quando o valor máximo (ou 0) é atingido, uma interrupção ou evento pode ocorrer. Quando um contador de repetição é usado, um contador específico número de vezes é contado. O número gerará uma interrupção 1 ou evento. A contagem crescente ou decrescente depende do modo de contagem.
Desta vez para emitir a onda PWM, não há necessidade de usar interrupções, apenas sua função de contagem é suficiente.
2.2 Comparar registro
Quando o valor do contador CNT for igual ao valor do registro de comparação CCR, a polaridade do sinal de referência de saída OCxREF mudará, onde OCxREF=1 (nível alto) é chamado de nível efetivo, OCxREF=0 (nível baixo) plano) é chamado de nível inválido.
A saída do sinal aqui é OCxREF.
Antes de entrar no gerador de zona morta, você pode definir o modo de comparação de saída. Para a saída de ondas PWM, existem dois modos para escolher, nomeadamente PWM1 e PWM2.
2.3 Gerador de zona morta
Após passar pelo gerador de zona morta, serão gerados dois sinais complementares com zonas mortas, OCx_DT e OCxN_DT. Se nenhum controle de zona morta for adicionado, o sinal que entra no circuito de controle de saída é diretamente OCxREF.
A onda PWM simples não será apresentada em detalhes aqui.
2.4 Controle de saída
A saída do sinal do gerador de zona morta será dividida em dois canais, um é o sinal original e o outro é o sinal invertido, que é controlado especificamente pelos bits CCxP e CCxNP do registrador CCER. Se o sinal de polaridade selecionada é emitido do pino OCx para o pino externo CHx/CHxN (ou seja, se está habilitado) é configurado pelo bit CxE/CxNE do registro CCER.
3. Estrutura
typedef struct
{
uint16_t TIM_Prescaler; //时钟预分频,对应PSC
uint16_t TIM_CounterMode; //时钟计数模式,对应3中计数方法
uint16_t TIM_Period; //定时器周期,对应ARR寄存器
uint16_t TIM_ClockDivision; //时钟分频,设置定时器时钟 CK_INT 频率与死区发生器以及数字滤
//波器,采样时钟频率分频比。可以选择 1、2、4 分频。
uint8_t TIM_RepetitionCounter; //重复计数器,对应RAR
} TIM_TimeBaseInitTypeDef;
typedef struct
{
uint16_t TIM_OCMode; //输出模式,PWM1及PWM2,对应寄存器CCMR1->OCxM
uint16_t TIM_OutputState; //比较输出使能,对应CCER->CCxE
uint16_t TIM_OutputNState; //比较互补输出使能,对应CCER->CCxNE
uint16_t TIM_Pulse; //脉冲宽度,即比较寄存器的值,对应CCR1
uint16_t TIM_OCPolarity; //输出极性,对应CCER->CCxP
uint16_t TIM_OCNPolarity; //互补输出极性,对应CCER->CCxP
uint16_t TIM_OCIdleState; //空闲状态比较输出状态,对应CR2->OIS1
uint16_t TIM_OCNIdleState; //空闲状态下比较互补输出状态,对应CR2->OIS1N
} TIM_OCInitTypeDef;
Existem duas estruturas principais usadas para configurar o pwm, uma é a estrutura de inicialização da base de tempo, a outra é a estrutura de comparação de saída e a estrutura de inicialização da base de tempo
A estrutura da comparação de saída corresponde ao registro da figura mostrada abaixo
Mas além destas duas estruturas, precisamos também de permitir um registo
Correspondente ao registo BDER->MOE, a introdução oficial é a seguinte
Basta habilitar o pino de saída
4. Programação
Resumindo, os objetivos da programação são:
1. Configure os pinos GPIO do canal
2. Configure as duas estruturas
3. Habilite a fonte do clock e habilite o canal de saída
O programa a seguir configura uma onda PWM com 1Khz e ciclo de trabalho de 40%.
void advance_tim1_gpio_config(void)
{
//1.结构体
GPIO_InitTypeDef GPIO_InitStructure;
//2.开时钟
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE);
//3.配置
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_8;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
//4.初始化
GPIO_Init(GPIOA, &GPIO_InitStructure);
//5.使能(无)
}
void advance_tim1_mode_config()
{
//1.结构体,时基结构体及输出比较结构体
TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure;
TIM_OCInitTypeDef TIM_OCInitStructure;
//2.开时钟,TIM1的时钟
RCC_APB2PeriphClockCmd(RCC_APB2Periph_TIM1, ENABLE);
//3.配置及初始化
/*--------------------时基结构体初始化-------------------------*/
// PWM 信号的频率 F = TIM_CLK/{(ARR+1)*(PSC+1)}
TIM_TimeBaseStructure.TIM_Period = 9; //ARR寄存器的值
TIM_TimeBaseStructure.TIM_Prescaler = 7199; //PSC分频的值
TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up; //向上计数
TIM_TimeBaseStructure.TIM_RepetitionCounter=0; //重复计数器为0
TIM_TimeBaseInit(TIM1, &TIM_TimeBaseStructure);
/*--------------------输出比较结构体初始化-------------------*/
TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM1; //输出模式:PWM1
TIM_OCInitStructure.TIM_OutputState = TIM_OutputState_Enable; //比较输出使能
TIM_OCInitStructure.TIM_Pulse = 4; //设置占空比
TIM_OCInitStructure.TIM_OCPolarity = TIM_OCPolarity_High; //有效电平
TIM_OCInitStructure.TIM_OCIdleState = TIM_OCIdleState_Set; //空闲时比较输出状态
TIM_OC1Init(TIM1, &TIM_OCInitStructure);
//4.使能,此处使能为将内部时钟作为TIM1时钟源的使能
TIM_Cmd(TIM1, ENABLE); //使能计数器
TIM_CtrlPWMOutputs(TIM1, ENABLE); //使能输出通道
}
Nota: O registro ARR e o registro PSC começam a contar a partir de 0, portanto o valor deve ser reduzido em um.
Frequência de onda PWM=TIM_CLK/{(ARR+1)*(PSC+1)}
Entre eles, TIM_CLK é geralmente a frequência do APB2, porque o TIM1 é montado no APB2 e o APB2 geralmente é de 72 MHz.
Ciclo de trabalho=TIM_OCInitStructure.TIM_Pulse/(ARR+1)
Configure pessoalmente a onda PWM, geralmente siga as etapas a seguir
1. Confirme a frequência da onda PWM
2. Confirme a precisão da onda PWM (correspondente ao registro ARR)
3. Confirme o ciclo de trabalho, TIM_OCInitStructure.TIM_Pulse
Além disso, existe uma função que modifica especificamente o ciclo de trabalho (ou seja, modifica o valor de TIM_OCInitStructure.TIM_Pulse).Eu não sabia disso antes, então eu mesmo escrevi um (evite essa armadilha).
void TIM_SetCompare1(TIM_TypeDef* TIMx, uint16_t Compare1);
5.Descrição
Além dos registradores explicados neste artigo, existem também algumas funções de pré-carregamento, como TIM_OC1PreloadConfi();
Espere, esta função corresponde a CCMR->OC1PE, mas não preciso desta função por enquanto, então não vou apresentá-la em detalhes.
A descrição oficial é a seguinte: Além disso, para a unidade base de tempo, existem sombras em certos registros, e os registros de sombra correspondentes não serão introduzidos em detalhes.
Um artigo sobre controle de ondas PWM ESC será publicado posteriormente.
As referências incluem "STM32F10x-Chinese Reference Manual" e "STM32 Library Development Practical Guide - Based on the Wildfire Guide Development Board"