diff --git a/esp-hal-common/ld/esp32s3/esp32s3.x b/esp-hal-common/ld/esp32s3/esp32s3.x index 731d279cc3e..bae052ad0be 100644 --- a/esp-hal-common/ld/esp32s3/esp32s3.x +++ b/esp-hal-common/ld/esp32s3/esp32s3.x @@ -34,6 +34,7 @@ SECTIONS { INSERT BEFORE .data; INCLUDE "fixups/rodata_dummy.x" +INCLUDE "fixups/external_ram_dummy.x" /* End of ESP32S3 fixups */ /* Shared sections - ordering matters */ @@ -44,6 +45,7 @@ INCLUDE "rwdata.x" INCLUDE "rtc_fast.x" INCLUDE "rtc_slow.x" INCLUDE "stack.x" +INCLUDE "external.x" /* End of Shared sections */ EXTERN(DefaultHandler); diff --git a/esp-hal-common/ld/esp32s3/memory.x b/esp-hal-common/ld/esp32s3/memory.x index 3b493fbcfee..1d2d3f96ef9 100644 --- a/esp-hal-common/ld/esp32s3/memory.x +++ b/esp-hal-common/ld/esp32s3/memory.x @@ -36,8 +36,11 @@ MEMORY /* RTC fast memory (executable). Persists over deep sleep. Only for core 0 (PRO_CPU) */ - rtc_fast_seg(RWX) : ORIGIN = 0x600fe000, len = 8k + rtc_fast_seg(RWX) : ORIGIN = 0x600fe000, len = 8k /* RTC slow memory (data accessible). Persists over deep sleep. */ rtc_slow_seg(RW) : ORIGIN = 0x50000000, len = 8k + + /* external memory, including data and text */ + psram_seg(RWX) : ORIGIN = 0x3C000020, len = 32M - 0x20 } diff --git a/esp-hal-common/ld/sections/external.x b/esp-hal-common/ld/sections/external.x new file mode 100644 index 00000000000..0ae2ac784ee --- /dev/null +++ b/esp-hal-common/ld/sections/external.x @@ -0,0 +1,36 @@ + + +SECTIONS { + .external.data : + { + _external_data_start = ABSOLUTE(.); + _external_no_heap_start = ABSOLUTE(.); + . = ALIGN(4); + *(.external.data .external.data.*) + _external_data_end = ABSOLUTE(.); + } > psram_seg AT > RODATA + + .external.bss (NOLOAD) : + { + _external_bss_start = ABSOLUTE(.); + . = ALIGN(4); + *(.external.bss .external.bss.*) + _external_bss_end = ABSOLUTE(.); + } > psram_seg + + .external.noinit (NOLOAD) : + { + . = ALIGN(4); + *(.external.noinit .external.noinit.*) + } > psram_seg + + /* must be last segment using psram_seg */ + .external_heap_start (NOLOAD) : + { + . = ALIGN (4); + _external_heap_start = ABSOLUTE(.); + } > psram_seg +} + +_external_ram_start = ABSOLUTE(ORIGIN(psram_seg)); +_external_ram_end = ABSOLUTE(ORIGIN(psram_seg)+LENGTH(psram_seg)); \ No newline at end of file diff --git a/esp-hal-common/ld/sections/fixups/external_ram_dummy.x b/esp-hal-common/ld/sections/fixups/external_ram_dummy.x new file mode 100644 index 00000000000..d87edf8ccc1 --- /dev/null +++ b/esp-hal-common/ld/sections/fixups/external_ram_dummy.x @@ -0,0 +1,17 @@ +/* + * This section is required to skip flash rodata sections, because `psram_seg` + * and `drom_seg` are on the same bus + */ + +SECTIONS { + .ext_ram_dummy (NOLOAD) : + { + . = ORIGIN(psram_seg) + (_rodata_reserved_end - _rodata_dummy_start); + + /* Prepare the alignment of the section above + */ + + . = ALIGN(0x10000); + } > psram_seg +} +INSERT BEFORE .external.data; \ No newline at end of file diff --git a/esp-hal-common/ld/sections/fixups/rodata_dummy.x b/esp-hal-common/ld/sections/fixups/rodata_dummy.x index 4b2573e9d6b..78b51c845dc 100644 --- a/esp-hal-common/ld/sections/fixups/rodata_dummy.x +++ b/esp-hal-common/ld/sections/fixups/rodata_dummy.x @@ -8,6 +8,7 @@ SECTIONS { * Thus, it must have its alignment and (at least) its size. */ + _rodata_dummy_start = ABSOLUTE(.); /* Start at the same alignment constraint than .flash.text */ . = ALIGN(ALIGNOF(.text)); diff --git a/esp-hal-common/ld/sections/rodata.x b/esp-hal-common/ld/sections/rodata.x index 4d1832a864e..272902183ba 100644 --- a/esp-hal-common/ld/sections/rodata.x +++ b/esp-hal-common/ld/sections/rodata.x @@ -15,6 +15,7 @@ SECTIONS { { . = ALIGN(4); *( .rodata_wlog_*.* ) + _rodata_reserved_end = ABSOLUTE(.); . = ALIGN(4); } > RODATA } \ No newline at end of file diff --git a/esp-hal-common/src/soc/esp32s3/psram.rs b/esp-hal-common/src/soc/esp32s3/psram.rs index 36eee7a9078..b716c4be66f 100644 --- a/esp-hal-common/src/soc/esp32s3/psram.rs +++ b/esp-hal-common/src/soc/esp32s3/psram.rs @@ -22,6 +22,17 @@ pub fn psram_vaddr_start() -> usize { unsafe { PSRAM_VADDR as usize } } +pub fn psram_vaddr_heap_start() -> usize { + extern "C" { + static mut _external_heap_start: u32; + } + unsafe { (&_external_heap_start as *const u32) as usize } +} + +pub fn psram_heap_size() -> usize { + PSRAM_BYTES - (psram_vaddr_heap_start() - psram_vaddr_start()) +} + cfg_if::cfg_if! { if #[cfg(feature = "psram-2m")] { const PSRAM_SIZE: u32 = 2; @@ -57,6 +68,8 @@ pub const PSRAM_BYTES: usize = PSRAM_SIZE as usize * 1024 * 1024; feature = "opsram-16m" ))] pub fn init_psram(_peripheral: impl crate::peripheral::Peripheral
) { + use procmacros::ram; + const CONFIG_ESP32S3_INSTRUCTION_CACHE_SIZE: u32 = 0x4000; const CONFIG_ESP32S3_ICACHE_ASSOCIATED_WAYS: u8 = 8; const CONFIG_ESP32S3_INSTRUCTION_CACHE_LINE_SIZE: u8 = 32; @@ -67,6 +80,11 @@ pub fn init_psram(_peripheral: impl crate::peripheral::Peripheral
i32;
}
unsafe {
- const MMU_PAGE_SIZE: u32 = 0x10000;
- const ICACHE_MMU_SIZE: usize = 0x800;
- const FLASH_MMU_TABLE_SIZE: usize = ICACHE_MMU_SIZE / core::mem::size_of:: bool;
+ }
+ unsafe {
+ if __zero_bss() {
+ crate::xtensa_lx_rt::zero_bss(&mut _external_bss_start, &mut _external_bss_end);
+ }
+ }
+ }
}
#[cfg(any(feature = "psram-2m", feature = "psram-4m", feature = "psram-8m"))]