设置 | 登录 | 注册

目前共有4篇帖子。

【驗證性實驗】TIM1定時器死區時間(dead-time)的加入及檢測

1楼 巨大八爪鱼 2017-1-10 17:53
【程序】
#include <stm32f10x.h>

#define _BV(n) (1 << (n))

uint8_t i = 0;
uint8_t seg8[] = {0xc0, 0xf9, 0xa4, 0xb0, 0x99, 0x92, 0x82, 0xf8, 0x80, 0x90};

void delay(void)
{
    uint32_t i;
    for (i = 0; i < 20000; i++);
}

void SerIn(uint8_t data)
{
    uint8_t i;
    for (i = 0; i < 8; i++)
    {
        GPIOC->BRR = _BV(15);
        if (data & 0x80)
            GPIOA->BSRR = _BV(0);
        else
            GPIOA->BRR = _BV(0);
        GPIOC->BSRR = _BV(15);
        data <<= 1;
    }
}

void ParOut(void)
{
    GPIOC->BRR = _BV(14);
    GPIOC->BSRR = _BV(14);
}

int main(void)
{
    // OC1輸出端PA8用杜邦線接PA15, OC1N互補輸出端PB13接PC13
    // 同時PC13上有一個低電平點亮的LED指示燈
    RCC->APB2ENR = _BV(2) | _BV(3) | _BV(4) | _BV(11); // 開啟PA、PB、PC和TIM1時鐘, 不需要開啟AFIO的時鐘
    GPIOA->CRH = 0x8000000b; // PA15設為帶下拉的輸入, PA8設為復用50MHz推輓輸出
    GPIOA->CRL = 0x00000003; // PA0設為50MHz推輓輸出
    GPIOB->CRH = 0x00b00000; // PB13設為復用50MHz推輓輸出
    GPIOC->CRH = 0x33800000; // PC13設為帶下拉的輸入, PC14~15設為50MHz推輓輸出

    TIM1->ARR = 5099; // 計數值
    TIM1->PSC = 65535; // 定時器分頻
   
    TIM1->CCR1 = 2000;
    TIM1->CCMR1 = 0x70; // OC1M=111, PWM模式2, 輸出比較匹配時OC1REF信號產生上升沿
    TIM1->BDTR = 0x80ff; // MOE=1, 並添加死區時間, 大約為幾us, 輸出端OC1的dead-time延遲產生在OC1REF信號的上升沿
    // TIM1->BDTR = 0x8000; // 不加死區時間的情況
    TIM1->CCER = 0x05; // CC1NE=1, CC1E=1
   
    // 刷新寄存器
    TIM1->CR1 = 0x204; // CKD=10, URS=1
    TIM1->EGR = 0x01; // UG=1
   
    // 開始計數
    TIM1->CR1 |= _BV(0); // CEN=1
   
    SerIn(seg8[0]);
    SerIn(_BV(0));
    ParOut();
           
    while (1)
    {
        // 如果檢測到OC1、OC1N同時輸出低電平, 則表明有dead-time延遲
        if ((GPIOA->IDR & _BV(15)) == 0 && (GPIOC->IDR & _BV(13)) == 0)
        {
            i++;
            if (i > 9)
                i = 0;
            SerIn(seg8[i]);
            SerIn(_BV(0));
            ParOut();
            while ((GPIOA->IDR & _BV(15)) == 0 && (GPIOC->IDR & _BV(13)) == 0);
        }
    }
}
2楼 巨大八爪鱼 2017-1-10 17:58
【運行結果】
剛開始時LED燈是滅的,數碼管顯示0
之後每當LED由滅變亮(輸出比較匹配),以及LED由亮變滅(定時器歸0並重新開始計時),數碼管的數字都會加1

如果把程序改成不加死區時間,即TIM1->BDTR = 0x8000,那麼理論上數碼管就會一直顯示0。不過程序實際運行時最開始的那段時間有一次數碼管會在LED燈狀態翻轉的時候從0跳到1,但是之後一直保持1,這只能算實驗誤差。
3楼 巨大八爪鱼 2017-1-10 18:13

如圖,加了死區時間後,OC1會在上升沿那裏出現延遲,而OC1N會在下降沿那裏出現延遲。所以一個計數周期內會出現兩次OC1=OC1N=0,使數碼管的值加1。

4楼 巨大八爪鱼 2017-1-10 18:14
如果沒有加入死區時間,那麼理論上OC1的波形就會和OC1REF完全相同,OC1N和OC1完全相反,不會出現OC1=OC1N=0的情況,因此數碼管的值一直不變。

内容转换:

回复帖子
内容:
用户名: 您目前是匿名发表。
验证码:
看不清?换一张
©2010-2025 Purasbar Ver3.0 [手机版] [桌面版]
除非另有声明,本站采用知识共享署名-相同方式共享 3.0 Unported许可协议进行许可。