arch/risc-v/espressif: Add LP Mailbox support for esp32p4

Add LP Mailbox support for esp32p4 to share data between HP and LP core

Signed-off-by: Eren Terzioglu <eren.terzioglu@espressif.com>
This commit is contained in:
Eren Terzioglu
2026-05-19 13:44:23 +02:00
committed by Xiang Xiao
parent 8a8a5af90d
commit 5a8678b591
6 changed files with 411 additions and 5 deletions
@@ -221,7 +221,7 @@ if(DEFINED ENV{ESP_HAL_3RDPARTY_VERSION})
CACHE STRING "ESP HAL 3rdparty version")
else()
set(ESP_HAL_3RDPARTY_VERSION
91d8aa6e82c74cc73eeb3df7e4005739fab8c322
e8d8638febf5310bf5b8f9bd04cf7fab9e9a4cb0
CACHE STRING "ESP HAL 3rdparty version")
endif()
+10 -3
View File
@@ -630,9 +630,10 @@ config ESPRESSIF_USE_LP_CORE
---help---
Enable LP core (Low-power core) coprocessor
if ESPRESSIF_USE_LP_CORE
config ESPRESSIF_ULP_COPROC_RESERVE_MEM_SIZE
int "RTC slow memory reserved for coprocessor"
depends on ESPRESSIF_USE_LP_CORE
default 4096
range 32 16352
---help---
@@ -641,14 +642,12 @@ config ESPRESSIF_ULP_COPROC_RESERVE_MEM_SIZE
config ESPRESSIF_ULP_SHARED_MEM_SIZE
int "Size of the shared memory for ULP core"
depends on ESPRESSIF_USE_LP_CORE
default 16
---help---
Size of the shared memory defined in bytes.
config ESPRESSIF_ULP_ENABLE_UBSAN
bool "Enable UBSan (undefined behavior sanitizer) for LP core application"
depends on ESPRESSIF_USE_LP_CORE
depends on DEBUG_SYMBOLS
default n
---help---
@@ -922,6 +921,7 @@ config ESPRESSIF_ULP_WAKEUP_LPUART_CHAR_SEQ
depends on ESPRESSIF_ULP_WAKEUP_LPUART_CHAR_SEQ_MODE
default "esp"
endif # ESPRESSIF_USE_LP_CORE
endmenu # LP Core (Low-power core) Coprocessor Configuration
menu "PM Configuration"
@@ -1721,6 +1721,13 @@ config ESPRESSIF_ANA_COMPR1
---help---
Enable analog comparator unit 1.
config ESPRESSIF_LP_MAILBOX
bool "LP Mailbox"
default n
depends on ARCH_CHIP_ESP32P4 && ESPRESSIF_USE_LP_CORE
---help---
Enable lp mailbox support for data passing between cores.
config ESPRESSIF_ADC
bool "Analog-to-digital converter (ADC)"
default n
+5 -1
View File
@@ -205,6 +205,10 @@ ifeq ($(CONFIG_ESPRESSIF_USE_LP_CORE),y)
CHIP_CSRCS += esp_ulp.c
endif
ifeq ($(CONFIG_ESPRESSIF_LP_MAILBOX),y)
CHIP_CSRCS += esp_lp_mailbox.c
endif
ifeq ($(CONFIG_PM),y)
ifneq ($(CONFIG_ARCH_CUSTOM_PMINIT),y)
CHIP_CSRCS += esp_pm_initialize.c
@@ -229,7 +233,7 @@ endif
ESP_HAL_3RDPARTY_REPO = esp-hal-3rdparty
ifndef ESP_HAL_3RDPARTY_VERSION
ESP_HAL_3RDPARTY_VERSION = 91d8aa6e82c74cc73eeb3df7e4005739fab8c322
ESP_HAL_3RDPARTY_VERSION = e8d8638febf5310bf5b8f9bd04cf7fab9e9a4cb0
endif
ifndef ESP_HAL_3RDPARTY_URL
@@ -0,0 +1,327 @@
/****************************************************************************
* arch/risc-v/src/common/espressif/esp_lp_mailbox.c
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
****************************************************************************/
/****************************************************************************
* Included Files
****************************************************************************/
#include <nuttx/config.h>
#include <nuttx/arch.h>
#include <nuttx/irq.h>
#include <nuttx/debug.h>
#include "lp_core_mailbox.h"
/****************************************************************************
* Pre-processor Definitions
****************************************************************************/
/****************************************************************************
* Private Types
****************************************************************************/
struct esp_lp_mailbox_priv_s
{
const struct file_operations *ops; /* Standard file operations */
lp_mailbox_t mailbox; /* LP Mailbox handler struct */
lp_mailbox_config_t config; /* LP Mailbox configuration */
xcpt_t handler; /* Async I/O callaback handler */
bool async_op; /* Flag to check active transaction mode */
};
/****************************************************************************
* Private Function Prototypes
****************************************************************************/
static int esp_lp_mailbox_read(struct file *filep,
char *buffer,
size_t buflen);
static int esp_lp_mailbox_write(struct file *filep,
const char *buffer,
size_t buflen);
static int esp_lp_mailbox_ioctl(struct file *filep,
int cmd,
unsigned long arg);
/****************************************************************************
* Private Data
****************************************************************************/
static const struct file_operations g_esp_lp_mailbox_fops =
{
.open = NULL, /* open */
.close = NULL, /* close */
.read = esp_lp_mailbox_read, /* read */
.write = esp_lp_mailbox_write, /* write */
.ioctl = esp_lp_mailbox_ioctl /* ioctl */
};
struct esp_lp_mailbox_priv_s esp_lp_mailbox_priv =
{
.ops = &g_esp_lp_mailbox_fops,
.mailbox = NULL,
.config =
{
0
},
.handler = NULL,
.async_op = false,
};
/****************************************************************************
* Private Functions
****************************************************************************/
/****************************************************************************
* Name: esp_lp_mailbox_rcv_callback
*
* Description:
* Handler for the LP Mailbox controller interrupt.
*
* Input Parameters:
* msg - Message content
*
* Returned Value:
* None.
*
****************************************************************************/
static void esp_lp_mailbox_rcv_callback(lp_message_t msg)
{
if (esp_lp_mailbox_priv.handler != NULL)
{
esp_lp_mailbox_priv.handler(0, NULL, (void *)msg);
}
}
/****************************************************************************
* Name: esp_lp_mailbox_read
*
* Description:
* Read LP Mailbox data.
*
* Input Parameters:
* filep - The pointer of file, represents each user using the driver
* buffer - Buffer to save data
* buflen - Length of the buffer
*
* Returned Value:
* Returns OK on success; a negated errno value on failure
*
****************************************************************************/
static int esp_lp_mailbox_read(struct file *filep,
char *buffer,
size_t buflen)
{
struct inode *inode = filep->f_inode;
struct esp_lp_mailbox_priv_s *priv = inode->i_private;
lp_message_t msg;
int i = 0;
int ret = OK;
lp_message_t recv;
DEBUGASSERT(priv);
while (i < buflen)
{
ret = lp_core_mailbox_receive(priv->mailbox, &recv, UINT32_MAX);
if (ret != OK)
{
ferr("Failed to receive %dth byte\n", i + 1);
return i;
}
buffer[i] = recv;
i++;
}
return buflen;
}
/****************************************************************************
* Name: esp_lp_mailbox_write
*
* Description:
* Write data to LP Mailbox.
*
* Input Parameters:
* filep - The pointer of file, represents each user using the driver
* buffer - Buffer to write data
* buflen - Length of the buffer
*
* Returned Value:
* Returns OK on success; a negated errno value on failure
*
****************************************************************************/
static int esp_lp_mailbox_write(struct file *filep,
const char *buffer,
size_t buflen)
{
struct inode *inode = filep->f_inode;
struct esp_lp_mailbox_priv_s *priv = inode->i_private;
lp_message_t msg;
int i = 0;
int ret = OK;
bool async_send = false;
DEBUGASSERT(priv);
if (priv->async_op == true && priv->handler == NULL)
{
async_send = true;
}
while (i < buflen)
{
if (async_send == true)
{
ret = lp_core_mailbox_send_async(priv->mailbox, buffer[i]);
}
else
{
ret = lp_core_mailbox_send(priv->mailbox, buffer[i], UINT32_MAX);
}
if (ret != OK)
{
ferr("Failed to send %dth byte\n", i + 1);
return i;
}
i++;
}
return buflen;
}
/****************************************************************************
* Name: esp_lp_mailbox_ioctl
*
* Description:
* Write data to LP Mailbox.
*
* Input Parameters:
* filep - The pointer of file, represents each user using the driver
* buffer - Buffer to write data
* buflen - Length of the buffer
*
* Returned Value:
* Returns OK on success; a negated errno value on failure
*
****************************************************************************/
static int esp_lp_mailbox_ioctl(struct file *filep,
int cmd,
unsigned long arg)
{
struct inode *inode = filep->f_inode;
struct esp_lp_mailbox_priv_s *priv = inode->i_private;
int ret = OK;
xcpt_t handler;
/* Decode and dispatch the driver-specific IOCTL command */
switch (cmd)
{
case FIOC_NOTIFY:
{
/* Set event callback */
handler = (xcpt_t)arg;
if (handler == NULL)
{
if (priv->async_op == true)
{
ret = lp_core_mailbox_receive_async_cancel(priv->mailbox,
NULL);
priv->async_op = false;
}
else
{
priv->async_op = true;
}
}
else
{
ret = lp_core_mailbox_receive_async(priv->mailbox, 1,
esp_lp_mailbox_rcv_callback);
priv->async_op = true;
}
if (ret != OK)
{
priv->async_op = false;
ferr("Could not register callback-%lx to lp-mailbox!\n",
(uint32_t)handler);
return ERROR;
}
priv->handler = handler;
break;
}
default:
{
ferr("Unrecognized IOCTL command: %d\n", cmd);
ret = -ENOTTY;
break;
}
}
return ret;
}
/****************************************************************************
* Public Functions
****************************************************************************/
/****************************************************************************
* Name: esp_lp_mailbox_init
*
* Description:
* Initialize and register LP mailbox driver.
*
* Input Parameters:
* None.
*
* Returned Value:
* Returns OK on success; a negated errno value on failure.
*
****************************************************************************/
int esp_lp_mailbox_init(void)
{
int ret = lp_core_mailbox_init(&esp_lp_mailbox_priv.mailbox,
&esp_lp_mailbox_priv.config);
if (ret != OK)
{
ferr("Failed to initialize LP Mailbox driver: %d\n", ret);
return ret;
}
register_driver("/dev/lp_mailbox", esp_lp_mailbox_priv.ops,
0666, (void *)&esp_lp_mailbox_priv);
return OK;
}
@@ -0,0 +1,66 @@
/****************************************************************************
* arch/risc-v/src/common/espressif/esp_lp_mailbox.h
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership. The
* ASF licenses this file to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
****************************************************************************/
#ifndef __ARCH_RISCV_SRC_COMMON_ESPRESSIF_ESP_LP_MAILBOX_H
#define __ARCH_RISCV_SRC_COMMON_ESPRESSIF_ESP_LP_MAILBOX_H
/****************************************************************************
* Included Files
****************************************************************************/
#include <nuttx/config.h>
#include <stdint.h>
#undef EXTERN
#if defined(__cplusplus)
#define EXTERN extern "C"
extern "C"
{
#else
#define EXTERN extern
#endif
/****************************************************************************
* Public Function Prototypes
****************************************************************************/
/****************************************************************************
* Name: esp_lp_mailbox_init
*
* Description:
* Initialize LP mailbox driver.
*
* Input Parameters:
* None.
*
* Returned Value:
* Returns OK on success; a negated errno value on failure.
*
****************************************************************************/
int esp_lp_mailbox_init(void);
#ifdef __cplusplus
}
#endif
#undef EXTERN
#endif /* __ARCH_RISCV_SRC_COMMON_ESPRESSIF_ESP_LP_MAILBOX_H */
+2
View File
@@ -408,6 +408,8 @@ CHIP_CSRCS += chip$(DELIM)$(ESP_HAL_3RDPARTY_REPO)$(DELIM)components$(DELIM)spi_
CHIP_CSRCS += chip$(DELIM)$(ESP_HAL_3RDPARTY_REPO)$(DELIM)components$(DELIM)ulp$(DELIM)lp_core$(DELIM)lp_core_i2c.c
CHIP_CSRCS += chip$(DELIM)$(ESP_HAL_3RDPARTY_REPO)$(DELIM)components$(DELIM)ulp$(DELIM)lp_core$(DELIM)lp_core_spi.c
CHIP_CSRCS += chip$(DELIM)$(ESP_HAL_3RDPARTY_REPO)$(DELIM)components$(DELIM)ulp$(DELIM)lp_core$(DELIM)lp_core.c
CHIP_CSRCS += chip$(DELIM)$(ESP_HAL_3RDPARTY_REPO)$(DELIM)components$(DELIM)ulp$(DELIM)lp_core$(DELIM)lp_core_mailbox.c
CHIP_CSRCS += chip$(DELIM)$(ESP_HAL_3RDPARTY_REPO)$(DELIM)components$(DELIM)ulp$(DELIM)lp_core$(DELIM)lp_core_mailbox_impl_hw.c
CHIP_CSRCS += chip$(DELIM)$(ESP_HAL_3RDPARTY_REPO)$(DELIM)components$(DELIM)ulp$(DELIM)lp_core$(DELIM)shared$(DELIM)ulp_lp_core_memory_shared.c
CHIP_CSRCS += chip$(DELIM)$(ESP_HAL_3RDPARTY_REPO)$(DELIM)components$(DELIM)ulp$(DELIM)lp_core$(DELIM)shared$(DELIM)ulp_lp_core_lp_timer_shared.c
CHIP_CSRCS += chip$(DELIM)$(ESP_HAL_3RDPARTY_REPO)$(DELIM)components$(DELIM)upper_hal_ana_cmpr$(DELIM)ana_cmpr.c