diff --git a/components/esptool_py/run_serial_tool.cmake b/components/esptool_py/run_serial_tool.cmake index 93abb87fdc..e9109a2616 100644 --- a/components/esptool_py/run_serial_tool.cmake +++ b/components/esptool_py/run_serial_tool.cmake @@ -43,7 +43,10 @@ else() list(APPEND serial_tool_cmd -b ${ESPBAUD}) endif() +# SERIAL_TOOL_ARGS is defined during the first cmake run +# SERIAL_TOOL_EXTRA_ARGS is used for additional arguments from the command line during run-time list(APPEND serial_tool_cmd ${SERIAL_TOOL_ARGS}) +list(APPEND serial_tool_cmd $ENV{SERIAL_TOOL_EXTRA_ARGS}) execute_process(COMMAND ${serial_tool_cmd} WORKING_DIRECTORY "${WORKING_DIRECTORY}" diff --git a/tools/idf_py_actions/serial_ext.py b/tools/idf_py_actions/serial_ext.py index 51dd9f6ca6..c07aa8d3b0 100644 --- a/tools/idf_py_actions/serial_ext.py +++ b/tools/idf_py_actions/serial_ext.py @@ -3,6 +3,7 @@ import json import os +import shlex import sys from typing import Any, Dict, List @@ -158,7 +159,7 @@ def action_extensions(base_actions: Dict, project_path: str) -> Dict: RunTool('idf_monitor', monitor_args, args.project_dir, build_dir=args.build_dir, hints=hints, interactive=True)() - def flash(action: str, ctx: click.core.Context, args: PropertyDict) -> None: + def flash(action: str, ctx: click.core.Context, args: PropertyDict, force: bool, extra_args: str) -> None: """ Run esptool to flash the entire project, from an argfile generated by the build system """ @@ -169,7 +170,13 @@ def action_extensions(base_actions: Dict, project_path: str) -> Dict: return esp_port = args.port or _get_default_serial_port(args) - run_target(action, args, {'ESPBAUD': str(args.baud), 'ESPPORT': esp_port}) + extra = list() + if force: + extra.append('--force') + if extra_args: + extra += shlex.split(extra_args) + env = {'ESPBAUD': str(args.baud), 'ESPPORT': esp_port, 'SERIAL_TOOL_EXTRA_ARGS': ';'.join(extra)} + run_target(action, args, env) def erase_flash(action: str, ctx: click.core.Context, args: PropertyDict) -> None: ensure_build_directory(args, ctx.info_name) @@ -213,13 +220,27 @@ def action_extensions(base_actions: Dict, project_path: str) -> Dict: } BAUD_AND_PORT = [baud_rate, port] + flash_options = BAUD_AND_PORT + [ + { + 'names': ['--force'], + 'is_flag': True, + 'help': 'Force write, skip security and compatibility checks. Use with caution!', + }, + { + 'names': ['--extra-args'], + 'help': ( + 'Pass extra arguments to esptool separated by space. For more details see `esptool.py write_flash --help`. ' + 'For example to compress and verify data use: `idf.py flash --extra-args="--compress --verify"`. Use with caution!' + ) + } + ] serial_actions = { 'global_action_callbacks': [global_callback], 'actions': { 'flash': { 'callback': flash, 'help': 'Flash the project.', - 'options': global_options + BAUD_AND_PORT, + 'options': global_options + flash_options, 'order_dependencies': ['all', 'erase-flash'], }, 'erase-flash': { @@ -308,29 +329,31 @@ def action_extensions(base_actions: Dict, project_path: str) -> Dict: 'partition-table-flash': { 'callback': flash, 'help': 'Flash partition table only.', - 'options': BAUD_AND_PORT, + 'options': flash_options, 'order_dependencies': ['partition-table', 'erase-flash'], }, 'bootloader-flash': { 'callback': flash, 'help': 'Flash bootloader only.', - 'options': BAUD_AND_PORT, + 'options': flash_options, 'order_dependencies': ['bootloader', 'erase-flash'], }, 'app-flash': { 'callback': flash, 'help': 'Flash the app only.', - 'options': BAUD_AND_PORT, + 'options': flash_options, 'order_dependencies': ['app', 'erase-flash'], }, 'encrypted-app-flash': { 'callback': flash, 'help': 'Flash the encrypted app only.', + 'options': flash_options, 'order_dependencies': ['app', 'erase-flash'], }, 'encrypted-flash': { 'callback': flash, 'help': 'Flash the encrypted project.', + 'options': flash_options, 'order_dependencies': ['all', 'erase-flash'], }, 'erase-otadata': {