From 2e2c640ec102a68ecc51f9d7f224190f7c1a921b Mon Sep 17 00:00:00 2001 From: Thomas Doerfler Date: Thu, 24 Jul 2008 12:44:26 +0000 Subject: Support for new rtems_interrupt_handler_iterate() function. --- c/src/lib/libbsp/shared/ChangeLog | 5 ++ c/src/lib/libbsp/shared/include/irq-generic.h | 4 -- c/src/lib/libbsp/shared/src/irq-generic.c | 78 +++++++++++---------------- c/src/lib/libbsp/shared/src/irq-legacy.c | 70 ++++++++++++++---------- 4 files changed, 79 insertions(+), 78 deletions(-) (limited to 'c/src') diff --git a/c/src/lib/libbsp/shared/ChangeLog b/c/src/lib/libbsp/shared/ChangeLog index c742b6e030..78d03a6c57 100644 --- a/c/src/lib/libbsp/shared/ChangeLog +++ b/c/src/lib/libbsp/shared/ChangeLog @@ -1,3 +1,8 @@ +2008-07-24 Sebastian Huber + + * include/irq-generic.h, src/irq-generic.c, src/irq-legacy.c: Support + for new rtems_interrupt_handler_iterate() function. + 2008-07-15 Joel Sherrill * bootcard.c: Must include bsp.h or bspopts.h or we cannot know if diff --git a/c/src/lib/libbsp/shared/include/irq-generic.h b/c/src/lib/libbsp/shared/include/irq-generic.h index cd56251bb9..58d4f4639f 100644 --- a/c/src/lib/libbsp/shared/include/irq-generic.h +++ b/c/src/lib/libbsp/shared/include/irq-generic.h @@ -235,10 +235,6 @@ static inline void bsp_interrupt_handler_dispatch( rtems_vector_number vector) /** @} */ -rtems_status_code bsp_interrupt_handler_query( rtems_vector_number vector, bsp_interrupt_handler_entry *head); - -rtems_status_code bsp_interrupt_handler_query_free( bsp_interrupt_handler_entry *head); - #ifdef __cplusplus } #endif /* __cplusplus */ diff --git a/c/src/lib/libbsp/shared/src/irq-generic.c b/c/src/lib/libbsp/shared/src/irq-generic.c index 0428359d86..95edee674a 100644 --- a/c/src/lib/libbsp/shared/src/irq-generic.c +++ b/c/src/lib/libbsp/shared/src/irq-generic.c @@ -483,24 +483,22 @@ static rtems_status_code bsp_interrupt_handler_remove( rtems_vector_number vecto return RTEMS_SUCCESSFUL; } -rtems_status_code rtems_interrupt_handler_install( rtems_vector_number vector, const char *info, rtems_option options, rtems_interrupt_handler handler, void *arg) -{ - return bsp_interrupt_handler_install( vector, info, options, handler, arg); -} - -rtems_status_code rtems_interrupt_handler_remove( rtems_vector_number vector, rtems_interrupt_handler handler, void *arg) -{ - return bsp_interrupt_handler_remove( vector, handler, arg); -} - -rtems_status_code bsp_interrupt_handler_query( rtems_vector_number vector, bsp_interrupt_handler_entry *head) +/** + * @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_interrupt_per_handler_routine routine, void *arg) { rtems_status_code sc = RTEMS_SUCCESSFUL; - bsp_interrupt_handler_entry *current_input = NULL; - bsp_interrupt_handler_entry *current_output = NULL; - - /* Terminate list */ - head = NULL; + bsp_interrupt_handler_entry *current = NULL; + rtems_option options = 0; + rtems_vector_number index = 0; /* Check parameters and system state */ if (!bsp_interrupt_is_initialized()) { @@ -517,27 +515,15 @@ rtems_status_code bsp_interrupt_handler_query( rtems_vector_number vector, bsp_i return sc; } - /* Fill output list */ - current_input = &bsp_interrupt_handler_table [bsp_interrupt_handler_index( vector)]; - if (!bsp_interrupt_is_empty_handler_entry( current_input)) { + /* Interate */ + index = bsp_interrupt_handler_index( vector); + current = &bsp_interrupt_handler_table [index]; + if (!bsp_interrupt_is_empty_handler_entry( current)) { do { - bsp_interrupt_handler_entry *e = malloc( sizeof( bsp_interrupt_handler_entry)); - if (e == NULL) { - bsp_interrupt_handler_query_free( head); - bsp_interrupt_unlock(); - return RTEMS_NO_MEMORY; - } - *e = *current_input; - e->next = NULL; - if (head == NULL) { - head = e; - current_output = head; - } else { - current_output->next = e; - current_output = current_output->next; - } - current_input = current_input->next; - } while (current_input != NULL); + options = bsp_interrupt_is_handler_unique( index) ? RTEMS_INTERRUPT_UNIQUE : RTEMS_INTERRUPT_SHARED; + routine( arg, current->info, options, current->handler, current->arg); + current = current->next; + } while (current != NULL); } /* Unlock */ @@ -549,17 +535,17 @@ rtems_status_code bsp_interrupt_handler_query( rtems_vector_number vector, bsp_i return RTEMS_SUCCESSFUL; } -rtems_status_code bsp_interrupt_handler_query_free( bsp_interrupt_handler_entry *head) +rtems_status_code rtems_interrupt_handler_install( rtems_vector_number vector, const char *info, rtems_option options, rtems_interrupt_handler handler, void *arg) { - rtems_status_code sc = RTEMS_SUCCESSFUL; - bsp_interrupt_handler_entry *next = NULL; + return bsp_interrupt_handler_install( vector, info, options, handler, arg); +} - /* Free list */ - while (head != NULL) { - next = head->next; - free( head); - head = next; - } +rtems_status_code rtems_interrupt_handler_remove( rtems_vector_number vector, rtems_interrupt_handler handler, void *arg) +{ + return bsp_interrupt_handler_remove( vector, handler, arg); +} - 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); } diff --git a/c/src/lib/libbsp/shared/src/irq-legacy.c b/c/src/lib/libbsp/shared/src/irq-legacy.c index d71a55a0e7..cfe43030ea 100644 --- a/c/src/lib/libbsp/shared/src/irq-legacy.c +++ b/c/src/lib/libbsp/shared/src/irq-legacy.c @@ -18,6 +18,7 @@ * LICENSE in this distribution or at http://www.rtems.com/license/LICENSE. */ +#include #include #include @@ -29,12 +30,37 @@ typedef struct { void *arg; } bsp_interrupt_legacy_entry; +typedef struct { + rtems_irq_hdl handler; + void *handler_arg; + bsp_interrupt_legacy_entry *legacy_handler_arg; +} bsp_interrupt_legacy_iterate_entry; + static void bsp_interrupt_legacy_dispatch( rtems_vector_number vector, void *arg) { - bsp_interrupt_legacy_entry *e = arg; + bsp_interrupt_legacy_entry *e = (bsp_interrupt_legacy_entry *) arg; e->handler( e->arg); } +static void bsp_interrupt_legacy_per_handler_routine( + void *arg, + const char *info, + rtems_option options, + rtems_interrupt_handler handler, + void *handler_arg +) +{ + bsp_interrupt_legacy_iterate_entry *ie = (bsp_interrupt_legacy_iterate_entry *) arg; + bsp_interrupt_legacy_entry *e = NULL; + + if (handler == bsp_interrupt_legacy_dispatch) { + e = (bsp_interrupt_legacy_entry *) handler_arg; + if (e->handler == ie->handler && e->arg == ie->handler_arg) { + ie->legacy_handler_arg = e; + } + } +} + /** * @deprecated Obsolete. */ @@ -45,6 +71,8 @@ int BSP_get_current_rtems_irq_handler( rtems_irq_connect_data *cd) cd->on = NULL; cd->off = NULL; cd->isOn = NULL; + + return 1; } /** @@ -74,7 +102,7 @@ int BSP_install_rtems_irq_handler( const rtems_irq_connect_data *cd) return 0; } - if (cd->on) { + if (cd->on != NULL) { cd->on( cd); } @@ -108,7 +136,7 @@ int BSP_install_rtems_shared_irq_handler( const rtems_irq_connect_data *cd) return 0; } - if (cd->on) { + if (cd->on != NULL) { cd->on( cd); } @@ -121,44 +149,30 @@ int BSP_install_rtems_shared_irq_handler( const rtems_irq_connect_data *cd) int BSP_remove_rtems_irq_handler( const rtems_irq_connect_data *cd) { rtems_status_code sc = RTEMS_SUCCESSFUL; - bsp_interrupt_handler_entry *head = NULL; - bsp_interrupt_handler_entry *current = NULL; - bsp_interrupt_legacy_entry *e = NULL; + bsp_interrupt_legacy_iterate_entry e = { + .handler = cd->hdl, + .handler_arg = cd->handle, + .legacy_handler_arg = NULL + }; - sc = bsp_interrupt_handler_query( cd->name, head); + sc = rtems_interrupt_handler_iterate( cd->name, bsp_interrupt_legacy_per_handler_routine, &e); if (sc != RTEMS_SUCCESSFUL) { return 0; } - current = head; - while (current != NULL) { - if (current->handler == bsp_interrupt_legacy_dispatch) { - e = current->arg; - if (e->arg == cd->handle) { - break; - } else { - e = NULL; - } - } - current = current->next; - } - - sc = bsp_interrupt_handler_query_free( head); - if (sc != RTEMS_SUCCESSFUL) { + if (e.legacy_handler_arg == NULL) { return 0; } - if (e == NULL) { - return 0; - } - - if (cd->off) { + if (cd->off != NULL) { cd->off( cd); } - sc = rtems_interrupt_handler_remove( cd->name, bsp_interrupt_legacy_dispatch, e); + + sc = rtems_interrupt_handler_remove( cd->name, bsp_interrupt_legacy_dispatch, e.legacy_handler_arg); if (sc != RTEMS_SUCCESSFUL) { return 0; } + return 1; } -- cgit v1.2.3