# Update Mboot or MicroPython from a .dfu.gz file on the board's filesystem # MIT license; Copyright (c) 2019 Damien P. George import struct, time import uzlib, machine, stm FLASH_KEY1 = 0x45670123 FLASH_KEY2 = 0xcdef89ab def check_mem_contains(addr, buf): mem8 = stm.mem8 r = range(len(buf)) for off in r: if mem8[addr + off] != buf[off]: return False return True def check_mem_erased(addr, size): mem16 = stm.mem16 r = range(0, size, 2) for off in r: if mem16[addr + off] != 0xffff: return False return True def dfu_read(filename): f = open(filename, 'rb') hdr = f.read(3) f.seek(0) if hdr == b'Dfu': pass elif hdr == b'\x1f\x8b\x08': f = uzlib.DecompIO(f, 16 + 15) else: print('Invalid firmware', filename) return None elems = [] hdr = f.read(11) sig, ver, size, num_targ = struct.unpack('<5sBIB', hdr) file_offset = 11 for i in range(num_targ): hdr = f.read(274) sig, alt, has_name, name, t_size, num_elem = struct.unpack('<6sBi255sII', hdr) file_offset += 274 file_offset_t = file_offset for j in range(num_elem): hdr = f.read(8) addr, e_size = struct.unpack(' 16 * 1024 and not check_mem_erased(mboot_addr + 16 * 1024, 16 * 1024): flash_erase_sector(1) flash_write(mboot_addr, mboot_fw) flash_lock() machine.enable_irq(irq) print('New Mboot programmed.') if check_mem_contains(mboot_addr, mboot_fw): print('Verification of new Mboot succeeded.') else: print('Verification of new Mboot FAILED! Try rerunning.') print('Programming finished, can now reset or turn off.') def update_mpy(filename, fs_base, fs_len): # Check firmware is of .dfu.gz type try: with open(filename, 'rb') as f: hdr = uzlib.DecompIO(f, 16 + 15).read(6) except Exception: hdr = None if hdr != b'DfuSe\x01': print('Firmware must be a .dfu.gz file.') return ELEM_TYPE_END = 1 ELEM_TYPE_MOUNT = 2 ELEM_TYPE_FSLOAD = 3 ELEM_MOUNT_FAT = 1 mount_point = 1 mount = struct.pack('