From d858498a53fe98ed705595b8639b50b219d6262f Mon Sep 17 00:00:00 2001 From: Kevin O'Connor Date: Sat, 25 Apr 2020 13:06:51 -0400 Subject: [PATCH] heater: Move M105 command handling from gcode.py to heater.py Signed-off-by: Kevin O'Connor --- klippy/extras/heater_bed.py | 4 +-- klippy/extras/pid_calibrate.py | 2 +- klippy/gcode.py | 54 ++++++++++------------------------ klippy/heater.py | 46 +++++++++++++++++++++++++---- klippy/kinematics/extruder.py | 2 +- 5 files changed, 59 insertions(+), 49 deletions(-) diff --git a/klippy/extras/heater_bed.py b/klippy/extras/heater_bed.py index c8f68f2e..c3505528 100644 --- a/klippy/extras/heater_bed.py +++ b/klippy/extras/heater_bed.py @@ -19,10 +19,10 @@ class PrinterHeaterBed: # Set Bed Temperature gcode = self.printer.lookup_object('gcode') temp = gcode.get_float('S', params, 0.) - toolhead = self.printer.lookup_object('toolhead') self.heater.set_temp(temp) if wait and temp: - gcode.wait_for_temperature(self.heater) + pheater = self.printer.lookup_object('heater') + pheater.wait_for_temperature(self.heater) def cmd_M190(self, params): # Set Bed Temperature and Wait self.cmd_M140(params, wait=True) diff --git a/klippy/extras/pid_calibrate.py b/klippy/extras/pid_calibrate.py index 689084e9..49ae3bb4 100644 --- a/klippy/extras/pid_calibrate.py +++ b/klippy/extras/pid_calibrate.py @@ -31,7 +31,7 @@ class PIDCalibrate: except self.printer.command_error as e: heater.set_control(old_control) raise - self.gcode.wait_for_temperature(heater) + pheater.wait_for_temperature(heater) heater.set_control(old_control) if write_file: calibrate.write_file('/tmp/heattest.txt') diff --git a/klippy/gcode.py b/klippy/gcode.py index 005feeab..6cac494e 100644 --- a/klippy/gcode.py +++ b/klippy/gcode.py @@ -59,7 +59,6 @@ class GCodeParser: self.position_with_transform = (lambda: [0., 0., 0., 0.]) self.need_ack = False self.toolhead = None - self.heaters = None self.axis2pos = {'X': 0, 'Y': 1, 'Z': 2, 'E': 3} def is_traditional_gcode(self, cmd): # A "traditional" g-code command is a letter and followed by a number @@ -177,8 +176,6 @@ class GCodeParser: def _handle_ready(self): self.is_printer_ready = True self.gcode_handlers = self.ready_gcode_handlers - # Lookup printer components - self.heaters = self.printer.lookup_object('heater') self.toolhead = self.printer.lookup_object('toolhead') if self.move_transform is None: self.move_with_transform = self.toolhead.move @@ -306,16 +303,19 @@ class GCodeParser: return self.mutex # Response handling def ack(self, msg=None): - if not self.need_ack or self.is_fileinput: - return + if not self.need_ack: + return False + if self.is_fileinput: + return True + ok_msg = "ok\n" + if msg: + ok_msg = "ok %s\n" % (msg,) try: - if msg: - os.write(self.fd, "ok %s\n" % (msg,)) - else: - os.write(self.fd, "ok\n") + os.write(self.fd, ok_msg) except os.error: logging.exception("Write g-code ack") self.need_ack = False + return True def respond_raw(self, msg): if self.is_fileinput: return @@ -389,32 +389,16 @@ class GCodeParser: return eparams except ValueError as e: raise self.error("Malformed command '%s'" % (params['#original'],)) - # Temperature wrappers - def _get_temp(self, eventtime): - # Tn:XXX /YYY B:XXX /YYY - out = [] - if self.heaters is not None: - for gcode_id, sensor in sorted(self.heaters.get_gcode_sensors()): - cur, target = sensor.get_temp(eventtime) - out.append("%s:%.1f /%.1f" % (gcode_id, cur, target)) - if not out: - return "T:0" - return " ".join(out) - def wait_for_temperature(self, heater): - # Helper to wait on heater.check_busy() and report M105 temperatures - if self.is_fileinput: - return - eventtime = self.reactor.monotonic() - while self.is_printer_ready and heater.check_busy(eventtime): - print_time = self.toolhead.get_last_move_time() - self.respond_raw(self._get_temp(eventtime)) - eventtime = self.reactor.pause(eventtime + 1.) # G-Code special command handlers def cmd_default(self, params): + cmd = params.get('#command') + if cmd == 'M105': + # Don't warn about temperature requests when not ready + self.ack("T:0") + return if not self.is_printer_ready: raise self.error(self.printer.get_state_message()) return - cmd = params.get('#command') if not cmd: logging.debug(params['#original']) return @@ -446,7 +430,7 @@ class GCodeParser: 'G1', 'G4', 'G28', 'M400', 'G20', 'M82', 'M83', 'G90', 'G91', 'G92', 'M114', 'M220', 'M221', 'SET_GCODE_OFFSET', 'SAVE_GCODE_STATE', 'RESTORE_GCODE_STATE', - 'M105', 'M112', 'M115', 'IGNORE', 'GET_POSITION', + 'M112', 'M115', 'IGNORE', 'GET_POSITION', 'RESTART', 'FIRMWARE_RESTART', 'ECHO', 'STATUS', 'HELP'] # G-Code movement commands cmd_G1_aliases = ['G0'] @@ -602,14 +586,6 @@ class GCodeParser: self.last_position[:3] = state['last_position'][:3] self.move_with_transform(self.last_position, speed) # G-Code miscellaneous commands - cmd_M105_when_not_ready = True - def cmd_M105(self, params): - # Get Extruder Temperature - msg = self._get_temp(self.reactor.monotonic()) - if self.need_ack: - self.ack(msg) - else: - self.respond_raw(msg) cmd_M112_when_not_ready = True def cmd_M112(self, params): # Emergency Stop diff --git a/klippy/heater.py b/klippy/heater.py index 5e671a5b..4914c767 100644 --- a/klippy/heater.py +++ b/klippy/heater.py @@ -231,12 +231,15 @@ class PrinterHeaters: self.gcode_id_to_sensor = {} self.available_heaters = [] self.available_sensors = [] + self.has_started = False + self.printer.register_event_handler("klippy:ready", self._handle_ready) self.printer.register_event_handler("gcode:request_restart", self.turn_off_all_heaters) - # Register TURN_OFF_HEATERS command + # Register commands gcode = self.printer.lookup_object('gcode') gcode.register_command("TURN_OFF_HEATERS", self.cmd_TURN_OFF_HEATERS, desc=self.cmd_TURN_OFF_HEATERS_help) + gcode.register_command("M105", self.cmd_M105, when_not_ready=True) def add_sensor_factory(self, sensor_type, sensor_factory): self.sensor_factories[sensor_type] = sensor_factory def setup_heater(self, config, gcode_id=None): @@ -267,8 +270,6 @@ class PrinterHeaters: raise self.printer.config_error( "Unknown temperature sensor '%s'" % (sensor_type,)) return self.sensor_factories[sensor_type](config) - def get_gcode_sensors(self): - return self.gcode_id_to_sensor.items() def register_sensor(self, config, psensor, gcode_id=None): if gcode_id is None: gcode_id = config.get('gcode_id', None) @@ -279,15 +280,48 @@ class PrinterHeaters: "G-Code sensor id %s already registered" % (gcode_id,)) self.gcode_id_to_sensor[gcode_id] = psensor self.available_sensors.append(config.get_name()) + def get_status(self, eventtime): + return {'available_heaters': self.available_heaters, + 'available_sensors': self.available_sensors} def turn_off_all_heaters(self, print_time=0.): for heater in self.heaters.values(): heater.set_temp(0.) cmd_TURN_OFF_HEATERS_help = "Turn off all heaters" def cmd_TURN_OFF_HEATERS(self, params): self.turn_off_all_heaters() - def get_status(self, eventtime): - return {'available_heaters': self.available_heaters, - 'available_sensors': self.available_sensors} + # G-Code M105 temperature reporting + def _handle_ready(self): + self.has_started = True + def _get_temp(self, eventtime): + # Tn:XXX /YYY B:XXX /YYY + out = [] + if self.has_started: + for gcode_id, sensor in sorted(self.gcode_id_to_sensor.items()): + cur, target = sensor.get_temp(eventtime) + out.append("%s:%.1f /%.1f" % (gcode_id, cur, target)) + if not out: + return "T:0" + return " ".join(out) + def cmd_M105(self, params): + # Get Extruder Temperature + gcode = self.printer.lookup_object("gcode") + reactor = self.printer.get_reactor() + msg = self._get_temp(reactor.monotonic()) + did_ack = gcode.ack(msg) + if not did_ack: + gcode.respond_raw(msg) + def wait_for_temperature(self, heater): + # Helper to wait on heater.check_busy() and report M105 temperatures + if self.printer.get_start_args().get('debugoutput') is not None: + return + toolhead = self.printer.lookup_object("toolhead") + gcode = self.printer.lookup_object("gcode") + reactor = self.printer.get_reactor() + eventtime = reactor.monotonic() + while not self.printer.is_shutdown() and heater.check_busy(eventtime): + print_time = toolhead.get_last_move_time() + gcode.respond_raw(self._get_temp(eventtime)) + eventtime = reactor.pause(eventtime + 1.) def add_printer_objects(config): config.get_printer().add_object('heater', PrinterHeaters(config)) diff --git a/klippy/kinematics/extruder.py b/klippy/kinematics/extruder.py index f25b36a7..c7884932 100644 --- a/klippy/kinematics/extruder.py +++ b/klippy/kinematics/extruder.py @@ -167,7 +167,7 @@ class PrinterExtruder: heater = extruder.get_heater() heater.set_temp(temp) if wait and temp: - gcode.wait_for_temperature(heater) + self.printer.lookup_object('heater').wait_for_temperature(heater) def cmd_M109(self, params): # Set Extruder Temperature and Wait self.cmd_M104(params, wait=True)