示例#1
0
void us_ticker_set_interrupt(timestamp_t timestamp)
{
    /* Clear any previously pending interrupts */
    us_ticker_clear_interrupt();
    NVIC_ClearPendingIRQ(TIMER_MODINIT.irq_n);

    /* In continuous mode, counter will be reset to zero with the following sequence: 
     * 1. Stop counting
     * 2. Configure new CMP value
     * 3. Restart counting
     *
     * This behavior is not what we want. To fix it, we could configure new CMP value
     * without stopping counting first.
     */
    TIMER_T *timer_base = (TIMER_T *) NU_MODBASE(TIMER_MODINIT.modname);

    /* NOTE: Because H/W timer requests min compare value, our implementation would have alarm delay of 
     *       (TMR_CMP_MIN - interval_clk) clocks when interval_clk is between [1, TMR_CMP_MIN). */
    uint32_t cmp_timer = timestamp * NU_TMRCLK_PER_TICK;
    cmp_timer = NU_CLAMP(cmp_timer, TMR_CMP_MIN, TMR_CMP_MAX);
    timer_base->CMP = cmp_timer;

    /* We can call ticker_irq_handler now. */
    NVIC_EnableIRQ(TIMER_MODINIT.irq_n);
}
示例#2
0
static void lp_ticker_arm_cd(void)
{
    TIMER_T * timer3_base = (TIMER_T *) NU_MODBASE(timer3_modinit.modname);

    // Reset 8-bit PSC counter, 24-bit up counter value and CNTEN bit
    // NUC472/M451: See TIMER_CTL_RSTCNT_Msk
    // M480
    timer3_base->CNT = 0;
    while (timer3_base->CNT & TIMER_CNT_RSTACT_Msk);
    // One-shot mode, Clock = 1 KHz
    uint32_t clk_timer3 = TIMER_GetModuleClock((TIMER_T *) NU_MODBASE(timer3_modinit.modname));
    uint32_t prescale_timer3 = clk_timer3 / TMR3_CLK_PER_SEC - 1;
    MBED_ASSERT((prescale_timer3 != (uint32_t) -1) && prescale_timer3 <= 127);
    MBED_ASSERT((clk_timer3 % TMR3_CLK_PER_SEC) == 0);
    // NOTE: TIMER_CTL_CNTDATEN_Msk exists in NUC472, but not in M451/M480. In M451/M480, TIMER_CNT is updated continuously by default.
    timer3_base->CTL &= ~(TIMER_CTL_OPMODE_Msk | TIMER_CTL_PSC_Msk/* | TIMER_CTL_CNTDATEN_Msk*/);
    timer3_base->CTL |= TIMER_ONESHOT_MODE | prescale_timer3/* | TIMER_CTL_CNTDATEN_Msk*/;

    cd_minor_clks = cd_major_minor_clks;
    cd_minor_clks = NU_CLAMP(cd_minor_clks, TMR_CMP_MIN, TMR_CMP_MAX);
    timer3_base->CMP = cd_minor_clks;

    TIMER_EnableInt(timer3_base);
    TIMER_EnableWakeup((TIMER_T *) NU_MODBASE(timer3_modinit.modname));
    TIMER_Start(timer3_base);
}
示例#3
0
static void lp_ticker_arm_cd(void)
{
    TIMER_T * timer3_base = (TIMER_T *) NU_MODBASE(timer3_modinit.modname);
    
    // Reset 8-bit PSC counter, 24-bit up counter value and CNTEN bit
    timer3_base->CTL |= TIMER_CTL_RSTCNT_Msk;
    // One-shot mode, Clock = 1 KHz 
    uint32_t clk_timer3 = TIMER_GetModuleClock((TIMER_T *) NU_MODBASE(timer3_modinit.modname));
    uint32_t prescale_timer3 = clk_timer3 / TMR3_CLK_FREQ - 1;
    MBED_ASSERT((prescale_timer3 != (uint32_t) -1) && prescale_timer3 <= 127);
    timer3_base->CTL &= ~(TIMER_CTL_OPMODE_Msk | TIMER_CTL_PSC_Msk | TIMER_CTL_CNTDATEN_Msk);
    timer3_base->CTL |= TIMER_ONESHOT_MODE | prescale_timer3 | TIMER_CTL_CNTDATEN_Msk;
    
    cd_minor_ms = cd_major_minor_ms;
    cd_minor_ms = NU_CLAMP(cd_minor_ms, TMR_CMP_MIN * MS_PER_TMR3_CLK, TMR_CMP_MAX * MS_PER_TMR3_CLK);
    timer3_base->CMP = cd_minor_ms / MS_PER_TMR3_CLK;
    
    TIMER_EnableInt(timer3_base);
    TIMER_EnableWakeup((TIMER_T *) NU_MODBASE(timer3_modinit.modname));
    TIMER_Start(timer3_base);
}
示例#4
0
static void us_ticker_arm_cd(void)
{
    TIMER_T * timer1_base = (TIMER_T *) NU_MODBASE(timer1hires_modinit.modname);
    
    cd_minor_us = cd_major_minor_us;

    // Reset 8-bit PSC counter, 24-bit up counter value and CNTEN bit
    timer1_base->CTL |= TIMER_CTL_RSTCNT_Msk;
    // One-shot mode, Clock = 1 MHz 
    uint32_t clk_timer1 = TIMER_GetModuleClock((TIMER_T *) NU_MODBASE(timer1hires_modinit.modname));
    uint32_t prescale_timer1 = clk_timer1 / TMR1HIRES_CLK_PER_SEC - 1;
    MBED_ASSERT((prescale_timer1 != (uint32_t) -1) && prescale_timer1 <= 127);
    MBED_ASSERT((clk_timer1 % TMR1HIRES_CLK_PER_SEC) == 0);
    // NOTE: TIMER_CTL_CNTDATEN_Msk exists in NUC472, but not in M451. In M451, TIMER_CNT is updated continuously by default.
    timer1_base->CTL &= ~(TIMER_CTL_OPMODE_Msk | TIMER_CTL_PSC_Msk/* | TIMER_CTL_CNTDATEN_Msk*/);
    timer1_base->CTL |= TIMER_ONESHOT_MODE | prescale_timer1/* | TIMER_CTL_CNTDATEN_Msk*/;
    
    uint32_t cmp_timer1 = cd_minor_us / US_PER_TMR1HIRES_CLK;
    cmp_timer1 = NU_CLAMP(cmp_timer1, TMR_CMP_MIN, TMR_CMP_MAX);
    timer1_base->CMP = cmp_timer1;
    
    TIMER_EnableInt(timer1_base);
    TIMER_Start(timer1_base);
}