aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorKevin O'Connor <kevin@koconnor.net>2021-06-03 23:24:44 -0400
committerKevin O'Connor <kevin@koconnor.net>2021-08-28 16:08:57 -0400
commit950477849d0871766ce9d4240ddd5976a9086e33 (patch)
treeb7ab57f4c86321502a84a6d8beac9c96f140aba1
parent2e131497ca342514d543fc91cb559df2d2802462 (diff)
downloadkutter-950477849d0871766ce9d4240ddd5976a9086e33.tar.gz
kutter-950477849d0871766ce9d4240ddd5976a9086e33.tar.xz
kutter-950477849d0871766ce9d4240ddd5976a9086e33.zip
mcu: Support multi-mcu homing
Support endstops and probes attached to a different micro-controller than their associated steppers. Signed-off-by: Kevin O'Connor <kevin@koconnor.net>
-rw-r--r--docs/Config_Reference.md14
-rw-r--r--docs/Multi_MCU_Homing.md42
-rw-r--r--docs/Overview.md5
-rw-r--r--docs/_klipper3d/mkdocs.yml5
-rw-r--r--klippy/mcu.py43
5 files changed, 89 insertions, 20 deletions
diff --git a/docs/Config_Reference.md b/docs/Config_Reference.md
index 906cfb8f..a3d9842a 100644
--- a/docs/Config_Reference.md
+++ b/docs/Config_Reference.md
@@ -119,7 +119,9 @@ different names for the stepper (eg, `stepper_x` vs `stepper_a`).
Below are common stepper definitions.
See the [rotation distance document](Rotation_Distance.md) for
-information on calculating the `rotation_distance` parameter.
+information on calculating the `rotation_distance` parameter. See the
+[Multi-MCU homing](Multi_MCU_Homing.md) document for information on
+homing using multiple micro-controllers.
```
[stepper_x]
@@ -152,8 +154,10 @@ microsteps:
# distance the axis travels for one full rotation of the final gear.
# The default is to not use a gear ratio.
endstop_pin:
-# Endstop switch detection pin. This parameter must be provided for
-# the X, Y, and Z steppers on cartesian style printers.
+# Endstop switch detection pin. If this endstop pin is on a
+# different mcu than the stepper motor then it enables "multi-mcu
+# homing". This parameter must be provided for the X, Y, and Z
+# steppers on cartesian style printers.
#position_min: 0
# Minimum valid distance (in mm) the user may command the stepper to
# move to. The default is 0mm.
@@ -1611,7 +1615,9 @@ stepper_z config section.
```
[probe]
pin:
-# Probe detection pin. This parameter must be provided.
+# Probe detection pin. If the pin is on a different microcontroller
+# than the Z steppers then it enables "multi-mcu homing". This
+# parameter must be provided.
#deactivate_on_each_sample: True
# This determines if Klipper should execute deactivation gcode
# between each probe attempt when performing a multiple probe
diff --git a/docs/Multi_MCU_Homing.md b/docs/Multi_MCU_Homing.md
new file mode 100644
index 00000000..22d2508e
--- /dev/null
+++ b/docs/Multi_MCU_Homing.md
@@ -0,0 +1,42 @@
+# Multiple Micro-controller Homing and Probing
+
+Klipper supports a mechanism for homing with an endstop attached to
+one micro-controller while its stepper motors are on a different
+micro-controller. This support is referred to as "multi-mcu
+homing". This feature is also used when a Z probe is on a different
+micro-controller than the Z stepper motors.
+
+This feature can be useful to simplify wiring, as it may be more
+convenient to attach an endstop or probe to a closer micro-controller.
+However, using this feature may result in "overshoot" of the stepper
+motors during homing and probing operations.
+
+The overshoot occurs due to possible message transmission delays
+between the micro-controller monitoring the endstop and the
+micro-controllers moving the stepper motors. The Klipper code is
+designed to limit this delay to no more than 25ms. (When multi-mcu
+homing is activated, the micro-controllers send periodic status
+messages and check that corresponding status messages are received
+within 25ms.)
+
+So, for example, if homing at 10mm/s then it is possible for an
+overshoot of up to 0.250mm (10mm/s * .025s == 0.250mm). Care should be
+taken when configuring multi-mcu homing to account for this type of
+overshoot. Using slower homing or probing speeds can reduce the
+overshoot.
+
+Stepper motor overshoot should not adversely impact the precision of
+the homing and probing procedure. The Klipper code will detect the
+overshoot and account for it in its calculations. However, it is
+important that the hardware design is capable of handling overshoot
+without causing damage to the machine.
+
+Should Klipper detect a communication issue between micro-controllers
+during multi-mcu homing then it will raise a "Communication timeout
+during homing" error.
+
+Note that an axis with multiple steppers (eg, `stepper_z` and
+`stepper_z1`) need to be on the same micro-controller in order to use
+multi-mcu homing. For example, if an endstop is on a separate
+micro-controller from `stepper_z` then `stepper_z1` must be on the
+same micro-controller as `stepper_z`.
diff --git a/docs/Overview.md b/docs/Overview.md
index 632f584e..a758a991 100644
--- a/docs/Overview.md
+++ b/docs/Overview.md
@@ -41,18 +41,19 @@ communication with the Klipper developers.
using adxl345 accelerometer hardware to measure resonance.
- [Pressure advance](Pressure_Advance.md): Calibrate extruder
pressure.
-- [Slicers](Slicers.md): Configure "slicer" software for Klipper.
+- [G-Codes](G-Codes.md): Information on commands supported by Klipper.
- [Command Templates](Command_Templates.md): G-Code macros and
conditional evaluation.
- [Status Reference](Status_Reference.md): Information available to
macros (and similar).
- [TMC Drivers](TMC_Drivers.md): Using Trinamic stepper motor drivers
with Klipper.
+- [Multi-MCU Homing](Multi_MCU_Homing.md): Homing and probing using multiple micro-controllers.
+- [Slicers](Slicers.md): Configure "slicer" software for Klipper.
- [Skew correction](skew_correction.md): Adjustments for axes not
perfectly square.
- [PWM tools](Using_PWM_Tools.md): Guide on how to use PWM controlled
tools such as lasers or spindles.
-- [G-Codes](G-Codes.md): Information on commands supported by Klipper.
## Developer Documentation
diff --git a/docs/_klipper3d/mkdocs.yml b/docs/_klipper3d/mkdocs.yml
index bf8f1908..c7724dc0 100644
--- a/docs/_klipper3d/mkdocs.yml
+++ b/docs/_klipper3d/mkdocs.yml
@@ -94,14 +94,15 @@ nav:
- Resonance_Compensation.md
- Measuring_Resonances.md
- Pressure_Advance.md
- - Slicers.md
+ - G-Codes.md
- Command templates:
- Command_Templates.md
- Status_Reference.md
- TMC_Drivers.md
+ - Multi_MCU_Homing.md
+ - Slicers.md
- skew_correction.md
- Using_PWM_Tools.md
- - G-Codes.md
- Developer Documentation:
- Code_Overview.md
- Kinematics.md
diff --git a/klippy/mcu.py b/klippy/mcu.py
index eb1f319f..d568d194 100644
--- a/klippy/mcu.py
+++ b/klippy/mcu.py
@@ -125,6 +125,9 @@ class MCU_trsync:
s.note_homing_end()
return params['trigger_reason']
+TRSYNC_TIMEOUT = 0.025
+TRSYNC_SINGLE_MCU_TIMEOUT = 0.250
+
class MCU_endstop:
RETRY_QUERY = 1.000
def __init__(self, mcu, pin_params):
@@ -139,15 +142,27 @@ class MCU_endstop:
self._rest_ticks = 0
ffi_main, ffi_lib = chelper.get_ffi()
self._trdispatch = ffi_main.gc(ffi_lib.trdispatch_alloc(), ffi_lib.free)
- self._trsync = MCU_trsync(mcu, self._trdispatch)
+ self._trsyncs = [MCU_trsync(mcu, self._trdispatch)]
def get_mcu(self):
return self._mcu
def add_stepper(self, stepper):
- if stepper.get_mcu() is not self._mcu:
- raise pins.error("Endstop and stepper must be on the same mcu")
- self._trsync.add_stepper(stepper)
+ trsyncs = {trsync.get_mcu(): trsync for trsync in self._trsyncs}
+ trsync = trsyncs.get(stepper.get_mcu())
+ if trsync is None:
+ trsync = MCU_trsync(stepper.get_mcu(), self._trdispatch)
+ self._trsyncs.append(trsync)
+ trsync.add_stepper(stepper)
+ # Check for unsupported multi-mcu shared stepper rails
+ sname = stepper.get_name()
+ if sname.startswith('stepper_'):
+ for ot in self._trsyncs:
+ for s in ot.get_steppers():
+ if ot is not trsync and s.get_name().startswith(sname[:9]):
+ cerror = self._mcu.get_printer().config_error
+ raise cerror("Multi-mcu homing not supported on"
+ " multi-mcu shared axis")
def get_steppers(self):
- return self._trsync.get_steppers()
+ return [s for trsync in self._trsyncs for s in trsync.get_steppers()]
def _build_config(self):
# Setup config
self._mcu.add_config_cmd("config_endstop oid=%d pin=%s pull_up=%d"
@@ -157,7 +172,7 @@ class MCU_endstop:
" rest_ticks=0 pin_value=0 trsync_oid=0 trigger_reason=0"
% (self._oid,), on_restart=True)
# Lookup commands
- cmd_queue = self._trsync.get_command_queue()
+ cmd_queue = self._trsyncs[0].get_command_queue()
self._home_cmd = self._mcu.lookup_command(
"endstop_home oid=%c clock=%u sample_ticks=%u sample_count=%c"
" rest_ticks=%u pin_value=%c trsync_oid=%c trigger_reason=%c",
@@ -173,8 +188,12 @@ class MCU_endstop:
self._rest_ticks = rest_ticks
reactor = self._mcu.get_printer().get_reactor()
self._trigger_completion = reactor.completion()
- etrsync = self._trsync
- etrsync.start(print_time, self._trigger_completion, .250)
+ expire_timeout = TRSYNC_TIMEOUT
+ if len(self._trsyncs) == 1:
+ expire_timeout = TRSYNC_SINGLE_MCU_TIMEOUT
+ for trsync in self._trsyncs:
+ trsync.start(print_time, self._trigger_completion, expire_timeout)
+ etrsync = self._trsyncs[0]
ffi_main, ffi_lib = chelper.get_ffi()
ffi_lib.trdispatch_start(self._trdispatch, etrsync.REASON_HOST_REQUEST)
self._home_cmd.send(
@@ -183,7 +202,7 @@ class MCU_endstop:
etrsync.get_oid(), etrsync.REASON_ENDSTOP_HIT], reqclock=clock)
return self._trigger_completion
def home_wait(self, home_end_time):
- etrsync = self._trsync
+ etrsync = self._trsyncs[0]
etrsync.set_home_end_time(home_end_time)
if self._mcu.is_fileoutput():
self._trigger_completion.complete(True)
@@ -191,10 +210,10 @@ class MCU_endstop:
self._home_cmd.send([self._oid, 0, 0, 0, 0, 0, 0, 0])
ffi_main, ffi_lib = chelper.get_ffi()
ffi_lib.trdispatch_stop(self._trdispatch)
- res = etrsync.stop()
- if res == etrsync.REASON_COMMS_TIMEOUT:
+ res = [trsync.stop() for trsync in self._trsyncs]
+ if any([r == etrsync.REASON_COMMS_TIMEOUT for r in res]):
return -1.
- if res != etrsync.REASON_ENDSTOP_HIT:
+ if res[0] != etrsync.REASON_ENDSTOP_HIT:
return 0.
if self._mcu.is_fileoutput():
return home_end_time