def dump_context(command, args, unknown_args): build_dir = get_build_dir(args, die_if_none=False) if build_dir is None: log.wrn('no --build-dir given or found; output will be limited') runners_yaml = None else: cache = load_cmake_cache(build_dir, args) board = cache['CACHED_BOARD'] yaml_path = runners_yaml_path(build_dir, board) runners_yaml = load_runners_yaml(yaml_path) # Re-build unless asked not to, to make sure the output is up to date. if build_dir and not args.skip_rebuild: rebuild(command, build_dir, args) if args.runner: try: cls = get_runner_cls(args.runner) except ValueError: log.die(f'invalid runner name {args.runner}; choices: ' + ', '.join(cls.name() for cls in ZephyrBinaryRunner.get_runners())) else: cls = None if runners_yaml is None: dump_context_no_config(command, cls) else: log.inf(f'build configuration:', colorize=True) log.inf(f'{INDENT}build directory: {build_dir}') log.inf(f'{INDENT}board: {board}') log.inf(f'{INDENT}runners.yaml: {yaml_path}') if cls: dump_runner_context(command, cls, runners_yaml) else: dump_all_runner_context(command, runners_yaml, board, build_dir)
def do_run_common(command, args, runner_args, cached_runner_var): if args.context: _dump_context(command, args, runner_args, cached_runner_var) return command_name = command.name build_dir = _build_dir(args) if not args.skip_rebuild: try: cmake.run_build(build_dir) except CalledProcessError: if args.build_dir: log.die('cannot run {}, build in {} failed'.format( command_name, args.build_dir)) else: log.die('cannot run {}; no --build-dir given and build in ' 'current directory {} failed'.format( command_name, build_dir)) # Runner creation, phase 1. # # Get the default runner name from the cache, allowing a command # line override. Get the ZephyrBinaryRunner class by name, and # make sure it supports the command. cache_file = path.join(build_dir, args.cmake_cache or cmake.DEFAULT_CACHE) cache = cmake.CMakeCache(cache_file) board = cache['CACHED_BOARD'] available = cache.get_list('ZEPHYR_RUNNERS') if not available: log.wrn('No cached runners are available in', cache_file) runner = args.runner or cache.get(cached_runner_var) if runner is None: raise CommandContextError( textwrap.dedent(""" No {} runner available for {}. Please either specify one manually, or check your board's documentation for alternative instructions.""".format(command_name, board))) log.inf('Using runner:', runner) if runner not in available: log.wrn('Runner {} is not configured for use with {}, ' 'this may not work'.format(runner, board)) runner_cls = get_runner_cls(runner) if command_name not in runner_cls.capabilities().commands: log.die('Runner {} does not support command {}'.format( runner, command_name)) # Runner creation, phase 2. # # At this point, the common options above are already parsed in # 'args', and unrecognized arguments are in 'runner_args'. # # - Pull the RunnerConfig out of the cache # - Override cached values with applicable command-line options cfg = cached_runner_config(build_dir, cache) _override_config_from_namespace(cfg, args) # Runner creation, phase 3. # # - Pull out cached runner arguments, and append command-line # values (which should override the cache) # - Construct a runner-specific argument parser to handle cached # values plus overrides given in runner_args # - Parse arguments and create runner instance from final # RunnerConfig and parsed arguments. cached_runner_args = cache.get_list('ZEPHYR_RUNNER_ARGS_{}'.format( cmake.make_c_identifier(runner))) assert isinstance(runner_args, list), runner_args # If the user passed -- to force the parent argument parser to stop # parsing, it will show up here, and needs to be filtered out. runner_args = [arg for arg in runner_args if arg != '--'] final_runner_args = cached_runner_args + runner_args parser = argparse.ArgumentParser(prog=runner) runner_cls.add_parser(parser) parsed_args, unknown = parser.parse_known_args(args=final_runner_args) if unknown: raise CommandContextError('Runner', runner, 'received unknown arguments', unknown) runner = runner_cls.create(cfg, parsed_args) runner.run(command_name)
def do_run_common(command, args, runner_args, cached_runner_var): if args.context: _dump_context(command, args, runner_args, cached_runner_var) return command_name = command.name build_dir = _build_dir(args) if not args.skip_rebuild: _banner('west {}: rebuilding'.format(command_name)) try: cmake.run_build(build_dir) except CalledProcessError: if args.build_dir: log.die('cannot run {}, build in {} failed'.format( command_name, args.build_dir)) else: log.die('cannot run {}; no --build-dir given and build in ' 'current directory {} failed'.format( command_name, build_dir)) # Runner creation, phase 1. # # Get the default runner name from the cache, allowing a command # line override. Get the ZephyrBinaryRunner class by name, and # make sure it supports the command. cache_file = path.join(build_dir, args.cmake_cache or cmake.DEFAULT_CACHE) try: cache = cmake.CMakeCache(cache_file) except FileNotFoundError: log.die('no CMake cache found (expected one at {})'.format(cache_file)) board = cache['CACHED_BOARD'] available = cache.get_list('ZEPHYR_RUNNERS') if not available: log.wrn('No cached runners are available in', cache_file) runner = args.runner or cache.get(cached_runner_var) if runner is None: log.die('No', command_name, 'runner available for board', board, '({} is not in the cache).'.format(cached_runner_var), "Check your board's documentation for instructions.") _banner('west {}: using runner {}'.format(command_name, runner)) if runner not in available: log.wrn('Runner {} is not configured for use with {}, ' 'this may not work'.format(runner, board)) runner_cls = get_runner_cls(runner) if command_name not in runner_cls.capabilities().commands: log.die('Runner {} does not support command {}'.format( runner, command_name)) # Runner creation, phase 2. # # At this point, the common options above are already parsed in # 'args', and unrecognized arguments are in 'runner_args'. # # - Set up runner logging to delegate to west. # - Pull the RunnerConfig out of the cache # - Override cached values with applicable command-line options logger = logging.getLogger('runners') logger.setLevel(LOG_LEVEL) logger.addHandler(WestLogHandler()) cfg = cached_runner_config(build_dir, cache) _override_config_from_namespace(cfg, args) # Runner creation, phase 3. # # - Pull out cached runner arguments, and append command-line # values (which should override the cache) # - Construct a runner-specific argument parser to handle cached # values plus overrides given in runner_args # - Parse arguments and create runner instance from final # RunnerConfig and parsed arguments. cached_runner_args = cache.get_list('ZEPHYR_RUNNER_ARGS_{}'.format( cmake.make_c_identifier(runner))) assert isinstance(runner_args, list), runner_args # If the user passed -- to force the parent argument parser to stop # parsing, it will show up here, and needs to be filtered out. runner_args = [arg for arg in runner_args if arg != '--'] final_runner_args = cached_runner_args + runner_args parser = argparse.ArgumentParser(prog=runner) runner_cls.add_parser(parser) parsed_args, unknown = parser.parse_known_args(args=final_runner_args) if unknown: log.die('Runner', runner, 'received unknown arguments:', unknown) runner = runner_cls.create(cfg, parsed_args) try: runner.run(command_name) except ValueError as ve: log.err(str(ve), fatal=True) dump_traceback() raise CommandError(1) except MissingProgram as e: log.die('required program', e.filename, 'not found; install it or add its location to PATH')