From ad8f28cf04d7d05aff385d915514171734f02e4b Mon Sep 17 00:00:00 2001 From: Fabiano Riccardi <fabiuz4@hotmail.it> Date: Tue, 18 Oct 2016 15:45:21 +0200 Subject: [PATCH] Now GPIOtimer is working but for output compare it call interrupt every 1.3ms Signed-off-by: Fabiano Riccardi <fabiuz4@hotmail.it> --- .../high_resolution_timer_base.cpp | 89 ++++++++----------- 1 file changed, 36 insertions(+), 53 deletions(-) diff --git a/miosix/arch/cortexM3_efm32gg/efm32gg332f1024_wandstem/interfaces-impl/high_resolution_timer_base.cpp b/miosix/arch/cortexM3_efm32gg/efm32gg332f1024_wandstem/interfaces-impl/high_resolution_timer_base.cpp index 751ef222..6229f945 100644 --- a/miosix/arch/cortexM3_efm32gg/efm32gg332f1024_wandstem/interfaces-impl/high_resolution_timer_base.cpp +++ b/miosix/arch/cortexM3_efm32gg/efm32gg332f1024_wandstem/interfaces-impl/high_resolution_timer_base.cpp @@ -49,10 +49,6 @@ static inline long long IRQgetTick(){ } inline void interruptGPIOTimerRoutine(){ - TIMER1->IEN &= ~TIMER_IEN_CC2; - TIMER3->IEN &= ~TIMER_IEN_CC2; - TIMER1->IFC = TIMER_IFC_CC2; - TIMER3->IFC = TIMER_IFC_CC2; if(TIMER1->CC[2].CTRL & TIMER_CC_CTRL_MODE_OUTPUTCOMPARE){ //keep high for at least x Us delayUs(1); @@ -106,32 +102,25 @@ static void setupTimers(){ /* Return EVENT if the timer triggers in this routine, otherwise the timer is set and returns WAITING */ +static int fase=0; + static WaitResult setupTimers2(){ + TIMER1->IEN |= TIMER_IEN_CC2; + fase=0; // We assume that this function is called only when the checkpoint is in future - if (ms32chkp[2] == ms32time){ - // If the most significant 32bit matches, enable TIM3 - TIMER3->IFC = TIMER_IFC_CC2; - TIMER3->IEN |= TIMER_IEN_CC2; - unsigned short temp=static_cast<unsigned short>(TIMER3->CC[2].CCV) + 1; - if (static_cast<unsigned short>(TIMER3->CNT) >= temp){ - TIMER1->CC[2].CTRL = (TIMER1->CC[2].CTRL & ~_TIMER_CC_CTRL_CMOA_MASK) | TIMER_CC_CTRL_CMOA_SET; - // If TIM3 matches by the time it is being enabled, disable it right away - TIMER3->IFC = TIMER_IFC_CC2; - TIMER3->IEN &= ~TIMER_IEN_CC2; - // Enable TIM1 since TIM3 has been already matched - TIMER1->IFC = TIMER_IFC_CC2; - TIMER1->IEN |= TIMER_IEN_CC2; - if (TIMER1->CNT >= TIMER1->CC[2].CCV){ - //This line introduce a delay of 10ticks... it should be revised - TIMER1->CC[2].CCV = static_cast<unsigned int>(10+TIMER1->CNT); - // If TIM1 matches by the time it is being enabled, call the scheduler right away - interruptGPIOTimerRoutine(); - return WaitResult::EVENT; - } - } + if ((ms32chkp[2] == ms32time && static_cast<unsigned short>(TIMER3->CC[2].CCV+1)==TIMER3->CNT && TIMER1->CNT >= TIMER1->CC[2].CCV ) + || IRQgetTick()>=HighResolutionTimerBase::instance().IRQgetSetTimeCCV2()){ + // Enable TIM1 since TIM3 has been already matched + TIMER1->CC[2].CTRL = (TIMER1->CC[2].CTRL & ~_TIMER_CC_CTRL_CMOA_MASK) | TIMER_CC_CTRL_CMOA_SET; + //This line introduce a delay of 10ticks... it should be revised + TIMER1->CC[2].CCV = static_cast<unsigned short>(10+TIMER1->CNT); + TIMER1->IFC = TIMER_IFC_CC2; + TIMER1->IEN &= ~TIMER_IEN_CC2; + // If TIM1 matches by the time it is being enabled, call the routine right away + interruptGPIOTimerRoutine(); + return WaitResult::EVENT; } return WaitResult::WAITING; - // If the most significant 32bit aren't match wait for TIM3 to overflow! } @@ -156,7 +145,6 @@ void __attribute__((used)) cstirqhnd3(){ TIMER3->IFC = TIMER_IFC_OF; ms32time += overflowIncrement; setupTimers(); - setupTimers2(); } //Checkpoint if ((TIMER3->IEN & TIMER_IEN_CC1) && (TIMER3->IF & TIMER_IF_CC1)){ @@ -175,38 +163,33 @@ void __attribute__((used)) cstirqhnd3(){ } } } - - //This if is to manage the GPIOtimer in OUTPUT Mode - if ((TIMER3->IEN & TIMER_IEN_CC2) && (TIMER3->IF & TIMER_IF_CC2)){ - TIMER3->IFC = TIMER_IFC_CC2; - unsigned short temp=static_cast<unsigned short>(TIMER3->CC[2].CCV) + 1; - if (static_cast<unsigned short>(TIMER3->CNT) >= temp){ - //Set the mode to raise the pin - TIMER1->CC[2].CTRL = (TIMER1->CC[2].CTRL & ~_TIMER_CC_CTRL_CMOA_MASK) | TIMER_CC_CTRL_CMOA_SET; - // Should happen if and only if most significant 32 bits have been matched - TIMER3->IEN &= ~ TIMER_IEN_CC2; - // Enable TIM1 since TIM3 has been already matched - TIMER1->IFC = TIMER_IFC_CC2; - TIMER1->IEN |= TIMER_IEN_CC2; - if (TIMER1->CNT >= TIMER1->CC[2].CCV){ - //This line introduce a delay of 10ticks... it should be revised - TIMER1->CC[2].CCV = static_cast<unsigned int>(10+TIMER1->CNT); - // If TIM1 matches by the time it is being enabled, call the scheduler right away - interruptGPIOTimerRoutine(); - } - } - } } void __attribute__((used)) cstirqhnd1(){ if ((TIMER1->IEN & TIMER_IEN_CC1) && (TIMER1->IF & TIMER_IF_CC1)){ TIMER1->IFC = TIMER_IFC_CC1; - // Should happen if and only if most significant 48 bits have been matched - callScheduler(); + callScheduler(); } //This if is used to manage the case of GPIOTimer, both INPUT and OUTPUT mode if ((TIMER1->IEN & TIMER_IEN_CC2) && (TIMER1->IF & TIMER_IF_CC2)){ - interruptGPIOTimerRoutine(); + TIMER1->IFC = TIMER_IFC_CC2; + if(fase==0 && + ((ms32chkp[2] == ms32time && TIMER3->CNT>=TIMER3->CC[2].CCV )) + ){ + fase=1; + TIMER1->CC[2].CTRL = (TIMER1->CC[2].CTRL & ~_TIMER_CC_CTRL_CMOA_MASK) | TIMER_CC_CTRL_CMOA_SET; + return; + } + if(TIMER3->CNT==0xFFFF) + if(fase==0 && TIMER3->CNT==0xFFFF && ms32chkp[2] == (ms32time+(1LLU<<timerBits)) && TIMER3->CNT==TIMER3->CC[2].CCV){ + fase=1; + TIMER1->CC[2].CTRL = (TIMER1->CC[2].CTRL & ~_TIMER_CC_CTRL_CMOA_MASK) | TIMER_CC_CTRL_CMOA_SET; + return; + } + if(fase==1){ + TIMER1->IEN &= ~TIMER_IEN_CC2; + interruptGPIOTimerRoutine(); + } } } @@ -363,9 +346,9 @@ WaitResult HighResolutionTimerBase::IRQsetNextInterrupt2(long long tick){ long long curTick = IRQgetTick(); if(curTick >= tick){ // The interrupt is in the past => call timerInt immediately - interruptGPIOTimerRoutine(); //TODO: It could cause multiple invocations of sched. + interruptGPIOTimerRoutine(); return WaitResult::WAKEUP_IN_THE_PAST; - }else{ + }else{ ms32chkp[2] = tick & upperMask; TIMER3->CC[2].CCV = static_cast<unsigned int>((tick & 0xFFFF0000)>>16)-1; TIMER1->CC[2].CCV = static_cast<unsigned int>(tick & 0xFFFF); -- GitLab