aboutsummaryrefslogtreecommitdiffstats
path: root/klippy/mcu.py
diff options
context:
space:
mode:
Diffstat (limited to 'klippy/mcu.py')
-rw-r--r--klippy/mcu.py43
1 files changed, 38 insertions, 5 deletions
diff --git a/klippy/mcu.py b/klippy/mcu.py
index 09f5d232..4be952f2 100644
--- a/klippy/mcu.py
+++ b/klippy/mcu.py
@@ -301,6 +301,35 @@ class MCU_adc:
if self._callback is not None:
self._callback(last_read_time, last_value)
+# Class to retry sending of a query command until a given response is received
+class RetryAsyncCommand:
+ TIMEOUT_TIME = 5.0
+ RETRY_TIME = 0.500
+ def __init__(self, mcu, serial, name, oid=None):
+ self.reactor = mcu.get_printer().get_reactor()
+ self.serial = serial
+ self.name = name
+ self.oid = oid
+ self.completion = self.reactor.completion()
+ self.min_query_time = self.reactor.monotonic()
+ self.serial.register_response(self.handle_callback, name, oid)
+ def handle_callback(self, params):
+ if params['#sent_time'] >= self.min_query_time:
+ self.min_query_time = self.reactor.NEVER
+ self.reactor.async_complete(self.completion, params)
+ def get_response(self, cmd, cmd_queue, minclock=0, minsystime=0.):
+ first_query_time = query_time = max(self.min_query_time, minsystime)
+ while 1:
+ self.serial.raw_send(cmd, minclock, minclock, cmd_queue)
+ params = self.completion.wait(query_time + self.RETRY_TIME)
+ if params is not None:
+ self.serial.register_response(None, self.name, self.oid)
+ return params
+ query_time = self.reactor.monotonic()
+ if query_time > first_query_time + self.TIMEOUT_TIME:
+ self.serial.register_response(None, self.name, self.oid)
+ raise error("Timeout on wait for '%s' response" % (self.name,))
+
# Wrapper around command sending
class CommandWrapper:
def __init__(self, mcu, serial, clocksync, cmd, cmd_queue):
@@ -314,16 +343,20 @@ class CommandWrapper:
self._serial.raw_send(cmd, minclock, reqclock, self._cmd_queue)
def send_with_response(self, data=(), response=None, response_oid=None,
minclock=0):
- minsystime = 0.
- if minclock:
- minsystime = self._clocksync.estimate_clock_systime(minclock)
cmd = self._cmd.encode(data)
src = serialhdl.SerialRetryCommand(self._serial, response, response_oid)
try:
- return src.get_response([cmd], self._cmd_queue,
- minclock=minclock, minsystime=minsystime)
+ return src.get_response(cmd, self._cmd_queue, minclock=minclock)
except serialhdl.error as e:
raise error(str(e))
+ def send_with_async_response(self, data=(),
+ response=None, response_oid=None, minclock=0):
+ minsystime = 0.
+ if minclock:
+ minsystime = self._clocksync.estimate_clock_systime(minclock)
+ cmd = self._cmd.encode(data)
+ src = RetryAsyncCommand(self._mcu, self._serial, response, response_oid)
+ return src.get_response(cmd, self._cmd_queue, minclock, minsystime)
class MCU:
error = error