From b2cf69dbb076bcb9380434d3934e5f3111cf707e Mon Sep 17 00:00:00 2001 From: Rui Azevedo Date: Sun, 7 Jul 2019 10:04:58 +0000 Subject: [PATCH 1/4] allow nRF51 to use up to 6 pwm pins by using also NRF_TIMER2 --- cores/nRF5/wiring_analog_nRF51.c | 101 ++++++++++++++++++++++++------- 1 file changed, 79 insertions(+), 22 deletions(-) diff --git a/cores/nRF5/wiring_analog_nRF51.c b/cores/nRF5/wiring_analog_nRF51.c index f22a8b5d..1542af96 100644 --- a/cores/nRF5/wiring_analog_nRF51.c +++ b/cores/nRF5/wiring_analog_nRF51.c @@ -28,25 +28,37 @@ extern "C" { #endif -#define PWM_COUNT 3 +#define PWM_COUNT 6 #define PIN_FREE 0xffffffff +struct PWMSrc { + NRF_TIMER_Type* timer; + bool used; +}; + +struct PWMSrc srcs[2]={ + {NRF_TIMER1,false}, + {NRF_TIMER2,false} +}; + struct PWMContext { uint32_t pin; uint32_t value; uint32_t channel; uint32_t mask; uint32_t event; + int src; }; static struct PWMContext pwmContext[PWM_COUNT] = { - { PIN_FREE, 0, 1, TIMER_INTENSET_COMPARE1_Msk, 1 }, - { PIN_FREE, 0, 2, TIMER_INTENSET_COMPARE2_Msk, 2 }, - { PIN_FREE, 0, 3, TIMER_INTENSET_COMPARE3_Msk, 3 } + { PIN_FREE, 0, 1, TIMER_INTENSET_COMPARE1_Msk, 1, 0 }, + { PIN_FREE, 0, 2, TIMER_INTENSET_COMPARE2_Msk, 2, 0 }, + { PIN_FREE, 0, 3, TIMER_INTENSET_COMPARE3_Msk, 3, 0 }, + { PIN_FREE, 0, 1, TIMER_INTENSET_COMPARE1_Msk, 1, 1 }, + { PIN_FREE, 0, 2, TIMER_INTENSET_COMPARE2_Msk, 2, 1 }, + { PIN_FREE, 0, 3, TIMER_INTENSET_COMPARE3_Msk, 3, 1 } }; -static int timerEnabled = 0; - static uint32_t adcReference = ADC_CONFIG_REFSEL_SupplyOneThirdPrescaling; static uint32_t adcPrescaling = ADC_CONFIG_INPSEL_AnalogInputOneThirdPrescaling; @@ -217,6 +229,18 @@ uint32_t analogRead( uint32_t ulPin ) return mapResolution(value, resolution, readResolution); } +int getFreePwm() { + for (int i = 0; i < PWM_COUNT; i++) + if (pwmContext[i].pin == PIN_FREE) return i; + return -1; +} + +int getPwmFromPin(uint32_t ulPin) { + for (int i = 0; i < PWM_COUNT; i++) + if (pwmContext[i].pin == ulPin||pwmContext[i].pin==PIN_FREE) return i; + return -1; +} + // Right now, PWM output only works on the pins with // hardware support. These are defined in the appropriate // pins_*.c file. For the rest of the pins, we default @@ -229,24 +253,34 @@ void analogWrite( uint32_t ulPin, uint32_t ulValue ) ulPin = g_ADigitalPinMap[ulPin]; - if (!timerEnabled) { - NVIC_SetPriority(TIMER1_IRQn, 3); - NVIC_ClearPendingIRQ(TIMER1_IRQn); - NVIC_EnableIRQ(TIMER1_IRQn); + int pwm=getPwmFromPin(ulPin); + struct PWMSrc* src=&srcs[pwmContext[pwm].src]; + NRF_TIMER_Type* pwmSrc=src->timer; + + if (!src->used) { - NRF_TIMER1->MODE = (NRF_TIMER1->MODE & ~TIMER_MODE_MODE_Msk) | ((TIMER_MODE_MODE_Timer << TIMER_MODE_MODE_Pos) & TIMER_MODE_MODE_Msk); + if (pwmSrc==NRF_TIMER1) { + NVIC_SetPriority(TIMER1_IRQn, 3); + NVIC_ClearPendingIRQ(TIMER1_IRQn); + NVIC_EnableIRQ(TIMER1_IRQn); + } else if (pwmSrc==NRF_TIMER2) { + NVIC_SetPriority(TIMER2_IRQn, 4); + NVIC_ClearPendingIRQ(TIMER2_IRQn); + NVIC_EnableIRQ(TIMER2_IRQn); + } else return; + src->used = true; - NRF_TIMER1->BITMODE = (NRF_TIMER1->BITMODE & ~TIMER_BITMODE_BITMODE_Msk) | ((TIMER_BITMODE_BITMODE_08Bit << TIMER_BITMODE_BITMODE_Pos) & TIMER_BITMODE_BITMODE_Msk); + pwmSrc->MODE = (pwmSrc->MODE & ~TIMER_MODE_MODE_Msk) | ((TIMER_MODE_MODE_Timer << TIMER_MODE_MODE_Pos) & TIMER_MODE_MODE_Msk); - NRF_TIMER1->PRESCALER = (NRF_TIMER1->PRESCALER & ~TIMER_PRESCALER_PRESCALER_Msk) | ((7 << TIMER_PRESCALER_PRESCALER_Pos) & TIMER_PRESCALER_PRESCALER_Msk); + pwmSrc->BITMODE = (pwmSrc->BITMODE & ~TIMER_BITMODE_BITMODE_Msk) | ((TIMER_BITMODE_BITMODE_08Bit << TIMER_BITMODE_BITMODE_Pos) & TIMER_BITMODE_BITMODE_Msk); - NRF_TIMER1->CC[0] = 0; + pwmSrc->PRESCALER = (pwmSrc->PRESCALER & ~TIMER_PRESCALER_PRESCALER_Msk) | ((7 << TIMER_PRESCALER_PRESCALER_Pos) & TIMER_PRESCALER_PRESCALER_Msk); - NRF_TIMER1->INTENSET = TIMER_INTENSET_COMPARE0_Msk; + pwmSrc->CC[0] = 0; - NRF_TIMER1->TASKS_START = 0x1UL; + pwmSrc->INTENSET = TIMER_INTENSET_COMPARE0_Msk; - timerEnabled = true; + pwmSrc->TASKS_START = 0x1UL; } for (int i = 0; i < PWM_COUNT; i++) { @@ -263,9 +297,9 @@ void analogWrite( uint32_t ulPin, uint32_t ulValue ) pwmContext[i].value = ulValue; - NRF_TIMER1->CC[pwmContext[i].channel] = ulValue; + pwmSrc->CC[pwmContext[i].channel] = ulValue; - NRF_TIMER1->INTENSET = pwmContext[i].mask; + pwmSrc->INTENSET = pwmContext[i].mask; break; } @@ -276,7 +310,7 @@ void TIMER1_IRQHandler(void) { if (NRF_TIMER1->EVENTS_COMPARE[0]) { for (int i = 0; i < PWM_COUNT; i++) { - if (pwmContext[i].pin != PIN_FREE && pwmContext[i].value != 0) { + if (pwmContext[i].src==0&&pwmContext[i].pin != PIN_FREE /*&& pwmContext[i].value != 0*/) { NRF_GPIO->OUTSET = (1UL << pwmContext[i].pin); } } @@ -285,8 +319,8 @@ void TIMER1_IRQHandler(void) } for (int i = 0; i < PWM_COUNT; i++) { - if (NRF_TIMER1->EVENTS_COMPARE[pwmContext[i].event]) { - if (pwmContext[i].pin != PIN_FREE && pwmContext[i].value != 255) { + if (pwmContext[i].src==0&&NRF_TIMER1->EVENTS_COMPARE[pwmContext[i].event]) { + if (pwmContext[i].pin != PIN_FREE /*&& pwmContext[i].value != 255*/) { NRF_GPIO->OUTCLR = (1UL << pwmContext[i].pin); } @@ -295,6 +329,29 @@ void TIMER1_IRQHandler(void) } } +void TIMER2_IRQHandler(void) +{ + if (NRF_TIMER2->EVENTS_COMPARE[0]) { + for (int i = 0; i < PWM_COUNT; i++) { + if (pwmContext[i].src==1&&pwmContext[i].pin != PIN_FREE /*&& pwmContext[i].value != 0*/) { + NRF_GPIO->OUTSET = (1UL << pwmContext[i].pin); + } + } + + NRF_TIMER2->EVENTS_COMPARE[0] = 0x0UL; + } + + for (int i = 0; i < PWM_COUNT; i++) { + if (pwmContext[i].src==1&&NRF_TIMER2->EVENTS_COMPARE[pwmContext[i].event]) { + if (pwmContext[i].pin != PIN_FREE /*&& pwmContext[i].value != 255*/) { + NRF_GPIO->OUTCLR = (1UL << pwmContext[i].pin); + } + + NRF_TIMER2->EVENTS_COMPARE[pwmContext[i].event] = 0x0UL; + } + } +} + #ifdef __cplusplus } #endif From 475d17b6478a323107496ef01cc40ab6fc6cef46 Mon Sep 17 00:00:00 2001 From: Rui Azevedo Date: Sun, 7 Jul 2019 11:03:38 +0000 Subject: [PATCH 2/4] restore check --- cores/nRF5/wiring_analog_nRF51.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/cores/nRF5/wiring_analog_nRF51.c b/cores/nRF5/wiring_analog_nRF51.c index 1542af96..29a69f82 100644 --- a/cores/nRF5/wiring_analog_nRF51.c +++ b/cores/nRF5/wiring_analog_nRF51.c @@ -310,7 +310,7 @@ void TIMER1_IRQHandler(void) { if (NRF_TIMER1->EVENTS_COMPARE[0]) { for (int i = 0; i < PWM_COUNT; i++) { - if (pwmContext[i].src==0&&pwmContext[i].pin != PIN_FREE /*&& pwmContext[i].value != 0*/) { + if (pwmContext[i].src==0&&pwmContext[i].pin != PIN_FREE && pwmContext[i].value != 0) { NRF_GPIO->OUTSET = (1UL << pwmContext[i].pin); } } @@ -320,7 +320,7 @@ void TIMER1_IRQHandler(void) for (int i = 0; i < PWM_COUNT; i++) { if (pwmContext[i].src==0&&NRF_TIMER1->EVENTS_COMPARE[pwmContext[i].event]) { - if (pwmContext[i].pin != PIN_FREE /*&& pwmContext[i].value != 255*/) { + if (pwmContext[i].pin != PIN_FREE && pwmContext[i].value != 255) { NRF_GPIO->OUTCLR = (1UL << pwmContext[i].pin); } @@ -333,7 +333,7 @@ void TIMER2_IRQHandler(void) { if (NRF_TIMER2->EVENTS_COMPARE[0]) { for (int i = 0; i < PWM_COUNT; i++) { - if (pwmContext[i].src==1&&pwmContext[i].pin != PIN_FREE /*&& pwmContext[i].value != 0*/) { + if (pwmContext[i].src==1&&pwmContext[i].pin != PIN_FREE && pwmContext[i].value != 0) { NRF_GPIO->OUTSET = (1UL << pwmContext[i].pin); } } @@ -343,7 +343,7 @@ void TIMER2_IRQHandler(void) for (int i = 0; i < PWM_COUNT; i++) { if (pwmContext[i].src==1&&NRF_TIMER2->EVENTS_COMPARE[pwmContext[i].event]) { - if (pwmContext[i].pin != PIN_FREE /*&& pwmContext[i].value != 255*/) { + if (pwmContext[i].pin != PIN_FREE && pwmContext[i].value != 255) { NRF_GPIO->OUTCLR = (1UL << pwmContext[i].pin); } From a4c8d034e6bee57827cdc7f9c00f51a133e1cfc6 Mon Sep 17 00:00:00 2001 From: Rui Azevedo Date: Tue, 30 Jul 2019 11:59:25 +0000 Subject: [PATCH 3/4] respect analogWriteResolution use given resolution intead of the 8 bits internal convertion. we are now reseting the counter on CC[0] match allowing control over bit resolution and frequency. reduced interrupt code, cycling checks only inside timer assigned pins added non standard pwmPrescaller (no standard here?) --- cores/nRF5/wiring_analog.h | 2 + cores/nRF5/wiring_analog_nRF51.c | 79 ++++++++++++++++++++------------ 2 files changed, 52 insertions(+), 29 deletions(-) diff --git a/cores/nRF5/wiring_analog.h b/cores/nRF5/wiring_analog.h index 7708b7a1..25f78c91 100644 --- a/cores/nRF5/wiring_analog.h +++ b/cores/nRF5/wiring_analog.h @@ -45,6 +45,8 @@ typedef enum _eAnalogReference AR_EXT0, AR_EXT1 } eAnalogReference ; +//not standard, set timer prescaller +void pwmPrescaller( int div ); #endif diff --git a/cores/nRF5/wiring_analog_nRF51.c b/cores/nRF5/wiring_analog_nRF51.c index 29a69f82..e1cf4f1b 100644 --- a/cores/nRF5/wiring_analog_nRF51.c +++ b/cores/nRF5/wiring_analog_nRF51.c @@ -29,6 +29,7 @@ extern "C" { #endif #define PWM_COUNT 6 +#define PWM_CH_COUNT 3 #define PIN_FREE 0xffffffff struct PWMSrc { @@ -50,7 +51,9 @@ struct PWMContext { int src; }; -static struct PWMContext pwmContext[PWM_COUNT] = { +extern struct PWMContext pwmContext[PWM_COUNT]; +// static +struct PWMContext pwmContext[PWM_COUNT] = { { PIN_FREE, 0, 1, TIMER_INTENSET_COMPARE1_Msk, 1, 0 }, { PIN_FREE, 0, 2, TIMER_INTENSET_COMPARE2_Msk, 2, 0 }, { PIN_FREE, 0, 3, TIMER_INTENSET_COMPARE3_Msk, 3, 0 }, @@ -65,14 +68,21 @@ static uint32_t adcPrescaling = ADC_CONFIG_INPSEL_AnalogInputOneThirdPrescaling; static uint32_t readResolution = 10; static uint32_t writeResolution = 8; -void analogReadResolution( int res ) +static int8_t timerPrescaller=7; +//not standard, set timer prescaller +inline void pwmPrescaller( int div ) {timerPrescaller=div;} + +inline void analogReadResolution( int res ) { readResolution = res; } -void analogWriteResolution( int res ) +inline void analogWriteResolution( int res ) { writeResolution = res; + //this might need to reconfigure the timer... + //for now call it once on setup before using pwm + //TODO: check if this is the expected behaviour } static inline uint32_t mapResolution( uint32_t value, uint32_t from, uint32_t to ) @@ -229,10 +239,17 @@ uint32_t analogRead( uint32_t ulPin ) return mapResolution(value, resolution, readResolution); } -int getFreePwm() { - for (int i = 0; i < PWM_COUNT; i++) - if (pwmContext[i].pin == PIN_FREE) return i; - return -1; +// int getFreePwm() { +// for (int i = 0; i < PWM_COUNT; i++) +// if (pwmContext[i].pin == PIN_FREE) return i; +// return -1; +// } + +static int timerResolution(int nbits) { + if(nbits<=8) return TIMER_BITMODE_BITMODE_08Bit; + if(nbits<=16) return TIMER_BITMODE_BITMODE_16Bit; + if(nbits<=24) return TIMER_BITMODE_BITMODE_24Bit; + return TIMER_BITMODE_BITMODE_32Bit; } int getPwmFromPin(uint32_t ulPin) { @@ -272,11 +289,11 @@ void analogWrite( uint32_t ulPin, uint32_t ulValue ) pwmSrc->MODE = (pwmSrc->MODE & ~TIMER_MODE_MODE_Msk) | ((TIMER_MODE_MODE_Timer << TIMER_MODE_MODE_Pos) & TIMER_MODE_MODE_Msk); - pwmSrc->BITMODE = (pwmSrc->BITMODE & ~TIMER_BITMODE_BITMODE_Msk) | ((TIMER_BITMODE_BITMODE_08Bit << TIMER_BITMODE_BITMODE_Pos) & TIMER_BITMODE_BITMODE_Msk); + pwmSrc->BITMODE = (pwmSrc->BITMODE & ~TIMER_BITMODE_BITMODE_Msk) | ((timerResolution(writeResolution) << TIMER_BITMODE_BITMODE_Pos) & TIMER_BITMODE_BITMODE_Msk); - pwmSrc->PRESCALER = (pwmSrc->PRESCALER & ~TIMER_PRESCALER_PRESCALER_Msk) | ((7 << TIMER_PRESCALER_PRESCALER_Pos) & TIMER_PRESCALER_PRESCALER_Msk); + pwmSrc->PRESCALER = (pwmSrc->PRESCALER & ~TIMER_PRESCALER_PRESCALER_Msk) | ((timerPrescaller << TIMER_PRESCALER_PRESCALER_Pos) & TIMER_PRESCALER_PRESCALER_Msk); - pwmSrc->CC[0] = 0; + pwmSrc->CC[0] = (1<INTENSET = TIMER_INTENSET_COMPARE0_Msk; @@ -285,15 +302,18 @@ void analogWrite( uint32_t ulPin, uint32_t ulValue ) for (int i = 0; i < PWM_COUNT; i++) { if (pwmContext[i].pin == PIN_FREE || pwmContext[i].pin == ulPin) { - pwmContext[i].pin = ulPin; - NRF_GPIO->PIN_CNF[ulPin] = ((uint32_t)GPIO_PIN_CNF_DIR_Output << GPIO_PIN_CNF_DIR_Pos) - | ((uint32_t)GPIO_PIN_CNF_INPUT_Disconnect << GPIO_PIN_CNF_INPUT_Pos) - | ((uint32_t)GPIO_PIN_CNF_PULL_Disabled << GPIO_PIN_CNF_PULL_Pos) - | ((uint32_t)GPIO_PIN_CNF_DRIVE_S0S1 << GPIO_PIN_CNF_DRIVE_Pos) - | ((uint32_t)GPIO_PIN_CNF_SENSE_Disabled << GPIO_PIN_CNF_SENSE_Pos); + if (pwmContext[i].pin != ulPin) { + pwmContext[i].pin = ulPin; + + NRF_GPIO->PIN_CNF[ulPin] = ((uint32_t)GPIO_PIN_CNF_DIR_Output << GPIO_PIN_CNF_DIR_Pos) + | ((uint32_t)GPIO_PIN_CNF_INPUT_Disconnect << GPIO_PIN_CNF_INPUT_Pos) + | ((uint32_t)GPIO_PIN_CNF_PULL_Disabled << GPIO_PIN_CNF_PULL_Pos) + | ((uint32_t)GPIO_PIN_CNF_DRIVE_S0S1 << GPIO_PIN_CNF_DRIVE_Pos) + | ((uint32_t)GPIO_PIN_CNF_SENSE_Disabled << GPIO_PIN_CNF_SENSE_Pos); + } - ulValue = mapResolution(ulValue, writeResolution, 8); + // ulValue = mapResolution(ulValue, writeResolution, writeResolution); pwmContext[i].value = ulValue; @@ -309,18 +329,19 @@ void analogWrite( uint32_t ulPin, uint32_t ulValue ) void TIMER1_IRQHandler(void) { if (NRF_TIMER1->EVENTS_COMPARE[0]) { - for (int i = 0; i < PWM_COUNT; i++) { - if (pwmContext[i].src==0&&pwmContext[i].pin != PIN_FREE && pwmContext[i].value != 0) { + for (int i = 0; i < PWM_CH_COUNT; i++) { + if (/*pwmContext[i].src==0&*&*/pwmContext[i].pin != PIN_FREE && pwmContext[i].value != 0) { NRF_GPIO->OUTSET = (1UL << pwmContext[i].pin); } + NRF_TIMER1->TASKS_CLEAR = 1;//restart count } - NRF_TIMER1->EVENTS_COMPARE[0] = 0x0UL; + NRF_TIMER1->EVENTS_COMPARE[0] = 0x0UL;//restart cpimying (this gives us more control over frequency and resolution) } - for (int i = 0; i < PWM_COUNT; i++) { - if (pwmContext[i].src==0&&NRF_TIMER1->EVENTS_COMPARE[pwmContext[i].event]) { - if (pwmContext[i].pin != PIN_FREE && pwmContext[i].value != 255) { + for (int i = 0; i < PWM_CH_COUNT; i++) { + if (/*pwmContext[i].src==0&&*/NRF_TIMER1->EVENTS_COMPARE[pwmContext[i].event]) { + if (pwmContext[i].pin != PIN_FREE && pwmContext[i].value != (1<OUTCLR = (1UL << pwmContext[i].pin); } @@ -332,21 +353,21 @@ void TIMER1_IRQHandler(void) void TIMER2_IRQHandler(void) { if (NRF_TIMER2->EVENTS_COMPARE[0]) { - for (int i = 0; i < PWM_COUNT; i++) { - if (pwmContext[i].src==1&&pwmContext[i].pin != PIN_FREE && pwmContext[i].value != 0) { + for (int i = PWM_CH_COUNT; i < PWM_COUNT; i++) { + if (pwmContext[i].pin != PIN_FREE && pwmContext[i].value != 0) { NRF_GPIO->OUTSET = (1UL << pwmContext[i].pin); } + NRF_TIMER2->TASKS_CLEAR = 1;//restart count } NRF_TIMER2->EVENTS_COMPARE[0] = 0x0UL; } - for (int i = 0; i < PWM_COUNT; i++) { - if (pwmContext[i].src==1&&NRF_TIMER2->EVENTS_COMPARE[pwmContext[i].event]) { - if (pwmContext[i].pin != PIN_FREE && pwmContext[i].value != 255) { + for (int i = PWM_CH_COUNT; i < PWM_COUNT; i++) { + if (NRF_TIMER2->EVENTS_COMPARE[pwmContext[i].event]) { + if (pwmContext[i].pin != PIN_FREE && pwmContext[i].value != (1<OUTCLR = (1UL << pwmContext[i].pin); } - NRF_TIMER2->EVENTS_COMPARE[pwmContext[i].event] = 0x0UL; } } From 7eaeb99d91ce5471ead9ae098175424dac030953 Mon Sep 17 00:00:00 2001 From: Rui Azevedo Date: Tue, 30 Jul 2019 12:14:13 +0000 Subject: [PATCH 4/4] clear/set pin state on 0 and 2^res-1 --- cores/nRF5/wiring_analog_nRF51.c | 34 +++++++++++++++++++++----------- 1 file changed, 22 insertions(+), 12 deletions(-) diff --git a/cores/nRF5/wiring_analog_nRF51.c b/cores/nRF5/wiring_analog_nRF51.c index e1cf4f1b..3878ba58 100644 --- a/cores/nRF5/wiring_analog_nRF51.c +++ b/cores/nRF5/wiring_analog_nRF51.c @@ -68,7 +68,7 @@ static uint32_t adcPrescaling = ADC_CONFIG_INPSEL_AnalogInputOneThirdPrescaling; static uint32_t readResolution = 10; static uint32_t writeResolution = 8; -static int8_t timerPrescaller=7; +static uint32_t timerPrescaller=7; //not standard, set timer prescaller inline void pwmPrescaller( int div ) {timerPrescaller=div;} @@ -330,8 +330,11 @@ void TIMER1_IRQHandler(void) { if (NRF_TIMER1->EVENTS_COMPARE[0]) { for (int i = 0; i < PWM_CH_COUNT; i++) { - if (/*pwmContext[i].src==0&*&*/pwmContext[i].pin != PIN_FREE && pwmContext[i].value != 0) { - NRF_GPIO->OUTSET = (1UL << pwmContext[i].pin); + if (pwmContext[i].pin != PIN_FREE) { + if(pwmContext[i].value != 0) + NRF_GPIO->OUTSET = (1UL << pwmContext[i].pin); + else + NRF_GPIO->OUTCLR = (1UL << pwmContext[i].pin); } NRF_TIMER1->TASKS_CLEAR = 1;//restart count } @@ -340,11 +343,13 @@ void TIMER1_IRQHandler(void) } for (int i = 0; i < PWM_CH_COUNT; i++) { - if (/*pwmContext[i].src==0&&*/NRF_TIMER1->EVENTS_COMPARE[pwmContext[i].event]) { - if (pwmContext[i].pin != PIN_FREE && pwmContext[i].value != (1<OUTCLR = (1UL << pwmContext[i].pin); + if (NRF_TIMER1->EVENTS_COMPARE[pwmContext[i].event]) { + if (pwmContext[i].pin != PIN_FREE) { + if (pwmContext[i].value != (1<OUTCLR = (1UL << pwmContext[i].pin); + else + NRF_GPIO->OUTSET = (1UL << pwmContext[i].pin); } - NRF_TIMER1->EVENTS_COMPARE[pwmContext[i].event] = 0x0UL; } } @@ -354,19 +359,24 @@ void TIMER2_IRQHandler(void) { if (NRF_TIMER2->EVENTS_COMPARE[0]) { for (int i = PWM_CH_COUNT; i < PWM_COUNT; i++) { - if (pwmContext[i].pin != PIN_FREE && pwmContext[i].value != 0) { - NRF_GPIO->OUTSET = (1UL << pwmContext[i].pin); + if (pwmContext[i].pin != PIN_FREE) { + if(pwmContext[i].value != 0) + NRF_GPIO->OUTSET = (1UL << pwmContext[i].pin); + else + NRF_GPIO->OUTCLR = (1UL << pwmContext[i].pin); } NRF_TIMER2->TASKS_CLEAR = 1;//restart count } - NRF_TIMER2->EVENTS_COMPARE[0] = 0x0UL; } for (int i = PWM_CH_COUNT; i < PWM_COUNT; i++) { if (NRF_TIMER2->EVENTS_COMPARE[pwmContext[i].event]) { - if (pwmContext[i].pin != PIN_FREE && pwmContext[i].value != (1<OUTCLR = (1UL << pwmContext[i].pin); + if (pwmContext[i].pin != PIN_FREE) { + if (pwmContext[i].value != (1<OUTCLR = (1UL << pwmContext[i].pin); + else + NRF_GPIO->OUTSET = (1UL << pwmContext[i].pin); } NRF_TIMER2->EVENTS_COMPARE[pwmContext[i].event] = 0x0UL; }