Any way to transfer image files between master and slave esp32 chips using SPI?
Any way to transfer image files between master and slave esp32 chips using SPI?
I’m using SPI slave example which allows for data transfer between a master and slave over SPI, utilizing a GPIO for handshake between master and slave. Is there a way to transfer an image file using this protocol? This is the approach I was thinking of, but appreciate some feedback:
1. Master sends small amount of file data to slave
2. Slave saves received data to non spi buffer and signals to master to send more. This process repeats till slave has received all data from the image file.
3. Once master has transmitted all the data to slave, slave can either save the buffer to a spiffs file or so something else with the buffer.
Alternatively, what’s the best approach to transfer an image from one esp32 chip to an esp32-s3 chip over spi? A library perhaps?
1. Master sends small amount of file data to slave
2. Slave saves received data to non spi buffer and signals to master to send more. This process repeats till slave has received all data from the image file.
3. Once master has transmitted all the data to slave, slave can either save the buffer to a spiffs file or so something else with the buffer.
Alternatively, what’s the best approach to transfer an image from one esp32 chip to an esp32-s3 chip over spi? A library perhaps?
-
- Posts: 1818
- Joined: Mon Oct 17, 2022 7:38 pm
- Location: Europe, Germany
Re: Any way to transfer image files between master and slave esp32 chips using SPI?
If you have enough RAM to hold all the data of one transaction, you'd usually just let the SPI DMA all the received data into the buffer in one go and be done.
You could also use double-buffering, processing one buffer of received data while the next chunk is being received into the other buffer, then switching buffers.
You could also use double-buffering, processing one buffer of received data while the next chunk is being received into the other buffer, then switching buffers.
Re: Any way to transfer image files between master and slave esp32 chips using SPI?
@MicroController Thanks. Does Espressif have an example for SPI DMA to look at? I haven't come across that yet and am curious.
-
- Posts: 1818
- Joined: Mon Oct 17, 2022 7:38 pm
- Location: Europe, Germany
Re: Any way to transfer image files between master and slave esp32 chips using SPI?
To use DMA, just pass SPI_DMA_CH_AUTO to spi_bus_initialize(), and make sure the buffers you use for transfers are DMA-compatible.
See also https://github.com/espressif/esp-idf/tr ... /spi_slave (has both the master and slave code).
See also https://github.com/espressif/esp-idf/tr ... /spi_slave (has both the master and slave code).
Re: Any way to transfer image files between master and slave esp32 chips using SPI?
Thanks. Turns out I already have the SPI_DMA_CH_AUTO flag in spi_bus_initialize(). The buffers you refer to - do they need to be internal buffers or can they reside on external SPI RAM? Read somewhere that DMA capable RAM doesn't yet work with external RAM - is that still the case? Asking because the following lines of code cause my code to reboot endlessly:
Here's the error I get
This error resolves itself when I remove the MALLOC_CAP_DMA flag from heap_caps_malloc().
I'm working with a ESP32 master and ESP32-S3 slave (WROOM-1 module with 8 MB RAM). My concern is that if I transfer a 1 MB file's worth of data from the master, how I'd end up transferring it efficiently from master to slave and then displaying it on a LCD attached to the slave. No matter how many internal buffers I end up using, they're not going to be large enough to accommodate 1 MB worth of data.
Code: Select all
DMA_ATTR static uint8_t *recvbuf = NULL;
recvbuf = heap_caps_malloc(1000000, MALLOC_CAP_SPIRAM | MALLOC_CAP_DMA)
Guru Meditation Error: Core 0 panic'ed (LoadProhibited). Exception was unhandled.
Core 0 register dump:
PC : 0x400556d5 PS : 0x00060e30 A0 : 0x82014022 A1 : 0x3fc992b0
0x400556d5: strlen in ROM
A2 : 0x00000000 A3 : 0xfffffffc A4 : 0x000000ff A5 : 0x0000ff00
A6 : 0x00ff0000 A7 : 0xff000000 A8 : 0x00000000 A9 : 0x00000000
A10 : 0x00000000 A11 : 0x00000010 A12 : 0x3fc994f4 A13 : 0x00000000
A14 : 0x3fc994c4 A15 : 0x00000001 SAR : 0x00000004 EXCCAUSE: 0x0000001c
EXCVADDR: 0x00000000 LBEG : 0x400556d5 LEND : 0x400556e5 LCOUNT : 0xffffffff
0x400556d5: strlen in ROM
0x400556e5: strlen in ROM
Backtrace: 0x400556d2:0x3fc992b0 |<-CORRUPTED
0x400556d2: strlen in ROM
ELF file SHA256: 13b93f7d1
Rebooting...
ESP-ROM:esp32s3-20210327
Build:Mar 27 2021
rst:0xc (RTC_SW_CPU_RST),boot:0x8 (SPI_FAST_FLASH_BOOT)
Saved PC:0x40375aa0
0x40375aa0: esp_restart_noos at C:/Users/karun/ESP/esp-idf/components/esp_system/port/soc/esp32s3/system_internal.c:158 (discriminator 1)
SPIWP:0xee
mode:DIO, clock div:1
load:0x3fce3810,len:0x171c
load:0x403c9700,len:0x4
load:0x403c9704,len:0xc20
load:0x403cc700,len:0x2f94
SHA-256 comparison failed:
Calculated: 69b7a3013875b94363c030717518c738ac90a249877a1ef67f5047554d9c611a
Expected: ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff
Attempting to boot anyway...
entry 0x403c9910
This error resolves itself when I remove the MALLOC_CAP_DMA flag from heap_caps_malloc().
I'm working with a ESP32 master and ESP32-S3 slave (WROOM-1 module with 8 MB RAM). My concern is that if I transfer a 1 MB file's worth of data from the master, how I'd end up transferring it efficiently from master to slave and then displaying it on a LCD attached to the slave. No matter how many internal buffers I end up using, they're not going to be large enough to accommodate 1 MB worth of data.
-
- Posts: 1818
- Joined: Mon Oct 17, 2022 7:38 pm
- Location: Europe, Germany
Re: Any way to transfer image files between master and slave esp32 chips using SPI?
1) you should always check the result of malloc for NULL before using the pointerCode: Select all
recvbuf = heap_caps_malloc(1000000, MALLOC_CAP_SPIRAM | MALLOC_CAP_DMA);
2) on the -S3, DMA should work with PSRAM; though the heap allocator may not know that. Try heap_caps_malloc(1000000, MALLOC_CAP_SPIRAM);
Re: Any way to transfer image files between master and slave esp32 chips using SPI?
Thanks. Checking for NULL - great learning point for a newbie. So this is what I've got now:
Also using SPI mode 1 when defining spi_slave_interface_config_t as I understand there's some sort of a lag issue with SPI modes 0 and 2.
But yields status 258 (with message rxdata not in DMA-capable memory or not WORD aligned). I get this despite using DMA_ATTR or WORD_ALIGNED_ATTR when declaring recvbuf. Is recvbuf not DMA capable based on the code above? So how to prevent the message that rxdata is not in DMA-capable memory or word aligned? Do I need to make recvbuf a global variable with DMA_ATTR (or WORD_ALIGNED_ATTR) instead? If yes, why does it matter if recvbuf is global vs. static local?
Code: Select all
WORD_ALIGNED_ATTR char sendbuf[128]={0};
DMA_ATTR static char *recvbuf = NULL;
recvbuf = heap_caps_malloc(130, MALLOC_CAP_SPIRAM);
assert(recvbuf != NULL);
memset(recvbuf, 0, 2000000);
spi_slave_transaction_t t;
memset(&t, 0, sizeof(t));
t.tx_buffer=sendbuf;
t.rx_buffer = recvbuf;
But
Code: Select all
ret=spi_slave_transmit(RCV_HOST, &t, portMAX_DELAY);
-
- Posts: 1818
- Joined: Mon Oct 17, 2022 7:38 pm
- Location: Europe, Germany
Re: Any way to transfer image files between master and slave esp32 chips using SPI?
Looking at the TRM, I think on the hardware side peripheral <-> PSRAM DMA should work. It says "inlinks" should be aligned to the "block size", so you can try heap_caps_aligned_alloc():
If that doesn't do the trick, it may be that peripheral <-> PSRAM DMA actually doesn't work, or that the SPI driver just lacks the ability to see that PSRAM is DMA-capable.
Code: Select all
const uint32_t ALIGNMENT = 64;
recvbuf = heap_caps_aligned_alloc(ALIGNMENT, 130, MALLOC_CAP_SPIRAM);
Re: Any way to transfer image files between master and slave esp32 chips using SPI?
Your suggestion below to use heap_caps_aligned_calloc() didn't resolve the issue either. However, if I replace recvbuf = heap_caps_malloc(2000000, MALLOC_CAP_SPIRAM); with WORD_ALIGNED_ATTR char recvbuf[128]={0}; instead (as shown in the original spi_slave example), then it works perfectly fine. But then this approach relies on internal RAM, which isn't adequate to transfer large amounts of data over DMA. So how can I use external PSRAM with DMA?
Also, documentation for esp32-s3 shows the following:
Also, documentation for esp32-s3 shows the following:
Does this mean that PSRAM can’t be used with DMA, especially if DMA transaction descriptors can’t be placed in PSRAM?Although ESP32-S3 has hardware support for DMA to or from external RAM, there are still limitations:
DMA transaction descriptors cannot be placed in PSRAM.
The bandwidth that DMA accesses external RAM is very limited, especially when the core is trying to access the external RAM at the same time.
-
- Posts: 1818
- Joined: Mon Oct 17, 2022 7:38 pm
- Location: Europe, Germany
Re: Any way to transfer image files between master and slave esp32 chips using SPI?
If the hardware or driver won't let you DMA directly from peripheral to PSRAM, another option is to go through the internal RAM, i.e. DMA one chunk of data to internal RAM, copy it to PSRAM, then DMA the next chunk.
On the -S3, data can be DMA'd to and from PSRAM; between PSRAM and internal RAM, and even from PSRAM to PSRAM (see https://docs.espressif.com/projects/esp ... emcpy.html and https://github.com/project-x51/esp32-s3-memorycopy). That's why I tend to believe that the hardware should actually be capable of peripheral -> PSRAM DMA.
On the -S3, data can be DMA'd to and from PSRAM; between PSRAM and internal RAM, and even from PSRAM to PSRAM (see https://docs.espressif.com/projects/esp ... emcpy.html and https://github.com/project-x51/esp32-s3-memorycopy). That's why I tend to believe that the hardware should actually be capable of peripheral -> PSRAM DMA.
Who is online
Users browsing this forum: No registered users and 64 guests