diff --git a/examples/system/.build-test-rules.yml b/examples/system/.build-test-rules.yml index 7481a8b4c2..1319c5d187 100644 --- a/examples/system/.build-test-rules.yml +++ b/examples/system/.build-test-rules.yml @@ -394,6 +394,3 @@ examples/system/xip_from_psram: disable: - if: IDF_TARGET == "esp32" reason: target esp32 doesn't support this feature. - - if: IDF_TARGET == "esp32p4" - temporary: true - reason: not supported on p4 #TODO: IDF-7556 diff --git a/examples/system/xip_from_psram/CMakeLists.txt b/examples/system/xip_from_psram/CMakeLists.txt index 2fab110f0a..0251663be4 100644 --- a/examples/system/xip_from_psram/CMakeLists.txt +++ b/examples/system/xip_from_psram/CMakeLists.txt @@ -5,4 +5,8 @@ cmake_minimum_required(VERSION 3.16) include($ENV{IDF_PATH}/tools/cmake/project.cmake) + +# "Trim" the build. Include the minimal set of components, main, and anything it depends on. +set(COMPONENTS main) + project(xip_from_psram) diff --git a/examples/system/xip_from_psram/README.md b/examples/system/xip_from_psram/README.md index 5afc68ebd2..8d54b7287f 100644 --- a/examples/system/xip_from_psram/README.md +++ b/examples/system/xip_from_psram/README.md @@ -1,5 +1,5 @@ -| Supported Targets | ESP32-S2 | ESP32-S3 | -| ----------------- | -------- | -------- | +| Supported Targets | ESP32-P4 | ESP32-S2 | ESP32-S3 | +| ----------------- | -------- | -------- | -------- | # XIP (Execute-In-Place) From PSRAM Example @@ -10,14 +10,14 @@ This example illustrates a typical usage of XIP (Execute-In-Place) From PSRAM. W ## Overview Here we define two sets of operations related to external memory: -SET1: Operations where CPU fetches data and instructions from external memory. +SET1: Operations where CPU fetches data and instructions from external memory. SET2: `ESP Flash` driver operations and other operations from drivers based on `ESP Flash` (NVS, Partition drivers, etc.). By default, during `SET2` operations, concurrent access requests to the Flash and PSRAM (`SET1` operations) will be disabled otherwise both the `SET1` and `SET2` operations are not guaranteed to be safe (this is an undefined behaviour). Only ISRs in internal RAM will get executed during `SET2` operations. Besides, if any functions or data are accessed in these ISRs (usually this happens in ISR callbacks), they need to be placed into internal RAM as well. For interrupt handlers which need to execute when the cache is disabled (e.g., for low latency operations), you need to set the ESP_INTR_FLAG_IRAM flag when the interrupt handler is registered. -When **CONFIG_SPIRAM_FETCH_INSTRUCTIONS** and **CONFIG_SPIRAM_RODATA** are both enabled, the `flash.text` sections (for instructions) and the `.rodata` section (read only data) will be moved to PSRAM. Corresponding virtual memory range will be re-mapped to PSRAM. Under this condition, ESP-IDF won't disable concurrent accesses to external memory (`SET1` operations) anymore. +When **CONFIG_SPIRAM_XIP_FROM_PSRAM** is enabled, the `flash.text` sections (for instructions) and the `.rodata` section (read only data) will be moved to PSRAM. Corresponding virtual memory range will be mapped to PSRAM. Under this condition, ESP-IDF won't disable concurrent accesses to external memory (`SET1` operations) anymore. By using this feature, during `SET2` operations, placement of ISRs, ISR callbacks, and related data are no longer limited to internal RAM. @@ -27,17 +27,17 @@ To show this feature, in this example we go through the following steps: `General Steps`: 1. Create a partition for Flash Erase Operation -2. Create an esp_timer in one-shot mode +2. Create an esp_timer in one-shot mode `PSRAM Steps`: 3. Do a Flash erase operation, and start the timer -4. ESP-Timer callback is dispatched and it calls a function in PSRAM during the flash erase operation +4. ESP-Timer callback is dispatched and it calls a function in PSRAM during the flash erase operation 5. The Flash erase operation finishes 6. Show the result about the callback(in PSRAM) response and execute time `IRAM Steps`: 7. Do a Flash erase operation, and start the timer -8. ESP-Timer callback is dispatched and it calls a function in IRAM during the flash erase operation +8. ESP-Timer callback is dispatched and it calls a function in IRAM during the flash erase operation 9. The flash erase operation finishes 10. Show the result about the callback(in IRAM) response and execute time @@ -46,28 +46,28 @@ To show this feature, in this example we go through the following steps: Initialization and config -> Flash erase start -> ESP-Timer callback(in PSRAM) appear -> Flash erase finish -> Flash erase start -> ESP-Timer callback(in IRAM) appear -> Flash erase finish ISR CPU - | | | | - | | - | * <----flash operation starts + | | + | | + | * <----flash operation starts | * - callback starts * --------> * - (in PSRAM) * * - callback finishes * <-------- * + callback starts * --------> * + (in PSRAM) * * + callback finishes * <-------- * | * | * | * <----flash operation finishes | | | | | | - | | | | - | | - | * <----flash operation starts + | | + | | + | * <----flash operation starts | * - callback starts * --------> * - (in IRAM) * * - callback finishes * <-------- * + callback starts * --------> * + (in IRAM) * * + callback finishes * <-------- * | * | * | * <----flash operation finishes diff --git a/examples/system/xip_from_psram/main/CMakeLists.txt b/examples/system/xip_from_psram/main/CMakeLists.txt index 298ffae6d6..d62665541a 100644 --- a/examples/system/xip_from_psram/main/CMakeLists.txt +++ b/examples/system/xip_from_psram/main/CMakeLists.txt @@ -1,2 +1,3 @@ idf_component_register(SRCS "xip_from_psram_example_main.c" - INCLUDE_DIRS ".") + INCLUDE_DIRS "." + REQUIRES esp_psram esp_partition spi_flash esp_timer) diff --git a/examples/system/xip_from_psram/pytest_xip_from_psram.py b/examples/system/xip_from_psram/pytest_xip_from_psram.py index 9af84289d6..a9e9ed9107 100644 --- a/examples/system/xip_from_psram/pytest_xip_from_psram.py +++ b/examples/system/xip_from_psram/pytest_xip_from_psram.py @@ -1,12 +1,12 @@ -# SPDX-FileCopyrightText: 2022 Espressif Systems (Shanghai) CO LTD +# SPDX-FileCopyrightText: 2022-2024 Espressif Systems (Shanghai) CO LTD # SPDX-License-Identifier: CC0-1.0 - import pytest from pytest_embedded.dut import Dut @pytest.mark.esp32s2 @pytest.mark.esp32s3 +@pytest.mark.esp32p4 @pytest.mark.generic # in order to build the default sdkconfig(the CI won't build the sdkconfig.defaults if there is a sdkconfig.ci.xx) @pytest.mark.parametrize( @@ -47,3 +47,24 @@ def test_xip_from_psram_example_f4r8(dut: Dut) -> None: res = dut.expect(r'callback\(in IRAM\) response time: (\d{1,3}) us') response_time = res.group(1).decode('utf8') assert float(response_time) <= 12 + + +@pytest.mark.esp32p4 +@pytest.mark.generic +@pytest.mark.parametrize( + 'config', + [ + 'esp32p4_200m', + ], + indirect=True, +) +def test_xip_from_psram_example_p4_200m(dut: Dut) -> None: + dut.expect_exact('found partition') + + res = dut.expect(r'callback\(in PSRAM\) response time: (\d{1,3}) us') + response_time = res.group(1).decode('utf8') + assert float(response_time) <= 10 + + res = dut.expect(r'callback\(in IRAM\) response time: (\d{1,3}) us') + response_time = res.group(1).decode('utf8') + assert float(response_time) <= 10 diff --git a/examples/system/xip_from_psram/sdkconfig.defaults b/examples/system/xip_from_psram/sdkconfig.defaults index 1fd37b3537..de0fd2d0fd 100644 --- a/examples/system/xip_from_psram/sdkconfig.defaults +++ b/examples/system/xip_from_psram/sdkconfig.defaults @@ -3,5 +3,4 @@ CONFIG_PARTITION_TABLE_CUSTOM_FILENAME="partitions.csv" CONFIG_PARTITION_TABLE_FILENAME="partitions.csv" CONFIG_ESP_TIMER_SUPPORTS_ISR_DISPATCH_METHOD=y CONFIG_SPIRAM=y -CONFIG_SPIRAM_FETCH_INSTRUCTIONS=y -CONFIG_SPIRAM_RODATA=y +CONFIG_SPIRAM_XIP_FROM_PSRAM=y diff --git a/examples/system/xip_from_psram/sdkconfig.esp32p4_200m b/examples/system/xip_from_psram/sdkconfig.esp32p4_200m new file mode 100644 index 0000000000..1a97836862 --- /dev/null +++ b/examples/system/xip_from_psram/sdkconfig.esp32p4_200m @@ -0,0 +1,3 @@ +CONFIG_IDF_TARGET="esp32p4" +CONFIG_IDF_EXPERIMENTAL_FEATURES=y +CONFIG_SPIRAM_SPEED_200M=y