[PATCH v3 23/42] bsps/irq: Add bsp_interrupt_check_and_lock()

Sebastian Huber sebastian.huber at embedded-brains.de
Fri Jul 23 13:56:31 UTC 2021


Return RTEMS_INCORRECT_STATE instead of RTEMS_INTERNAL_ERROR in case the
interrupt support is not initialized.  This is similar to
rtems_timer_server_fire_after() for example.

Update #3269.
---
 bsps/include/bsp/irq-generic.h        | 38 ++++++++++++++++-
 bsps/shared/irq/irq-generic.c         | 60 ++++++++++++++++-----------
 bsps/shared/irq/irq-handler-iterate.c | 51 +++++++----------------
 3 files changed, 86 insertions(+), 63 deletions(-)

diff --git a/bsps/include/bsp/irq-generic.h b/bsps/include/bsp/irq-generic.h
index 0f9bd5765b..e9cb0b4bb9 100644
--- a/bsps/include/bsp/irq-generic.h
+++ b/bsps/include/bsp/irq-generic.h
@@ -428,12 +428,46 @@ bool bsp_interrupt_handler_is_empty(rtems_vector_number vector);
 
 /** @} */
 
-/* For internal use only */
+/**
+ * @brief Acquires the interrupt support lock.
+ *
+ * The interrupt support lock is a mutex.  The mutex is only acquired if the
+ * system is the ::SYSTEM_STATE_UP state.
+ */
 void bsp_interrupt_lock(void);
 
-/* For internal use only */
+/**
+ * @brief Releases the interrupt support lock.
+ *
+ * The mutex is only released if the system is the ::SYSTEM_STATE_UP state.
+ */
 void bsp_interrupt_unlock(void);
 
+/**
+ * @brief Checks the vector and routine.  When the checks were successful, the
+ *   interrupt support lock will be obtained.
+ *
+ * @param vector is the interrupt vector number to check.
+ *
+ * @param routine is the routine to check.
+ *
+ * @retval ::RTEMS_SUCCESSFUL The requested operation was successful.
+ *
+ * @retval ::RTEMS_INCORRECT_STATE The interrupt support was not initialized.
+ *
+ * @retval ::RTEMS_CALLED_FROM_ISR The function was called from within
+ *   interrupt context.
+ *
+ * @retval ::RTEMS_INVALID_ADDRESS The ``routine`` parameter was NULL.
+ *
+ * @retval ::RTEMS_INVALID_ID There was no interrupt vector associated with the
+ *   number specified by ``vector``.
+ */
+rtems_status_code bsp_interrupt_check_and_lock(
+  rtems_vector_number     vector,
+  rtems_interrupt_handler handler
+);
+
 /**
  * @brief This table contains a bit map which indicates if an entry is unique
  *   or shared.
diff --git a/bsps/shared/irq/irq-generic.c b/bsps/shared/irq/irq-generic.c
index a7e8c1163f..59963182ab 100644
--- a/bsps/shared/irq/irq-generic.c
+++ b/bsps/shared/irq/irq-generic.c
@@ -122,6 +122,32 @@ static inline bool bsp_interrupt_allocate_handler_index(
   #endif
 }
 
+rtems_status_code bsp_interrupt_check_and_lock(
+  rtems_vector_number     vector,
+  rtems_interrupt_handler handler
+)
+{
+  if ( !bsp_interrupt_is_initialized() ) {
+    return RTEMS_INCORRECT_STATE;
+  }
+
+  if ( handler == NULL ) {
+    return RTEMS_INVALID_ADDRESS;
+  }
+
+  if ( !bsp_interrupt_is_valid_vector( vector ) ) {
+    return RTEMS_INVALID_ID;
+  }
+
+  if ( rtems_interrupt_is_in_progress() ) {
+    return RTEMS_CALLED_FROM_ISR;
+  }
+
+  bsp_interrupt_lock();
+
+  return RTEMS_SUCCESSFUL;
+}
+
 void bsp_interrupt_initialize(void)
 {
   rtems_status_code sc = RTEMS_SUCCESSFUL;
@@ -162,25 +188,18 @@ static rtems_status_code bsp_interrupt_handler_install(
   void *arg
 )
 {
+  rtems_status_code sc;
   rtems_interrupt_level level;
   rtems_vector_number index = 0;
   rtems_interrupt_entry *head = NULL;
   bool enable_vector = false;
   bool replace = RTEMS_INTERRUPT_IS_REPLACE(options);
 
-  /* Check parameters and system state */
-  if (!bsp_interrupt_is_initialized()) {
-    return RTEMS_INTERNAL_ERROR;
-  } else if (!bsp_interrupt_is_valid_vector(vector)) {
-    return RTEMS_INVALID_ID;
-  } else if (handler == NULL) {
-    return RTEMS_INVALID_ADDRESS;
-  } else if (rtems_interrupt_is_in_progress()) {
-    return RTEMS_CALLED_FROM_ISR;
-  }
+  sc = bsp_interrupt_check_and_lock( vector, handler );
 
-  /* Lock */
-  bsp_interrupt_lock();
+  if ( sc != RTEMS_SUCCESSFUL ) {
+    return sc;
+  }
 
   /* Get handler table index */
   index = bsp_interrupt_handler_index(vector);
@@ -325,6 +344,7 @@ static rtems_status_code bsp_interrupt_handler_remove(
   void *arg
 )
 {
+  rtems_status_code sc;
   rtems_interrupt_level level;
   rtems_vector_number index = 0;
   rtems_interrupt_entry *head = NULL;
@@ -332,19 +352,11 @@ static rtems_status_code bsp_interrupt_handler_remove(
   rtems_interrupt_entry *previous = NULL;
   rtems_interrupt_entry *match = NULL;
 
-  /* Check parameters and system state */
-  if (!bsp_interrupt_is_initialized()) {
-    return RTEMS_INTERNAL_ERROR;
-  } else if (!bsp_interrupt_is_valid_vector(vector)) {
-    return RTEMS_INVALID_ID;
-  } else if (handler == NULL) {
-    return RTEMS_INVALID_ADDRESS;
-  } else if (rtems_interrupt_is_in_progress()) {
-    return RTEMS_CALLED_FROM_ISR;
-  }
+  sc = bsp_interrupt_check_and_lock( vector, handler );
 
-  /* Lock */
-  bsp_interrupt_lock();
+  if ( sc != RTEMS_SUCCESSFUL ) {
+    return sc;
+  }
 
   /* Get handler table index */
   index = bsp_interrupt_handler_index(vector);
diff --git a/bsps/shared/irq/irq-handler-iterate.c b/bsps/shared/irq/irq-handler-iterate.c
index 3c642b075e..385cb8db2d 100644
--- a/bsps/shared/irq/irq-handler-iterate.c
+++ b/bsps/shared/irq/irq-handler-iterate.c
@@ -36,39 +36,26 @@
 
 #include <bsp/irq-generic.h>
 
-/**
- * @brief Iterates over all installed interrupt handler of a vector.
- *
- * @ingroup bsp_interrupt
- *
- * @return In addition to the standard status codes this function returns
- * RTEMS_INTERNAL_ERROR if the BSP interrupt support is not initialized.
- *
- * @see rtems_interrupt_handler_iterate().
- */
-static rtems_status_code bsp_interrupt_handler_iterate(
-  rtems_vector_number vector,
+rtems_status_code rtems_interrupt_handler_iterate(
+  rtems_vector_number                 vector,
   rtems_interrupt_per_handler_routine routine,
-  void *arg
+  void                               *arg
 )
 {
-  rtems_interrupt_entry *current = NULL;
-  rtems_option options = 0;
-  rtems_vector_number index = 0;
+  rtems_status_code      sc;
+  rtems_vector_number    index;
+  rtems_option           options;
+  rtems_interrupt_entry *current;
 
-  /* Check parameters and system state */
-  if (!bsp_interrupt_is_initialized()) {
-    return RTEMS_INTERNAL_ERROR;
-  } else if (!bsp_interrupt_is_valid_vector(vector)) {
-    return RTEMS_INVALID_ID;
-  } else if (rtems_interrupt_is_in_progress()) {
-    return RTEMS_CALLED_FROM_ISR;
-  }
+  sc = bsp_interrupt_check_and_lock(
+    vector,
+    (rtems_interrupt_handler) routine
+  );
 
-  /* Lock */
-  bsp_interrupt_lock();
+  if ( sc != RTEMS_SUCCESSFUL ) {
+    return sc;
+  }
 
-  /* Interate */
   index = bsp_interrupt_handler_index(vector);
   current = &bsp_interrupt_handler_table [index];
   if (!bsp_interrupt_is_empty_handler_entry(current)) {
@@ -80,17 +67,7 @@ static rtems_status_code bsp_interrupt_handler_iterate(
     } while (current != NULL);
   }
 
-  /* Unlock */
   bsp_interrupt_unlock();
 
   return RTEMS_SUCCESSFUL;
 }
-
-rtems_status_code rtems_interrupt_handler_iterate(
-  rtems_vector_number vector,
-  rtems_interrupt_per_handler_routine routine,
-  void *arg
-)
-{
-  return bsp_interrupt_handler_iterate(vector, routine, arg);
-}
-- 
2.26.2



More information about the devel mailing list