feat(esp_hw_support): two interrupts sources can now be mapped to the same interrupt line

This commit is contained in:
Omar Chebib
2024-12-06 14:53:44 +08:00
parent f3af70530e
commit 16b8a2ea3b
5 changed files with 175 additions and 31 deletions

View File

@@ -94,7 +94,7 @@ extern "C" {
* the int can be left enabled while the flash cache is disabled.
*
* @return ESP_ERR_INVALID_ARG if cpu or intno is invalid
* ESP_OK otherwise
* ESP_OK on success
*/
esp_err_t esp_intr_mark_shared(int intno, int cpu, bool is_in_iram);
@@ -108,7 +108,7 @@ esp_err_t esp_intr_mark_shared(int intno, int cpu, bool is_in_iram);
* @param cpu CPU on which the interrupt should be marked as shared (0 or 1)
*
* @return ESP_ERR_INVALID_ARG if cpu or intno is invalid
* ESP_OK otherwise
* ESP_OK on success
*/
esp_err_t esp_intr_reserve(int intno, int cpu);
@@ -131,9 +131,10 @@ esp_err_t esp_intr_reserve(int intno, int cpu);
* @param flags An ORred mask of the ESP_INTR_FLAG_* defines. These restrict the
* choice of interrupts that this routine can choose from. If this value
* is 0, it will default to allocating a non-shared interrupt of level
* 1, 2 or 3. If this is ESP_INTR_FLAG_SHARED, it will allocate a shared
* interrupt of level 1. Setting ESP_INTR_FLAG_INTRDISABLED will return
* from this function with the interrupt disabled.
* 1, 2 or 3. If ESP_INTR_FLAG_SHARED mask is provided, a shared interrupt of
* the given level will be allocated (or level 1 if not specified).
* Setting ESP_INTR_FLAG_INTRDISABLED will return from this function with the
* interrupt disabled.
* @param handler The interrupt handler. Must be NULL when an interrupt of level >3
* is requested, because these types of interrupts aren't C-callable.
* @param arg Optional argument for passed to the interrupt handler
@@ -143,13 +144,13 @@ esp_err_t esp_intr_reserve(int intno, int cpu);
*
* @return ESP_ERR_INVALID_ARG if the combination of arguments is invalid.
* ESP_ERR_NOT_FOUND No free interrupt found with the specified flags
* ESP_OK otherwise
* ESP_OK on success
*/
esp_err_t esp_intr_alloc(int source, int flags, intr_handler_t handler, void *arg, intr_handle_t *ret_handle);
/**
* @brief Allocate an interrupt with the given parameters.
* @brief Allocate an interrupt with the given parameters, including an interrupt status register.
*
*
* This essentially does the same as esp_intr_alloc, but allows specifying a register and mask
@@ -165,9 +166,10 @@ esp_err_t esp_intr_alloc(int source, int flags, intr_handler_t handler, void *ar
* @param flags An ORred mask of the ESP_INTR_FLAG_* defines. These restrict the
* choice of interrupts that this routine can choose from. If this value
* is 0, it will default to allocating a non-shared interrupt of level
* 1, 2 or 3. If this is ESP_INTR_FLAG_SHARED, it will allocate a shared
* interrupt of level 1. Setting ESP_INTR_FLAG_INTRDISABLED will return
* from this function with the interrupt disabled.
* 1, 2 or 3. If ESP_INTR_FLAG_SHARED mask is provided, a shared interrupt of
* the given level will be allocated (or level 1 if not specified).
* Setting ESP_INTR_FLAG_INTRDISABLED will return from this function with the
* interrupt disabled.
* @param intrstatusreg The address of an interrupt status register
* @param intrstatusmask A mask. If a read of address intrstatusreg has any of the bits
* that are 1 in the mask set, the ISR will be called. If not, it will be
@@ -181,11 +183,92 @@ esp_err_t esp_intr_alloc(int source, int flags, intr_handler_t handler, void *ar
*
* @return ESP_ERR_INVALID_ARG if the combination of arguments is invalid.
* ESP_ERR_NOT_FOUND No free interrupt found with the specified flags
* ESP_OK otherwise
* ESP_OK on success
*/
esp_err_t esp_intr_alloc_intrstatus(int source, int flags, uint32_t intrstatusreg, uint32_t intrstatusmask, intr_handler_t handler, void *arg, intr_handle_t *ret_handle);
/**
* @brief Allocate an interrupt with the given parameters that can be bound to an existing interrupt handler.
*
*
* This function does the same as esp_intr_alloc, but allows specifying a previously allocated handler as
* the interrupt to share with the given source. This can be very handy to treat two pre-determined interrupt
* sources in the same interrupt handler. The interrupt will be allocated on the same core as the given
* `shared_handle`. Moreover, make sure to specify the same interrupt level as the one being used by `shared_handle`
* to prevent any failure from this function.
*
* @param source The interrupt source. One of the ETS_*_INTR_SOURCE interrupt mux
* sources, as defined in soc/soc.h, or one of the internal
* ETS_INTERNAL_*_INTR_SOURCE sources as defined in this header.
* @param flags An ORred mask of the ESP_INTR_FLAG_* defines. These restrict the
* choice of interrupts that this routine can choose from. If this value
* is 0, it will default to allocating a non-shared interrupt of level
* 1, 2 or 3. If ESP_INTR_FLAG_SHARED mask is provided, a shared interrupt of
* the given level will be allocated (or level 1 if not specified).
* Setting ESP_INTR_FLAG_INTRDISABLED will return from this function with the
* interrupt disabled.
* @param handler The interrupt handler. Must be NULL when an interrupt of level >3
* is requested, because these types of interrupts aren't C-callable.
* @param arg Optional argument for passed to the interrupt handler
* @param shared_handle Previously allocated interrupt to share the CPU interrupt line with. If NULL,
* calling this function equivalent to esp_intr_alloc, else, ESP_INTR_FLAG_SHARED must
* be provided in the flags parameter.
* @param ret_handle Pointer to an intr_handle_t to store a handle that can later be
* used to request details or free the interrupt. Can be NULL if no handle
* is required.
*
* @return ESP_ERR_INVALID_ARG if the combination of arguments is invalid.
* ESP_ERR_NOT_FOUND No free interrupt found with the specified flasg or the given level is different
* from the one assigned to the share_handle parameter.
* ESP_OK on success
*/
esp_err_t esp_intr_alloc_bind(int source, int flags, intr_handler_t handler, void *arg, intr_handle_t shared_handle, intr_handle_t *ret_handle);
/**
* @brief Allocate an interrupt with the given parameters, including an interrupt status register, that can
* be bound to an existing interrupt handler
*
*
* This function does the same as esp_intr_alloc_intrstatus, but allows specifying a previously allocated handler as
* the interrupt to share with the given source. This can be very handy to treat two pre-determined interrupt
* sources in the same interrupt handler. The interrupt will be allocated on the same core as the given
* `shared_handle`. Moreover, make sure to specify the same interrupt level as the one being used by `shared_handle`
* to prevent any failure from this function.
*
* @param source The interrupt source. One of the ETS_*_INTR_SOURCE interrupt mux
* sources, as defined in soc/soc.h, or one of the internal
* ETS_INTERNAL_*_INTR_SOURCE sources as defined in this header.
* @param flags An ORred mask of the ESP_INTR_FLAG_* defines. These restrict the
* choice of interrupts that this routine can choose from. If this value
* is 0, it will default to allocating a non-shared interrupt of level
* 1, 2 or 3. If ESP_INTR_FLAG_SHARED mask is provided, a shared interrupt of
* the given level will be allocated (or level 1 if not specified).
* Setting ESP_INTR_FLAG_INTRDISABLED will return from this function with the
* interrupt disabled.
* @param intrstatusreg The address of an interrupt status register
* @param intrstatusmask A mask. If a read of address intrstatusreg has any of the bits
* that are 1 in the mask set, the ISR will be called. If not, it will be
* skipped.
* @param handler The interrupt handler. Must be NULL when an interrupt of level >3
* is requested, because these types of interrupts aren't C-callable.
* @param arg Optional argument for passed to the interrupt handler
* @param shared_handle Previously allocated interrupt to share the CPU interrupt line with. If NULL,
* calling this function equivalent to esp_intr_alloc, else, ESP_INTR_FLAG_SHARED must
* be provided in the flags parameter.
* @param ret_handle Pointer to an intr_handle_t to store a handle that can later be
* used to request details or free the interrupt. Can be NULL if no handle
* is required.
*
* @return ESP_ERR_INVALID_ARG if the combination of arguments is invalid.
* ESP_ERR_NOT_FOUND No free interrupt found with the specified flasg or the given level is different
* from the one assigned to the share_handle parameter.
* ESP_OK on success
*/
esp_err_t esp_intr_alloc_intrstatus_bind(int source, int flags, uint32_t intrstatusreg, uint32_t intrstatusmask, intr_handler_t handler,
void *arg, intr_handle_t shared_handle, intr_handle_t *ret_handle);
/**
* @brief Disable and free an interrupt.
*
@@ -202,7 +285,7 @@ esp_err_t esp_intr_alloc_intrstatus(int source, int flags, uint32_t intrstatusre
*
* @return ESP_ERR_INVALID_ARG the handle is NULL
* ESP_FAIL failed to release this handle
* ESP_OK otherwise
* ESP_OK on success
*/
esp_err_t esp_intr_free(intr_handle_t handle);
@@ -239,7 +322,7 @@ int esp_intr_get_intno(intr_handle_t handle);
* @param handle The handle, as obtained by esp_intr_alloc or esp_intr_alloc_intrstatus
*
* @return ESP_ERR_INVALID_ARG if the combination of arguments is invalid.
* ESP_OK otherwise
* ESP_OK on success
*/
esp_err_t esp_intr_disable(intr_handle_t handle);
@@ -252,7 +335,7 @@ esp_err_t esp_intr_disable(intr_handle_t handle);
* @param handle The handle, as obtained by esp_intr_alloc or esp_intr_alloc_intrstatus
*
* @return ESP_ERR_INVALID_ARG if the combination of arguments is invalid.
* ESP_OK otherwise
* ESP_OK on success
*/
esp_err_t esp_intr_enable(intr_handle_t handle);
@@ -266,7 +349,7 @@ esp_err_t esp_intr_enable(intr_handle_t handle);
* Handlers residing in IRAM can be called when cache is disabled.
*
* @return ESP_ERR_INVALID_ARG if the combination of arguments is invalid.
* ESP_OK otherwise
* ESP_OK on success
*/
esp_err_t esp_intr_set_in_iram(intr_handle_t handle, bool is_in_iram);