STM32上進行Delay延時的方法

1、使用SYStick專門的延時。

void delay_us(uint32_t us)
{
    static uint32_t delay_flag = 0;

    delay_flag = 1;
    /* set reload register HCLK = 48M */
    SysTick->LOAD = (SYSTEM_CORE_CLOCK / 1000000) * us;
    /* Load the SysTick Counter Value */
    SysTick->VAL = 0;
    /* Enable the Systick Timer */
    SysTick->CTRL = SysTick_CTRL_CLKSOURCE_Msk | SysTick_CTRL_ENABLE_Msk;
    /* Systick Timer Timeout*/
    while ((SysTick->CTRL & SysTick_CTRL_COUNTFLAG_Msk) != SysTick_CTRL_COUNTFLAG_Msk)
    {
        /* if(SysTick->CTRL & SysTick_CTRL_ENABLE_Msk) != SysTick_CTRL_ENABLE_Msk) 讀取CTRL進行判斷將會出錯 */
        if(delay_flag == 0)
        {
            /* Tiemr is disabled */
            delay_flag = 1;
            /* Enable the Systick Timer */
            SysTick->CTRL  = SysTick_CTRL_CLKSOURCE_Msk | SysTick_CTRL_ENABLE_Msk;
        }
    }
    /* clear timer */
    SysTick->VAL = 0;     
    /* disable timer */
    SysTick->CTRL = 0;

    
    delay_flag = 0;
}

2、使用定時器LPTIM(其他定時器也可),系統中LPTIM定時器2.5ms產生一次中斷,中斷函數裏主時間進行自增g_SystemRAM.Debug.System_Tick += 25;

uint16_t System_GetCntLp(void)
{
    uint16_t LptimCnt1 = 0;
    uint16_t LptimCnt2 = 0;
    uint8_t Cnt = 0;
    do
    {
        LptimCnt1 = LL_LPTIM_GetCounter(LPTIM1);
        LptimCnt2 = LL_LPTIM_GetCounter(LPTIM1);

        if(LptimCnt1 == LptimCnt2)
        {
            break;
        }
        else
        {
            Cnt ++;
            if(Cnt > 5)
            {
                Cnt = 0;
                break;
            }
            continue;
        }
    }while(1);
    
    return LptimCnt1;

}

uint32_t System_GetTickLp(void) // 單位 100us
{
    float Tick = 0;
    uint16_t Cnt = 0;
    uint32_t Sys_Tick = g_SystemRAM.Debug.System_Tick;

    Cnt = System_GetCntLp() + 1;

    if(Sys_Tick != g_SystemRAM.Debug.System_Tick)
    {
        Sys_Tick = g_SystemRAM.Debug.System_Tick;
        Cnt = System_GetCntLp() + 1;
    }

    Tick = Sys_Tick + 0.3048 * Cnt;

    return (uint32_t)Tick;
}

void System_Delay100Us(uint32_t Time)
{
    /* 只能在主函數中使用,或在中斷優先級小於LPTIM的中斷回調函數中使用 */
    /* 延時等待超過2.5ms時,若是在中斷優先級高於LPTIM的中斷回調函數中使用則將出錯
       (LPTIM中斷 無法響應,主時間無法自增,僅計數器運行)   */
       
    uint32_t Tick = System_GetTickLp();
    
    while((System_GetTickLp() - Tick) < Time);

}

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章