From: Oleksij Rempel <o.rempel@pengutronix.de>
To: barebox@lists.infradead.org
Cc: Oleksij Rempel <o.rempel@pengutronix.de>
Subject: [PATCH v2 9/9] test: Add pytest suite for NVMEM framework
Date: Thu, 5 Jun 2025 09:47:13 +0200 [thread overview]
Message-ID: <20250605074713.4170334-10-o.rempel@pengutronix.de> (raw)
In-Reply-To: <20250605074713.4170334-1-o.rempel@pengutronix.de>
Introduce test_nvmem.py, a pytest-based suite for
validating Barebox's NVMEM framework and shell commands.
It uses pytest-labgrid for target interaction.
Tests cover:
- nvmem command: Listing, dynamic rmem creation (-c, -v), parameter
validation, help.
- CDEV operations (/dev/rmemX): md/mw for read/write with various access
sizes (byte, word, long), byte swapping (-x), string/numerical data,
and wrapped md output.
- Protection: protect/unprotect commands, including writes to
protected/unprotected areas, out-of-bounds protection attempts, and
merging of overlapping protected ranges.
Includes helpers for parsing md output and checks command return
codes and data integrity. A session-wide fixture skips tests if
essential related CONFIGs are disabled.
Signed-off-by: Oleksij Rempel <o.rempel@pengutronix.de>
---
test/py/test_nvmem.py | 1019 +++++++++++++++++++++++++++++++++++++++++
1 file changed, 1019 insertions(+)
create mode 100644 test/py/test_nvmem.py
diff --git a/test/py/test_nvmem.py b/test/py/test_nvmem.py
new file mode 100644
index 000000000000..03f31108c498
--- /dev/null
+++ b/test/py/test_nvmem.py
@@ -0,0 +1,1019 @@
+import pytest
+import re
+
+# --- Essential Configuration Check ---
+
+# This list should contain the CONFIG strings for all commands and features
+# that are absolutely essential for the NVMEM test suite to run.
+ESSENTIAL_CONFIGS = [
+ "CONFIG_CMD_NVMEM", # For the 'nvmem' command itself
+ "CONFIG_CMD_MD", # For the 'md' (memory display) command
+ "CONFIG_CMD_MW", # For the 'mw' (memory write) command
+ "CONFIG_CMD_FLASH", # For 'protect' and 'unprotect' commands
+ "CONFIG_NVMEM_RMEM", # For creating dynamic rmem NVMEM devices
+ "CONFIG_FS_DEVFS" # For /dev/ device character file paths
+]
+
+@pytest.fixture(scope="session", autouse=True)
+def check_essential_barebox_configs(barebox_config):
+ """
+ Session-scoped autouse fixture to check for essential Barebox CONFIGs.
+ If any essential CONFIG is not enabled in 'barebox_config',
+ this fixture will skip all tests in the current session.
+ """
+ missing_configs = []
+ if not barebox_config:
+ pytest.skip(
+ "Skipping all NVMEM tests: Barebox config not available."
+ )
+ return
+
+ for config_opt in ESSENTIAL_CONFIGS:
+ if config_opt not in barebox_config:
+ missing_configs.append(config_opt)
+
+ if missing_configs:
+ pytest.skip(
+ "Skipping all NVMEM tests: Essential Barebox CONFIGs missing: "
+ f"{', '.join(missing_configs)}"
+ )
+
+# --- Individual Test Skip Helper ---
+def skip_disabled(barebox_config, *config_options_needed):
+ if not barebox_config:
+ pytest.skip(
+ "Test skipped: Barebox config not available for this test."
+ )
+ return
+ missing_for_this_test = []
+ for config_opt in config_options_needed:
+ if config_opt not in barebox_config:
+ missing_for_this_test.append(config_opt)
+ if missing_for_this_test:
+ pytest.skip(
+ "Test skipped, requires specific Barebox CONFIGs: "
+ f"{', '.join(missing_for_this_test)}"
+ )
+
+# --- Constants ---
+NVMEM_MAX_DYNAMIC_SIZE = 1024 * 1024
+TEST_ENV_VAR_NAME = "TESTNVMEMDEV"
+DEFAULT_DEVICE_SIZE = 1024
+
+# --- Helper Functions ---
+def string_to_hex_bytes_for_mw(s: str) -> str:
+ return " ".join([f"0x{ord(c):02x}" for c in s])
+
+def parse_md_output(output_lines: list[str],
+ access_size_char: str = 'b') -> str:
+ hex_data = []
+
+ unit_hex_len = 0
+ if access_size_char == 'b': unit_hex_len = 2
+ elif access_size_char == 'w': unit_hex_len = 4
+ elif access_size_char == 'l': unit_hex_len = 8
+ elif access_size_char == 'q': unit_hex_len = 16 # For 64-bit quad
+ else:
+ return ""
+
+ hex_part_regex_str = r"^[0-9a-fA-F]+:\s+((?:[0-9a-fA-F]{" + str(unit_hex_len) + r"}\s*)+)"
+ hex_part_regex = re.compile(hex_part_regex_str)
+
+ for i, line in enumerate(output_lines):
+ match = hex_part_regex.match(line)
+ if match:
+ captured_group1 = match.group(1)
+ data_part = "".join(captured_group1.split())
+ hex_data.append(data_part)
+
+ full_hex_string = "".join(hex_data)
+ return full_hex_string.lower()
+
+def parse_md_word_value(output_lines: list[str]) -> int | None: # For 16-bit
+ hex_string = parse_md_output(output_lines, 'w')
+ if hex_string and len(hex_string) == 4: # 16-bit word is 4 hex chars
+ try:
+ return int(hex_string, 16)
+ except ValueError:
+ return None
+ return None
+
+def parse_md_long_value(output_lines: list[str]) -> int | None: # For 32-bit
+ hex_string = parse_md_output(output_lines, 'l')
+ if hex_string and len(hex_string) == 8:
+ try:
+ return int(hex_string, 16)
+ except ValueError:
+ return None
+ return None
+
+def parse_md_bytes_to_string(output_lines: list[str], expected_num_bytes: int) -> str | None:
+ hex_string = parse_md_output(output_lines, 'b')
+
+ expected_hex_len = expected_num_bytes * 2
+ if len(hex_string) > expected_hex_len:
+ hex_string = hex_string[:expected_hex_len]
+
+ if hex_string and len(hex_string) == expected_hex_len :
+ try:
+ if len(hex_string) % 2 != 0:
+ return None
+
+ bytes_obj = bytes.fromhex(hex_string)
+ decoded_string = bytes_obj.decode('ascii', errors='replace')
+ return decoded_string
+ except ValueError:
+ return None
+ return None
+
+# --- Pytest Fixtures (test-specific setup) ---
+@pytest.fixture(scope="function")
+def created_nvmem_device_name(barebox, barebox_config):
+ """
+ Creates a new dynamic NVMEM rmem device and yields its actual name
+ suitable for /dev/ path construction (e.g., "rmem0").
+ This fixture assumes sequential execution and that it can reliably
+ determine the newly created device by diffing `nvmem` output.
+ """
+ stdout_before, _, _ = barebox.run('nvmem')
+ rmem_devices_before = {
+ line.strip() for line in stdout_before if line.strip().startswith('rmem')
+ }
+
+ create_cmd = f'nvmem -c {DEFAULT_DEVICE_SIZE}'
+ barebox.run_check(create_cmd)
+
+ stdout_after, _, _ = barebox.run('nvmem')
+ rmem_devices_after = {
+ line.strip() for line in stdout_after if line.strip().startswith('rmem')
+ }
+
+ newly_created_devices = rmem_devices_after - rmem_devices_before
+ if not newly_created_devices:
+ pytest.fail("Failed to identify newly created NVMEM device: "
+ "No new 'rmem' devices found in 'nvmem' list.")
+
+ actual_device_name_listed = ""
+ if len(newly_created_devices) > 1:
+ for dev_name in newly_created_devices:
+ if re.match(r"rmem\d+0$", dev_name):
+ actual_device_name_listed = dev_name
+ break
+ if not actual_device_name_listed:
+ # Fallback if no "rmemX0" found among multiple new devices
+ actual_device_name_listed = list(newly_created_devices)[0]
+ else:
+ actual_device_name_listed = list(newly_created_devices)[0]
+
+ # Derive the cdev name (e.g., "rmem0") from the listed name (e.g., "rmem00")
+ cdev_name_match = re.match(r"(rmem\d+)0$", actual_device_name_listed)
+ if cdev_name_match:
+ final_cdev_name = cdev_name_match.group(1)
+ else:
+ # If it doesn't end with '0' (e.g. it's already 'rmemX')
+ cdev_name_match_direct = re.match(r"(rmem\d+)$", actual_device_name_listed)
+ if not cdev_name_match_direct:
+ pytest.fail(
+ f"Could not derive cdev base name from listed name "
+ f"'{actual_device_name_listed}' using patterns (rmemX)0 or (rmemX)."
+ )
+ final_cdev_name = cdev_name_match_direct.group(1)
+ yield final_cdev_name
+
+
+# --- Test Functions ---
+
+# == NVMEM Command Tests ==
+def test_nvmem_list_empty_or_static(barebox, barebox_config):
+ """
+ Tests the `nvmem` command without arguments.
+ It should successfully execute and list any currently available NVMEM devices
+ (which might include static ones or be empty if none are configured/created).
+
+ Manual Reproduction:
+ 1. In Barebox shell, run: `nvmem`
+ 2. Observe the output. The command should not error.
+ """
+ _, _, returncode = barebox.run('nvmem')
+ assert returncode == 0, "`nvmem` command failed"
+
+def test_nvmem_create_dynamic_device(barebox, barebox_config):
+ """
+ Tests creating a dynamic NVMEM rmem device using `nvmem -c <size>`.
+ It verifies that after creation, a new rmem device appears in the `nvmem` list.
+
+ Manual Reproduction:
+ 1. In Barebox shell, run: `nvmem` (to see initial list)
+ 2. Run: `nvmem -c 1k`
+ 3. Run: `nvmem` (again, to see the new device, e.g., "rmem00")
+ """
+ stdout_before, _, _ = barebox.run('nvmem')
+ rmem_devices_before = {
+ line.strip() for line in stdout_before if line.strip().startswith('rmem')
+ }
+ barebox.run_check(f'nvmem -c 1k') # Create a 1KB device
+ stdout_after, _, returncode = barebox.run('nvmem')
+ assert returncode == 0, "`nvmem` command failed after creating a device"
+ rmem_devices_after = {
+ line.strip() for line in stdout_after if line.strip().startswith('rmem')
+ }
+ new_devices = rmem_devices_after - rmem_devices_before
+ assert len(new_devices) == 1, (
+ f"Expected 1 new rmem device, found {len(new_devices)}. "
+ f"New: {new_devices}"
+ )
+ new_device_name = list(new_devices)[0]
+ assert re.match(r"rmem\d+0?$", new_device_name), (
+ f"New device name '{new_device_name}' does not match expected "
+ "'rmemX' or 'rmemX0' pattern."
+ )
+
+def test_nvmem_create_dynamic_device_with_var(barebox, barebox_config):
+ """
+ Tests `nvmem -c <size> -v <varname>` functionality.
+ It verifies:
+ 1. The specified environment variable is set to the created device's cdev name (e.g., "rmem1").
+ 2. The device (e.g., "rmem1" or "rmem10") is listed by the `nvmem` command.
+ This test uses a compound command to ensure the `echo` sees the variable set by `nvmem -v`.
+
+ Manual Reproduction:
+ 1. In Barebox shell, run: `nvmem` (to see current rmem device count, e.g., rmem0 exists)
+ 2. Run: `nvmem -c 2k -v MYVAR` (this should create, e.g., rmem1)
+ 3. Run: `echo ${MYVAR}` (should output, e.g., "rmem1")
+ 4. Run: `nvmem` (should list the new device, e.g., "rmem10")
+ """
+ var_to_set_in_barebox = "VTESTVAR_COMPOUND"
+
+ stdout_list_b, _, _ = barebox.run('nvmem')
+ # Count existing 'rmem' entries to predict the next index.
+ num_current_rmem = sum(1 for l in stdout_list_b if l.strip().startswith('rmem'))
+ expected_dev_name_in_var = f"rmem{num_current_rmem}" # e.g., rmem0, rmem1
+
+ # Compound command to create device and echo the variable in the same shell context
+ compound_cmd = (
+ f'nvmem -c 2k -v {var_to_set_in_barebox} && '
+ f'echo ${{{var_to_set_in_barebox}}}'
+ )
+
+ stdout_compound_raw = barebox.run_check(compound_cmd)
+
+ actual_dev_name_in_var = stdout_compound_raw[0].strip() if stdout_compound_raw else "'' (compound cmd gave no stdout lines)"
+
+ assert actual_dev_name_in_var == expected_dev_name_in_var, (
+ f"Environment variable {var_to_set_in_barebox} (from compound cmd) was "
+ f"'{actual_dev_name_in_var}', expected "
+ f"'{expected_dev_name_in_var}'"
+ )
+
+ # Verify the device is listed by `nvmem`
+ stdout_list_a, _, returncode = barebox.run('nvmem')
+ assert returncode == 0
+
+ # The 'nvmem' list might show "rmemX0" while the var stores "rmemX".
+ # The pattern checks for this.
+ list_pattern_check = actual_dev_name_in_var
+ pattern = re.compile(f"^{re.escape(list_pattern_check)}0?$")
+ assert any(pattern.match(line.strip()) for line in stdout_list_a), (
+ f"Device corresponding to '{list_pattern_check}' (pattern: '{pattern.pattern}') "
+ f"not found in `nvmem` list. List was: {stdout_list_a}"
+ )
+
+
+def test_nvmem_create_invalid_size_zero(barebox, barebox_config):
+ """
+ Tests `nvmem -c 0` (creating a device with zero size).
+ This operation should fail and the command should return a non-zero exit status
+ and print an error message.
+
+ Manual Reproduction:
+ 1. In Barebox shell, run: `nvmem -c 0`
+ 2. Observe the error message (e.g., "Error: Invalid size '0'...")
+ 3. Run: `echo $?` (should be non-zero)
+ """
+ stdout, _, returncode = barebox.run('nvmem -c 0')
+ assert returncode != 0, "`nvmem -c 0` should fail (non-zero return code)"
+ assert any("Error: Invalid size '0'" in line for line in stdout), \
+ "Expected error message for zero size not found in stdout."
+
+def test_nvmem_create_invalid_size_too_large(barebox, barebox_config):
+ """
+ Tests `nvmem -c <size>` where size exceeds NVMEM_MAX_DYNAMIC_SIZE.
+ This operation should fail, return a non-zero exit status, and print an error.
+
+ Manual Reproduction:
+ 1. In Barebox shell, run: `nvmem -c 2000000` (assuming 2MB > NVMEM_MAX_SIZE)
+ 2. Observe the error message (e.g., "Error: Size '...' exceeds maximum...")
+ 3. Run: `echo $?` (should be non-zero)
+ """
+ invalid_size = NVMEM_MAX_DYNAMIC_SIZE + 1
+ stdout, stderr, returncode = barebox.run(f'nvmem -c {invalid_size}')
+
+ assert returncode != 0, (
+ f"`nvmem -c {invalid_size}` was expected to fail (non-zero returncode), "
+ f"but got {returncode}."
+ )
+ assert any(f"Error: Size '{invalid_size}' exceeds maximum" in line
+ for line in stdout), (
+ f"Expected error message for excessive size not found in stdout. "
+ f"Stdout was: {stdout!r}"
+ )
+
+
+def test_nvmem_option_v_without_c(barebox, barebox_config):
+ """
+ Tests using `nvmem -v <varname>` without the required `-c <size>` option.
+ This should be a usage error, returning a non-zero exit status and an error message.
+
+ Manual Reproduction:
+ 1. In Barebox shell, run: `nvmem -v somevar`
+ 2. Observe the error message (e.g., "Error: -v <VARNAME> option requires -c <SIZE>...")
+ 3. Run: `echo $?` (should be non-zero)
+ """
+ stdout, _, returncode = barebox.run('nvmem -v somevarname')
+ assert returncode != 0, "`nvmem -v` without `-c` should fail"
+ assert any("Error: -v <VARNAME> option requires -c <SIZE>" in line
+ for line in stdout), \
+ "Expected error for missing -c with -v not found."
+
+def test_nvmem_help_on_h_option(barebox, barebox_config):
+ """
+ Tests `nvmem -h` for displaying help/usage information.
+ Typically, help options result in a non-zero exit status after printing usage.
+
+ Manual Reproduction:
+ 1. In Barebox shell, run: `nvmem -h`
+ 2. Observe the usage information.
+ 3. Run: `echo $?` (often non-zero for help options)
+ """
+ stdout, _, returncode = barebox.run('nvmem -h')
+ assert returncode != 0, "`nvmem -h` should return non-zero"
+ assert any("Usage: nvmem" in line for line in stdout) or \
+ any("Options:" in line for line in stdout), \
+ "Help output (Usage:/Options:) not found for `nvmem -h`."
+
+# == CDEV Read/Write Tests (using mw and md) ==
+def test_nvmem_cdev_mw_md_long(barebox, barebox_config,
+ created_nvmem_device_name):
+ """
+ Tests writing a 32-bit long value to an NVMEM device using `mw -l`
+ and reading it back using `md -l` for verification.
+
+ Manual Reproduction (assuming rmem0 is created):
+ 1. Create device: `nvmem -c 1k` (note the device name, e.g., rmem0)
+ 2. Write: `mw -d /dev/rmem0 -l 0x170 0x12345678`
+ 3. Read: `md -s /dev/rmem0 -l 0x170+4` (verify output shows 12345678)
+ """
+ actual_dev_name = created_nvmem_device_name
+
+ if not actual_dev_name:
+ pytest.fail(f"Fixture created_nvmem_device_name returned empty. Cannot proceed.")
+
+ dev_path = f"/dev/{actual_dev_name}"
+
+ test_val_hex = "0x12345678"
+ test_addr_hex = "0x170"
+
+ mw_cmd = f'mw -d {dev_path} -l {test_addr_hex} {test_val_hex}'
+ try:
+ barebox.run_check(mw_cmd)
+ except Exception as e:
+ pytest.fail(f"mw command '{mw_cmd}' failed: {e}")
+
+ md_cmd = f'md -s {dev_path} -l {test_addr_hex}+4'
+ stdout_md = barebox.run_check(md_cmd)
+
+ read_val_int = parse_md_long_value(stdout_md)
+ assert read_val_int is not None, (
+ f"Failed to parse long value from md output: {stdout_md}"
+ )
+ assert read_val_int == int(test_val_hex, 16), \
+ "Read long value does not match written value."
+
+
+def test_nvmem_cdev_mw_md_bytes_string(barebox, barebox_config,
+ created_nvmem_device_name):
+ """
+ Tests writing a string as a sequence of bytes to an NVMEM device using `mw -b`
+ and reading it back using `md -b`, then verifying the string content.
+
+ Manual Reproduction (assuming rmem0 is created):
+ 1. Create device: `nvmem -c 1k`
+ 2. Write "Test": `mw -d /dev/rmem0 -b 0x40 0x54 0x65 0x73 0x74`
+ 3. Read: `md -s /dev/rmem0 -b 0x40+4` (verify ASCII part shows "Test")
+ """
+ actual_dev_name = created_nvmem_device_name
+ if not actual_dev_name:
+ pytest.fail(f"Fixture created_nvmem_device_name returned empty for test_nvmem_cdev_mw_md_bytes_string.")
+ dev_path = f"/dev/{actual_dev_name}"
+
+ test_string = "BareboxNVMEMTest" # Length 16
+ hex_bytes_for_mw_cmd = string_to_hex_bytes_for_mw(test_string)
+ num_bytes = len(test_string)
+ test_addr_hex = "0x40"
+
+ mw_cmd = f'mw -d {dev_path} -b {test_addr_hex} {hex_bytes_for_mw_cmd}'
+ try:
+ barebox.run_check(mw_cmd)
+ except Exception as e:
+ pytest.fail(f"mw command failed in test_nvmem_cdev_mw_md_bytes_string: {e}")
+
+ md_cmd = f'md -s {dev_path} -b {test_addr_hex}+{num_bytes}'
+ stdout_md = barebox.run_check(md_cmd)
+
+ read_string = parse_md_bytes_to_string(stdout_md, num_bytes)
+
+ assert read_string is not None, (
+ f"Failed to parse byte string from md output: {stdout_md}"
+ )
+ assert read_string == test_string, \
+ "Read byte string does not match written string."
+
+def test_nvmem_cdev_mw_md_long_bytes_string_wrapped(barebox, barebox_config,
+ created_nvmem_device_name):
+ """
+ Tests writing a longer string (34 bytes) to an NVMEM device,
+ which is likely to cause `md -b` output to wrap over multiple lines.
+ Verifies that the parser correctly handles wrapped output.
+
+ Manual Reproduction (assuming rmem0 is created):
+ 1. Create device: `nvmem -c 1k`
+ 2. Write 34-byte string (e.g., "ThisIsALongerTestStringForNVMEM012"):
+ `mw -d /dev/rmem0 -b 0x80 0x54 0x68 ... 0x32` (full hex string)
+ 3. Read: `md -s /dev/rmem0 -b 0x80+34` (observe wrapped output and verify ASCII)
+ """
+ actual_dev_name = created_nvmem_device_name
+ if not actual_dev_name:
+ pytest.fail(f"Fixture created_nvmem_device_name returned empty for test_nvmem_cdev_mw_md_long_bytes_string_wrapped.")
+ dev_path = f"/dev/{actual_dev_name}"
+
+ test_string = "ThisIsALongerTestStringForNVMEM012"
+ assert len(test_string) == 34
+
+ hex_bytes_for_mw_cmd = string_to_hex_bytes_for_mw(test_string)
+ num_bytes = len(test_string)
+ test_addr_hex = "0x80"
+
+ mw_cmd = f'mw -d {dev_path} -b {test_addr_hex} {hex_bytes_for_mw_cmd}'
+ try:
+ barebox.run_check(mw_cmd)
+ except Exception as e:
+ pytest.fail(f"mw command failed in test_nvmem_cdev_mw_md_long_bytes_string_wrapped: {e}")
+
+ md_cmd = f'md -s {dev_path} -b {test_addr_hex}+{num_bytes}'
+ stdout_md = barebox.run_check(md_cmd)
+
+ read_string = parse_md_bytes_to_string(stdout_md, num_bytes)
+
+ assert read_string is not None, (
+ f"Failed to parse byte string from md output (wrapped test): {stdout_md}"
+ )
+ assert read_string == test_string, \
+ "Read byte string (wrapped test) does not match written string."
+
+# --- New tests for different parameters ---
+def test_nvmem_cdev_mw_md_word(barebox, barebox_config, created_nvmem_device_name):
+ """
+ Tests writing a 16-bit word value to an NVMEM device using `mw -w`
+ and reading it back using `md -w`.
+
+ Manual Reproduction (assuming rmem0 is created):
+ 1. Create device: `nvmem -c 1k`
+ 2. Write: `mw -d /dev/rmem0 -w 0xB0 0xABCD`
+ 3. Read: `md -s /dev/rmem0 -w 0xB0+2` (verify output shows ABCD)
+ """
+ actual_dev_name = created_nvmem_device_name
+ if not actual_dev_name:
+ pytest.fail(f"Fixture created_nvmem_device_name returned empty for test_nvmem_cdev_mw_md_word.")
+ dev_path = f"/dev/{actual_dev_name}"
+
+ test_val_hex = "0xABCD"
+ test_addr_hex = "0xB0"
+
+ mw_cmd = f'mw -d {dev_path} -w {test_addr_hex} {test_val_hex}'
+ try:
+ barebox.run_check(mw_cmd)
+ except Exception as e:
+ pytest.fail(f"mw -w command failed: {e}")
+
+ md_cmd = f'md -s {dev_path} -w {test_addr_hex}+2'
+ stdout_md = barebox.run_check(md_cmd)
+
+ read_val_int = parse_md_word_value(stdout_md)
+
+ assert read_val_int is not None, (
+ f"Failed to parse word value from md output: {stdout_md}"
+ )
+ assert read_val_int == int(test_val_hex, 16), \
+ "Read word value does not match written value."
+
+def test_nvmem_cdev_mw_md_long_swapped(barebox, barebox_config, created_nvmem_device_name):
+ """
+ Tests writing a 32-bit long value with byte swapping (`mw -l -x`)
+ and verifies the content by reading back with and without byte swap (`md -l` and `md -l -x`).
+
+ Manual Reproduction (assuming rmem0 is created):
+ 1. Create device: `nvmem -c 1k`
+ 2. Write with swap: `mw -d /dev/rmem0 -l -x 0xC0 0x12345678`
+ 3. Read without swap: `md -s /dev/rmem0 -l 0xC0+4` (should show 78563412)
+ 4. Read with swap: `md -s /dev/rmem0 -l -x 0xC0+4` (should show 12345678)
+ """
+ actual_dev_name = created_nvmem_device_name
+ if not actual_dev_name:
+ pytest.fail(f"Fixture created_nvmem_device_name returned empty for test_nvmem_cdev_mw_md_long_swapped.")
+ dev_path = f"/dev/{actual_dev_name}"
+
+ original_val_hex = "0x12345678"
+ swapped_val_on_device_hex = "0x78563412"
+ test_addr_hex = "0xC0"
+
+ mw_cmd = f'mw -d {dev_path} -l -x {test_addr_hex} {original_val_hex}'
+ try:
+ barebox.run_check(mw_cmd)
+ except Exception as e:
+ pytest.fail(f"mw -l -x command failed: {e}")
+
+ md_cmd_no_swap = f'md -s {dev_path} -l {test_addr_hex}+4'
+ stdout_md_no_swap = barebox.run_check(md_cmd_no_swap)
+ read_val_no_swap = parse_md_long_value(stdout_md_no_swap)
+ assert read_val_no_swap is not None, \
+ f"Failed to parse md (no swap) output: {stdout_md_no_swap}"
+ assert read_val_no_swap == int(swapped_val_on_device_hex, 16), \
+ "Reading without swap did not yield the byte-swapped value."
+
+ md_cmd_with_swap = f'md -s {dev_path} -l -x {test_addr_hex}+4'
+ stdout_md_with_swap = barebox.run_check(md_cmd_with_swap)
+ read_val_with_swap = parse_md_long_value(stdout_md_with_swap)
+ assert read_val_with_swap is not None, \
+ f"Failed to parse md -x (with swap) output: {stdout_md_with_swap}"
+ assert read_val_with_swap == int(original_val_hex, 16), \
+ "Reading with swap did not yield the original value."
+
+
+# == Protection Mechanism Tests ==
+def test_nvmem_protect_then_write_fail(barebox, barebox_config,
+ created_nvmem_device_name):
+ """
+ Tests NVMEM protection:
+ 1. Writes an initial value to a memory region.
+ 2. Protects that region.
+ 3. Attempts to write a new value to the protected region (should fail).
+ 4. Verifies that the region still contains the original value.
+
+ Manual Reproduction (assuming rmem0 is created):
+ 1. Create device: `nvmem -c 1k`
+ 2. Write initial: `mw -d /dev/rmem0 -l 0x10 0x11223344`
+ 3. Protect: `protect /dev/rmem0 0x10+4`
+ 4. Attempt write (fail): `mw -d /dev/rmem0 -l 0x10 0xAABBCCDD` (observe error)
+ 5. Verify: `md -s /dev/rmem0 -l 0x10+4` (should still be 11223344)
+ """
+ actual_dev_name = created_nvmem_device_name
+ if not actual_dev_name:
+ pytest.fail(f"Fixture created_nvmem_device_name returned empty for test_nvmem_protect_then_write_fail.")
+ dev_path = f"/dev/{actual_dev_name}"
+
+ addr_hex = "0x10"
+ length = 4
+ val_before_hex = "0x11223344"
+ val_attempt_hex = "0xAABBCCDD"
+ try:
+ barebox.run_check(
+ f'mw -d {dev_path} -l {addr_hex} {val_before_hex}'
+ )
+ except Exception as e:
+ pytest.fail(f"Initial mw command failed in test_nvmem_protect_then_write_fail: {e}")
+
+ stdout_protect, _, ret_protect = barebox.run(
+ f'protect {dev_path} {addr_hex}+{length}'
+ )
+ assert ret_protect == 0, "Protect command failed."
+
+ stdout_mw, stderr_mw, returncode_mw = barebox.run(
+ f'mw -d {dev_path} -l {addr_hex} {val_attempt_hex}'
+ )
+ assert returncode_mw != 0, "mw to protected area should fail."
+ full_output_mw = "".join(stdout_mw) + "".join(stderr_mw)
+ assert "overlaps with protected" in full_output_mw or \
+ "Read-only file system" in full_output_mw, \
+ "Expected error/warning for writing to protected area not found."
+
+ md_cmd_after = f'md -s {dev_path} -l {addr_hex}+{length}'
+ stdout_md_after = barebox.run_check(md_cmd_after)
+
+ read_val_after_int = parse_md_long_value(stdout_md_after)
+
+ if read_val_after_int is None:
+ pytest.fail(
+ f"Failed to parse 'md' output after failed write attempt. "
+ f"Raw 'md' output was: {stdout_md_after!r}"
+ )
+ assert read_val_after_int == int(val_before_hex, 16), \
+ "Value in protected area changed after failed write attempt."
+
+def test_nvmem_unprotect_then_write_ok(barebox, barebox_config,
+ created_nvmem_device_name):
+ """
+ Tests NVMEM unprotection:
+ 1. Writes an initial value and protects a region.
+ 2. Unprotects the region.
+ 3. Writes a new value to the (now unprotected) region (should succeed).
+ 4. Verifies the new value is present.
+
+ Manual Reproduction (assuming rmem0 is created):
+ 1. Create device: `nvmem -c 1k`
+ 2. Write initial: `mw -d /dev/rmem0 -l 0x20 0xDEADBEEF`
+ 3. Protect: `protect /dev/rmem0 0x20+4`
+ 4. Unprotect: `unprotect /dev/rmem0 0x20 4` (observe "Unprotected range..." log)
+ 5. Write new: `mw -d /dev/rmem0 -l 0x20 0x12345678`
+ 6. Verify: `md -s /dev/rmem0 -l 0x20+4` (should be 12345678)
+ """
+ actual_dev_name = created_nvmem_device_name
+ if not actual_dev_name:
+ pytest.fail(f"Fixture created_nvmem_device_name returned empty for test_nvmem_unprotect_then_write_ok.")
+ dev_path = f"/dev/{actual_dev_name}"
+
+ device_size = DEFAULT_DEVICE_SIZE
+ addr_hex = "0x20"
+ length = 4
+ val_initial_hex = "0xDEADBEEF"
+ val_after_unprotect_hex = "0x12345678"
+ try:
+ barebox.run_check(
+ f'mw -d {dev_path} -l {addr_hex} {val_initial_hex}'
+ )
+ barebox.run_check(f'protect {dev_path} {addr_hex}+{length}')
+ except Exception as e:
+ pytest.fail(f"Setup mw or protect failed in test_nvmem_unprotect_then_write_ok: {e}")
+
+ stdout_unprotect, _, ret_unprotect = barebox.run(
+ f'unprotect {dev_path} {addr_hex} {length}'
+ )
+ assert ret_unprotect == 0, "Unprotect command failed."
+ assert any(f"Unprotected range [0x0, len {device_size}]" in line
+ for line in stdout_unprotect), \
+ "Expected 'Unprotected range [0x0, len <size>]' log not found."
+
+ try:
+ barebox.run_check(
+ f'mw -d {dev_path} -l {addr_hex} {val_after_unprotect_hex}'
+ )
+ except Exception as e:
+ pytest.fail(f"Final mw command failed in test_nvmem_unprotect_then_write_ok: {e}")
+
+ stdout_md_final = barebox.run_check(
+ f'md -s {dev_path} -l {addr_hex}+{length}'
+ )
+ read_val_final_int = parse_md_long_value(stdout_md_final)
+ assert read_val_final_int == int(val_after_unprotect_hex, 16), \
+ "Value after unprotect and write is incorrect."
+
+def test_nvmem_protect_write_outside_range_ok(barebox, barebox_config,
+ created_nvmem_device_name):
+ """
+ Tests that writing outside a protected range is successful,
+ while the protected range itself remains inaccessible.
+
+ Manual Reproduction (assuming rmem0 is created):
+ 1. Create device: `nvmem -c 1k`
+ 2. Write initial to protected area: `mw -d /dev/rmem0 -l 0x30 0x00000000`
+ 3. Protect: `protect /dev/rmem0 0x30+4`
+ 4. Write outside: `mw -d /dev/rmem0 -l 0x50 0xABCDEF01`
+ 5. Verify outside: `md -s /dev/rmem0 -l 0x50+4` (should be ABCDEF01)
+ 6. Attempt write to protected (fail): `mw -d /dev/rmem0 -l 0x30 0xFFFFFFFF`
+ 7. Verify protected unchanged: `md -s /dev/rmem0 -l 0x30+4` (should be 00000000)
+ """
+ actual_dev_name = created_nvmem_device_name
+ if not actual_dev_name:
+ pytest.fail(f"Fixture created_nvmem_device_name returned empty for test_nvmem_protect_write_outside_range_ok.")
+ dev_path = f"/dev/{actual_dev_name}"
+
+ protected_addr_hex = "0x30"
+ protected_len = 4
+ initial_val_prot_hex = "0x00000000"
+ write_addr_outside_hex = "0x50"
+ val_to_write_outside_hex = "0xABCDEF01"
+ try:
+ barebox.run_check(
+ f'mw -d {dev_path} -l {protected_addr_hex} '
+ f'{initial_val_prot_hex}'
+ )
+ barebox.run_check(
+ f'protect {dev_path} {protected_addr_hex}+{protected_len}'
+ )
+ barebox.run_check(
+ f'mw -d {dev_path} -l {write_addr_outside_hex} '
+ f'{val_to_write_outside_hex}'
+ )
+ except Exception as e:
+ pytest.fail(f"Setup command failed in test_nvmem_protect_write_outside_range_ok: {e}")
+
+ stdout_md_out = barebox.run_check(
+ f'md -s {dev_path} -l {write_addr_outside_hex}+4'
+ )
+ read_val_out_int = parse_md_long_value(stdout_md_out)
+ assert read_val_out_int == int(val_to_write_outside_hex, 16), \
+ "Value written outside protected range is incorrect."
+ _, _, ret_mw_prot = barebox.run(
+ f'mw -d {dev_path} -l {protected_addr_hex} 0xFFFFFFFF'
+ )
+ assert ret_mw_prot != 0, "Write to protected area should have failed."
+ stdout_md_prot = barebox.run_check(
+ f'md -s {dev_path} -l {protected_addr_hex}+{protected_len}'
+ )
+ read_val_prot_int = parse_md_long_value(stdout_md_prot)
+ assert read_val_prot_int == int(initial_val_prot_hex, 16), \
+ "Protected area content changed or was not initially set."
+
+def test_nvmem_write_span_unprotected_protected(barebox, barebox_config,
+ created_nvmem_device_name):
+ """
+ Tests writing a sequence of bytes (`mw -b`) that spans from an unprotected
+ area into a protected area. Expects the write to fail for bytes entering
+ the protected region, but bytes in the unprotected part might be written.
+
+ Manual Reproduction (assuming rmem0 is created):
+ 1. Create device: `nvmem -c 1k`
+ 2. Protect e.g. `0x10` to `0x13`: `protect /dev/rmem0 0x10+4`
+ 3. Attempt to write 4 bytes `AA BB CC DD` starting at `0x0E`:
+ `mw -d /dev/rmem0 -b 0x0E 0xAA 0xBB 0xCC 0xDD`
+ (Expect `AA` at `0x0E`, `BB` at `0x0F` to be written. `CC` at `0x10` fails.)
+ 4. Verify: `md -s /dev/rmem0 -b 0x0E+4` (should show `AA BB 00 00` if area was zeroed)
+ """
+ actual_dev_name = created_nvmem_device_name
+ if not actual_dev_name:
+ pytest.fail(f"Fixture created_nvmem_device_name returned empty for test_nvmem_write_span_unprotected_protected.")
+ dev_path = f"/dev/{actual_dev_name}"
+
+ prot_start_addr_val = 0x10
+ prot_start_addr_hex = f"0x{prot_start_addr_val:x}"
+ prot_len = 4
+ try:
+ barebox.run_check(
+ f'protect {dev_path} {prot_start_addr_hex}+{prot_len}'
+ )
+ except Exception as e:
+ pytest.fail(f"Protect command failed in test_nvmem_write_span_unprotected_protected: {e}")
+
+ write_start_addr_val = prot_start_addr_val - 2
+ write_start_addr_hex = f"0x{write_start_addr_val:x}"
+ hex_vals_to_write = "0xAA 0xBB 0xCC 0xDD"
+ write_span_len = 4
+ stdout_mw, stderr_mw, returncode_mw = barebox.run(
+ f'mw -d {dev_path} -b {write_start_addr_hex} '
+ f'{hex_vals_to_write}'
+ )
+ assert returncode_mw != 0, "mw spanning protected boundary should fail."
+ full_output_mw = "".join(stdout_mw) + "".join(stderr_mw)
+ assert "overlaps with protected" in full_output_mw or \
+ "Read-only file system" in full_output_mw, \
+ "Expected error/warning for spanning write not found."
+ stdout_md_verify = barebox.run_check(
+ f'md -s {dev_path} -b {write_start_addr_hex}+{write_span_len}'
+ )
+ read_hex_verify = parse_md_output(stdout_md_verify, 'b')
+ assert read_hex_verify == "aabb0000", \
+ "Data in spanned region is not as expected after partial write."
+
+def test_nvmem_write_at_start_and_end_exact(barebox, barebox_config,
+ created_nvmem_device_name):
+ """
+ Tests writing exactly at the start (offset 0) and filling up to the
+ exact end of the NVMEM device. Also tests that writing 1 byte past
+ the end fails.
+
+ Manual Reproduction (assuming rmem0 is created, size 1024 bytes):
+ 1. Create device: `nvmem -c 1024`
+ 2. Write at start: `mw -d /dev/rmem0 -l 0x0 0x1A2B3C4D`
+ 3. Verify: `md -s /dev/rmem0 -l 0x0+4`
+ 4. Write at end (last 4 bytes): `mw -d /dev/rmem0 -l 0x3FC 0x5E6F7A8B` (1020 = 0x3FC)
+ 5. Verify: `md -s /dev/rmem0 -l 0x3FC+4`
+ 6. Attempt write past end: `mw -d /dev/rmem0 -b 0x400 0xFF` (should fail)
+ """
+ actual_dev_name = created_nvmem_device_name
+ if not actual_dev_name:
+ pytest.fail(f"Fixture created_nvmem_device_name returned empty for test_nvmem_write_at_start_and_end_exact.")
+ dev_path = f"/dev/{actual_dev_name}"
+
+ device_size = DEFAULT_DEVICE_SIZE
+ val_start_hex = "0x1A2B3C4D"
+ addr_start_hex = "0x0"
+ try:
+ barebox.run_check(
+ f'mw -d {dev_path} -l {addr_start_hex} {val_start_hex}'
+ )
+ except Exception as e:
+ pytest.fail(f"mw to start of device failed in test_nvmem_write_at_start_and_end_exact: {e}")
+
+ stdout_md_start = barebox.run_check(
+ f'md -s {dev_path} -l {addr_start_hex}+4'
+ )
+ assert parse_md_long_value(stdout_md_start) == int(val_start_hex, 16), \
+ "Value at device start is incorrect."
+ val_end_hex = "0x5E6F7A8B"
+ addr_end_val = device_size - 4
+ addr_end_hex = f"0x{addr_end_val:x}"
+ try:
+ barebox.run_check(
+ f'mw -d {dev_path} -l {addr_end_hex} {val_end_hex}'
+ )
+ except Exception as e:
+ pytest.fail(f"mw to end of device failed in test_nvmem_write_at_start_and_end_exact: {e}")
+
+ stdout_md_end = barebox.run_check(
+ f'md -s {dev_path} -l {addr_end_hex}+4'
+ )
+ assert parse_md_long_value(stdout_md_end) == int(val_end_hex, 16), \
+ "Value at device end is incorrect."
+ addr_past_end_val = device_size
+ addr_past_end_hex = f"0x{addr_past_end_val:x}"
+ _, _, ret_mw_past = barebox.run(
+ f'mw -d {dev_path} -b {addr_past_end_hex} 0xFF'
+ )
+ assert ret_mw_past != 0, "mw write past end should fail."
+
+def test_nvmem_protect_beyond_end_fail(barebox, barebox_config,
+ created_nvmem_device_name):
+ """
+ Tests attempting to protect a range that extends beyond the device's
+ boundaries or starts entirely outside. Expects these operations to fail
+ with a non-zero return code from the `protect` command.
+
+ Manual Reproduction (assuming rmem0 is created, size 1024 bytes):
+ 1. Create device: `nvmem -c 1k`
+ 2. Case 1 (partially out): `protect /dev/rmem0 0x3f0+32`
+ Expected: Command fails, `echo $?` is non-zero. Observe error message.
+ 3. Case 2 (fully out): `protect /dev/rmem0 0x400+4`
+ Expected: Command fails, `echo $?` is non-zero. Observe error message.
+ """
+ actual_dev_name = created_nvmem_device_name
+ if not actual_dev_name:
+ pytest.fail(f"Fixture created_nvmem_device_name returned empty for test_nvmem_protect_beyond_end_fail.")
+ dev_path = f"/dev/{actual_dev_name}"
+
+ device_size = DEFAULT_DEVICE_SIZE
+ # Case 1: Protection starts within bounds but length extends beyond.
+ prot_addr1_hex = f"0x{device_size - 16:x}"
+ prot_len1_requested = 32
+
+ protect_cmd1 = f'protect {dev_path} {prot_addr1_hex}+{prot_len1_requested}'
+ stdout_protect1, stderr_protect1, ret1 = barebox.run(protect_cmd1)
+
+ assert ret1 != 0, (
+ f"Protect partially beyond boundary expected to fail (non-zero return), "
+ f"but got {ret1}. Stdout: {stdout_protect1!r}, Stderr: {stderr_protect1!r}"
+ )
+ # Error message check removed as per user request.
+
+ # Case 2: Protection starts entirely outside the device.
+ prot_addr2_hex = f"0x{device_size:x}"
+ prot_len2 = 4
+ protect_cmd2 = f'protect {dev_path} {prot_addr2_hex}+{prot_len2}'
+ stdout_protect2, stderr_protect2, ret2 = barebox.run(protect_cmd2)
+
+ assert ret2 != 0, (
+ f"Protect starting entirely beyond boundary expected to fail (non-zero return), "
+ f"but got {ret2}. Stdout: {stdout_protect2!r}, Stderr: {stderr_protect2!r}"
+ )
+ # Error message check removed as per user request.
+
+
+def test_nvmem_protect_zero_length_noop(barebox, barebox_config,
+ created_nvmem_device_name):
+ """
+ Tests protecting a range with zero length (`protect <dev> <addr>+0`).
+ This is expected to be an invalid operation and should fail with a non-zero
+ return code. The area should remain writable.
+
+ Manual Reproduction (assuming rmem0 is created):
+ 1. Create device: `nvmem -c 1k`
+ 2. Attempt protect with zero length: `protect /dev/rmem0 0x50+0`
+ Expected: Command fails, `echo $?` is non-zero. Observe error message.
+ 3. Verify writable: `mw -d /dev/rmem0 -l 0x50 0xCAFED00D` (should succeed)
+ 4. Read back: `md -s /dev/rmem0 -l 0x50+4` (should show CAFED00D)
+ """
+ actual_dev_name = created_nvmem_device_name
+ if not actual_dev_name:
+ pytest.fail(f"Fixture created_nvmem_device_name returned empty for test_nvmem_protect_zero_length_noop.")
+ dev_path = f"/dev/{actual_dev_name}"
+
+ addr_hex = "0x50"
+ val_hex = "0xCAFED00D"
+ protect_cmd = f'protect {dev_path} {addr_hex}+0'
+ stdout_prot, stderr_prot, ret_prot = barebox.run(protect_cmd)
+
+ assert ret_prot != 0, "Protect with zero length should now fail (return non-zero)."
+ # Error message check removed as per user request.
+
+ # Since protection should have failed, the area should still be writable.
+ try:
+ barebox.run_check(
+ f'mw -d {dev_path} -l {addr_hex} {val_hex}'
+ )
+ except Exception as e:
+ pytest.fail(f"mw command failed in test_nvmem_protect_zero_length_noop after failed protect: {e}")
+
+ stdout_md = barebox.run_check(
+ f'md -s {dev_path} -l {addr_hex}+4'
+ )
+ assert parse_md_long_value(stdout_md) == int(val_hex, 16), \
+ "Value should be writable after failed zero-length protect."
+
+def test_nvmem_protect_merge_overlapping(barebox, barebox_config,
+ created_nvmem_device_name):
+ """
+ Tests if two overlapping `protect` calls result in a single, correctly
+ merged protected range. The log message from `rmem.c` should reflect
+ the final merged range.
+
+ Manual Reproduction (assuming rmem0 is created):
+ 1. Create device: `nvmem -c 1k`
+ 2. Protect [0x10, len 4]: `protect /dev/rmem0 0x10+4` (observe log)
+ 3. Protect [0x12, len 4]: `protect /dev/rmem0 0x12+4`
+ (observe log, should show merged range, e.g., [0x10, len 6])
+ 4. Attempt writes to 0x10 and 0x14 (should fail).
+ """
+ actual_dev_name = created_nvmem_device_name
+ if not actual_dev_name:
+ pytest.fail(f"Fixture created_nvmem_device_name returned empty for test_nvmem_protect_merge_overlapping.")
+ dev_path = f"/dev/{actual_dev_name}"
+
+ addr1_hex, len1 = "0x10", 4
+ stdout_p1, _, ret_p1 = barebox.run(
+ f'protect {dev_path} {addr1_hex}+{len1}'
+ )
+ assert ret_p1 == 0, "First protect call failed."
+ assert any(f"Protected range [{addr1_hex}, len {len1}]" in line
+ for line in stdout_p1), "Log for first protection incorrect."
+ addr2_hex, len2 = "0x12", 4
+ exp_merged_addr_hex, exp_merged_len = "0x10", 6
+ stdout_p2, _, ret_p2 = barebox.run(
+ f'protect {dev_path} {addr2_hex}+{len2}'
+ )
+ assert ret_p2 == 0, "Second (overlapping) protect call failed."
+ _, _, ret_mw_0x10 = barebox.run(f'mw -d {dev_path} -b 0x10 0xFF')
+ assert ret_mw_0x10 != 0, "Write to start of merged range (0x10) fail."
+ _, _, ret_mw_0x14 = barebox.run(f'mw -d {dev_path} -b 0x14 0xFF')
+ assert ret_mw_0x14 != 0, "Write to middle of merged range (0x14) fail."
+ barebox.run_check(f'mw -d {dev_path} -b 0x0F 0xAA')
+ barebox.run_check(f'mw -d {dev_path} -b 0x16 0xBB')
+
+def test_nvmem_mw_multiple_bytes_single_command(barebox, barebox_config,
+ created_nvmem_device_name):
+ """
+ Tests `mw -b` with multiple hexadecimal byte values provided in a single command line,
+ e.g., `mw -d /dev/rmem0 -b 0x90 0x4F 0x4B`.
+
+ Manual Reproduction (assuming rmem0 is created):
+ 1. Create device: `nvmem -c 1k`
+ 2. Write "OK": `mw -d /dev/rmem0 -b 0x90 0x4F 0x4B`
+ 3. Verify: `md -s /dev/rmem0 -b 0x90+2` (should show "OK")
+ """
+ actual_dev_name = created_nvmem_device_name
+ if not actual_dev_name:
+ pytest.fail(f"Fixture created_nvmem_device_name returned empty for test_nvmem_mw_multiple_bytes_single_command.")
+ dev_path = f"/dev/{actual_dev_name}"
+
+ hex_bytes_for_mw_cmd = "0x4F 0x4B"
+ num_bytes = 2
+ test_addr_hex = "0x90"
+ try:
+ barebox.run_check(
+ f'mw -d {dev_path} -b {test_addr_hex} {hex_bytes_for_mw_cmd}'
+ )
+ except Exception as e:
+ pytest.fail(f"mw command failed in test_nvmem_mw_multiple_bytes_single_command: {e}")
+
+ stdout_md = barebox.run_check(
+ f'md -s {dev_path} -b {test_addr_hex}+{num_bytes}'
+ )
+ read_hex_string = parse_md_output(stdout_md, 'b')
+ expected_hex_string = "4f4b"
+ assert read_hex_string == expected_hex_string, (
+ f"Read hex string '{read_hex_string}' does not match expected "
+ f"'{expected_hex_string}'."
+ )
+
+def test_nvmem_unprotect_noop_if_not_protected(barebox, barebox_config,
+ created_nvmem_device_name):
+ """
+ Tests that calling `unprotect` on a device with no active protections
+ is a no-op and succeeds. It should still log the standard "Unprotected range..."
+ message for the whole device.
+
+ Manual Reproduction (assuming rmem0 is created):
+ 1. Create device: `nvmem -c 1k` (ensure no protections are set on it)
+ 2. Run: `unprotect /dev/rmem0 0x0 1024`
+ Expected: Command succeeds, prints "Unprotected range [0x0, len 1024]"
+ """
+ actual_dev_name = created_nvmem_device_name
+ if not actual_dev_name:
+ pytest.fail(f"Fixture created_nvmem_device_name returned empty for test_nvmem_unprotect_noop_if_not_protected.")
+ dev_path = f"/dev/{actual_dev_name}"
+
+ device_size = DEFAULT_DEVICE_SIZE
+ stdout_unprot, _, ret_unprot = barebox.run(
+ f'unprotect {dev_path} 0x0 {device_size}'
+ )
+ assert ret_unprot == 0, "Unprotect should succeed if no ranges protected."
+ assert any(f"Unprotected range [0x0, len {device_size}]" in line
+ for line in stdout_unprot), \
+ "Expected 'Unprotected range' log for whole device not found."
--
2.39.5
prev parent reply other threads:[~2025-06-05 7:49 UTC|newest]
Thread overview: 10+ messages / expand[flat|nested] mbox.gz Atom feed top
2025-06-05 7:47 [PATCH v2 0/9] NVMEM: Introduce write protection support Oleksij Rempel
2025-06-05 7:47 ` [PATCH v2 1/9] nvmem: Add 'protect' operation to core framework Oleksij Rempel
2025-06-05 7:47 ` [PATCH v2 2/9] nvmem: rmem: add write and protect support Oleksij Rempel
2025-06-05 7:47 ` [PATCH v2 3/9] commands: nvmem: Add support for creating dynamic rmem devices Oleksij Rempel
2025-06-05 7:47 ` [PATCH v2 4/9] regmap: Add reg_seal operation for hardware protection Oleksij Rempel
2025-06-05 7:47 ` [PATCH v2 5/9] nvmem: regmap: Implement protect operation using regmap_seal Oleksij Rempel
2025-06-05 7:47 ` [PATCH v2 6/9] nvmem: bsec: Implement NVMEM protect via regmap_seal for OTP locking Oleksij Rempel
2025-06-05 7:47 ` [PATCH v2 7/9] nvmem: rmem: generate unic device name Oleksij Rempel
2025-06-05 7:47 ` [PATCH v2 8/9] fs: Report errors for out-of-bounds protect operations Oleksij Rempel
2025-06-05 7:47 ` Oleksij Rempel [this message]
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20250605074713.4170334-10-o.rempel@pengutronix.de \
--to=o.rempel@pengutronix.de \
--cc=barebox@lists.infradead.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox