pwmcmds: Export the maximum PWM value

Instead of assuming the maximum PWM value is 255, export a constant
from the firmware to the host with the maximum value.

Signed-off-by: Kevin O'Connor <kevin@koconnor.net>
This commit is contained in:
Kevin O'Connor 2017-05-07 17:33:45 -04:00
parent a361b92184
commit 5c4cc0d646
5 changed files with 23 additions and 14 deletions

View File

@ -50,7 +50,7 @@ Common startup commands:
may be useful for configuring the initial value of LEDs and for may be useful for configuring the initial value of LEDs and for
configuring the initial value of stepper driver micro-stepping pins. configuring the initial value of stepper driver micro-stepping pins.
* `set_pwm_out pin=%u cycle_ticks=%u value=%c` : This command will * `set_pwm_out pin=%u cycle_ticks=%u value=%hu` : This command will
immediately configure the given pin to use hardware based immediately configure the given pin to use hardware based
pulse-width-modulation (PWM) with the given number of pulse-width-modulation (PWM) with the given number of
cycle_ticks. The "cycle_ticks" is the number of MCU clock ticks each cycle_ticks. The "cycle_ticks" is the number of MCU clock ticks each
@ -148,7 +148,7 @@ This section lists some commonly used config commands.
feature can be used with heater pins to ensure the host does not feature can be used with heater pins to ensure the host does not
enable the heater and then go off-line. enable the heater and then go off-line.
* `config_pwm_out oid=%c pin=%u cycle_ticks=%u default_value=%c * `config_pwm_out oid=%c pin=%u cycle_ticks=%u default_value=%hu
max_duration=%u` : This command creates an internal object for max_duration=%u` : This command creates an internal object for
hardware based PWM pins that the host may schedule updates for. Its hardware based PWM pins that the host may schedule updates for. Its
usage is analogous to config_digital_out - see the description of usage is analogous to config_digital_out - see the description of
@ -205,11 +205,11 @@ only of interest to developers looking to gain insight into Klipper.
same 'oid' parameter must have been issued during micro-controller same 'oid' parameter must have been issued during micro-controller
configuration. configuration.
* `schedule_pwm_out oid=%c clock=%u value=%c` : Schedules a change to * `schedule_pwm_out oid=%c clock=%u value=%hu` : Schedules a change to
a hardware PWM output pin. See the 'schedule_digital_out' and a hardware PWM output pin. See the 'schedule_digital_out' and
'config_pwm_out' commands for more info. 'config_pwm_out' commands for more info.
* `schedule_soft_pwm_out oid=%c clock=%u value=%c` : Schedules a * `schedule_soft_pwm_out oid=%c clock=%u value=%hu` : Schedules a
change to a software PWM output pin. See the 'schedule_digital_out' change to a software PWM output pin. See the 'schedule_digital_out'
and 'config_soft_pwm_out' commands for more info. and 'config_soft_pwm_out' commands for more info.

View File

@ -272,7 +272,6 @@ class MCU_digital_out:
self.set_digital(mcu_time, dval) self.set_digital(mcu_time, dval)
class MCU_pwm: class MCU_pwm:
PWM_MAX = 255.
def __init__(self, mcu, pin, cycle_time, hard_cycle_ticks, max_duration): def __init__(self, mcu, pin, cycle_time, hard_cycle_ticks, max_duration):
self._mcu = mcu self._mcu = mcu
self._hard_cycle_ticks = hard_cycle_ticks self._hard_cycle_ticks = hard_cycle_ticks
@ -280,6 +279,7 @@ class MCU_pwm:
pin, pullup, self._invert = parse_pin_extras(pin) pin, pullup, self._invert = parse_pin_extras(pin)
self._last_clock = 0 self._last_clock = 0
self._mcu_freq = 0. self._mcu_freq = 0.
self._pwm_max = 0.
self._cmd_queue = mcu.alloc_command_queue() self._cmd_queue = mcu.alloc_command_queue()
if hard_cycle_ticks: if hard_cycle_ticks:
mcu.add_config_cmd( mcu.add_config_cmd(
@ -297,16 +297,20 @@ class MCU_pwm:
def build_config(self): def build_config(self):
self._mcu_freq = self._mcu.get_mcu_freq() self._mcu_freq = self._mcu.get_mcu_freq()
if self._hard_cycle_ticks: if self._hard_cycle_ticks:
self._pwm_max = self._mcu.serial.msgparser.get_constant_float(
"PWM_MAX")
self._set_cmd = self._mcu.lookup_command( self._set_cmd = self._mcu.lookup_command(
"schedule_pwm_out oid=%c clock=%u value=%c") "schedule_pwm_out oid=%c clock=%u value=%hu")
else: else:
self._pwm_max = self._mcu.serial.msgparser.get_constant_float(
"SOFT_PWM_MAX")
self._set_cmd = self._mcu.lookup_command( self._set_cmd = self._mcu.lookup_command(
"schedule_soft_pwm_out oid=%c clock=%u value=%c") "schedule_soft_pwm_out oid=%c clock=%u value=%hu")
def set_pwm(self, mcu_time, value): def set_pwm(self, mcu_time, value):
clock = int(mcu_time * self._mcu_freq) clock = int(mcu_time * self._mcu_freq)
if self._invert: if self._invert:
value = 1. - value value = 1. - value
value = int(value * self.PWM_MAX + 0.5) value = int(value * self._pwm_max + 0.5)
msg = self._set_cmd.encode(self._oid, clock, value) msg = self._set_cmd.encode(self._oid, clock, value)
self._mcu.send(msg, minclock=self._last_clock, reqclock=clock self._mcu.send(msg, minclock=self._last_clock, reqclock=clock
, cq=self._cmd_queue) , cq=self._cmd_queue)

View File

@ -162,6 +162,8 @@ static const uint8_t pwm_pins[ARRAY_SIZE(pwm_regs)] PROGMEM = {
#endif #endif
}; };
DECL_CONSTANT(PWM_MAX, 255);
struct gpio_pwm struct gpio_pwm
gpio_pwm_setup(uint8_t pin, uint32_t cycle_time, uint8_t val) gpio_pwm_setup(uint8_t pin, uint32_t cycle_time, uint8_t val)
{ {

View File

@ -90,6 +90,9 @@ DECL_COMMAND(command_set_digital_out, "set_digital_out pin=%u value=%c");
* Soft PWM output pins * Soft PWM output pins
****************************************************************/ ****************************************************************/
#define MAX_SOFT_PWM 255
DECL_CONSTANT(SOFT_PWM_MAX, MAX_SOFT_PWM);
struct soft_pwm_s { struct soft_pwm_s {
struct timer timer; struct timer timer;
uint32_t on_duration, off_duration, end_time; uint32_t on_duration, off_duration, end_time;
@ -159,7 +162,7 @@ command_config_soft_pwm_out(uint32_t *args)
struct soft_pwm_s *s = oid_alloc(args[0], command_config_soft_pwm_out struct soft_pwm_s *s = oid_alloc(args[0], command_config_soft_pwm_out
, sizeof(*s)); , sizeof(*s));
s->cycle_time = args[2]; s->cycle_time = args[2];
s->pulse_time = s->cycle_time / 255; s->pulse_time = s->cycle_time / MAX_SOFT_PWM;
s->default_value = !!args[3]; s->default_value = !!args[3];
s->max_duration = args[4]; s->max_duration = args[4];
s->flags = s->default_value ? SPF_ON : 0; s->flags = s->default_value ? SPF_ON : 0;
@ -177,7 +180,7 @@ command_schedule_soft_pwm_out(uint32_t *args)
uint8_t value = args[2]; uint8_t value = args[2];
uint8_t next_flags = SPF_CHECK_END | SPF_HAVE_NEXT; uint8_t next_flags = SPF_CHECK_END | SPF_HAVE_NEXT;
uint32_t next_on_duration, next_off_duration; uint32_t next_on_duration, next_off_duration;
if (value == 0 || value == 255) { if (value == 0 || value == MAX_SOFT_PWM) {
next_on_duration = next_off_duration = 0; next_on_duration = next_off_duration = 0;
next_flags |= value ? SPF_NEXT_ON : 0; next_flags |= value ? SPF_NEXT_ON : 0;
if (!!value != s->default_value && s->max_duration) if (!!value != s->default_value && s->max_duration)
@ -208,7 +211,7 @@ command_schedule_soft_pwm_out(uint32_t *args)
irq_enable(); irq_enable();
} }
DECL_COMMAND(command_schedule_soft_pwm_out, DECL_COMMAND(command_schedule_soft_pwm_out,
"schedule_soft_pwm_out oid=%c clock=%u value=%c"); "schedule_soft_pwm_out oid=%c clock=%u value=%hu");
static void static void
soft_pwm_shutdown(void) soft_pwm_shutdown(void)

View File

@ -43,7 +43,7 @@ command_config_pwm_out(uint32_t *args)
p->max_duration = args[4]; p->max_duration = args[4];
} }
DECL_COMMAND(command_config_pwm_out, DECL_COMMAND(command_config_pwm_out,
"config_pwm_out oid=%c pin=%u cycle_ticks=%u default_value=%c" "config_pwm_out oid=%c pin=%u cycle_ticks=%u default_value=%hu"
" max_duration=%u"); " max_duration=%u");
void void
@ -57,7 +57,7 @@ command_schedule_pwm_out(uint32_t *args)
sched_add_timer(&p->timer); sched_add_timer(&p->timer);
} }
DECL_COMMAND(command_schedule_pwm_out, DECL_COMMAND(command_schedule_pwm_out,
"schedule_pwm_out oid=%c clock=%u value=%c"); "schedule_pwm_out oid=%c clock=%u value=%hu");
static void static void
pwm_shutdown(void) pwm_shutdown(void)
@ -75,4 +75,4 @@ command_set_pwm_out(uint32_t *args)
{ {
gpio_pwm_setup(args[0], args[1], args[2]); gpio_pwm_setup(args[0], args[1], args[2]);
} }
DECL_COMMAND(command_set_pwm_out, "set_pwm_out pin=%u cycle_ticks=%u value=%c"); DECL_COMMAND(command_set_pwm_out, "set_pwm_out pin=%u cycle_ticks=%u value=%hu");