kinetis-tpm: Implement pulse_cycles directly instead of duty cycle
When using low PWM frequency i.e 50Hz the resolution of pulse_cycles got lost from converting pulse_cycles to duty cycle % and then back to pulse_cycles again. Furthermore TPM_UpdateChnlEdgeLevelSelect call would restart the pwm constantly on a mcux_tpm_set_cycles call now only call TPM_UpdateChnlEdgeLevelSelect when changing the polarity Signed-off-by: Peter van der Perk <peter.vanderperk@nxp.com>
This commit is contained in:
parent
d2d0e8553e
commit
886a99e736
1 changed files with 27 additions and 20 deletions
|
@ -55,29 +55,22 @@ static int mcux_tpm_set_cycles(const struct device *dev, uint32_t channel,
|
|||
{
|
||||
const struct mcux_tpm_config *config = dev->config;
|
||||
struct mcux_tpm_data *data = dev->data;
|
||||
uint8_t duty_cycle;
|
||||
|
||||
if (period_cycles == 0U) {
|
||||
LOG_ERR("Channel can not be set to inactive level");
|
||||
return -ENOTSUP;
|
||||
}
|
||||
|
||||
if (channel >= config->channel_count) {
|
||||
LOG_ERR("Invalid channel");
|
||||
return -ENOTSUP;
|
||||
}
|
||||
|
||||
duty_cycle = pulse_cycles * 100U / period_cycles;
|
||||
data->channel[channel].dutyCyclePercent = duty_cycle;
|
||||
|
||||
if ((flags & PWM_POLARITY_INVERTED) == 0) {
|
||||
data->channel[channel].level = kTPM_HighTrue;
|
||||
} else {
|
||||
data->channel[channel].level = kTPM_LowTrue;
|
||||
if (period_cycles == 0 || period_cycles == TPM_MAX_COUNTER_VALUE(base)) {
|
||||
return -ENOTSUP;
|
||||
}
|
||||
|
||||
LOG_DBG("pulse_cycles=%d, period_cycles=%d, duty_cycle=%d, flags=%d",
|
||||
pulse_cycles, period_cycles, duty_cycle, flags);
|
||||
if ((TPM_MAX_COUNTER_VALUE(base) == 0xFFFFU) &&
|
||||
(pulse_cycles > TPM_MAX_COUNTER_VALUE(base))) {
|
||||
return -ENOTSUP;
|
||||
}
|
||||
|
||||
LOG_DBG("pulse_cycles=%d, period_cycles=%d, flags=%d", pulse_cycles, period_cycles, flags);
|
||||
|
||||
if (period_cycles != data->period_cycles) {
|
||||
uint32_t pwm_freq;
|
||||
|
@ -106,6 +99,9 @@ static int mcux_tpm_set_cycles(const struct device *dev, uint32_t channel,
|
|||
|
||||
TPM_StopTimer(config->base);
|
||||
|
||||
/* Set counter back to zero */
|
||||
config->base->CNT = 0;
|
||||
|
||||
status = TPM_SetupPwm(config->base, data->channel,
|
||||
config->channel_count, config->mode,
|
||||
pwm_freq, data->clock_freq);
|
||||
|
@ -115,13 +111,24 @@ static int mcux_tpm_set_cycles(const struct device *dev, uint32_t channel,
|
|||
return -ENOTSUP;
|
||||
}
|
||||
TPM_StartTimer(config->base, config->tpm_clock_source);
|
||||
} else {
|
||||
TPM_UpdateChnlEdgeLevelSelect(config->base, channel,
|
||||
data->channel[channel].level);
|
||||
TPM_UpdatePwmDutycycle(config->base, channel, config->mode,
|
||||
duty_cycle);
|
||||
}
|
||||
|
||||
if ((flags & PWM_POLARITY_INVERTED) == 0 &&
|
||||
data->channel[channel].level != kTPM_HighTrue) {
|
||||
data->channel[channel].level = kTPM_HighTrue;
|
||||
TPM_UpdateChnlEdgeLevelSelect(config->base, channel, kTPM_HighTrue);
|
||||
} else if ((flags & PWM_POLARITY_INVERTED) != 0 &&
|
||||
data->channel[channel].level != kTPM_LowTrue) {
|
||||
data->channel[channel].level = kTPM_LowTrue;
|
||||
TPM_UpdateChnlEdgeLevelSelect(config->base, channel, kTPM_LowTrue);
|
||||
}
|
||||
|
||||
if (pulse_cycles == period_cycles) {
|
||||
pulse_cycles = period_cycles + 1U;
|
||||
}
|
||||
|
||||
config->base->CONTROLS[channel].CnV = pulse_cycles;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue