Hi all, This is the inital step to adding tests for the SF subsystem plus very minor fixes. It is based on work I found on the mailing list[1]. For now, it doesn't do much but I plan on adding code to reset the flash to its initial state (based on an env flag) and more code to test the `sf protect` subcommand (which is the main goal of this series). I'm sending it now to make sure it's headed in the right direction.
Base on Stephen's comment[2], I haven't added the radomized features. I'll see how this iteration goes and maybe add it later. Changes since v2: - remove double blank lines - in sf_prepare, fix the way `speed` is read from env__sf_config - in sf_prepare, fix assert of env__sf_config['offset'] - in sf_prepare, do not fail if env__sf_config['crc32'] == 0 - in sf_{read,update}, `pattern` is in bytes. Make sure md/mw use the right sizes. - in sf_{read,update}, rename `crc_read` to `crc_pattern` when appropriate - add missing pytest.mark on test_sf_update Changes since v1: - remove unnecessary skip flag from environment - move crc32() to u_boot_utils.py and add extra checks - rewrite sf_prepare to return a dict of parameter - use assert instead of pytest.fail - remove verbose from sf_prepare() - update documentation - improve readability - use ' consistently instead of " - use sf_read() in test_sf_read() - rename crc variables - add speed parameter with optional random range - allow `sf read` to write at 0x00 Thanks, Liam Beguin [ 1 ] https://patchwork.ozlabs.org/patch/623061/ [ 2 ] https://lists.denx.de/pipermail/u-boot/2018-March/321688.html Liam Beguin (7): spi: spi_flash: do not fail silently on bad user input cmd: sf: fix map_physmem check test/py: README: fix typo test/py: README: add HOSTNAME to PYTHONPATH test/py: do not import pytest multiple times test/py: add generic CRC32 function test/py: add spi_flash tests cmd/sf.c | 2 +- drivers/mtd/spi/spi_flash.c | 2 +- test/py/README.md | 6 +- test/py/tests/test_sf.py | 217 ++++++++++++++++++++++++++++++++++++++++++++ test/py/u_boot_utils.py | 24 ++++- 5 files changed, 245 insertions(+), 6 deletions(-) create mode 100644 test/py/tests/test_sf.py base-commit: f95ab1fb6e37f0601f397091bb011edf7a98b890 Published-As: https://github.com/Liambeguin/u-boot/releases/tag/test_sf-v3 interdiff vs v2: diff --git a/test/py/tests/test_sf.py b/test/py/tests/test_sf.py index 0cc2a60e68d4..8bd1623ff303 100644 --- a/test/py/tests/test_sf.py +++ b/test/py/tests/test_sf.py @@ -7,7 +7,6 @@ import pytest import random import u_boot_utils - """ Note: This test relies on boardenv_* containing configuration values to define which SPI Flash areas are available for testing. Without this, this test will @@ -45,7 +44,6 @@ env__sf_configs = ( ) """ - def sf_prepare(u_boot_console, env__sf_config): """Check global state of the SPI Flash before running any test. @@ -63,10 +61,11 @@ def sf_prepare(u_boot_console, env__sf_config): probe_id = env__sf_config.get('id', 0) speed = env__sf_config.get('speed', 0) - if isinstance(speed, list) and len(speed) == 2: - sf_params['speed'] = random.randint(speed[0], speed[1]) - else: + if isinstance(speed, int): sf_params['speed'] = speed + else: + assert len(speed) == 2, "If speed is a list, it must have 2 entries" + sf_params['speed'] = random.randint(speed[0], speed[1]) cmd = 'sf probe %d %d' % (probe_id, sf_params['speed']) @@ -87,7 +86,7 @@ def sf_prepare(u_boot_console, env__sf_config): sf_params['total_size'] = int(m.group(1)) sf_params['total_size'] *= 1024 * 1024 - assert env__sf_config['offset'] is not None, \ + assert 'offset' in env__sf_config, \ '\'offset\' is required for this test.' sf_params['len'] = env__sf_config.get('len', sf_params['erase_size']) @@ -97,12 +96,11 @@ def sf_prepare(u_boot_console, env__sf_config): 'erase length not multiple of erase size.' assert not (env__sf_config.get('writeable', False) and - env__sf_config.get('crc32', False)), \ - 'Cannot check crc32 on writeable sections' + 'crc32' in env__sf_config), \ + 'Cannot check crc32 on writeable sections' return sf_params - def sf_read(u_boot_console, env__sf_config, sf_params): """Helper function used to read and compute the CRC32 value of a section of SPI Flash memory. @@ -120,26 +118,25 @@ def sf_read(u_boot_console, env__sf_config, sf_params): addr = sf_params['ram_base'] offset = env__sf_config['offset'] count = sf_params['len'] - pattern = random.randint(0, 0xFFFFFFFF) + pattern = random.randint(0, 0xFF) crc_expected = env__sf_config.get('crc32', None) - cmd = 'mw.b %08x %08x %x' % (addr, pattern, count) + cmd = 'mw.b %08x %02x %x' % (addr, pattern, count) u_boot_console.run_command(cmd) - crc_read = u_boot_utils.crc32(u_boot_console, addr, count) + crc_pattern = u_boot_utils.crc32(u_boot_console, addr, count) if crc_expected: - assert crc_read != crc_expected + assert crc_pattern != crc_expected cmd = 'sf read %08x %08x %x' % (addr, offset, count) response = u_boot_console.run_command(cmd) assert 'Read: OK' in response, 'Read operation failed' crc_readback = u_boot_utils.crc32(u_boot_console, addr, count) - assert crc_read != crc_readback, 'sf read did not update RAM content.' + assert crc_pattern != crc_readback, 'sf read did not update RAM content.' if crc_expected: assert crc_readback == crc_expected return crc_readback - def sf_update(u_boot_console, env__sf_config, sf_params): """Helper function used to update a section of SPI Flash memory. @@ -155,18 +152,17 @@ def sf_update(u_boot_console, env__sf_config, sf_params): addr = sf_params['ram_base'] offset = env__sf_config['offset'] count = sf_params['len'] - pattern = int(random.random() * 0xFFFFFFFF) + pattern = int(random.random() * 0xFF) - cmd = 'mw.b %08x %08x %x' % (addr, pattern, count) + cmd = 'mw.b %08x %02x %x' % (addr, pattern, count) u_boot_console.run_command(cmd) - crc_read = u_boot_utils.crc32(u_boot_console, addr, count) + crc_pattern = u_boot_utils.crc32(u_boot_console, addr, count) cmd = 'sf update %08x %08x %x' % (addr, offset, count) u_boot_console.run_command(cmd) crc_readback = sf_read(u_boot_console, env__sf_config, sf_params) - assert crc_readback == crc_read - + assert crc_readback == crc_pattern @pytest.mark.buildconfigspec('cmd_sf') @pytest.mark.buildconfigspec('cmd_crc32') @@ -175,7 +171,6 @@ def test_sf_read(u_boot_console, env__sf_config): sf_params = sf_prepare(u_boot_console, env__sf_config) sf_read(u_boot_console, env__sf_config, sf_params) - @pytest.mark.buildconfigspec('cmd_sf') @pytest.mark.buildconfigspec('cmd_crc32') @pytest.mark.buildconfigspec('cmd_memory') @@ -188,7 +183,6 @@ def test_sf_read_twice(u_boot_console, env__sf_config): assert crc1 == crc2, 'CRC32 of two successive read operation do not match' - @pytest.mark.buildconfigspec('cmd_sf') @pytest.mark.buildconfigspec('cmd_crc32') @pytest.mark.buildconfigspec('cmd_memory') @@ -205,15 +199,15 @@ def test_sf_erase(u_boot_console, env__sf_config): output = u_boot_console.run_command(cmd) assert 'Erased: OK' in output, 'Erase operation failed' - cmd = 'mw.b %08x ffffffff %x' % (addr, count) + cmd = 'mw.b %08x ff %x' % (addr, count) u_boot_console.run_command(cmd) crc_ffs = u_boot_utils.crc32(u_boot_console, addr, count) crc_read = sf_read(u_boot_console, env__sf_config, sf_params) assert crc_ffs == crc_read, 'Unexpected CRC32 after erase operation.' - @pytest.mark.buildconfigspec('cmd_sf') +@pytest.mark.buildconfigspec('cmd_crc32') @pytest.mark.buildconfigspec('cmd_memory') def test_sf_update(u_boot_console, env__sf_config): if not env__sf_config.get('writeable', False): -- 2.16.1.72.g5be1f00a9a70 _______________________________________________ U-Boot mailing list U-Boot@lists.denx.de https://lists.denx.de/listinfo/u-boot