summaryrefslogtreecommitdiffstats
path: root/cpukit/score
diff options
context:
space:
mode:
authorJoel Sherrill <joel.sherrill@OARcorp.com>2008-01-22 18:28:53 +0000
committerJoel Sherrill <joel.sherrill@OARcorp.com>2008-01-22 18:28:53 +0000
commit3168deaa10fae157b38a94c5204a66d28a43ad7a (patch)
tree0bda84e785960fa6641c2b167d626cf3271b3352 /cpukit/score
parent2008-01-22 Joel Sherrill <joel.sherrill@OARcorp.com> (diff)
downloadrtems-3168deaa10fae157b38a94c5204a66d28a43ad7a.tar.bz2
2008-01-22 Joel Sherrill <joel.sherrill@oarcorp.com>
* rtems/include/rtems/rtems/event.h, rtems/inline/rtems/rtems/eventset.inl, rtems/src/event.c, rtems/src/eventseize.c, rtems/src/eventsurrender.c, rtems/src/eventtimeout.c, score/Makefile.am, score/preinstall.am, score/include/rtems/score/interr.h, score/include/rtems/score/thread.h, score/include/rtems/score/threadq.h, score/include/rtems/score/tqdata.h, score/inline/rtems/score/threadq.inl, score/inline/rtems/score/tqdata.inl, score/src/threadq.c, score/src/threadqdequeue.c, score/src/threadqdequeuefifo.c, score/src/threadqdequeuepriority.c, score/src/threadqenqueue.c, score/src/threadqenqueuefifo.c, score/src/threadqenqueuepriority.c, score/src/threadqextract.c, score/src/threadqextractfifo.c, score/src/threadqextractpriority.c, score/src/threadqextractwithproxy.c, score/src/threadqfirst.c, score/src/threadqfirstfifo.c, score/src/threadqfirstpriority.c, score/src/threadqflush.c, score/src/threadqrequeue.c, score/src/threadqtimeout.c: Refactor thread queue enqueue and event blocking synchronization critical sections. This resulted in three copies of essentially the same hard to test critical section code becoming the one shared routine _Thread_blocking_operation_Cancel. In addition, the thread queue and event code now share a common synchronization enumerated type. Along the way, switches were reworked to eliminate dead code generated by gcc and comments and copyrights were updated. * score/include/rtems/score/threadsync.h, score/src/threadblockingoperationcancel.c: New files.
Diffstat (limited to 'cpukit/score')
-rw-r--r--cpukit/score/Makefile.am12
-rw-r--r--cpukit/score/include/rtems/score/interr.h3
-rw-r--r--cpukit/score/include/rtems/score/thread.h23
-rw-r--r--cpukit/score/include/rtems/score/threadq.h12
-rw-r--r--cpukit/score/include/rtems/score/threadsync.h58
-rw-r--r--cpukit/score/include/rtems/score/tqdata.h16
-rw-r--r--cpukit/score/inline/rtems/score/threadq.inl10
-rw-r--r--cpukit/score/inline/rtems/score/tqdata.inl4
-rw-r--r--cpukit/score/preinstall.am4
-rw-r--r--cpukit/score/src/threadblockingoperationcancel.c81
-rw-r--r--cpukit/score/src/threadq.c25
-rw-r--r--cpukit/score/src/threadqdequeue.c21
-rw-r--r--cpukit/score/src/threadqdequeuefifo.c12
-rw-r--r--cpukit/score/src/threadqdequeuepriority.c27
-rw-r--r--cpukit/score/src/threadqenqueue.c27
-rw-r--r--cpukit/score/src/threadqenqueuefifo.c66
-rw-r--r--cpukit/score/src/threadqenqueuepriority.c76
-rw-r--r--cpukit/score/src/threadqextract.c2
-rw-r--r--cpukit/score/src/threadqextractfifo.c2
-rw-r--r--cpukit/score/src/threadqextractpriority.c2
-rw-r--r--cpukit/score/src/threadqextractwithproxy.c2
-rw-r--r--cpukit/score/src/threadqfirst.c2
-rw-r--r--cpukit/score/src/threadqfirstfifo.c2
-rw-r--r--cpukit/score/src/threadqfirstpriority.c2
-rw-r--r--cpukit/score/src/threadqflush.c2
-rw-r--r--cpukit/score/src/threadqrequeue.c39
-rw-r--r--cpukit/score/src/threadqtimeout.c2
27 files changed, 318 insertions, 216 deletions
diff --git a/cpukit/score/Makefile.am b/cpukit/score/Makefile.am
index 3446062f6b..3440af7090 100644
--- a/cpukit/score/Makefile.am
+++ b/cpukit/score/Makefile.am
@@ -28,10 +28,11 @@ include_rtems_score_HEADERS = include/rtems/score/address.h \
include/rtems/score/object.h include/rtems/score/priority.h \
include/rtems/score/stack.h include/rtems/score/states.h \
include/rtems/score/sysstate.h include/rtems/score/thread.h \
- include/rtems/score/threadq.h include/rtems/score/timespec.h \
- include/rtems/score/tod.h include/rtems/score/tqdata.h \
- include/rtems/score/userext.h include/rtems/score/watchdog.h \
- include/rtems/score/wkspace.h include/rtems/score/cpuopts.h
+ include/rtems/score/threadq.h include/rtems/score/threadsync.h \
+ include/rtems/score/timespec.h include/rtems/score/tod.h \
+ include/rtems/score/tqdata.h include/rtems/score/userext.h \
+ include/rtems/score/watchdog.h include/rtems/score/wkspace.h \
+ include/rtems/score/cpuopts.h
if HAS_MP
# We only build multiprocessing related files if HAS_MP was defined
@@ -142,7 +143,8 @@ libscore_a_SOURCES += src/thread.c src/threadchangepriority.c \
src/threadsettransient.c src/threadstackallocate.c \
src/threadstackfree.c src/threadstart.c src/threadstartmultitasking.c \
src/threadsuspend.c src/threadtickletimeslice.c \
- src/threadyieldprocessor.c src/iterateoverthreads.c
+ src/threadyieldprocessor.c src/iterateoverthreads.c \
+ src/threadblockingoperationcancel.c
## THREAD_C_FILES only used by ITRON API
if LIBITRON
diff --git a/cpukit/score/include/rtems/score/interr.h b/cpukit/score/include/rtems/score/interr.h
index 323bc06818..a8792c334b 100644
--- a/cpukit/score/include/rtems/score/interr.h
+++ b/cpukit/score/include/rtems/score/interr.h
@@ -63,7 +63,8 @@ typedef enum {
INTERNAL_ERROR_INVALID_GLOBAL_ID,
INTERNAL_ERROR_BAD_STACK_HOOK,
INTERNAL_ERROR_BAD_ATTRIBUTES,
- INTERNAL_ERROR_IMPLEMENTATION_KEY_CREATE_INCONSISTENCY
+ INTERNAL_ERROR_IMPLEMENTATION_KEY_CREATE_INCONSISTENCY,
+ INTERNAL_ERROR_IMPLEMENTATION_BLOCKING_OPERATION_CANCEL
} Internal_errors_Core_list;
/**
diff --git a/cpukit/score/include/rtems/score/thread.h b/cpukit/score/include/rtems/score/thread.h
index 9b9f324b9e..fcf26c9507 100644
--- a/cpukit/score/include/rtems/score/thread.h
+++ b/cpukit/score/include/rtems/score/thread.h
@@ -6,7 +6,7 @@
*/
/*
- * COPYRIGHT (c) 1989-2007.
+ * COPYRIGHT (c) 1989-2008.
* On-Line Applications Research Corporation (OAR).
*
* The license and distribution terms for this file may be
@@ -785,6 +785,27 @@ Thread_Control *_Thread_Get (
Objects_Locations *location
);
+/**
+ * @brief Cancel a blocking operation due to ISR
+ *
+ * This method is used to cancel a blocking operation that was
+ * satisfied from an ISR while the thread executing was in the
+ * process of blocking.
+ *
+ * @param[in] sync_state is the synchronization state
+ * @param[in] the_thread is the thread whose blocking is canceled
+ * @param[in] level is the previous ISR disable level
+ *
+ * @note This is a rare routine in RTEMS. It is called with
+ * interrupts disabled and only when an ISR completed
+ * a blocking condition in process.
+ */
+void _Thread_blocking_operation_Cancel(
+ Thread_blocking_operation_States sync_state,
+ Thread_Control *the_thread,
+ ISR_Level level
+);
+
#ifndef __RTEMS_APPLICATION__
#include <rtems/score/thread.inl>
#endif
diff --git a/cpukit/score/include/rtems/score/threadq.h b/cpukit/score/include/rtems/score/threadq.h
index 7b609285eb..2345087c04 100644
--- a/cpukit/score/include/rtems/score/threadq.h
+++ b/cpukit/score/include/rtems/score/threadq.h
@@ -6,7 +6,7 @@
*/
/*
- * COPYRIGHT (c) 1989-2006.
+ * COPYRIGHT (c) 1989-2008.
* On-Line Applications Research Corporation (OAR).
*
* The license and distribution terms for this file may be
@@ -178,9 +178,10 @@ Thread_Control *_Thread_queue_Dequeue_priority(
* the_thread_queue with an optional timeout using the
* priority discipline.
*/
-void _Thread_queue_Enqueue_priority(
+Thread_blocking_operation_States _Thread_queue_Enqueue_priority (
Thread_queue_Control *the_thread_queue,
- Thread_Control *the_thread
+ Thread_Control *the_thread,
+ ISR_Level *level_p
);
/** @brief Thread queue Extract priority Helper
@@ -230,9 +231,10 @@ Thread_Control *_Thread_queue_Dequeue_fifo(
* the_thread_queue with an optional timeout using the
* FIFO discipline.
*/
-void _Thread_queue_Enqueue_fifo(
+Thread_blocking_operation_States _Thread_queue_Enqueue_fifo (
Thread_queue_Control *the_thread_queue,
- Thread_Control *the_thread
+ Thread_Control *the_thread,
+ ISR_Level *level_p
);
/** @brief Thread queue Extract FIFO
diff --git a/cpukit/score/include/rtems/score/threadsync.h b/cpukit/score/include/rtems/score/threadsync.h
new file mode 100644
index 0000000000..6902f7b33b
--- /dev/null
+++ b/cpukit/score/include/rtems/score/threadsync.h
@@ -0,0 +1,58 @@
+/**
+ * @file rtems/score/threadsync.h
+ *
+ * This include file contains all constants and structures associated
+ * with synchronizing a thread blocking operation with potential
+ * actions in an ISR.
+ */
+
+/*
+ * COPYRIGHT (c) 1989-2008.
+ * On-Line Applications Research Corporation (OAR).
+ *
+ * The license and distribution terms for this file may be
+ * found in the file LICENSE in this distribution or at
+ * http://www.rtems.com/license/LICENSE.
+ *
+ * $Id$
+ */
+
+#ifndef _RTEMS_SCORE_THREAD_SYNC_H
+#define _RTEMS_SCORE_THREAD_SYNC_H
+
+/**
+ * @defgroup ScoreThread Thread Blocking Operation Synchronization Handler
+ *
+ * This handler encapsulates functionality related to the management of
+ * synchronization critical sections during blocking operations.
+ */
+/**@{*/
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/**
+ * The following enumerated types indicate what happened while the thread
+ * blocking was in the synchronization window.
+ */
+typedef enum {
+ THREAD_BLOCKING_OPERATION_SYNCHRONIZED,
+ THREAD_BLOCKING_OPERATION_NOTHING_HAPPENED,
+ THREAD_BLOCKING_OPERATION_TIMEOUT,
+ THREAD_BLOCKING_OPERATION_SATISFIED
+} Thread_blocking_operation_States;
+
+/*
+ * Operations require a thread pointer so they are prototyped
+ * in thread.h
+ */
+
+#ifdef __cplusplus
+}
+#endif
+
+/**@}*/
+
+#endif
+/* end of include file */
diff --git a/cpukit/score/include/rtems/score/tqdata.h b/cpukit/score/include/rtems/score/tqdata.h
index b70124ff9e..5b7ce98a03 100644
--- a/cpukit/score/include/rtems/score/tqdata.h
+++ b/cpukit/score/include/rtems/score/tqdata.h
@@ -6,7 +6,7 @@
*/
/*
- * COPYRIGHT (c) 1989-2006.
+ * COPYRIGHT (c) 1989-2008.
* On-Line Applications Research Corporation (OAR).
*
* The license and distribution terms for this file may be
@@ -35,6 +35,7 @@ extern "C" {
#include <rtems/score/chain.h>
#include <rtems/score/priority.h>
#include <rtems/score/states.h>
+#include <rtems/score/threadsync.h>
/**
* The following enumerated type details all of the disciplines
@@ -46,17 +47,6 @@ typedef enum {
} Thread_queue_Disciplines;
/**
- * The following enumerated types indicate what happened while the thread
- * queue was in the synchronization window.
- */
-typedef enum {
- THREAD_QUEUE_SYNCHRONIZED,
- THREAD_QUEUE_NOTHING_HAPPENED,
- THREAD_QUEUE_TIMEOUT,
- THREAD_QUEUE_SATISFIED
-} Thread_queue_States;
-
-/**
* This is one of the constants used to manage the priority queues.
*
* There are four chains used to maintain a priority -- each chain
@@ -99,7 +89,7 @@ typedef struct {
Chain_Control Priority[TASK_QUEUE_DATA_NUMBER_OF_PRIORITY_HEADERS];
} Queues;
/** This field is used to manage the critical section. */
- Thread_queue_States sync_state;
+ Thread_blocking_operation_States sync_state;
/** This field indicates the thread queue's blocking discipline. */
Thread_queue_Disciplines discipline;
/** This indicates the blocking state for threads waiting on this
diff --git a/cpukit/score/inline/rtems/score/threadq.inl b/cpukit/score/inline/rtems/score/threadq.inl
index ccbb928849..5e0d921ac8 100644
--- a/cpukit/score/inline/rtems/score/threadq.inl
+++ b/cpukit/score/inline/rtems/score/threadq.inl
@@ -6,7 +6,7 @@
*/
/*
- * COPYRIGHT (c) 1989-2006.
+ * COPYRIGHT (c) 1989-2008.
* On-Line Applications Research Corporation (OAR).
*
* The license and distribution terms for this file may be
@@ -55,10 +55,12 @@ static inline void _Thread_queue_Process_timeout(
* a timeout is not allowed to occur.
*/
- if ( the_thread_queue->sync_state != THREAD_QUEUE_SYNCHRONIZED &&
+ if ( the_thread_queue->sync_state != THREAD_BLOCKING_OPERATION_SYNCHRONIZED &&
_Thread_Is_executing( the_thread ) ) {
- if ( the_thread_queue->sync_state != THREAD_QUEUE_SATISFIED )
- the_thread_queue->sync_state = THREAD_QUEUE_TIMEOUT;
+ if ( the_thread_queue->sync_state != THREAD_BLOCKING_OPERATION_SATISFIED ) {
+ the_thread->Wait.return_code = the_thread->Wait.queue->timeout_status;
+ the_thread_queue->sync_state = THREAD_BLOCKING_OPERATION_TIMEOUT;
+ }
} else {
the_thread->Wait.return_code = the_thread->Wait.queue->timeout_status;
_Thread_queue_Extract( the_thread->Wait.queue, the_thread );
diff --git a/cpukit/score/inline/rtems/score/tqdata.inl b/cpukit/score/inline/rtems/score/tqdata.inl
index d1248f4b74..b063998f8e 100644
--- a/cpukit/score/inline/rtems/score/tqdata.inl
+++ b/cpukit/score/inline/rtems/score/tqdata.inl
@@ -6,7 +6,7 @@
*/
/*
- * COPYRIGHT (c) 1989-2006.
+ * COPYRIGHT (c) 1989-2008.
* On-Line Applications Research Corporation (OAR).
*
* The license and distribution terms for this file may be
@@ -58,7 +58,7 @@ RTEMS_INLINE_ROUTINE void _Thread_queue_Enter_critical_section (
Thread_queue_Control *the_thread_queue
)
{
- the_thread_queue->sync_state = THREAD_QUEUE_NOTHING_HAPPENED;
+ the_thread_queue->sync_state = THREAD_BLOCKING_OPERATION_NOTHING_HAPPENED;
}
/**
diff --git a/cpukit/score/preinstall.am b/cpukit/score/preinstall.am
index 040616aa6a..cb27e47d48 100644
--- a/cpukit/score/preinstall.am
+++ b/cpukit/score/preinstall.am
@@ -131,6 +131,10 @@ $(PROJECT_INCLUDE)/rtems/score/threadq.h: include/rtems/score/threadq.h $(PROJEC
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/rtems/score/threadq.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/rtems/score/threadq.h
+$(PROJECT_INCLUDE)/rtems/score/threadsync.h: include/rtems/score/threadsync.h $(PROJECT_INCLUDE)/rtems/score/$(dirstamp)
+ $(INSTALL_DATA) $< $(PROJECT_INCLUDE)/rtems/score/threadsync.h
+PREINSTALL_FILES += $(PROJECT_INCLUDE)/rtems/score/threadsync.h
+
$(PROJECT_INCLUDE)/rtems/score/timespec.h: include/rtems/score/timespec.h $(PROJECT_INCLUDE)/rtems/score/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/rtems/score/timespec.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/rtems/score/timespec.h
diff --git a/cpukit/score/src/threadblockingoperationcancel.c b/cpukit/score/src/threadblockingoperationcancel.c
new file mode 100644
index 0000000000..b2b7a22745
--- /dev/null
+++ b/cpukit/score/src/threadblockingoperationcancel.c
@@ -0,0 +1,81 @@
+/*
+ * Cancel Thread Blocking Operation
+ *
+ *
+ * COPYRIGHT (c) 1989-2007.
+ * On-Line Applications Research Corporation (OAR).
+ *
+ * The license and distribution terms for this file may be
+ * found in the file LICENSE in this distribution or at
+ * http://www.rtems.com/license/LICENSE.
+ *
+ * $Id$
+ */
+
+#if HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include <rtems/system.h>
+#include <rtems/score/thread.h>
+#if defined(RTEMS_MULTIPROCESSING)
+#include <rtems/score/mpci.h>
+#endif
+
+void _Thread_blocking_operation_Cancel(
+ Thread_blocking_operation_States sync_state,
+ Thread_Control *the_thread,
+ ISR_Level level
+)
+{
+ /*
+ * Cases that should not happen and why.
+ *
+ * THREAD_BLOCKING_OPERATION_SYNCHRONIZED:
+ *
+ * This indicates that someone did not enter a blocking
+ * operation critical section.
+ *
+ * THREAD_BLOCKING_OPERATION_NOTHING_HAPPENED:
+ *
+ * This indicates that there was nothing to cancel so
+ * we should not have been called.
+ */
+
+ #if defined(RTEMS_DEBUG)
+ if ( (sync_state == THREAD_BLOCKING_OPERATION_SYNCHRONIZED)
+ (sync_state == THREAD_BLOCKING_OPERATION_NOTHING_HAPPENED) ) {
+ _Internal_error_Occurred(
+ INTERNAL_ERROR_CORE,
+ TRUE,
+ INTERNAL_ERROR_IMPLEMENTATION_BLOCKING_OPERATION_CANCEL
+ );
+ }
+ #endif
+
+ /*
+ * If the sync state is timed out, this is very likely not needed.
+ * But better safe than sorry when it comes to critical sections.
+ */
+ if ( _Watchdog_Is_active( &the_thread->Timer ) ) {
+ _Watchdog_Deactivate( &the_thread->Timer );
+ the_thread->Wait.queue = NULL;
+ _ISR_Enable( level );
+ (void) _Watchdog_Remove( &the_thread->Timer );
+ } else
+ _ISR_Enable( level );
+
+ /*
+ * Global objects with thread queue's should not be operated on from an
+ * ISR. But the sync code still must allow short timeouts to be processed
+ * correctly.
+ */
+
+ _Thread_Unblock( the_thread );
+
+#if defined(RTEMS_MULTIPROCESSING)
+ if ( !_Objects_Is_local_id( the_thread->Object.id ) )
+ _Thread_MP_Free_proxy( the_thread );
+#endif
+
+}
diff --git a/cpukit/score/src/threadq.c b/cpukit/score/src/threadq.c
index d17c3d8f7e..baa85a13e1 100644
--- a/cpukit/score/src/threadq.c
+++ b/cpukit/score/src/threadq.c
@@ -2,7 +2,7 @@
* Thread Queue Handler
*
*
- * COPYRIGHT (c) 1989-1999.
+ * COPYRIGHT (c) 1989-2008.
* On-Line Applications Research Corporation (OAR).
*
* The license and distribution terms for this file may be
@@ -47,23 +47,20 @@ void _Thread_queue_Initialize(
uint32_t timeout_status
)
{
- uint32_t index;
-
the_thread_queue->state = state;
the_thread_queue->discipline = the_discipline;
the_thread_queue->timeout_status = timeout_status;
- the_thread_queue->sync_state = THREAD_QUEUE_SYNCHRONIZED;
+ the_thread_queue->sync_state = THREAD_BLOCKING_OPERATION_SYNCHRONIZED;
+
+ if ( the_discipline == THREAD_QUEUE_DISCIPLINE_PRIORITY ) {
+ uint32_t index;
- switch ( the_discipline ) {
- case THREAD_QUEUE_DISCIPLINE_FIFO:
- _Chain_Initialize_empty( &the_thread_queue->Queues.Fifo );
- break;
- case THREAD_QUEUE_DISCIPLINE_PRIORITY:
- for( index=0 ;
- index < TASK_QUEUE_DATA_NUMBER_OF_PRIORITY_HEADERS ;
- index++)
- _Chain_Initialize_empty( &the_thread_queue->Queues.Priority[index] );
- break;
+ for( index=0 ;
+ index < TASK_QUEUE_DATA_NUMBER_OF_PRIORITY_HEADERS ;
+ index++)
+ _Chain_Initialize_empty( &the_thread_queue->Queues.Priority[index] );
+ } else { /* must be THREAD_QUEUE_DISCIPLINE_FIFO */
+ _Chain_Initialize_empty( &the_thread_queue->Queues.Fifo );
}
}
diff --git a/cpukit/score/src/threadqdequeue.c b/cpukit/score/src/threadqdequeue.c
index d5968b0210..160bd6e84c 100644
--- a/cpukit/score/src/threadqdequeue.c
+++ b/cpukit/score/src/threadqdequeue.c
@@ -2,7 +2,7 @@
* Thread Queue Handler
*
*
- * COPYRIGHT (c) 1989-1999.
+ * COPYRIGHT (c) 1989-2008.
* On-Line Applications Research Corporation (OAR).
*
* The license and distribution terms for this file may be
@@ -47,19 +47,12 @@ Thread_Control *_Thread_queue_Dequeue(
Thread_queue_Control *the_thread_queue
)
{
- Thread_Control *the_thread;
+ Thread_Control *(*dequeue_p)( Thread_queue_Control * );
- switch ( the_thread_queue->discipline ) {
- case THREAD_QUEUE_DISCIPLINE_FIFO:
- the_thread = _Thread_queue_Dequeue_fifo( the_thread_queue );
- break;
- case THREAD_QUEUE_DISCIPLINE_PRIORITY:
- the_thread = _Thread_queue_Dequeue_priority( the_thread_queue );
- break;
- default: /* this is only to prevent warnings */
- the_thread = NULL;
- break;
- }
+ if ( the_thread_queue->discipline == THREAD_QUEUE_DISCIPLINE_PRIORITY )
+ dequeue_p = _Thread_queue_Dequeue_priority;
+ else /* must be THREAD_QUEUE_DISCIPLINE_FIFO */
+ dequeue_p = _Thread_queue_Dequeue_fifo;
- return( the_thread );
+ return (*dequeue_p)( the_thread_queue );
}
diff --git a/cpukit/score/src/threadqdequeuefifo.c b/cpukit/score/src/threadqdequeuefifo.c
index 787ec41074..d494b90b85 100644
--- a/cpukit/score/src/threadqdequeuefifo.c
+++ b/cpukit/score/src/threadqdequeuefifo.c
@@ -2,7 +2,7 @@
* Thread Queue Handler
*
*
- * COPYRIGHT (c) 1989-2006.
+ * COPYRIGHT (c) 1989-2008.
* On-Line Applications Research Corporation (OAR).
*
* The license and distribution terms for this file may be
@@ -75,14 +75,14 @@ Thread_Control *_Thread_queue_Dequeue_fifo(
}
switch ( the_thread_queue->sync_state ) {
- case THREAD_QUEUE_SYNCHRONIZED:
- case THREAD_QUEUE_SATISFIED:
+ case THREAD_BLOCKING_OPERATION_SYNCHRONIZED:
+ case THREAD_BLOCKING_OPERATION_SATISFIED:
_ISR_Enable( level );
return NULL;
- case THREAD_QUEUE_NOTHING_HAPPENED:
- case THREAD_QUEUE_TIMEOUT:
- the_thread_queue->sync_state = THREAD_QUEUE_SATISFIED;
+ case THREAD_BLOCKING_OPERATION_NOTHING_HAPPENED:
+ case THREAD_BLOCKING_OPERATION_TIMEOUT:
+ the_thread_queue->sync_state = THREAD_BLOCKING_OPERATION_SATISFIED;
_ISR_Enable( level );
return _Thread_Executing;
}
diff --git a/cpukit/score/src/threadqdequeuepriority.c b/cpukit/score/src/threadqdequeuepriority.c
index 4da18165d9..d9aa1b14f8 100644
--- a/cpukit/score/src/threadqdequeuepriority.c
+++ b/cpukit/score/src/threadqdequeuepriority.c
@@ -2,7 +2,7 @@
* Thread Queue Handler
*
*
- * COPYRIGHT (c) 1989-2006.
+ * COPYRIGHT (c) 1989-2008.
* On-Line Applications Research Corporation (OAR).
*
* The license and distribution terms for this file may be
@@ -55,6 +55,7 @@ Thread_Control *_Thread_queue_Dequeue_priority(
Chain_Node *last_node;
Chain_Node *next_node;
Chain_Node *previous_node;
+ Thread_blocking_operation_States sync;
_ISR_Disable( level );
for( index=0 ;
@@ -67,17 +68,21 @@ Thread_Control *_Thread_queue_Dequeue_priority(
}
}
- switch ( the_thread_queue->sync_state ) {
- case THREAD_QUEUE_SYNCHRONIZED:
- case THREAD_QUEUE_SATISFIED:
- _ISR_Enable( level );
- return NULL;
+ /*
+ * If we interrupted a blocking operation, cancel it.
+ */
+ sync = the_thread_queue->sync_state;
+ if ( (sync == THREAD_BLOCKING_OPERATION_SYNCHRONIZED) ||
+ (sync == THREAD_BLOCKING_OPERATION_SATISFIED) ) {
+ _ISR_Enable( level );
+ return NULL;
+ }
- case THREAD_QUEUE_NOTHING_HAPPENED:
- case THREAD_QUEUE_TIMEOUT:
- the_thread_queue->sync_state = THREAD_QUEUE_SATISFIED;
- _ISR_Enable( level );
- return _Thread_Executing;
+ if ( (sync == THREAD_BLOCKING_OPERATION_NOTHING_HAPPENED) ||
+ (sync == THREAD_BLOCKING_OPERATION_TIMEOUT ) ) {
+ the_thread_queue->sync_state = THREAD_BLOCKING_OPERATION_SATISFIED;
+ _ISR_Enable( level );
+ return _Thread_Executing;
}
dequeue:
diff --git a/cpukit/score/src/threadqenqueue.c b/cpukit/score/src/threadqenqueue.c
index 2cc1141993..688962950a 100644
--- a/cpukit/score/src/threadqenqueue.c
+++ b/cpukit/score/src/threadqenqueue.c
@@ -2,7 +2,7 @@
* Thread Queue Handler
*
*
- * COPYRIGHT (c) 1989-2006.
+ * COPYRIGHT (c) 1989-2008.
* On-Line Applications Research Corporation (OAR).
*
* The license and distribution terms for this file may be
@@ -51,7 +51,14 @@ void _Thread_queue_Enqueue_with_handler(
Thread_queue_Timeout_callout handler
)
{
- Thread_Control *the_thread;
+ Thread_Control *the_thread;
+ ISR_Level level;
+ Thread_blocking_operation_States sync_state;
+ Thread_blocking_operation_States (*enqueue_p)(
+ Thread_queue_Control *,
+ Thread_Control *,
+ ISR_Level *
+ );
the_thread = _Thread_Executing;
@@ -82,12 +89,12 @@ void _Thread_queue_Enqueue_with_handler(
/*
* Now enqueue the thread per the discipline for this thread queue.
*/
- switch( the_thread_queue->discipline ) {
- case THREAD_QUEUE_DISCIPLINE_FIFO:
- _Thread_queue_Enqueue_fifo( the_thread_queue, the_thread );
- break;
- case THREAD_QUEUE_DISCIPLINE_PRIORITY:
- _Thread_queue_Enqueue_priority( the_thread_queue, the_thread );
- break;
- }
+ if ( the_thread_queue->discipline == THREAD_QUEUE_DISCIPLINE_PRIORITY )
+ enqueue_p = _Thread_queue_Enqueue_priority;
+ else /* must be THREAD_QUEUE_DISCIPLINE_FIFO */
+ enqueue_p = _Thread_queue_Enqueue_fifo;
+
+ sync_state = (*enqueue_p)( the_thread_queue, the_thread, &level );
+ if ( sync_state != THREAD_BLOCKING_OPERATION_NOTHING_HAPPENED )
+ _Thread_blocking_operation_Cancel( sync_state, the_thread, level );
}
diff --git a/cpukit/score/src/threadqenqueuefifo.c b/cpukit/score/src/threadqenqueuefifo.c
index c7260807ed..229261efad 100644
--- a/cpukit/score/src/threadqenqueuefifo.c
+++ b/cpukit/score/src/threadqenqueuefifo.c
@@ -2,7 +2,7 @@
* Thread Queue Handler
*
*
- * COPYRIGHT (c) 1989-1999.
+ * COPYRIGHT (c) 1989-2008.
* On-Line Applications Research Corporation (OAR).
*
* The license and distribution terms for this file may be
@@ -41,64 +41,38 @@
* only case
*/
-void _Thread_queue_Enqueue_fifo (
+Thread_blocking_operation_States _Thread_queue_Enqueue_fifo (
Thread_queue_Control *the_thread_queue,
- Thread_Control *the_thread
+ Thread_Control *the_thread,
+ ISR_Level *level_p
)
{
- ISR_Level level;
- Thread_queue_States sync_state;
+ Thread_blocking_operation_States sync_state;
+ ISR_Level level;
_ISR_Disable( level );
- sync_state = the_thread_queue->sync_state;
- the_thread_queue->sync_state = THREAD_QUEUE_SYNCHRONIZED;
-
- switch ( sync_state ) {
- case THREAD_QUEUE_SYNCHRONIZED:
- /*
- * This should never happen. It indicates that someone did not
- * enter a thread queue critical section.
- */
- break;
-
- case THREAD_QUEUE_NOTHING_HAPPENED:
+ sync_state = the_thread_queue->sync_state;
+ the_thread_queue->sync_state = THREAD_BLOCKING_OPERATION_SYNCHRONIZED;
+ if (sync_state == THREAD_BLOCKING_OPERATION_NOTHING_HAPPENED) {
_Chain_Append_unprotected(
&the_thread_queue->Queues.Fifo,
&the_thread->Object.Node
);
the_thread->Wait.queue = the_thread_queue;
- _ISR_Enable( level );
- return;
- case THREAD_QUEUE_TIMEOUT:
- the_thread->Wait.return_code = the_thread->Wait.queue->timeout_status;
- the_thread->Wait.queue = NULL;
+ the_thread_queue->sync_state = THREAD_BLOCKING_OPERATION_SYNCHRONIZED;
_ISR_Enable( level );
- break;
-
- case THREAD_QUEUE_SATISFIED:
- if ( _Watchdog_Is_active( &the_thread->Timer ) ) {
- _Watchdog_Deactivate( &the_thread->Timer );
- the_thread->Wait.queue = NULL;
- _ISR_Enable( level );
- (void) _Watchdog_Remove( &the_thread->Timer );
- } else
- _ISR_Enable( level );
- break;
- }
-
+ return THREAD_BLOCKING_OPERATION_NOTHING_HAPPENED;
+ }
+
/*
- * Global objects with thread queue's should not be operated on from an
- * ISR. But the sync code still must allow short timeouts to be processed
- * correctly.
+ * An interrupt completed the thread's blocking request.
+ * For example, the blocking thread could have been given
+ * the mutex by an ISR or timed out.
+ *
+ * WARNING! Returning with interrupts disabled!
*/
-
- _Thread_Unblock( the_thread );
-
-#if defined(RTEMS_MULTIPROCESSING)
- if ( !_Objects_Is_local_id( the_thread->Object.id ) )
- _Thread_MP_Free_proxy( the_thread );
-#endif
-
+ *level_p = level;
+ return sync_state;
}
diff --git a/cpukit/score/src/threadqenqueuepriority.c b/cpukit/score/src/threadqenqueuepriority.c
index 9974a3a674..cad998cf87 100644
--- a/cpukit/score/src/threadqenqueuepriority.c
+++ b/cpukit/score/src/threadqenqueuepriority.c
@@ -2,7 +2,7 @@
* Thread Queue Handler
*
*
- * COPYRIGHT (c) 1989-1999.
+ * COPYRIGHT (c) 1989-2008.
* On-Line Applications Research Corporation (OAR).
*
* The license and distribution terms for this file may be
@@ -42,9 +42,10 @@
* forward equal
*/
-void _Thread_queue_Enqueue_priority(
+Thread_blocking_operation_States _Thread_queue_Enqueue_priority (
Thread_queue_Control *the_thread_queue,
- Thread_Control *the_thread
+ Thread_Control *the_thread,
+ ISR_Level *level_p
)
{
Priority_Control search_priority;
@@ -58,7 +59,6 @@ void _Thread_queue_Enqueue_priority(
Chain_Node *search_node;
Priority_Control priority;
States_Control block_state;
- Thread_queue_States sync_state;
_Chain_Initialize_empty( &the_thread->Wait.Block2n );
@@ -96,10 +96,11 @@ restart_forward_search:
(Thread_Control *)search_thread->Object.Node.next;
}
- if ( the_thread_queue->sync_state != THREAD_QUEUE_NOTHING_HAPPENED )
+ if ( the_thread_queue->sync_state !=
+ THREAD_BLOCKING_OPERATION_NOTHING_HAPPENED )
goto synchronize;
- the_thread_queue->sync_state = THREAD_QUEUE_SYNCHRONIZED;
+ the_thread_queue->sync_state = THREAD_BLOCKING_OPERATION_SYNCHRONIZED;
if ( priority == search_priority )
goto equal_priority;
@@ -114,7 +115,7 @@ restart_forward_search:
search_node->previous = the_node;
the_thread->Wait.queue = the_thread_queue;
_ISR_Enable( level );
- return;
+ return THREAD_BLOCKING_OPERATION_NOTHING_HAPPENED;
restart_reverse_search:
search_priority = PRIORITY_MAXIMUM + 1;
@@ -142,10 +143,11 @@ restart_reverse_search:
search_thread->Object.Node.previous;
}
- if ( the_thread_queue->sync_state != THREAD_QUEUE_NOTHING_HAPPENED )
+ if ( the_thread_queue->sync_state !=
+ THREAD_BLOCKING_OPERATION_NOTHING_HAPPENED )
goto synchronize;
- the_thread_queue->sync_state = THREAD_QUEUE_SYNCHRONIZED;
+ the_thread_queue->sync_state = THREAD_BLOCKING_OPERATION_SYNCHRONIZED;
if ( priority == search_priority )
goto equal_priority;
@@ -160,7 +162,7 @@ restart_reverse_search:
next_node->previous = the_node;
the_thread->Wait.queue = the_thread_queue;
_ISR_Enable( level );
- return;
+ return THREAD_BLOCKING_OPERATION_NOTHING_HAPPENED;
equal_priority: /* add at end of priority group */
search_node = _Chain_Tail( &search_thread->Wait.Block2n );
@@ -173,54 +175,16 @@ equal_priority: /* add at end of priority group */
search_node->previous = the_node;
the_thread->Wait.queue = the_thread_queue;
_ISR_Enable( level );
- return;
+ return THREAD_BLOCKING_OPERATION_NOTHING_HAPPENED;
synchronize:
-
- sync_state = the_thread_queue->sync_state;
- the_thread_queue->sync_state = THREAD_QUEUE_SYNCHRONIZED;
-
- switch ( sync_state ) {
- case THREAD_QUEUE_SYNCHRONIZED:
- /*
- * This should never happen. It indicates that someone did not
- * enter a thread queue critical section.
- */
- break;
-
- case THREAD_QUEUE_NOTHING_HAPPENED:
- /*
- * This should never happen. All of this was dealt with above.
- */
- break;
-
- case THREAD_QUEUE_TIMEOUT:
- the_thread->Wait.return_code = the_thread->Wait.queue->timeout_status;
- the_thread->Wait.queue = NULL;
- _ISR_Enable( level );
- break;
-
- case THREAD_QUEUE_SATISFIED:
- if ( _Watchdog_Is_active( &the_thread->Timer ) ) {
- _Watchdog_Deactivate( &the_thread->Timer );
- the_thread->Wait.queue = NULL;
- _ISR_Enable( level );
- (void) _Watchdog_Remove( &the_thread->Timer );
- } else
- _ISR_Enable( level );
- break;
- }
-
/*
- * Global objects with thread queue's should not be operated on from an
- * ISR. But the sync code still must allow short timeouts to be processed
- * correctly.
+ * An interrupt completed the thread's blocking request.
+ * For example, the blocking thread could have been given
+ * the mutex by an ISR or timed out.
+ *
+ * WARNING! Returning with interrupts disabled!
*/
-
- _Thread_Unblock( the_thread );
-
-#if defined(RTEMS_MULTIPROCESSING)
- if ( !_Objects_Is_local_id( the_thread->Object.id ) )
- _Thread_MP_Free_proxy( the_thread );
-#endif
+ *level_p = level;
+ return the_thread_queue->sync_state;
}
diff --git a/cpukit/score/src/threadqextract.c b/cpukit/score/src/threadqextract.c
index a8faef03f7..f971a7b970 100644
--- a/cpukit/score/src/threadqextract.c
+++ b/cpukit/score/src/threadqextract.c
@@ -2,7 +2,7 @@
* Thread Queue Handler
*
*
- * COPYRIGHT (c) 1989-1999.
+ * COPYRIGHT (c) 1989-2008.
* On-Line Applications Research Corporation (OAR).
*
* The license and distribution terms for this file may be
diff --git a/cpukit/score/src/threadqextractfifo.c b/cpukit/score/src/threadqextractfifo.c
index f7ecf3e270..7fd6f41d34 100644
--- a/cpukit/score/src/threadqextractfifo.c
+++ b/cpukit/score/src/threadqextractfifo.c
@@ -2,7 +2,7 @@
* Thread Queue Handler
*
*
- * COPYRIGHT (c) 1989-2006.
+ * COPYRIGHT (c) 1989-2008.
* On-Line Applications Research Corporation (OAR).
*
* The license and distribution terms for this file may be
diff --git a/cpukit/score/src/threadqextractpriority.c b/cpukit/score/src/threadqextractpriority.c
index ef45fb4423..739e6985c4 100644
--- a/cpukit/score/src/threadqextractpriority.c
+++ b/cpukit/score/src/threadqextractpriority.c
@@ -2,7 +2,7 @@
* Thread Queue Handler
*
*
- * COPYRIGHT (c) 1989-2006.
+ * COPYRIGHT (c) 1989-2008.
* On-Line Applications Research Corporation (OAR).
*
* The license and distribution terms for this file may be
diff --git a/cpukit/score/src/threadqextractwithproxy.c b/cpukit/score/src/threadqextractwithproxy.c
index 14653091b3..5c24431ab5 100644
--- a/cpukit/score/src/threadqextractwithproxy.c
+++ b/cpukit/score/src/threadqextractwithproxy.c
@@ -2,7 +2,7 @@
* Thread Queue Handler
*
*
- * COPYRIGHT (c) 1989-1999.
+ * COPYRIGHT (c) 1989-2008.
* On-Line Applications Research Corporation (OAR).
*
* The license and distribution terms for this file may be
diff --git a/cpukit/score/src/threadqfirst.c b/cpukit/score/src/threadqfirst.c
index bcbe759eda..9112b0ab72 100644
--- a/cpukit/score/src/threadqfirst.c
+++ b/cpukit/score/src/threadqfirst.c
@@ -2,7 +2,7 @@
* Thread Queue Handler
*
*
- * COPYRIGHT (c) 1989-1999.
+ * COPYRIGHT (c) 1989-2008.
* On-Line Applications Research Corporation (OAR).
*
* The license and distribution terms for this file may be
diff --git a/cpukit/score/src/threadqfirstfifo.c b/cpukit/score/src/threadqfirstfifo.c
index b002f1f448..9163780c76 100644
--- a/cpukit/score/src/threadqfirstfifo.c
+++ b/cpukit/score/src/threadqfirstfifo.c
@@ -2,7 +2,7 @@
* Thread Queue Handler
*
*
- * COPYRIGHT (c) 1989-1999.
+ * COPYRIGHT (c) 1989-2008.
* On-Line Applications Research Corporation (OAR).
*
* The license and distribution terms for this file may be
diff --git a/cpukit/score/src/threadqfirstpriority.c b/cpukit/score/src/threadqfirstpriority.c
index 81ac2742eb..442a4323b3 100644
--- a/cpukit/score/src/threadqfirstpriority.c
+++ b/cpukit/score/src/threadqfirstpriority.c
@@ -2,7 +2,7 @@
* Thread Queue Handler
*
*
- * COPYRIGHT (c) 1989-1999.
+ * COPYRIGHT (c) 1989-2008.
* On-Line Applications Research Corporation (OAR).
*
* The license and distribution terms for this file may be
diff --git a/cpukit/score/src/threadqflush.c b/cpukit/score/src/threadqflush.c
index ecb9b0df20..f609a0fc60 100644
--- a/cpukit/score/src/threadqflush.c
+++ b/cpukit/score/src/threadqflush.c
@@ -2,7 +2,7 @@
* Thread Queue Handler
*
*
- * COPYRIGHT (c) 1989-1999.
+ * COPYRIGHT (c) 1989-2008.
* On-Line Applications Research Corporation (OAR).
*
* The license and distribution terms for this file may be
diff --git a/cpukit/score/src/threadqrequeue.c b/cpukit/score/src/threadqrequeue.c
index a536eecdcf..4c50565b86 100644
--- a/cpukit/score/src/threadqrequeue.c
+++ b/cpukit/score/src/threadqrequeue.c
@@ -2,7 +2,7 @@
* Thread Queue Handler
*
*
- * COPYRIGHT (c) 1989-2006.
+ * COPYRIGHT (c) 1989-2008.
* On-Line Applications Research Corporation (OAR).
*
* The license and distribution terms for this file may be
@@ -46,28 +46,29 @@ void _Thread_queue_Requeue(
Thread_Control *the_thread
)
{
- /* just in case the thread really wasn't blocked here */
- if ( !the_thread_queue ) {
+ /*
+ * Just in case the thread really wasn't blocked on a thread queue
+ * when we get here.
+ */
+ if ( !the_thread_queue )
return;
- }
- switch ( the_thread_queue->discipline ) {
- case THREAD_QUEUE_DISCIPLINE_FIFO:
- /* queueing by FIFO -- nothing to do */
- break;
- case THREAD_QUEUE_DISCIPLINE_PRIORITY: {
- Thread_queue_Control *tq = the_thread_queue;
- ISR_Level level;
+ /*
+ * If queueing by FIFO, there is nothing to do. This only applies to
+ * priority blocking discipline.
+ */
+ if ( the_thread_queue->discipline == THREAD_QUEUE_DISCIPLINE_PRIORITY ) {
+ Thread_queue_Control *tq = the_thread_queue;
+ ISR_Level level;
+ ISR_Level level_ignored;
- _ISR_Disable( level );
- if ( _States_Is_waiting_on_thread_queue( the_thread->current_state ) ) {
- _Thread_queue_Enter_critical_section( tq );
- _Thread_queue_Extract_priority_helper( tq, the_thread, TRUE );
- _Thread_queue_Enqueue_priority( tq, the_thread );
- }
- _ISR_Enable( level );
- break;
+ _ISR_Disable( level );
+ if ( _States_Is_waiting_on_thread_queue( the_thread->current_state ) ) {
+ _Thread_queue_Enter_critical_section( tq );
+ _Thread_queue_Extract_priority_helper( tq, the_thread, TRUE );
+ (void) _Thread_queue_Enqueue_priority( tq, the_thread, &level_ignored );
}
+ _ISR_Enable( level );
}
}
diff --git a/cpukit/score/src/threadqtimeout.c b/cpukit/score/src/threadqtimeout.c
index ae11f0b40f..7b0fcd5061 100644
--- a/cpukit/score/src/threadqtimeout.c
+++ b/cpukit/score/src/threadqtimeout.c
@@ -2,7 +2,7 @@
* Thread Queue Handler
*
*
- * COPYRIGHT (c) 1989-2007.
+ * COPYRIGHT (c) 1989-2008.
* On-Line Applications Research Corporation (OAR).
*
* The license and distribution terms for this file may be