From ea0f2313432d2d9afa82835c34ebf5fa8b525622 Mon Sep 17 00:00:00 2001 From: Kevin O'Connor Date: Sun, 17 Mar 2019 22:26:37 -0400 Subject: [PATCH] flash_usb: Improve USB reconnect timing Instead of waiting one second after entering bootloader mode, wait for the device file to reappear. This should make the flashing more resilient to slight timing difference in the OS. Signed-off-by: Kevin O'Connor --- scripts/flash_usb.py | 36 ++++++++++++++++++++++++++++++------ 1 file changed, 30 insertions(+), 6 deletions(-) diff --git a/scripts/flash_usb.py b/scripts/flash_usb.py index f1106474..9f1a7ea6 100755 --- a/scripts/flash_usb.py +++ b/scripts/flash_usb.py @@ -17,12 +17,12 @@ def enter_bootloader(device): fcntl.ioctl(fd, termios.TIOCMBIS, struct.pack('I', termios.TIOCM_DTR)) t = termios.tcgetattr(fd) t[4] = t[5] = termios.B1200 + sys.stderr.write("Entering bootloader on %s\n" % (device,)) termios.tcsetattr(fd, termios.TCSANOW, t) fcntl.ioctl(fd, termios.TIOCMBIC, struct.pack('I', termios.TIOCM_DTR)) f.close() except (IOError, OSError) as e: pass - time.sleep(1.0) # Translate a serial device name to a stable serial name in /dev/serial/by-path/ def translate_serial_to_tty(device): @@ -45,14 +45,37 @@ def translate_serial_to_usb_path(device): m = ttypath_r.match(lname) if m is None: raise error("Unable to find tty usb device") - return m.group("path") + devpath = os.path.realpath("/sys/class/tty/%s/device" % (fname,)) + return m.group("path"), devpath + +# Wait for a given path to appear +def wait_path(path, alt_path=None): + time.sleep(.100) + start_alt_path = None + end_time = time.time() + 4.0 + while 1: + time.sleep(0.100) + cur_time = time.time() + if os.path.exists(path): + sys.stderr.write("Device reconnect on %s\n" % (path,)) + time.sleep(0.100) + return path + if alt_path is not None and os.path.exists(alt_path): + if start_alt_path is None: + start_alt_path = cur_time + continue + if cur_time >= start_alt_path + 0.300: + sys.stderr.write("Device reconnect on alt path %s\n" % ( + alt_path,)) + return alt_path + if cur_time > end_time: + return path # Flash via a call to bossac def flash_bossac(device, binfile, extra_flags=[]): ttyname, pathname = translate_serial_to_tty(device) enter_bootloader(pathname) - if os.path.exists(ttyname) and not os.path.exists(pathname): - pathname = ttyname + pathname = wait_path(pathname, ttyname) baseargs = ["lib/bossac/bin/bossac", "-U", "-p", pathname] args = baseargs + extra_flags + ["-w", binfile, "-v"] sys.stderr.write(" ".join(args) + '\n\n') @@ -64,7 +87,7 @@ def flash_bossac(device, binfile, extra_flags=[]): try: subprocess.check_output(args, stderr=subprocess.STDOUT) if "-b" not in extra_flags: - time.sleep(1.) + wait_path(pathname) subprocess.check_output(args, stderr=subprocess.STDOUT) except subprocess.CalledProcessError as e: pass @@ -85,8 +108,9 @@ def flash_dfuutil(device, binfile, extra_flags=[], sudo=True): if hexfmt_r.match(device.strip()): call_dfuutil(["-d", ","+device.strip()] + extra_flags, binfile, sudo) return - buspath = translate_serial_to_usb_path(device) + buspath, devpath = translate_serial_to_usb_path(device) enter_bootloader(device) + pathname = wait_path(devpath) call_dfuutil(["-p", buspath] + extra_flags, binfile, sudo)