From 9f39de74b6a10dbc1a72e5dbdba0f717760a1005 Mon Sep 17 00:00:00 2001 From: horw Date: Wed, 7 Feb 2024 15:45:14 +0800 Subject: [PATCH] feat: support --esp-flash-force to run esptool.flash with the force flag --- .../pytest_embedded_arduino/serial.py | 3 ++ .../pytest_embedded_idf/serial.py | 20 ++++------ pytest-embedded-idf/tests/test_idf.py | 37 +++++++++++++++++++ .../pytest_embedded_serial_esp/serial.py | 8 +++- pytest-embedded/pytest_embedded/plugin.py | 15 +++++++- 5 files changed, 69 insertions(+), 14 deletions(-) diff --git a/pytest-embedded-arduino/pytest_embedded_arduino/serial.py b/pytest-embedded-arduino/pytest_embedded_arduino/serial.py index a7f71989..2cd402f0 100644 --- a/pytest-embedded-arduino/pytest_embedded_arduino/serial.py +++ b/pytest-embedded-arduino/pytest_embedded_arduino/serial.py @@ -51,6 +51,9 @@ def flash(self) -> None: flash_settings.append(f'--{k}') flash_settings.append(v) + if self.esp_flash_force: + flash_settings.append('--force') + try: esptool.main( ['--chip', self.app.target, 'write_flash', *flash_files, *flash_settings], diff --git a/pytest-embedded-idf/pytest_embedded_idf/serial.py b/pytest-embedded-idf/pytest_embedded_idf/serial.py index e1f59396..ee2943cf 100644 --- a/pytest-embedded-idf/pytest_embedded_idf/serial.py +++ b/pytest-embedded-idf/pytest_embedded_idf/serial.py @@ -109,8 +109,10 @@ def load_ram(self) -> None: ) def _force_flag(self): + if self.esp_flash_force: + return ['--force'] config = self.app.sdkconfig - if any((config.get('CONFIG_SECURE_FLASH_ENC_ENABLED', False), config.get('CONFIG_SECURE_BOOT', False))): + if any((config.get('SECURE_FLASH_ENC_ENABLED', False), config.get('SECURE_BOOT', False))): return ['--force'] return [] @@ -159,25 +161,19 @@ def flash(self) -> None: flash_files = [] for file in self.app.flash_files: if file.encrypted: - encrypt_files.append(hex(file.offset)) - encrypt_files.append(str(file.file_path)) + encrypt_files.extend([hex(file.offset), str(file.file_path)]) else: - flash_files.append(hex(file.offset)) - flash_files.append(file.file_path) + flash_files.extend([hex(file.offset), str(file.file_path)]) if flash_files and encrypt_files: - _args.extend(flash_files) - _args.append('--encrypt-files') - _args.extend(encrypt_files) + _args.extend([*flash_files, '--encrypt-files', *encrypt_files]) else: if flash_files: _args.extend(flash_files) else: - _args.append('--encrypt') - _args.extend(encrypt_files) + _args.extend(['--encrypt', *encrypt_files]) - _args.extend(self.app.flash_args['write_flash_args']) - _args.extend(self._force_flag()) + _args.extend([*self.app.flash_args['write_flash_args'], *self._force_flag()]) esptool.main(_args, esp=self.esp) diff --git a/pytest-embedded-idf/tests/test_idf.py b/pytest-embedded-idf/tests/test_idf.py index 8c01292f..b44fd6a6 100644 --- a/pytest-embedded-idf/tests/test_idf.py +++ b/pytest-embedded-idf/tests/test_idf.py @@ -35,6 +35,43 @@ def test_idf_serial_flash(dut): result.assert_outcomes(passed=1) +def test_esp_flash_force_flag(testdir): + testdir.makepyfile(""" + import pexpect + import pytest + + def test_idf_serial_flash(dut): + dut.expect('Hello world!') + assert dut.serial.esp_flash_force == True + """) + result = testdir.runpytest( + '-s', + '--embedded-services', 'esp,idf', + '--app-path', os.path.join(testdir.tmpdir, 'hello_world_esp32'), + '--esp-flash-force', + ) + + result.assert_outcomes(passed=1) + + +def test_esp_flash_no_force_flag(testdir): + testdir.makepyfile(""" + import pexpect + import pytest + + def test_idf_serial_flash(dut): + dut.expect('Hello world!') + assert dut.serial.esp_flash_force == False + """) + result = testdir.runpytest( + '-s', + '--embedded-services', 'esp,idf', + '--app-path', os.path.join(testdir.tmpdir, 'hello_world_esp32'), + ) + + result.assert_outcomes(passed=1) + + def test_expect_no_matching(testdir): testdir.makepyfile(""" import pexpect diff --git a/pytest-embedded-serial-esp/pytest_embedded_serial_esp/serial.py b/pytest-embedded-serial-esp/pytest_embedded_serial_esp/serial.py index 93184d77..508dc4c8 100644 --- a/pytest-embedded-serial-esp/pytest_embedded_serial_esp/serial.py +++ b/pytest-embedded-serial-esp/pytest_embedded_serial_esp/serial.py @@ -55,6 +55,7 @@ def __init__( port_mac: str = None, baud: int = Serial.DEFAULT_BAUDRATE, esptool_baud: int = ESPTOOL_DEFAULT_BAUDRATE, + esp_flash_force: bool = False, skip_autoflash: bool = False, erase_all: bool = False, meta: Optional[Meta] = None, @@ -119,6 +120,7 @@ def __init__( self.skip_autoflash = skip_autoflash self.erase_all = erase_all self.esptool_baud = esptool_baud + self.esp_flash_force = esp_flash_force super().__init__(msg_queue=msg_queue, port=self.esp._port, baud=baud, meta=meta, **kwargs) @@ -175,7 +177,11 @@ def hard_reset(self): def erase_flash(self): """Erase the complete flash""" logging.info('Erasing the flash') - esptool.main(['erase_flash', '--force'], esp=self.esp) + options = ['erase_flash'] + if self.esp_flash_force: + options.append('--force') + + esptool.main(options, esp=self.esp) if self._meta: self._meta.drop_port_app_cache(self.port) diff --git a/pytest-embedded/pytest_embedded/plugin.py b/pytest-embedded/pytest_embedded/plugin.py index eb5e42b8..f0a5bcc4 100644 --- a/pytest-embedded/pytest_embedded/plugin.py +++ b/pytest-embedded/pytest_embedded/plugin.py @@ -164,7 +164,11 @@ def pytest_addoption(parser): '--port-mac', help='MAC address of the board. (Default: None)', ) - + esp_group.addoption( + '--esp-flash-force', + action='store_true', + help='force mode for esptool', + ) idf_group = parser.getgroup('embedded-idf') idf_group.addoption( '--part-tool', @@ -765,6 +769,13 @@ def app_path(request: FixtureRequest, test_file_path: str) -> t.Optional[str]: return _request_param_or_config_option_or_default(request, 'app_path', os.path.dirname(test_file_path)) +@pytest.fixture +@multi_dut_argument +def esp_flash_force(request: FixtureRequest) -> t.Optional[str]: + """Enable parametrization for the same cli option""" + return _request_param_or_config_option_or_default(request, 'esp_flash_force', False) + + @pytest.fixture @multi_dut_argument def build_dir(request: FixtureRequest) -> t.Optional[str]: @@ -1024,6 +1035,7 @@ def _fixture_classes_and_options( skip_autoflash, erase_all, esptool_baud, + esp_flash_force, part_tool, confirm_target_elf_sha256, erase_nvs, @@ -1122,6 +1134,7 @@ def _fixture_classes_and_options( 'port_mac': port_mac, 'baud': int(baud or EspSerial.DEFAULT_BAUDRATE), 'esptool_baud': int(os.getenv('ESPBAUD') or esptool_baud or EspSerial.ESPTOOL_DEFAULT_BAUDRATE), + 'esp_flash_force': esp_flash_force, 'skip_autoflash': skip_autoflash, 'erase_all': erase_all, 'meta': _meta,