Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
35 changes: 29 additions & 6 deletions libraries/mbed/targets/hal/TARGET_NXP/TARGET_LPC11U6X/pwmout_api.c
Original file line number Diff line number Diff line change
Expand Up @@ -137,16 +137,23 @@ void pwmout_write(pwmout_t* obj, float value) {
uint32_t t_on = (uint32_t)((float)(pwm->MATCHREL0 + 1) * value);
if (t_on > 0) {
pwm->MATCHREL1 = t_on - 1;
pwm->CTRL &= ~(1 << 2);

// Un-halt the timer and ensure the new pulse-width takes immediate effect if necessary
if (pwm->CTRL & (1 << 2)) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

might be good to add a comment here what this if () handles?

pwm->MATCH1 = pwm->MATCHREL1;
pwm->CTRL &= ~(1 << 2);
}
} else {
// Halt the timer and force the output low
pwm->CTRL |= (1 << 2) | (1 << 3);
pwm->OUTPUT = 0x00000000;
}
}

float pwmout_read(pwmout_t* obj) {
uint32_t t_off = obj->pwm->MATCHREL0 + 1;
uint32_t t_on = obj->pwm->MATCHREL1 + 1;
LPC_SCT0_Type* pwm = obj->pwm;
uint32_t t_off = pwm->MATCHREL0 + 1;
uint32_t t_on = (!(pwm->CTRL & (1 << 2))) ? pwm->MATCHREL1 + 1 : 0;
float v = (float)t_on/(float)t_off;
return (v > 1.0f) ? (1.0f) : (v);
}
Expand All @@ -163,17 +170,27 @@ void pwmout_period_ms(pwmout_t* obj, int ms) {
void pwmout_period_us(pwmout_t* obj, int us) {
LPC_SCT0_Type* pwm = obj->pwm;
uint32_t t_off = pwm->MATCHREL0 + 1;
uint32_t t_on = pwm->MATCHREL1 + 1;
uint32_t t_on = (!(pwm->CTRL & (1 << 2))) ? pwm->MATCHREL1 + 1 : 0;
float v = (float)t_on/(float)t_off;
uint32_t period_ticks = (uint32_t)(((uint64_t)SystemCoreClock * (uint64_t)us) / (uint64_t)1000000);
uint32_t pulsewidth_ticks = period_ticks * v;
pwm->MATCHREL0 = period_ticks - 1;
if (pulsewidth_ticks > 0) {
pwm->MATCHREL1 = pulsewidth_ticks - 1;
pwm->CTRL &= ~(1 << 2);

// Un-halt the timer and ensure the new period & pulse-width take immediate effect if necessary
if (pwm->CTRL & (1 << 2)) {
pwm->MATCH0 = pwm->MATCHREL0;
pwm->MATCH1 = pwm->MATCHREL1;
pwm->CTRL &= ~(1 << 2);
}
} else {
// Halt the timer and force the output low
pwm->CTRL |= (1 << 2) | (1 << 3);
pwm->OUTPUT = 0x00000000;

// Ensure the new period will take immediate effect when the timer is un-halted
pwm->MATCH0 = pwm->MATCHREL0;
}
}

Expand All @@ -189,8 +206,14 @@ void pwmout_pulsewidth_us(pwmout_t* obj, int us) {
LPC_SCT0_Type* pwm = obj->pwm;
if (us > 0) {
pwm->MATCHREL1 = (uint32_t)(((uint64_t)SystemCoreClock * (uint64_t)us) / (uint64_t)1000000) - 1;
pwm->CTRL &= ~(1 << 2);

// Un-halt the timer and ensure the new pulse-width takes immediate effect if necessary
if (pwm->CTRL & (1 << 2)) {
pwm->MATCH1 = pwm->MATCHREL1;
pwm->CTRL &= ~(1 << 2);
}
} else {
// Halt the timer and force the output low
pwm->CTRL |= (1 << 2) | (1 << 3);
pwm->OUTPUT = 0x00000000;
}
Expand Down
35 changes: 29 additions & 6 deletions libraries/mbed/targets/hal/TARGET_NXP/TARGET_LPC15XX/pwmout_api.c
Original file line number Diff line number Diff line change
Expand Up @@ -118,16 +118,23 @@ void pwmout_write(pwmout_t* obj, float value) {
uint32_t t_on = (uint32_t)((float)(pwm->MATCHREL0 + 1) * value);
if (t_on > 0) {
pwm->MATCHREL1 = t_on - 1;
pwm->CTRL &= ~(1 << 2);

// Un-halt the timer and ensure the new pulse-width takes immediate effect if necessary
if (pwm->CTRL & (1 << 2)) {
pwm->MATCH1 = pwm->MATCHREL1;
pwm->CTRL &= ~(1 << 2);
}
} else {
// Halt the timer and force the output low
pwm->CTRL |= (1 << 2) | (1 << 3);
pwm->OUTPUT = 0x00000000;
}
}

float pwmout_read(pwmout_t* obj) {
uint32_t t_off = obj->pwm->MATCHREL0 + 1;
uint32_t t_on = obj->pwm->MATCHREL1 + 1;
LPC_SCT0_Type* pwm = obj->pwm;
uint32_t t_off = pwm->MATCHREL0 + 1;
uint32_t t_on = (!(pwm->CTRL & (1 << 2))) ? pwm->MATCHREL1 + 1 : 0;
float v = (float)t_on/(float)t_off;
return (v > 1.0f) ? (1.0f) : (v);
}
Expand All @@ -144,17 +151,27 @@ void pwmout_period_ms(pwmout_t* obj, int ms) {
void pwmout_period_us(pwmout_t* obj, int us) {
LPC_SCT0_Type* pwm = obj->pwm;
uint32_t t_off = pwm->MATCHREL0 + 1;
uint32_t t_on = pwm->MATCHREL1 + 1;
uint32_t t_on = (!(pwm->CTRL & (1 << 2))) ? pwm->MATCHREL1 + 1 : 0;
float v = (float)t_on/(float)t_off;
uint32_t period_ticks = (uint32_t)(((uint64_t)SystemCoreClock * (uint64_t)us) / (uint64_t)1000000);
uint32_t pulsewidth_ticks = period_ticks * v;
pwm->MATCHREL0 = period_ticks - 1;
if (pulsewidth_ticks > 0) {
pwm->MATCHREL1 = pulsewidth_ticks - 1;
pwm->CTRL &= ~(1 << 2);

// Un-halt the timer and ensure the new period & pulse-width take immediate effect if necessary
if (pwm->CTRL & (1 << 2)) {
pwm->MATCH0 = pwm->MATCHREL0;
pwm->MATCH1 = pwm->MATCHREL1;
pwm->CTRL &= ~(1 << 2);
}
} else {
// Halt the timer and force the output low
pwm->CTRL |= (1 << 2) | (1 << 3);
pwm->OUTPUT = 0x00000000;

// Ensure the new period will take immediate effect when the timer is un-halted
pwm->MATCH0 = pwm->MATCHREL0;
}
}

Expand All @@ -170,8 +187,14 @@ void pwmout_pulsewidth_us(pwmout_t* obj, int us) {
LPC_SCT0_Type* pwm = obj->pwm;
if (us > 0) {
pwm->MATCHREL1 = (uint32_t)(((uint64_t)SystemCoreClock * (uint64_t)us) / (uint64_t)1000000) - 1;
pwm->CTRL &= ~(1 << 2);

// Un-halt the timer and ensure the new pulse-width takes immediate effect if necessary
if (pwm->CTRL & (1 << 2)) {
pwm->MATCH1 = pwm->MATCHREL1;
pwm->CTRL &= ~(1 << 2);
}
} else {
// Halt the timer and force the output low
pwm->CTRL |= (1 << 2) | (1 << 3);
pwm->OUTPUT = 0x00000000;
}
Expand Down