We are trying to max out the wifi throughput via nRF7002 when connected to SPI4. Currently we only achieve around 6.3Mbits/sec (TCP Upload to peer).
When measuring the SPI4 CLK we only see 16Mhz despite configuring 32Mhz in app overlay.
Question: What can we do to configure SPI4 for 32Mhz? Will this lead to higher throughput?
Hardware:
- nRF5340-DK
- nRF7002-EK
- Modifikations: CLK, MISO and MOSI pins are connected to P0.08, P0.10 and P0.09
Software:
- nrf connect sdk version: 2.9.1
- sample: wifi/throughput
- EXTRA_CONF_FILE: overlay-high-performance.conf
- SHIELD: nrf7002ek
- custom app.overlay:
&pinctrl { spi4_default: spi4_default { group1 { psels = <NRF_PSEL(SPIM_SCK, 0, 8)>, <NRF_PSEL(SPIM_MISO, 0, 10)>, <NRF_PSEL(SPIM_MOSI, 0, 9)>; nordic,drive-mode = <NRF_DRIVE_H0H1>; }; }; spi4_sleep: spi4_sleep { group1 { psels = <NRF_PSEL(SPIM_SCK, 0, 8)>, <NRF_PSEL(SPIM_MISO, 0, 10)>, <NRF_PSEL(SPIM_MOSI, 0, 9)>; low-power-enable; }; }; }; &spi4 { max-frequency = <33000000>; clock-frequency = <32000000>; nrf70: nrf7002-spi@0 { spi-max-frequency = <33000000>; }; };
Commandline:
west build -p -b nrf5340dk/nrf5340/cpuapp -- -DSHIELD=nrf7002ek -DEXTRA_CONF_FILE=overlay-high-performance.conf
Zperf:
zperf tcp upload XXX.XXX.XXX.XXX 5001 60 1024
Update 20.03.2025:
- Setting either &spi4
max-frequency
or nrf70spi-max-frequency
to<8000000>
leads to 8Mhz frequency on the oscilloscope - Setting &spi4
clock-frequency
to<8000000>
has no effect
This was done only to verify the setup. We are still unable to set the SPI4 frequency to 32Mhz as desired.
If we are commenting out lines 160-163 in ~/ncs/v2.9.1/zephyr/drivers/spi/spi_nrfx_spim.c we are actually seeing roughly 32Mhz and have a better throughput of 7.9Mbits/sec (TCP Upload to peer). This is however a brutal hack as it reconfigures the SPI on every transceive operation.
diff --git a/drivers/spi/spi_nrfx_spim.c b/drivers/spi/spi_nrfx_spim.c
index aacf863e3b4..2fae79168b1 100644
--- a/drivers/spi/spi_nrfx_spim.c
+++ b/drivers/spi/spi_nrfx_spim.c
@@ -157,10 +157,10 @@ static int configure(const struct device *dev,
nrfx_spim_config_t config;
nrfx_err_t result;
- if (dev_data->initialized && spi_context_configured(ctx, spi_cfg)) {
- /* Already configured. No need to do it again. */
- return 0;
- }
+ // if (dev_data->initialized && spi_context_configured(ctx, spi_cfg)) {
+ // /* Already configured. No need to do it again. */
+ // return 0;
+ // }
if (spi_cfg->operation & SPI_HALF_DUPLEX) {
LOG_ERR("Half-duplex not supported");
Update:
We are running in the following condition (lines 196-205 in ~/ncs/v2.9.1/zephyr/drivers/spi/spi_nrfx_spim.c) that limits SPI4 frequency to 16Mhz
#if defined(CONFIG_SOC_NRF5340_CPUAPP) /* On nRF5340, the 32 Mbps speed is supported by the application core * when it is running at 128 MHz (see the Timing specifications section * in the nRF5340 PS). */ if (max_freq > 16000000 && nrf_clock_hfclk_div_get(NRF_CLOCK) != NRF_CLOCK_HFCLK_DIV_1) { max_freq = 16000000; } #endif
This happens despite setting the clock divider to 1 first thing in main():
int main(void) { #if NRFX_CLOCK_ENABLED && (defined(CLOCK_FEATURE_HFCLK_DIVIDE_PRESENT) || NRF_CLOCK_HAS_HFCLK192M) /* For now hardcode to 128MHz */ nrfx_clock_divider_set(NRF_CLOCK_DOMAIN_HFCLK, NRF_CLOCK_HFCLK_DIV_1); #endif printk("Starting %s with CPU frequency: %d MHz\n", CONFIG_BOARD, SystemCoreClock/MHZ(1)); return 0; }