# decompyle3 version 3.9.0 # Python bytecode version base 3.7.0 (3394) # Decompiled from: Python 3.7.16 (default, Mar 30 2023, 01:25:49) # [GCC 12.2.1 20220924] # Embedded file name: BLFlashCommand.py __doc__ = '\nCreated on 20221216\n\n@author: Dillon\n' import os, re, sys, argparse, binascii, threading, configparser from libs import bflb_utils from libs.bflb_utils import get_serial_ports from libs.bflb_interface_eflash_loader import InterfaceEflashLoader def hex_to_dec(value): try: value = value.replace('0x', '') int(value, 16) return True except ValueError: return False class ThreadIot(threading.Thread): def __init__(self, config, act='download', callback=None): threading.Thread.__init__(self) self.obj = InterfaceEflashLoader() self.config = config self.callback = callback self.act = act def stop(self): pass def run(self): self.obj.run(self.act, self.config, self.callback) class MainClass: def __init__(self): self.dict_chip = { 'BL602': ('bl602', 'bl602'), 'BL702': ('bl702', 'bl702'), 'BL702L': ('bl702l', 'bl702l'), 'BL808': ('bl808', 'bl808'), 'BL606P': ('bl606p', 'bl808'), 'BL616': ('bl616', 'bl616')} def get_addr_from_partition_by_name(self, name, parition_file, index): try: with open(parition_file, 'rb') as fp: data = bytearray(fp.read()) fp.close() start = data.find(name.encode('utf-8')) if start != -1: addr = data[start + 9 + index * 4:start + 9 + 4 + index * 4] addr.reverse() addr = hex(int(binascii.hexlify(addr), 16)) return ( True, addr) print(data) print(name.encode('utf-8')) return (False, '0') except Exception as e: try: bflb_utils.printf(e) return (False, '0') finally: e = None del e def get_value(self, args): self.config = dict() self.config['param'] = dict() self.config['check_box'] = dict() self.config['input_path'] = dict() self.config['param']['interface_type'] = args.interface self.config['param']['comport_uart'] = args.port self.config['param']['chip'] = args.chipname.lower() if args.chipname.upper() not in self.dict_chip: bflb_utils.printf('Error: chipname ' + args.chipname + ' is error!') return chip = self.dict_chip[args.chipname.upper()] self.config['param']['chip_name'] = chip[0] self.config['param']['chip_type'] = chip[1] if args.interface.lower() == 'uart': self.config['param']['speed_uart'] = str(args.baudrate) self.config['param']['speed_jlink'] = '1000' else: self.config['param']['speed_uart'] = '2000000' if str(args.baudrate) == '2000000': self.config['param']['speed_jlink'] = '1000' else: self.config['param']['speed_jlink'] = str(args.baudrate) if args.efuse: self.config['check_box']['efuse'] = True self.config['input_path']['efuse'] = os.path.abspath(args.efuse) else: self.config['check_box']['efuse'] = False self.config['input_path']['efuse'] = '' self.config['input_path']['config'] = args.config try: try: self.erase = 1 self.skip_mode = '0x0, 0x0' self.boot2_isp_mode = 0 config = configparser.ConfigParser() if not os.path.exists(os.path.abspath(args.config)): bflb_utils.printf('Error: Config File Not Found!') return config.read((os.path.abspath(args.config)), encoding='utf-8') if config: for item in config.sections(): if item == 'cfg': self.erase = config.get('cfg', 'erase', fallback=1) self.skip_mode = config.get('cfg', 'skip_mode', fallback='0x0, 0x0') self.boot2_isp_mode = config.get('cfg', 'boot2_isp_mode', fallback=0) else: filedir = config.get(item, 'filedir') address = config.get(item, 'address') if not self.get_value_file(item, filedir, address, args.cpu_id): return False except Exception as e: try: config = None print('ConfigParser Error: ' + str(e)) finally: e = None del e finally: self.config['param']['erase'] = self.erase self.config['param']['skip_mode'] = self.skip_mode self.config['param']['boot2_isp_mode'] = self.boot2_isp_mode if args.key: self.config['check_box']['encrypt'] = True self.config['param']['aes_key'] = args.key self.config['param']['aes_iv'] = args.iv else: self.config['check_box']['encrypt'] = False self.config['param']['aes_key'] = '' self.config['param']['aes_iv'] = '' if args.pk: self.config['check_box']['sign'] = True self.config['input_path']['publickey'] = args.pk self.config['input_path']['privatekey'] = args.sk else: self.config['check_box']['sign'] = False self.config['input_path']['publickey'] = '' self.config['input_path']['privatekey'] = '' return self.config def get_value_file(self, name, path, addr, cpu_id=None): name = str(name) if os.path.isabs(path): path = os.path.abspath(path) else: config_dir = os.path.dirname(os.path.abspath(self.config['input_path']['config'])) path = os.path.join(config_dir, path) if cpu_id: path = path.replace('$(CHIPNAME)', self.config['param']['chip_name'] + '_' + cpu_id) else: path = path.replace('$(CHIPNAME)', self.config['param']['chip_name']) addr = str(addr) self.config[name] = {} self.config[name]['addr'] = addr self.config[name]['path'] = path if not os.path.exists(path): dir_path = os.path.dirname(path) file_name = os.path.basename(path) try: all_file_list = os.listdir(dir_path) except Exception as e: try: bflb_utils.printf(e) return False finally: e = None del e result = [] if '*' in file_name: file_name = file_name.replace('.', '\\.').replace('*', '.*[一-龥]*') for one_name in all_file_list: pattern = re.compile(file_name) temp_list = pattern.findall(one_name) if one_name in temp_list: result += temp_list if len(result) > 1: bflb_utils.printf('Error: ' + name + ' multiple files were matched! ') return False if len(result) == 0: error = 'Error: ' + name + ':' + path + ' image file is not existed' bflb_utils.printf(error) return False self.config[name]['path'] = os.path.join(dir_path, result[0]) if addr.find('@partition') != -1: bflb_utils.printf('{0} get address from partiton file {1}'.format(name, self.config['partition']['path'])) success, addr_pt = self.get_addr_from_partition_by_name(name, self.config['partition']['path'], 0) if not success: bflb_utils.printf('Fail, not find ', name, ' in partition') return False self.config[name]['addr'] = addr_pt bflb_utils.printf('Address=', addr_pt) addr = addr_pt if not hex_to_dec(addr): error = 'Error: ' + addr + ' is invalid hexadecimal value' bflb_utils.printf(error) return False return True def main(self, argv): port = None ports = [] for item in get_serial_ports(): ports.append(item['port']) if ports: try: port = sorted(ports, key=(lambda x: int(re.match('COM(\\d+)', x).group(1)) ))[0] except Exception: port = sorted(ports)[0] parser = argparse.ArgumentParser(description='flash-command') parser.add_argument('--interface', dest='interface', default='uart', help='interface to use') parser.add_argument('--port', dest='port', default=port, help='serial port to use') parser.add_argument('--chipname', dest='chipname', default='BL602', help='chip name') parser.add_argument('--baudrate', dest='baudrate', default=2000000, type=int, help='the speed at which to communicate') parser.add_argument('--config', dest='config', default='', help='run config') parser.add_argument('--cpu_id', dest='cpu_id', default='', help='cpu id') parser.add_argument('--efuse', dest='efuse', default='', help='efuse options') parser.add_argument('--key', dest='key', default='', help='aes key') parser.add_argument('--iv', dest='iv', default='', help='aes iv') parser.add_argument('--pk', dest='pk', help='ecc public key') parser.add_argument('--sk', dest='sk', default='', help='ecc private key') args = parser.parse_args(argv) if args.port: bflb_utils.printf('Serial port is ' + args.port) else: if port: bflb_utils.printf('Serial port is ' + port) else: bflb_utils.printf('Serial port is not found') bflb_utils.printf('==================================================') config = self.get_value(args) if config: self.obj = InterfaceEflashLoader() self.obj.run('download', config, None) if __name__ == '__main__': print(sys.argv) app = MainClass() app.main(sys.argv[1:]) # okay decompiling BLFlashCommand.pyc