summaryrefslogtreecommitdiffstats
path: root/cpukit/rtems
diff options
context:
space:
mode:
Diffstat (limited to 'cpukit/rtems')
-rw-r--r--cpukit/rtems/Makefile.am3
-rw-r--r--cpukit/rtems/include/rtems/rtems/barrierimpl.h1
-rw-r--r--cpukit/rtems/include/rtems/rtems/clock.h31
-rw-r--r--cpukit/rtems/include/rtems/rtems/event.h5
-rw-r--r--cpukit/rtems/include/rtems/rtems/messageimpl.h16
-rw-r--r--cpukit/rtems/include/rtems/rtems/regionimpl.h2
-rw-r--r--cpukit/rtems/include/rtems/rtems/timerimpl.h60
-rw-r--r--cpukit/rtems/src/clockgetuptime.c2
-rw-r--r--cpukit/rtems/src/clockgetuptimenanoseconds.c9
-rw-r--r--cpukit/rtems/src/clockgetuptimeseconds.c43
-rw-r--r--cpukit/rtems/src/clockgetuptimetimeval.c2
-rw-r--r--cpukit/rtems/src/clocksetnsecshandler.c34
-rw-r--r--cpukit/rtems/src/clocktick.c26
-rw-r--r--cpukit/rtems/src/eventmp.c3
-rw-r--r--cpukit/rtems/src/eventseize.c14
-rw-r--r--cpukit/rtems/src/eventsend.c1
-rw-r--r--cpukit/rtems/src/eventsurrender.c10
-rw-r--r--cpukit/rtems/src/eventtimeout.c70
-rw-r--r--cpukit/rtems/src/msgmp.c8
-rw-r--r--cpukit/rtems/src/msgqbroadcast.c12
-rw-r--r--cpukit/rtems/src/msgqflush.c13
-rw-r--r--cpukit/rtems/src/msgqreceive.c11
-rw-r--r--cpukit/rtems/src/msgqsend.c12
-rw-r--r--cpukit/rtems/src/msgqurgent.c11
-rw-r--r--cpukit/rtems/src/partmp.c5
-rw-r--r--cpukit/rtems/src/ratemoncancel.c2
-rw-r--r--cpukit/rtems/src/ratemondelete.c2
-rw-r--r--cpukit/rtems/src/regioncreate.c17
-rw-r--r--cpukit/rtems/src/regiondelete.c1
-rw-r--r--cpukit/rtems/src/regionextend.c1
-rw-r--r--cpukit/rtems/src/regiongetfreeinfo.c1
-rw-r--r--cpukit/rtems/src/regiongetinfo.c1
-rw-r--r--cpukit/rtems/src/regiongetsegment.c7
-rw-r--r--cpukit/rtems/src/regiongetsegmentsize.c1
-rw-r--r--cpukit/rtems/src/regionmp.c5
-rw-r--r--cpukit/rtems/src/regionprocessqueue.c2
-rw-r--r--cpukit/rtems/src/regionresizesegment.c1
-rw-r--r--cpukit/rtems/src/regionreturnsegment.c1
-rw-r--r--cpukit/rtems/src/semdelete.c2
-rw-r--r--cpukit/rtems/src/semmp.c5
-rw-r--r--cpukit/rtems/src/semobtain.c17
-rw-r--r--cpukit/rtems/src/semrelease.c23
-rw-r--r--cpukit/rtems/src/signalmp.c3
-rw-r--r--cpukit/rtems/src/systemeventsend.c1
-rw-r--r--cpukit/rtems/src/taskmp.c3
-rw-r--r--cpukit/rtems/src/tasksetpriority.c20
-rw-r--r--cpukit/rtems/src/taskwakeafter.c10
-rw-r--r--cpukit/rtems/src/taskwakewhen.c8
-rw-r--r--cpukit/rtems/src/timercancel.c3
-rw-r--r--cpukit/rtems/src/timercreate.c29
-rw-r--r--cpukit/rtems/src/timerdelete.c2
-rw-r--r--cpukit/rtems/src/timerfireafter.c2
-rw-r--r--cpukit/rtems/src/timerfirewhen.c2
-rw-r--r--cpukit/rtems/src/timerreset.c2
-rw-r--r--cpukit/rtems/src/timerserver.c568
-rw-r--r--cpukit/rtems/src/timerserverfireafter.c2
-rw-r--r--cpukit/rtems/src/timerserverfirewhen.c2
57 files changed, 438 insertions, 712 deletions
diff --git a/cpukit/rtems/Makefile.am b/cpukit/rtems/Makefile.am
index 5e6f2eafa0..f38990d2a7 100644
--- a/cpukit/rtems/Makefile.am
+++ b/cpukit/rtems/Makefile.am
@@ -155,10 +155,8 @@ librtems_a_SOURCES += src/clockgettod.c
librtems_a_SOURCES += src/clockgettodtimeval.c
librtems_a_SOURCES += src/clockgetuptime.c
librtems_a_SOURCES += src/clockgetuptimetimeval.c
-librtems_a_SOURCES += src/clockgetuptimeseconds.c
librtems_a_SOURCES += src/clockgetuptimenanoseconds.c
librtems_a_SOURCES += src/clockset.c
-librtems_a_SOURCES += src/clocksetnsecshandler.c
librtems_a_SOURCES += src/clocktick.c
librtems_a_SOURCES += src/clocktodtoseconds.c
librtems_a_SOURCES += src/clocktodvalidate.c
@@ -210,7 +208,6 @@ librtems_a_SOURCES += src/eventreceive.c
librtems_a_SOURCES += src/eventseize.c
librtems_a_SOURCES += src/eventsend.c
librtems_a_SOURCES += src/eventsurrender.c
-librtems_a_SOURCES += src/eventtimeout.c
librtems_a_SOURCES += src/systemeventsend.c
librtems_a_SOURCES += src/systemeventreceive.c
diff --git a/cpukit/rtems/include/rtems/rtems/barrierimpl.h b/cpukit/rtems/include/rtems/rtems/barrierimpl.h
index 963ebd93da..e718028715 100644
--- a/cpukit/rtems/include/rtems/rtems/barrierimpl.h
+++ b/cpukit/rtems/include/rtems/rtems/barrierimpl.h
@@ -86,6 +86,7 @@ RTEMS_INLINE_ROUTINE void _Barrier_Free (
Barrier_Control *the_barrier
)
{
+ _CORE_barrier_Destroy( &the_barrier->Barrier );
_Objects_Free( &_Barrier_Information, &the_barrier->Object );
}
diff --git a/cpukit/rtems/include/rtems/rtems/clock.h b/cpukit/rtems/include/rtems/rtems/clock.h
index 2a1c77251f..989bf2f5c9 100644
--- a/cpukit/rtems/include/rtems/rtems/clock.h
+++ b/cpukit/rtems/include/rtems/rtems/clock.h
@@ -14,7 +14,6 @@
*
* - set the current date and time
* - obtain the current date and time
- * - set the nanoseconds since last clock tick handler
* - announce a clock tick
* - obtain the system uptime
*/
@@ -35,6 +34,7 @@
#include <rtems/rtems/status.h>
#include <rtems/rtems/types.h>
#include <rtems/config.h>
+#include <rtems/score/timecounterimpl.h>
#include <sys/time.h> /* struct timeval */
@@ -69,12 +69,6 @@ typedef enum {
} rtems_clock_get_options;
/**
- * Type for the nanoseconds since last tick BSP extension.
- */
-typedef TOD_Nanoseconds_since_last_tick_routine
- rtems_nanoseconds_extension_routine;
-
-/**
* @brief Obtain Current Time of Day
*
* @deprecated rtems_clock_get() is deprecated. Use the more explicit
@@ -279,24 +273,6 @@ rtems_status_code rtems_clock_set(
rtems_status_code rtems_clock_tick( void );
/**
- * @brief Set the BSP specific Nanoseconds Extension
- *
- * Clock Manager
- *
- * This directive sets the BSP provided nanoseconds since last tick
- * extension.
- *
- * @param[in] routine is a pointer to the extension routine
- *
- * @return This method returns RTEMS_SUCCESSFUL if there was not an
- * error. Otherwise, a status code is returned indicating the
- * source of the error.
- */
-rtems_status_code rtems_clock_set_nanoseconds_extension(
- rtems_nanoseconds_extension_routine routine
-);
-
-/**
* @brief Obtain the System Uptime
*
* This directive returns the system uptime.
@@ -328,7 +304,10 @@ void rtems_clock_get_uptime_timeval( struct timeval *uptime );
*
* @retval The system uptime in seconds.
*/
-time_t rtems_clock_get_uptime_seconds( void );
+RTEMS_INLINE_ROUTINE time_t rtems_clock_get_uptime_seconds( void )
+{
+ return _Timecounter_Time_uptime - 1;
+}
/**
* @brief Returns the system uptime in nanoseconds.
diff --git a/cpukit/rtems/include/rtems/rtems/event.h b/cpukit/rtems/include/rtems/rtems/event.h
index dce7de1165..012452a9d8 100644
--- a/cpukit/rtems/include/rtems/rtems/event.h
+++ b/cpukit/rtems/include/rtems/rtems/event.h
@@ -319,6 +319,11 @@ rtems_status_code rtems_event_receive (
#define RTEMS_EVENT_SYSTEM_NETWORK_CLOSE RTEMS_EVENT_26
/**
+ * @brief Reserved system event for the timer server.
+ */
+#define RTEMS_EVENT_SYSTEM_TIMER_SERVER RTEMS_EVENT_30
+
+/**
* @brief Reserved system event for transient usage.
*/
#define RTEMS_EVENT_SYSTEM_TRANSIENT RTEMS_EVENT_31
diff --git a/cpukit/rtems/include/rtems/rtems/messageimpl.h b/cpukit/rtems/include/rtems/rtems/messageimpl.h
index e2bc88d0db..2399d65f29 100644
--- a/cpukit/rtems/include/rtems/rtems/messageimpl.h
+++ b/cpukit/rtems/include/rtems/rtems/messageimpl.h
@@ -18,6 +18,7 @@
#include <rtems/rtems/message.h>
#include <rtems/score/objectimpl.h>
+#include <rtems/score/coremsgimpl.h>
#ifdef __cplusplus
extern "C" {
@@ -138,6 +139,21 @@ RTEMS_INLINE_ROUTINE Message_queue_Control *_Message_queue_Get (
_Objects_Get( &_Message_queue_Information, id, location );
}
+RTEMS_INLINE_ROUTINE Message_queue_Control *
+_Message_queue_Get_interrupt_disable(
+ Objects_Id id,
+ Objects_Locations *location,
+ ISR_lock_Context *lock_context
+)
+{
+ return (Message_queue_Control *) _Objects_Get_isr_disable(
+ &_Message_queue_Information,
+ id,
+ location,
+ lock_context
+ );
+}
+
RTEMS_INLINE_ROUTINE Message_queue_Control *_Message_queue_Allocate( void )
{
return (Message_queue_Control *)
diff --git a/cpukit/rtems/include/rtems/rtems/regionimpl.h b/cpukit/rtems/include/rtems/rtems/regionimpl.h
index 9ff7b966ca..ae1a50d208 100644
--- a/cpukit/rtems/include/rtems/rtems/regionimpl.h
+++ b/cpukit/rtems/include/rtems/rtems/regionimpl.h
@@ -20,6 +20,7 @@
#include <rtems/rtems/region.h>
#include <rtems/score/heapimpl.h>
#include <rtems/score/objectimpl.h>
+#include <rtems/score/threadqimpl.h>
#include <rtems/debug.h>
#ifdef __cplusplus
@@ -84,6 +85,7 @@ RTEMS_INLINE_ROUTINE void _Region_Free (
Region_Control *the_region
)
{
+ _Thread_queue_Destroy( &the_region->Wait_queue );
_Objects_Free( &_Region_Information, &the_region->Object );
}
diff --git a/cpukit/rtems/include/rtems/rtems/timerimpl.h b/cpukit/rtems/include/rtems/rtems/timerimpl.h
index b695d5e2fe..e5b37aa5f1 100644
--- a/cpukit/rtems/include/rtems/rtems/timerimpl.h
+++ b/cpukit/rtems/include/rtems/rtems/timerimpl.h
@@ -50,9 +50,9 @@ extern "C" {
typedef struct Timer_server_Control Timer_server_Control;
/**
- * @brief Method used to schedule the insertion of task based timers.
+ * @brief Method used for task based timers.
*/
-typedef void (*Timer_server_Schedule_operation)(
+typedef void (*Timer_server_Method)(
Timer_server_Control *timer_server,
Timer_Control *timer
);
@@ -65,28 +65,52 @@ typedef struct {
Watchdog_Control System_watchdog;
/**
+ * @brief Remaining delta of the system watchdog.
+ */
+ Watchdog_Interval system_watchdog_delta;
+
+ /**
+ * @brief Unique identifier of the context which deals currently with the
+ * system watchdog.
+ */
+ Thread_Control *system_watchdog_helper;
+
+ /**
+ * @brief Each insert and tickle operation increases the generation count so
+ * that the system watchdog dealer notices updates of the watchdog chain.
+ */
+ uint32_t generation;
+
+ /**
* @brief Watchdog header managed by the timer server.
*/
Watchdog_Header Header;
/**
- * @brief Last known time snapshot of the timer server.
+ * @brief Last time snapshot of the timer server.
*
* The units may be ticks or seconds.
*/
- Watchdog_Interval volatile last_snapshot;
+ Watchdog_Interval last_snapshot;
+
+ /**
+ * @brief Current time snapshot of the timer server.
+ *
+ * The units may be ticks or seconds.
+ */
+ Watchdog_Interval current_snapshot;
} Timer_server_Watchdogs;
struct Timer_server_Control {
/**
- * @brief Timer server thread.
+ * @brief The cancel method of the timer server.
*/
- Thread_Control *thread;
+ Timer_server_Method cancel;
/**
* @brief The schedule operation method of the timer server.
*/
- Timer_server_Schedule_operation schedule_operation;
+ Timer_server_Method schedule_operation;
/**
* @brief Interval watchdogs triggered by the timer server.
@@ -97,26 +121,6 @@ struct Timer_server_Control {
* @brief TOD watchdogs triggered by the timer server.
*/
Timer_server_Watchdogs TOD_watchdogs;
-
- /**
- * @brief Chain of timers scheduled for insert.
- *
- * This pointer is not @c NULL whenever the interval and TOD chains are
- * processed. After the processing this list will be checked and if
- * necessary the processing will be restarted. Processing of these chains
- * can be only interrupted through interrupts.
- */
- Chain_Control *volatile insert_chain;
-
- /**
- * @brief Indicates that the timer server is active or not.
- *
- * The server is active after the delay on a system watchdog. The activity
- * period of the server ends when no more watchdogs managed by the server
- * fire. The system watchdogs must not be manipulated when the server is
- * active.
- */
- bool volatile active;
};
/**
@@ -220,6 +224,8 @@ RTEMS_INLINE_ROUTINE bool _Timer_Is_dormant_class (
return ( the_class == TIMER_DORMANT );
}
+void _Timer_Cancel( Timer_Control *the_timer );
+
/**@}*/
#ifdef __cplusplus
diff --git a/cpukit/rtems/src/clockgetuptime.c b/cpukit/rtems/src/clockgetuptime.c
index 91ce6c46ee..acbe39a00e 100644
--- a/cpukit/rtems/src/clockgetuptime.c
+++ b/cpukit/rtems/src/clockgetuptime.c
@@ -42,6 +42,6 @@ rtems_status_code rtems_clock_get_uptime(
if ( !uptime )
return RTEMS_INVALID_ADDRESS;
- _TOD_Get_uptime_as_timespec( uptime );
+ _TOD_Get_zero_based_uptime_as_timespec( uptime );
return RTEMS_SUCCESSFUL;
}
diff --git a/cpukit/rtems/src/clockgetuptimenanoseconds.c b/cpukit/rtems/src/clockgetuptimenanoseconds.c
index 0310e592e9..03ff73bba3 100644
--- a/cpukit/rtems/src/clockgetuptimenanoseconds.c
+++ b/cpukit/rtems/src/clockgetuptimenanoseconds.c
@@ -23,13 +23,8 @@
uint64_t rtems_clock_get_uptime_nanoseconds( void )
{
Timestamp_Control snapshot_as_timestamp;
- uint32_t nanoseconds;
- ISR_lock_Context lock_context;
- _TOD_Acquire( &_TOD, &lock_context );
- snapshot_as_timestamp = _TOD.uptime;
- nanoseconds = ( *_TOD.nanoseconds_since_last_tick )();
- _TOD_Release( &_TOD, &lock_context );
+ _TOD_Get_zero_based_uptime(&snapshot_as_timestamp);
- return _Timestamp_Get_As_nanoseconds( &snapshot_as_timestamp, nanoseconds );
+ return _Timestamp_Get_as_nanoseconds(&snapshot_as_timestamp);
}
diff --git a/cpukit/rtems/src/clockgetuptimeseconds.c b/cpukit/rtems/src/clockgetuptimeseconds.c
deleted file mode 100644
index 0312921113..0000000000
--- a/cpukit/rtems/src/clockgetuptimeseconds.c
+++ /dev/null
@@ -1,43 +0,0 @@
-/**
- * @file
- *
- * @brief Returns the system uptime in seconds.
- * @ingroup ClassicClock Clocks
- */
-
-/*
- * Copyright (c) 2012 embedded brains GmbH. All rights reserved.
- *
- * embedded brains GmbH
- * Obere Lagerstr. 30
- * 82178 Puchheim
- * Germany
- * <rtems@embedded-brains.de>
- *
- * The license and distribution terms for this file may be
- * found in the file LICENSE in this distribution or at
- * http://www.rtems.org/license/LICENSE.
- */
-
-#if HAVE_CONFIG_H
- #include "config.h"
-#endif
-
-#include <rtems/rtems/clock.h>
-#include <rtems/score/todimpl.h>
-
-time_t rtems_clock_get_uptime_seconds( void )
-{
- TOD_Control *tod = &_TOD;
- Timestamp_Control snapshot_as_timestamp;
- struct timespec snapshot_as_timespec;
- ISR_lock_Context lock_context;
-
- _TOD_Acquire( tod, &lock_context );
- snapshot_as_timestamp = tod->uptime;
- _TOD_Release( tod, &lock_context );
-
- _Timestamp_To_timespec( &snapshot_as_timestamp, &snapshot_as_timespec );
-
- return snapshot_as_timespec.tv_sec;
-}
diff --git a/cpukit/rtems/src/clockgetuptimetimeval.c b/cpukit/rtems/src/clockgetuptimetimeval.c
index 0cbaa836bc..2e09ae2cd2 100644
--- a/cpukit/rtems/src/clockgetuptimetimeval.c
+++ b/cpukit/rtems/src/clockgetuptimetimeval.c
@@ -30,6 +30,6 @@ void rtems_clock_get_uptime_timeval( struct timeval *uptime )
{
Timestamp_Control snapshot_as_timestamp;
- _TOD_Get_uptime( &snapshot_as_timestamp );
+ _TOD_Get_zero_based_uptime( &snapshot_as_timestamp );
_Timestamp_To_timeval( &snapshot_as_timestamp, uptime );
}
diff --git a/cpukit/rtems/src/clocksetnsecshandler.c b/cpukit/rtems/src/clocksetnsecshandler.c
deleted file mode 100644
index ae08246902..0000000000
--- a/cpukit/rtems/src/clocksetnsecshandler.c
+++ /dev/null
@@ -1,34 +0,0 @@
-/**
- * @file
- *
- * @brief Set the BSP specific Nanoseconds Extension
- * @ingroup ClassicClock Clocks
- */
-
-/*
- * COPYRIGHT (c) 1989-2006.
- * 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.org/license/LICENSE.
- */
-
-#if HAVE_CONFIG_H
-#include "config.h"
-#endif
-
-#include <rtems/rtems/clock.h>
-#include <rtems/score/todimpl.h>
-
-rtems_status_code rtems_clock_set_nanoseconds_extension(
- rtems_nanoseconds_extension_routine routine
-)
-{
- if ( !routine )
- return RTEMS_INVALID_ADDRESS;
-
- _TOD_Set_nanoseconds_since_last_tick_handler( routine );
-
- return RTEMS_SUCCESSFUL;
-}
diff --git a/cpukit/rtems/src/clocktick.c b/cpukit/rtems/src/clocktick.c
index a026b44494..e2cd35f5fc 100644
--- a/cpukit/rtems/src/clocktick.c
+++ b/cpukit/rtems/src/clocktick.c
@@ -19,30 +19,14 @@
#endif
#include <rtems/rtems/clock.h>
-#include <rtems/score/schedulerimpl.h>
-#include <rtems/score/threadimpl.h>
-#include <rtems/score/todimpl.h>
-#include <rtems/score/watchdogimpl.h>
+#include <rtems/score/timecounter.h>
rtems_status_code rtems_clock_tick( void )
{
-#if defined( RTEMS_SMP )
- _Thread_Disable_dispatch();
-#endif
-
- _TOD_Tickle_ticks();
-
- _Watchdog_Tickle_ticks();
-
- _Scheduler_Tick();
-
-#if defined( RTEMS_SMP )
- _Thread_Enable_dispatch();
-#else
- if ( _Thread_Is_context_switch_necessary() &&
- _Thread_Dispatch_is_enabled() )
- _Thread_Dispatch();
-#endif
+ _Timecounter_Tick_simple(
+ rtems_configuration_get_microseconds_per_tick(),
+ 0
+ );
return RTEMS_SUCCESSFUL;
}
diff --git a/cpukit/rtems/src/eventmp.c b/cpukit/rtems/src/eventmp.c
index b2a5ce8a72..e2e43fcd0d 100644
--- a/cpukit/rtems/src/eventmp.c
+++ b/cpukit/rtems/src/eventmp.c
@@ -59,7 +59,8 @@ rtems_status_code _Event_MP_Send_request_packet (
_MPCI_Send_request_packet(
_Objects_Get_node( event_id ),
&the_packet->Prefix,
- STATES_READY
+ STATES_READY,
+ RTEMS_TIMEOUT
);
break;
diff --git a/cpukit/rtems/src/eventseize.c b/cpukit/rtems/src/eventseize.c
index 929665641c..a9290b38e8 100644
--- a/cpukit/rtems/src/eventseize.c
+++ b/cpukit/rtems/src/eventseize.c
@@ -84,12 +84,17 @@ void _Event_Seize(
executing->Wait.return_argument = event_out;
_Thread_Wait_flags_set( executing, intend_to_block );
- cpu_self = _Thread_Dispatch_disable_critical();
+ cpu_self = _Thread_Dispatch_disable_critical( lock_context );
_Thread_Lock_release_default( executing, lock_context );
- _Giant_Acquire( cpu_self );
if ( ticks ) {
- _Watchdog_Initialize( &executing->Timer, _Event_Timeout, 0, executing );
+ _Thread_Wait_set_timeout_code( executing, RTEMS_TIMEOUT );
+ _Watchdog_Initialize(
+ &executing->Timer,
+ _Thread_Timeout,
+ 0,
+ executing
+ );
_Watchdog_Insert_ticks( &executing->Timer, ticks );
}
@@ -101,10 +106,9 @@ void _Event_Seize(
wait_class | THREAD_WAIT_STATE_BLOCKED
);
if ( !success ) {
- _Watchdog_Remove( &executing->Timer );
+ _Watchdog_Remove_ticks( &executing->Timer );
_Thread_Unblock( executing );
}
- _Giant_Release( cpu_self );
_Thread_Dispatch_enable( cpu_self );
}
diff --git a/cpukit/rtems/src/eventsend.c b/cpukit/rtems/src/eventsend.c
index c9e81fb95f..23eed740a8 100644
--- a/cpukit/rtems/src/eventsend.c
+++ b/cpukit/rtems/src/eventsend.c
@@ -44,7 +44,6 @@ rtems_status_code rtems_event_send(
THREAD_WAIT_CLASS_EVENT,
&lock_context
);
- _Objects_Put_for_get_isr_disable( &thread->Object );
sc = RTEMS_SUCCESSFUL;
break;
#ifdef RTEMS_MULTIPROCESSING
diff --git a/cpukit/rtems/src/eventsurrender.c b/cpukit/rtems/src/eventsurrender.c
index ba4e429f1e..156586023d 100644
--- a/cpukit/rtems/src/eventsurrender.c
+++ b/cpukit/rtems/src/eventsurrender.c
@@ -85,7 +85,7 @@ void _Event_Surrender(
success = _Thread_Wait_flags_try_change_critical(
the_thread,
intend_to_block,
- wait_class | THREAD_WAIT_STATE_INTERRUPT_SATISFIED
+ wait_class | THREAD_WAIT_STATE_READY_AGAIN
);
if ( success ) {
_Event_Satisfy( the_thread, event, pending_events, seized_events );
@@ -94,7 +94,7 @@ void _Event_Surrender(
_Event_Satisfy( the_thread, event, pending_events, seized_events );
_Thread_Wait_flags_set(
the_thread,
- wait_class | THREAD_WAIT_STATE_SATISFIED
+ wait_class | THREAD_WAIT_STATE_READY_AGAIN
);
unblock = true;
} else {
@@ -107,14 +107,12 @@ void _Event_Surrender(
if ( unblock ) {
Per_CPU_Control *cpu_self;
- cpu_self = _Thread_Dispatch_disable_critical();
+ cpu_self = _Thread_Dispatch_disable_critical( lock_context );
_Thread_Lock_release_default( the_thread, lock_context );
- _Giant_Acquire( cpu_self );
- _Watchdog_Remove( &the_thread->Timer );
+ _Watchdog_Remove_ticks( &the_thread->Timer );
_Thread_Unblock( the_thread );
- _Giant_Release( cpu_self );
_Thread_Dispatch_enable( cpu_self );
} else {
_Thread_Lock_release_default( the_thread, lock_context );
diff --git a/cpukit/rtems/src/eventtimeout.c b/cpukit/rtems/src/eventtimeout.c
deleted file mode 100644
index 9c091748c0..0000000000
--- a/cpukit/rtems/src/eventtimeout.c
+++ /dev/null
@@ -1,70 +0,0 @@
-/**
- * @file
- *
- * @brief Timeout Event
- * @ingroup ClassicEvent
- */
-
-/*
- * 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.org/license/LICENSE.
- */
-
-#if HAVE_CONFIG_H
- #include "config.h"
-#endif
-
-#include <rtems/rtems/eventimpl.h>
-#include <rtems/score/threadimpl.h>
-
-void _Event_Timeout(
- Objects_Id id,
- void *arg
-)
-{
- Thread_Control *the_thread;
- ISR_lock_Context lock_context;
- Thread_Wait_flags wait_flags;
- Thread_Wait_flags wait_class;
- Thread_Wait_flags intend_to_block;
- Thread_Wait_flags blocked;
- bool success;
- bool unblock;
-
- the_thread = arg;
- _Thread_Lock_acquire_default( the_thread, &lock_context );
-
- wait_flags = _Thread_Wait_flags_get( the_thread );
- wait_class = wait_flags & THREAD_WAIT_CLASS_MASK;
- intend_to_block = wait_class | THREAD_WAIT_STATE_INTEND_TO_BLOCK;
- blocked = wait_class | THREAD_WAIT_STATE_BLOCKED;
- success = _Thread_Wait_flags_try_change_critical(
- the_thread,
- intend_to_block,
- wait_class | THREAD_WAIT_STATE_INTERRUPT_TIMEOUT
- );
-
- if ( success ) {
- the_thread->Wait.return_code = RTEMS_TIMEOUT;
- unblock = false;
- } else if ( _Thread_Wait_flags_get( the_thread ) == blocked ) {
- the_thread->Wait.return_code = RTEMS_TIMEOUT;
- _Thread_Wait_flags_set(
- the_thread,
- wait_class | THREAD_WAIT_STATE_TIMEOUT
- );
- unblock = true;
- } else {
- unblock = false;
- }
-
- _Thread_Lock_release_default( the_thread, &lock_context );
-
- if ( unblock ) {
- _Thread_Unblock( the_thread );
- }
-}
diff --git a/cpukit/rtems/src/msgmp.c b/cpukit/rtems/src/msgmp.c
index 7043138963..83b5a31f52 100644
--- a/cpukit/rtems/src/msgmp.c
+++ b/cpukit/rtems/src/msgmp.c
@@ -148,7 +148,8 @@ rtems_status_code _Message_queue_MP_Send_request_packet (
return (rtems_status_code) _MPCI_Send_request_packet(
_Objects_Get_node(message_queue_id),
&the_packet->Prefix,
- STATES_WAITING_FOR_MESSAGE
+ STATES_WAITING_FOR_MESSAGE,
+ RTEMS_TIMEOUT
);
break;
@@ -173,7 +174,8 @@ rtems_status_code _Message_queue_MP_Send_request_packet (
return (rtems_status_code) _MPCI_Send_request_packet(
_Objects_Get_node(message_queue_id),
&the_packet->Prefix,
- STATES_WAITING_FOR_MESSAGE
+ STATES_WAITING_FOR_MESSAGE,
+ RTEMS_TIMEOUT
);
break;
@@ -291,7 +293,7 @@ void _Message_queue_MP_Process_packet (
the_thread = _Thread_MP_Find_proxy( the_packet->proxy_id );
if (! _Thread_Is_null( the_thread ) )
- _Thread_queue_Extract( the_thread->Wait.queue, the_thread );
+ _Thread_queue_Extract( the_thread );
_MPCI_Return_packet( the_packet_prefix );
break;
diff --git a/cpukit/rtems/src/msgqbroadcast.c b/cpukit/rtems/src/msgqbroadcast.c
index 64ea80e3de..aabbf3f6ac 100644
--- a/cpukit/rtems/src/msgqbroadcast.c
+++ b/cpukit/rtems/src/msgqbroadcast.c
@@ -40,6 +40,7 @@ rtems_status_code rtems_message_queue_broadcast(
Message_queue_Control *the_message_queue;
Objects_Locations location;
CORE_message_queue_Status core_status;
+ ISR_lock_Context lock_context;
if ( !buffer )
return RTEMS_INVALID_ADDRESS;
@@ -47,7 +48,11 @@ rtems_status_code rtems_message_queue_broadcast(
if ( !count )
return RTEMS_INVALID_ADDRESS;
- the_message_queue = _Message_queue_Get( id, &location );
+ the_message_queue = _Message_queue_Get_interrupt_disable(
+ id,
+ &location,
+ &lock_context
+ );
switch ( location ) {
case OBJECTS_LOCAL:
@@ -61,10 +66,9 @@ rtems_status_code rtems_message_queue_broadcast(
#else
NULL,
#endif
- count
+ count,
+ &lock_context
);
-
- _Objects_Put( &the_message_queue->Object );
return
_Message_queue_Translate_core_message_queue_return_code( core_status );
diff --git a/cpukit/rtems/src/msgqflush.c b/cpukit/rtems/src/msgqflush.c
index 7ae7ef4544..809c243b52 100644
--- a/cpukit/rtems/src/msgqflush.c
+++ b/cpukit/rtems/src/msgqflush.c
@@ -54,16 +54,23 @@ rtems_status_code rtems_message_queue_flush(
{
Message_queue_Control *the_message_queue;
Objects_Locations location;
+ ISR_lock_Context lock_context;
if ( !count )
return RTEMS_INVALID_ADDRESS;
- the_message_queue = _Message_queue_Get( id, &location );
+ the_message_queue = _Message_queue_Get_interrupt_disable(
+ id,
+ &location,
+ &lock_context
+ );
switch ( location ) {
case OBJECTS_LOCAL:
- *count = _CORE_message_queue_Flush( &the_message_queue->message_queue );
- _Objects_Put( &the_message_queue->Object );
+ *count = _CORE_message_queue_Flush(
+ &the_message_queue->message_queue,
+ &lock_context
+ );
return RTEMS_SUCCESSFUL;
#if defined(RTEMS_MULTIPROCESSING)
diff --git a/cpukit/rtems/src/msgqreceive.c b/cpukit/rtems/src/msgqreceive.c
index db09cfe547..2b9a4e742b 100644
--- a/cpukit/rtems/src/msgqreceive.c
+++ b/cpukit/rtems/src/msgqreceive.c
@@ -42,6 +42,7 @@ rtems_status_code rtems_message_queue_receive(
Objects_Locations location;
bool wait;
Thread_Control *executing;
+ ISR_lock_Context lock_context;
if ( !buffer )
return RTEMS_INVALID_ADDRESS;
@@ -49,7 +50,11 @@ rtems_status_code rtems_message_queue_receive(
if ( !size )
return RTEMS_INVALID_ADDRESS;
- the_message_queue = _Message_queue_Get( id, &location );
+ the_message_queue = _Message_queue_Get_interrupt_disable(
+ id,
+ &location,
+ &lock_context
+ );
switch ( location ) {
case OBJECTS_LOCAL:
@@ -66,9 +71,9 @@ rtems_status_code rtems_message_queue_receive(
buffer,
size,
wait,
- timeout
+ timeout,
+ &lock_context
);
- _Objects_Put( &the_message_queue->Object );
return _Message_queue_Translate_core_message_queue_return_code(
executing->Wait.return_code
);
diff --git a/cpukit/rtems/src/msgqsend.c b/cpukit/rtems/src/msgqsend.c
index 34b7c29e7c..fb3979ed78 100644
--- a/cpukit/rtems/src/msgqsend.c
+++ b/cpukit/rtems/src/msgqsend.c
@@ -62,11 +62,16 @@ rtems_status_code rtems_message_queue_send(
Message_queue_Control *the_message_queue;
Objects_Locations location;
CORE_message_queue_Status status;
+ ISR_lock_Context lock_context;
if ( !buffer )
return RTEMS_INVALID_ADDRESS;
- the_message_queue = _Message_queue_Get( id, &location );
+ the_message_queue = _Message_queue_Get_interrupt_disable(
+ id,
+ &location,
+ &lock_context
+ );
switch ( location ) {
case OBJECTS_LOCAL:
@@ -77,11 +82,10 @@ rtems_status_code rtems_message_queue_send(
id,
MESSAGE_QUEUE_MP_HANDLER,
false, /* sender does not block */
- 0 /* no timeout */
+ 0, /* no timeout */
+ &lock_context
);
- _Objects_Put( &the_message_queue->Object );
-
/*
* Since this API does not allow for blocking sends, we can directly
* return the returned status.
diff --git a/cpukit/rtems/src/msgqurgent.c b/cpukit/rtems/src/msgqurgent.c
index 85a9d4f1b4..e6ae5efcf0 100644
--- a/cpukit/rtems/src/msgqurgent.c
+++ b/cpukit/rtems/src/msgqurgent.c
@@ -45,11 +45,16 @@ rtems_status_code rtems_message_queue_urgent(
Message_queue_Control *the_message_queue;
Objects_Locations location;
CORE_message_queue_Status status;
+ ISR_lock_Context lock_context;
if ( !buffer )
return RTEMS_INVALID_ADDRESS;
- the_message_queue = _Message_queue_Get( id, &location );
+ the_message_queue = _Message_queue_Get_interrupt_disable(
+ id,
+ &location,
+ &lock_context
+ );
switch ( location ) {
case OBJECTS_LOCAL:
@@ -60,9 +65,9 @@ rtems_status_code rtems_message_queue_urgent(
id,
MESSAGE_QUEUE_MP_HANDLER,
false, /* sender does not block */
- 0 /* no timeout */
+ 0, /* no timeout */
+ &lock_context
);
- _Objects_Put( &the_message_queue->Object );
/*
* Since this API does not allow for blocking sends, we can directly
diff --git a/cpukit/rtems/src/partmp.c b/cpukit/rtems/src/partmp.c
index 943c24ac6d..9593ce58a9 100644
--- a/cpukit/rtems/src/partmp.c
+++ b/cpukit/rtems/src/partmp.c
@@ -104,7 +104,8 @@ rtems_status_code _Partition_MP_Send_request_packet (
_MPCI_Send_request_packet(
_Objects_Get_node( partition_id ),
&the_packet->Prefix,
- STATES_READY /* Not used */
+ STATES_READY, /* Not used */
+ RTEMS_TIMEOUT
);
break;
@@ -209,7 +210,7 @@ void _Partition_MP_Process_packet (
the_thread = _Thread_MP_Find_proxy( the_packet->proxy_id );
if ( ! _Thread_Is_null( the_thread ) )
- _Thread_queue_Extract( the_thread->Wait.queue, the_thread );
+ _Thread_queue_Extract( the_thread );
_MPCI_Return_packet( the_packet_prefix );
break;
diff --git a/cpukit/rtems/src/ratemoncancel.c b/cpukit/rtems/src/ratemoncancel.c
index d4a9102955..67b230fbfc 100644
--- a/cpukit/rtems/src/ratemoncancel.c
+++ b/cpukit/rtems/src/ratemoncancel.c
@@ -38,7 +38,7 @@ rtems_status_code rtems_rate_monotonic_cancel(
_Objects_Put( &the_period->Object );
return RTEMS_NOT_OWNER_OF_RESOURCE;
}
- (void) _Watchdog_Remove( &the_period->Timer );
+ _Watchdog_Remove_ticks( &the_period->Timer );
the_period->state = RATE_MONOTONIC_INACTIVE;
_Scheduler_Release_job( the_period->owner, 0 );
_Objects_Put( &the_period->Object );
diff --git a/cpukit/rtems/src/ratemondelete.c b/cpukit/rtems/src/ratemondelete.c
index 971ad8ef3d..77cf3fe306 100644
--- a/cpukit/rtems/src/ratemondelete.c
+++ b/cpukit/rtems/src/ratemondelete.c
@@ -37,7 +37,7 @@ rtems_status_code rtems_rate_monotonic_delete(
case OBJECTS_LOCAL:
_Scheduler_Release_job( the_period->owner, 0 );
_Objects_Close( &_Rate_monotonic_Information, &the_period->Object );
- (void) _Watchdog_Remove( &the_period->Timer );
+ _Watchdog_Remove_ticks( &the_period->Timer );
the_period->state = RATE_MONOTONIC_INACTIVE;
_Objects_Put( &the_period->Object );
_Rate_monotonic_Free( the_period );
diff --git a/cpukit/rtems/src/regioncreate.c b/cpukit/rtems/src/regioncreate.c
index 0daf644ce3..409510c892 100644
--- a/cpukit/rtems/src/regioncreate.c
+++ b/cpukit/rtems/src/regioncreate.c
@@ -71,6 +71,11 @@ rtems_status_code rtems_region_create(
return_status = RTEMS_TOO_MANY;
else {
+ _Thread_queue_Initialize(
+ &the_region->Wait_queue,
+ _Attributes_Is_priority( attribute_set ) ?
+ THREAD_QUEUE_DISCIPLINE_PRIORITY : THREAD_QUEUE_DISCIPLINE_FIFO
+ );
the_region->maximum_segment_size = _Heap_Initialize(
&the_region->Memory, starting_address, length, page_size
@@ -79,23 +84,13 @@ rtems_status_code rtems_region_create(
if ( !the_region->maximum_segment_size ) {
_Region_Free( the_region );
return_status = RTEMS_INVALID_SIZE;
- }
-
- else {
-
+ } else {
the_region->starting_address = starting_address;
the_region->length = length;
the_region->page_size = page_size;
the_region->attribute_set = attribute_set;
the_region->number_of_used_blocks = 0;
- _Thread_queue_Initialize(
- &the_region->Wait_queue,
- _Attributes_Is_priority( attribute_set ) ?
- THREAD_QUEUE_DISCIPLINE_PRIORITY : THREAD_QUEUE_DISCIPLINE_FIFO,
- RTEMS_TIMEOUT
- );
-
_Objects_Open(
&_Region_Information,
&the_region->Object,
diff --git a/cpukit/rtems/src/regiondelete.c b/cpukit/rtems/src/regiondelete.c
index 5a2df7c009..b5209da890 100644
--- a/cpukit/rtems/src/regiondelete.c
+++ b/cpukit/rtems/src/regiondelete.c
@@ -52,7 +52,6 @@ rtems_status_code rtems_region_delete(
#if defined(RTEMS_MULTIPROCESSING)
case OBJECTS_REMOTE: /* this error cannot be returned */
- break;
#endif
case OBJECTS_ERROR:
diff --git a/cpukit/rtems/src/regionextend.c b/cpukit/rtems/src/regionextend.c
index 65b68cdf1a..2ee2b992e4 100644
--- a/cpukit/rtems/src/regionextend.c
+++ b/cpukit/rtems/src/regionextend.c
@@ -65,7 +65,6 @@ rtems_status_code rtems_region_extend(
#if defined(RTEMS_MULTIPROCESSING)
case OBJECTS_REMOTE: /* this error cannot be returned */
- break;
#endif
case OBJECTS_ERROR:
diff --git a/cpukit/rtems/src/regiongetfreeinfo.c b/cpukit/rtems/src/regiongetfreeinfo.c
index be0f0089a9..6ebd1abbd2 100644
--- a/cpukit/rtems/src/regiongetfreeinfo.c
+++ b/cpukit/rtems/src/regiongetfreeinfo.c
@@ -56,7 +56,6 @@ rtems_status_code rtems_region_get_free_information(
#if defined(RTEMS_MULTIPROCESSING)
case OBJECTS_REMOTE: /* this error cannot be returned */
- break;
#endif
case OBJECTS_ERROR:
diff --git a/cpukit/rtems/src/regiongetinfo.c b/cpukit/rtems/src/regiongetinfo.c
index c3466f0566..d5eee727d3 100644
--- a/cpukit/rtems/src/regiongetinfo.c
+++ b/cpukit/rtems/src/regiongetinfo.c
@@ -50,7 +50,6 @@ rtems_status_code rtems_region_get_information(
#if defined(RTEMS_MULTIPROCESSING)
case OBJECTS_REMOTE: /* this error cannot be returned */
- break;
#endif
case OBJECTS_ERROR:
diff --git a/cpukit/rtems/src/regiongetsegment.c b/cpukit/rtems/src/regiongetsegment.c
index 1a52bc1d59..26437b5188 100644
--- a/cpukit/rtems/src/regiongetsegment.c
+++ b/cpukit/rtems/src/regiongetsegment.c
@@ -79,18 +79,16 @@ rtems_status_code rtems_region_get_segment(
_Thread_Disable_dispatch();
_RTEMS_Unlock_allocator();
- executing->Wait.queue = &the_region->Wait_queue;
executing->Wait.id = id;
executing->Wait.count = size;
executing->Wait.return_argument = segment;
- _Thread_queue_Enter_critical_section( &the_region->Wait_queue );
-
_Thread_queue_Enqueue(
&the_region->Wait_queue,
executing,
STATES_WAITING_FOR_SEGMENT,
- timeout
+ timeout,
+ RTEMS_TIMEOUT
);
_Objects_Put( &the_region->Object );
@@ -102,7 +100,6 @@ rtems_status_code rtems_region_get_segment(
#if defined(RTEMS_MULTIPROCESSING)
case OBJECTS_REMOTE: /* this error cannot be returned */
- break;
#endif
case OBJECTS_ERROR:
diff --git a/cpukit/rtems/src/regiongetsegmentsize.c b/cpukit/rtems/src/regiongetsegmentsize.c
index 8f823fcec9..ab07a56e9c 100644
--- a/cpukit/rtems/src/regiongetsegmentsize.c
+++ b/cpukit/rtems/src/regiongetsegmentsize.c
@@ -53,7 +53,6 @@ rtems_status_code rtems_region_get_segment_size(
#if defined(RTEMS_MULTIPROCESSING)
case OBJECTS_REMOTE: /* this error cannot be returned */
- break;
#endif
case OBJECTS_ERROR:
diff --git a/cpukit/rtems/src/regionmp.c b/cpukit/rtems/src/regionmp.c
index 58dfa99dde..135a69dd97 100644
--- a/cpukit/rtems/src/regionmp.c
+++ b/cpukit/rtems/src/regionmp.c
@@ -102,7 +102,8 @@ rtems_status_code _Region_MP_Send_request_packet (
return (rtems_status_code) _MPCI_Send_request_packet(
_Objects_Get_node( region_id ),
&the_packet->Prefix,
- STATES_READY /* Not used */
+ STATES_READY, /* Not used */
+ RTEMS_TIMEOUT
);
break;
@@ -195,7 +196,7 @@ void _Region_MP_Process_packet (
the_thread = _Thread_MP_Find_proxy( the_packet->proxy_id );
if ( ! _Thread_Is_null( the_thread ) )
- _Thread_queue_Extract( the_thread->Wait.queue, the_thread );
+ _Thread_queue_Extract( the_thread );
_MPCI_Return_packet( the_packet_prefix );
break;
diff --git a/cpukit/rtems/src/regionprocessqueue.c b/cpukit/rtems/src/regionprocessqueue.c
index 54081af84d..a06a077e3d 100644
--- a/cpukit/rtems/src/regionprocessqueue.c
+++ b/cpukit/rtems/src/regionprocessqueue.c
@@ -61,7 +61,7 @@ void _Region_Process_queue(
*(void **)the_thread->Wait.return_argument = the_segment;
the_region->number_of_used_blocks += 1;
- _Thread_queue_Extract( &the_region->Wait_queue, the_thread );
+ _Thread_queue_Extract( the_thread );
the_thread->Wait.return_code = RTEMS_SUCCESSFUL;
}
_Thread_Enable_dispatch();
diff --git a/cpukit/rtems/src/regionresizesegment.c b/cpukit/rtems/src/regionresizesegment.c
index ee3499a729..b1d9482c79 100644
--- a/cpukit/rtems/src/regionresizesegment.c
+++ b/cpukit/rtems/src/regionresizesegment.c
@@ -79,7 +79,6 @@ rtems_status_code rtems_region_resize_segment(
#if defined(RTEMS_MULTIPROCESSING)
case OBJECTS_REMOTE: /* this error cannot be returned */
- break;
#endif
case OBJECTS_ERROR:
diff --git a/cpukit/rtems/src/regionreturnsegment.c b/cpukit/rtems/src/regionreturnsegment.c
index 6ae537fd4f..98f2240a23 100644
--- a/cpukit/rtems/src/regionreturnsegment.c
+++ b/cpukit/rtems/src/regionreturnsegment.c
@@ -82,7 +82,6 @@ rtems_status_code rtems_region_return_segment(
#if defined(RTEMS_MULTIPROCESSING)
case OBJECTS_REMOTE: /* this error cannot be returned */
- break;
#endif
case OBJECTS_ERROR:
diff --git a/cpukit/rtems/src/semdelete.c b/cpukit/rtems/src/semdelete.c
index a805ac61de..e9c3ad21e9 100644
--- a/cpukit/rtems/src/semdelete.c
+++ b/cpukit/rtems/src/semdelete.c
@@ -76,12 +76,14 @@ rtems_status_code rtems_semaphore_delete(
SEMAPHORE_MP_OBJECT_WAS_DELETED,
CORE_MUTEX_WAS_DELETED
);
+ _CORE_mutex_Destroy( &the_semaphore->Core_control.mutex );
} else {
_CORE_semaphore_Flush(
&the_semaphore->Core_control.semaphore,
SEMAPHORE_MP_OBJECT_WAS_DELETED,
CORE_SEMAPHORE_WAS_DELETED
);
+ _CORE_semaphore_Destroy( &the_semaphore->Core_control.semaphore );
}
_Objects_Close( &_Semaphore_Information, &the_semaphore->Object );
diff --git a/cpukit/rtems/src/semmp.c b/cpukit/rtems/src/semmp.c
index eabd1b7a0b..f4c5cb73df 100644
--- a/cpukit/rtems/src/semmp.c
+++ b/cpukit/rtems/src/semmp.c
@@ -95,7 +95,8 @@ rtems_status_code _Semaphore_MP_Send_request_packet (
return _MPCI_Send_request_packet(
_Objects_Get_node( semaphore_id ),
&the_packet->Prefix,
- STATES_WAITING_FOR_SEMAPHORE
+ STATES_WAITING_FOR_SEMAPHORE,
+ RTEMS_TIMEOUT
);
break;
@@ -188,7 +189,7 @@ void _Semaphore_MP_Process_packet (
the_thread = _Thread_MP_Find_proxy( the_packet->proxy_id );
if ( ! _Thread_Is_null( the_thread ) )
- _Thread_queue_Extract( the_thread->Wait.queue, the_thread );
+ _Thread_queue_Extract( the_thread );
_MPCI_Return_packet( the_packet_prefix );
break;
diff --git a/cpukit/rtems/src/semobtain.c b/cpukit/rtems/src/semobtain.c
index 0edac96264..bda39fa80e 100644
--- a/cpukit/rtems/src/semobtain.c
+++ b/cpukit/rtems/src/semobtain.c
@@ -56,19 +56,16 @@ rtems_status_code rtems_semaphore_obtain(
attribute_set = the_semaphore->attribute_set;
wait = !_Options_Is_no_wait( option_set );
#if defined(RTEMS_SMP)
- _Thread_Disable_dispatch();
if ( _Attributes_Is_multiprocessor_resource_sharing( attribute_set ) ) {
MRSP_Status mrsp_status;
- _ISR_lock_ISR_enable( &lock_context );
mrsp_status = _MRSP_Obtain(
&the_semaphore->Core_control.mrsp,
executing,
wait,
- timeout
+ timeout,
+ &lock_context
);
- _Thread_Enable_dispatch();
- _Objects_Put_for_get_isr_disable( &the_semaphore->Object );
return _Semaphore_Translate_MRSP_status_code( mrsp_status );
} else
#endif
@@ -81,16 +78,12 @@ rtems_status_code rtems_semaphore_obtain(
timeout,
&lock_context
);
-#if defined(RTEMS_SMP)
- _Thread_Enable_dispatch();
-#endif
- _Objects_Put_for_get_isr_disable( &the_semaphore->Object );
return _Semaphore_Translate_core_mutex_return_code(
executing->Wait.return_code );
}
/* must be a counting semaphore */
- _CORE_semaphore_Seize_isr_disable(
+ _CORE_semaphore_Seize(
&the_semaphore->Core_control.semaphore,
executing,
id,
@@ -98,10 +91,6 @@ rtems_status_code rtems_semaphore_obtain(
timeout,
&lock_context
);
-#if defined(RTEMS_SMP)
- _Thread_Enable_dispatch();
-#endif
- _Objects_Put_for_get_isr_disable( &the_semaphore->Object );
return _Semaphore_Translate_core_semaphore_return_code(
executing->Wait.return_code );
diff --git a/cpukit/rtems/src/semrelease.c b/cpukit/rtems/src/semrelease.c
index 37a05b2507..5d41b6cfae 100644
--- a/cpukit/rtems/src/semrelease.c
+++ b/cpukit/rtems/src/semrelease.c
@@ -62,19 +62,26 @@ rtems_status_code rtems_semaphore_release(
CORE_mutex_Status mutex_status;
CORE_semaphore_Status semaphore_status;
rtems_attribute attribute_set;
+ ISR_lock_Context lock_context;
- the_semaphore = _Semaphore_Get( id, &location );
+ the_semaphore = _Semaphore_Get_interrupt_disable(
+ id,
+ &location,
+ &lock_context
+ );
switch ( location ) {
case OBJECTS_LOCAL:
attribute_set = the_semaphore->attribute_set;
#if defined(RTEMS_SMP)
if ( _Attributes_Is_multiprocessor_resource_sharing( attribute_set ) ) {
- MRSP_Status mrsp_status = _MRSP_Release(
+ MRSP_Status mrsp_status;
+
+ mrsp_status = _MRSP_Release(
&the_semaphore->Core_control.mrsp,
- _Thread_Get_executing()
+ _Thread_Executing,
+ &lock_context
);
- _Objects_Put( &the_semaphore->Object );
return _Semaphore_Translate_MRSP_status_code( mrsp_status );
} else
#endif
@@ -82,17 +89,17 @@ rtems_status_code rtems_semaphore_release(
mutex_status = _CORE_mutex_Surrender(
&the_semaphore->Core_control.mutex,
id,
- MUTEX_MP_SUPPORT
+ MUTEX_MP_SUPPORT,
+ &lock_context
);
- _Objects_Put( &the_semaphore->Object );
return _Semaphore_Translate_core_mutex_return_code( mutex_status );
} else {
semaphore_status = _CORE_semaphore_Surrender(
&the_semaphore->Core_control.semaphore,
id,
- MUTEX_MP_SUPPORT
+ MUTEX_MP_SUPPORT,
+ &lock_context
);
- _Objects_Put( &the_semaphore->Object );
return
_Semaphore_Translate_core_semaphore_return_code( semaphore_status );
}
diff --git a/cpukit/rtems/src/signalmp.c b/cpukit/rtems/src/signalmp.c
index 9d2177d214..4a2d5738af 100644
--- a/cpukit/rtems/src/signalmp.c
+++ b/cpukit/rtems/src/signalmp.c
@@ -60,7 +60,8 @@ rtems_status_code _Signal_MP_Send_request_packet (
return _MPCI_Send_request_packet(
_Objects_Get_node( task_id ),
&the_packet->Prefix,
- STATES_READY /* Not used */
+ STATES_READY, /* Not used */
+ RTEMS_TIMEOUT
);
break;
diff --git a/cpukit/rtems/src/systemeventsend.c b/cpukit/rtems/src/systemeventsend.c
index 1892c13fe7..3c821c9ef9 100644
--- a/cpukit/rtems/src/systemeventsend.c
+++ b/cpukit/rtems/src/systemeventsend.c
@@ -50,7 +50,6 @@ rtems_status_code rtems_event_system_send(
THREAD_WAIT_CLASS_SYSTEM_EVENT,
&lock_context
);
- _Objects_Put_for_get_isr_disable( &thread->Object );
sc = RTEMS_SUCCESSFUL;
break;
#ifdef RTEMS_MULTIPROCESSING
diff --git a/cpukit/rtems/src/taskmp.c b/cpukit/rtems/src/taskmp.c
index 4b97ffe639..339544cdc4 100644
--- a/cpukit/rtems/src/taskmp.c
+++ b/cpukit/rtems/src/taskmp.c
@@ -108,7 +108,8 @@ rtems_status_code _RTEMS_tasks_MP_Send_request_packet (
return _MPCI_Send_request_packet(
_Objects_Get_node( task_id ),
&the_packet->Prefix,
- STATES_READY /* Not used */
+ STATES_READY, /* Not used */
+ RTEMS_TIMEOUT
);
break;
diff --git a/cpukit/rtems/src/tasksetpriority.c b/cpukit/rtems/src/tasksetpriority.c
index 4e4835675d..582c67f9f2 100644
--- a/cpukit/rtems/src/tasksetpriority.c
+++ b/cpukit/rtems/src/tasksetpriority.c
@@ -41,16 +41,18 @@ rtems_status_code rtems_task_set_priority(
switch ( location ) {
case OBJECTS_LOCAL:
- *old_priority = _RTEMS_tasks_Priority_from_Core(
- the_thread->current_priority
- );
if ( new_priority != RTEMS_CURRENT_PRIORITY ) {
- the_thread->real_priority = _RTEMS_tasks_Priority_to_Core(
- new_priority
- );
- if ( !_Thread_Owns_resources( the_thread ) ||
- the_thread->current_priority > new_priority )
- _Thread_Change_priority( the_thread, new_priority, false );
+ _Thread_Set_priority(
+ the_thread,
+ _RTEMS_tasks_Priority_to_Core( new_priority ),
+ old_priority,
+ false
+ );
+ *old_priority = _RTEMS_tasks_Priority_from_Core( *old_priority );
+ } else {
+ *old_priority = _RTEMS_tasks_Priority_from_Core(
+ the_thread->current_priority
+ );
}
_Objects_Put( &the_thread->Object );
return RTEMS_SUCCESSFUL;
diff --git a/cpukit/rtems/src/taskwakeafter.c b/cpukit/rtems/src/taskwakeafter.c
index 6f0322723a..b7f328f5bc 100644
--- a/cpukit/rtems/src/taskwakeafter.c
+++ b/cpukit/rtems/src/taskwakeafter.c
@@ -30,23 +30,25 @@ rtems_status_code rtems_task_wake_after(
* It is critical to obtain the executing thread after thread dispatching is
* disabled on SMP configurations.
*/
- Thread_Control *executing;
+ Thread_Control *executing;
+ Per_CPU_Control *cpu_self;
- _Thread_Disable_dispatch();
+ cpu_self = _Thread_Dispatch_disable();
executing = _Thread_Executing;
if ( ticks == 0 ) {
_Thread_Yield( executing );
} else {
_Thread_Set_state( executing, STATES_DELAYING );
+ _Thread_Wait_flags_set( executing, THREAD_WAIT_STATE_BLOCKED );
_Watchdog_Initialize(
&executing->Timer,
- _Thread_Delay_ended,
+ _Thread_Timeout,
0,
executing
);
_Watchdog_Insert_ticks( &executing->Timer, ticks );
}
- _Thread_Enable_dispatch();
+ _Thread_Dispatch_enable( cpu_self );
return RTEMS_SUCCESSFUL;
}
diff --git a/cpukit/rtems/src/taskwakewhen.c b/cpukit/rtems/src/taskwakewhen.c
index a1fc15f047..cf0b303cd3 100644
--- a/cpukit/rtems/src/taskwakewhen.c
+++ b/cpukit/rtems/src/taskwakewhen.c
@@ -30,6 +30,7 @@ rtems_status_code rtems_task_wake_when(
{
Watchdog_Interval seconds;
Thread_Control *executing;
+ Per_CPU_Control *cpu_self;
if ( !_TOD_Is_set() )
return RTEMS_NOT_DEFINED;
@@ -47,12 +48,13 @@ rtems_status_code rtems_task_wake_when(
if ( seconds <= _TOD_Seconds_since_epoch() )
return RTEMS_INVALID_CLOCK;
- _Thread_Disable_dispatch();
+ cpu_self = _Thread_Dispatch_disable();
executing = _Thread_Executing;
_Thread_Set_state( executing, STATES_WAITING_FOR_TIME );
+ _Thread_Wait_flags_set( executing, THREAD_WAIT_STATE_BLOCKED );
_Watchdog_Initialize(
&executing->Timer,
- _Thread_Delay_ended,
+ _Thread_Timeout,
0,
executing
);
@@ -60,6 +62,6 @@ rtems_status_code rtems_task_wake_when(
&executing->Timer,
seconds - _TOD_Seconds_since_epoch()
);
- _Thread_Enable_dispatch();
+ _Thread_Dispatch_enable( cpu_self );
return RTEMS_SUCCESSFUL;
}
diff --git a/cpukit/rtems/src/timercancel.c b/cpukit/rtems/src/timercancel.c
index a8ce1478da..1e737a25bb 100644
--- a/cpukit/rtems/src/timercancel.c
+++ b/cpukit/rtems/src/timercancel.c
@@ -45,8 +45,7 @@ rtems_status_code rtems_timer_cancel(
switch ( location ) {
case OBJECTS_LOCAL:
- if ( !_Timer_Is_dormant_class( the_timer->the_class ) )
- (void) _Watchdog_Remove( &the_timer->Ticker );
+ _Timer_Cancel( the_timer );
_Objects_Put( &the_timer->Object );
return RTEMS_SUCCESSFUL;
diff --git a/cpukit/rtems/src/timercreate.c b/cpukit/rtems/src/timercreate.c
index 0b1c44bdc2..13a01feda9 100644
--- a/cpukit/rtems/src/timercreate.c
+++ b/cpukit/rtems/src/timercreate.c
@@ -21,10 +21,39 @@
#include <rtems/system.h>
#include <rtems/rtems/status.h>
#include <rtems/rtems/support.h>
+#include <rtems/score/assert.h>
#include <rtems/score/thread.h>
#include <rtems/rtems/timerimpl.h>
#include <rtems/score/watchdogimpl.h>
+void _Timer_Cancel( Timer_Control *the_timer )
+{
+ Timer_server_Control *timer_server;
+ ISR_Level level;
+
+ /* The timer class must not change during the cancel operation */
+ _ISR_Disable( level );
+
+ switch ( the_timer->the_class ) {
+ case TIMER_INTERVAL:
+ _Watchdog_Remove_ticks( &the_timer->Ticker );
+ break;
+ case TIMER_TIME_OF_DAY:
+ _Watchdog_Remove_seconds( &the_timer->Ticker );
+ break;
+ case TIMER_INTERVAL_ON_TASK:
+ case TIMER_TIME_OF_DAY_ON_TASK:
+ timer_server = _Timer_server;
+ (*timer_server->cancel)( timer_server, the_timer );
+ break;
+ default:
+ _Assert( the_timer->the_class == TIMER_DORMANT );
+ break;
+ }
+
+ _ISR_Enable( level );
+}
+
rtems_status_code rtems_timer_create(
rtems_name name,
rtems_id *id
diff --git a/cpukit/rtems/src/timerdelete.c b/cpukit/rtems/src/timerdelete.c
index 19232c8096..0849ec5ba6 100644
--- a/cpukit/rtems/src/timerdelete.c
+++ b/cpukit/rtems/src/timerdelete.c
@@ -38,7 +38,7 @@ rtems_status_code rtems_timer_delete(
case OBJECTS_LOCAL:
_Objects_Close( &_Timer_Information, &the_timer->Object );
- (void) _Watchdog_Remove( &the_timer->Ticker );
+ _Timer_Cancel( the_timer );
_Objects_Put( &the_timer->Object );
_Timer_Free( the_timer );
_Objects_Allocator_unlock();
diff --git a/cpukit/rtems/src/timerfireafter.c b/cpukit/rtems/src/timerfireafter.c
index 07862cde8c..84cf46bc37 100644
--- a/cpukit/rtems/src/timerfireafter.c
+++ b/cpukit/rtems/src/timerfireafter.c
@@ -46,7 +46,7 @@ rtems_status_code rtems_timer_fire_after(
switch ( location ) {
case OBJECTS_LOCAL:
- (void) _Watchdog_Remove( &the_timer->Ticker );
+ _Timer_Cancel( the_timer );
_ISR_Disable( level );
diff --git a/cpukit/rtems/src/timerfirewhen.c b/cpukit/rtems/src/timerfirewhen.c
index 6ac7d17433..1acbaf9b8f 100644
--- a/cpukit/rtems/src/timerfirewhen.c
+++ b/cpukit/rtems/src/timerfirewhen.c
@@ -51,7 +51,7 @@ rtems_status_code rtems_timer_fire_when(
switch ( location ) {
case OBJECTS_LOCAL:
- (void) _Watchdog_Remove( &the_timer->Ticker );
+ _Timer_Cancel( the_timer );
the_timer->the_class = TIMER_TIME_OF_DAY;
_Watchdog_Initialize( &the_timer->Ticker, routine, id, user_data );
_Watchdog_Insert_seconds(
diff --git a/cpukit/rtems/src/timerreset.c b/cpukit/rtems/src/timerreset.c
index 49c4925aa3..7ab172ea4f 100644
--- a/cpukit/rtems/src/timerreset.c
+++ b/cpukit/rtems/src/timerreset.c
@@ -67,7 +67,7 @@ rtems_status_code rtems_timer_reset(
return RTEMS_INCORRECT_STATE;
}
#endif
- _Watchdog_Remove( &the_timer->Ticker );
+ (*timer_server->cancel)( timer_server, the_timer );
(*timer_server->schedule_operation)( timer_server, the_timer );
} else {
/*
diff --git a/cpukit/rtems/src/timerserver.c b/cpukit/rtems/src/timerserver.c
index 25191e43d7..047fd0978e 100644
--- a/cpukit/rtems/src/timerserver.c
+++ b/cpukit/rtems/src/timerserver.c
@@ -15,7 +15,7 @@
/* COPYRIGHT (c) 1989-2008.
* On-Line Applications Research Corporation (OAR).
*
- * Copyright (c) 2009 embedded brains GmbH.
+ * Copyright (c) 2009-2015 embedded brains GmbH.
*
* The license and distribution terms for this file may be
* found in the file LICENSE in this distribution or at
@@ -26,188 +26,129 @@
#include "config.h"
#endif
+#include <rtems.h>
#include <rtems/rtems/timerimpl.h>
#include <rtems/rtems/tasksimpl.h>
-#include <rtems/score/isrlevel.h>
-#include <rtems/score/threadimpl.h>
+#include <rtems/score/apimutex.h>
#include <rtems/score/todimpl.h>
static Timer_server_Control _Timer_server_Default;
-static void _Timer_server_Stop_interval_system_watchdog(
- Timer_server_Control *ts
+static void _Timer_server_Cancel_method(
+ Timer_server_Control *ts,
+ Timer_Control *timer
)
{
- _Watchdog_Remove( &ts->Interval_watchdogs.System_watchdog );
+ if ( timer->the_class == TIMER_INTERVAL_ON_TASK ) {
+ _Watchdog_Remove( &ts->Interval_watchdogs.Header, &timer->Ticker );
+ } else if ( timer->the_class == TIMER_TIME_OF_DAY_ON_TASK ) {
+ _Watchdog_Remove( &ts->TOD_watchdogs.Header, &timer->Ticker );
+ }
}
-static void _Timer_server_Reset_interval_system_watchdog(
- Timer_server_Control *ts
-)
+static Watchdog_Interval _Timer_server_Get_ticks( void )
{
- ISR_Level level;
-
- _Timer_server_Stop_interval_system_watchdog( ts );
-
- _ISR_Disable( level );
- if ( !_Watchdog_Is_empty( &ts->Interval_watchdogs.Header ) ) {
- Watchdog_Interval delta_interval =
- _Watchdog_First( &ts->Interval_watchdogs.Header )->delta_interval;
- _ISR_Enable( level );
-
- /*
- * The unit is TICKS here.
- */
- _Watchdog_Insert_ticks(
- &ts->Interval_watchdogs.System_watchdog,
- delta_interval
- );
- } else {
- _ISR_Enable( level );
- }
+ return _Watchdog_Ticks_since_boot;
}
-static void _Timer_server_Stop_tod_system_watchdog(
- Timer_server_Control *ts
-)
+static Watchdog_Interval _Timer_server_Get_seconds( void )
{
- _Watchdog_Remove( &ts->TOD_watchdogs.System_watchdog );
+ return _TOD_Seconds_since_epoch();
}
-static void _Timer_server_Reset_tod_system_watchdog(
- Timer_server_Control *ts
+static void _Timer_server_Update_system_watchdog(
+ Timer_server_Watchdogs *watchdogs,
+ Watchdog_Header *system_header
)
{
- ISR_Level level;
+ ISR_lock_Context lock_context;
- _Timer_server_Stop_tod_system_watchdog( ts );
+ _Watchdog_Acquire( &watchdogs->Header, &lock_context );
- _ISR_Disable( level );
- if ( !_Watchdog_Is_empty( &ts->TOD_watchdogs.Header ) ) {
- Watchdog_Interval delta_interval =
- _Watchdog_First( &ts->TOD_watchdogs.Header )->delta_interval;
- _ISR_Enable( level );
+ if ( watchdogs->system_watchdog_helper == NULL ) {
+ Thread_Control *executing;
+ uint32_t my_generation;
- /*
- * The unit is SECONDS here.
- */
- _Watchdog_Insert_seconds(
- &ts->TOD_watchdogs.System_watchdog,
- delta_interval
- );
- } else {
- _ISR_Enable( level );
- }
-}
+ executing = _Thread_Executing;
+ watchdogs->system_watchdog_helper = executing;
-static void _Timer_server_Insert_timer(
- Timer_server_Control *ts,
- Timer_Control *timer
-)
-{
- if ( timer->the_class == TIMER_INTERVAL_ON_TASK ) {
- _Watchdog_Insert( &ts->Interval_watchdogs.Header, &timer->Ticker );
- } else if ( timer->the_class == TIMER_TIME_OF_DAY_ON_TASK ) {
- _Watchdog_Insert( &ts->TOD_watchdogs.Header, &timer->Ticker );
+ do {
+ my_generation = watchdogs->generation;
+
+ if ( !_Watchdog_Is_empty( &watchdogs->Header ) ) {
+ Watchdog_Control *first;
+ Watchdog_Interval delta;
+
+ first = _Watchdog_First( &watchdogs->Header );
+ delta = first->delta_interval;
+
+ if (
+ watchdogs->System_watchdog.state == WATCHDOG_INACTIVE
+ || delta != watchdogs->system_watchdog_delta
+ ) {
+ watchdogs->system_watchdog_delta = delta;
+ _Watchdog_Release( &watchdogs->Header, &lock_context );
+
+ _Watchdog_Remove( system_header, &watchdogs->System_watchdog );
+ watchdogs->System_watchdog.initial = delta;
+ _Watchdog_Insert( system_header, &watchdogs->System_watchdog );
+
+ _Watchdog_Acquire( &watchdogs->Header, &lock_context );
+ }
+ }
+ } while ( watchdogs->generation != my_generation );
+
+ watchdogs->system_watchdog_helper = NULL;
}
+
+ _Watchdog_Release( &watchdogs->Header, &lock_context );
}
-static void _Timer_server_Insert_timer_and_make_snapshot(
- Timer_server_Control *ts,
- Timer_Control *timer
+static void _Timer_server_Insert_timer(
+ Timer_server_Watchdogs *watchdogs,
+ Timer_Control *timer,
+ Watchdog_Header *system_header,
+ Watchdog_Interval (*get_ticks)( void )
)
{
- Watchdog_Control *first_watchdog;
- Watchdog_Interval delta_interval;
- Watchdog_Interval last_snapshot;
- Watchdog_Interval snapshot;
+ ISR_lock_Context lock_context;
+ Watchdog_Interval now;
Watchdog_Interval delta;
- ISR_Level level;
- /*
- * We have to update the time snapshots here, because otherwise we may have
- * problems with the integer range of the delta values. The time delta DT
- * from the last snapshot to now may be arbitrarily long. The last snapshot
- * is the reference point for the delta chain. Thus if we do not update the
- * reference point we have to add DT to the initial delta of the watchdog
- * being inserted. This could result in an integer overflow.
- */
+ _Watchdog_Acquire( &watchdogs->Header, &lock_context );
- _Thread_Disable_dispatch();
+ now = (*get_ticks)();
+ delta = now - watchdogs->last_snapshot;
+ watchdogs->last_snapshot = now;
+ watchdogs->current_snapshot = now;
- if ( timer->the_class == TIMER_INTERVAL_ON_TASK ) {
- /*
- * We have to advance the last known ticks value of the server and update
- * the watchdog chain accordingly.
- */
- _ISR_Disable( level );
- snapshot = _Watchdog_Ticks_since_boot;
- last_snapshot = ts->Interval_watchdogs.last_snapshot;
- if ( !_Watchdog_Is_empty( &ts->Interval_watchdogs.Header ) ) {
- first_watchdog = _Watchdog_First( &ts->Interval_watchdogs.Header );
-
- /*
- * We assume adequate unsigned arithmetic here.
- */
- delta = snapshot - last_snapshot;
-
- delta_interval = first_watchdog->delta_interval;
- if (delta_interval > delta) {
- delta_interval -= delta;
- } else {
- delta_interval = 0;
- }
- first_watchdog->delta_interval = delta_interval;
- }
- ts->Interval_watchdogs.last_snapshot = snapshot;
- _ISR_Enable( level );
+ if ( watchdogs->system_watchdog_delta > delta ) {
+ watchdogs->system_watchdog_delta -= delta;
+ } else {
+ watchdogs->system_watchdog_delta = 0;
+ }
- _Watchdog_Insert( &ts->Interval_watchdogs.Header, &timer->Ticker );
+ if ( !_Watchdog_Is_empty( &watchdogs->Header ) ) {
+ Watchdog_Control *first = _Watchdog_First( &watchdogs->Header );
- if ( !ts->active ) {
- _Timer_server_Reset_interval_system_watchdog( ts );
- }
- } else if ( timer->the_class == TIMER_TIME_OF_DAY_ON_TASK ) {
- /*
- * We have to advance the last known seconds value of the server and update
- * the watchdog chain accordingly.
- */
- _ISR_Disable( level );
- snapshot = (Watchdog_Interval) _TOD_Seconds_since_epoch();
- last_snapshot = ts->TOD_watchdogs.last_snapshot;
- if ( !_Watchdog_Is_empty( &ts->TOD_watchdogs.Header ) ) {
- first_watchdog = _Watchdog_First( &ts->TOD_watchdogs.Header );
- delta_interval = first_watchdog->delta_interval;
- if ( snapshot > last_snapshot ) {
- /*
- * We advanced in time.
- */
- delta = snapshot - last_snapshot;
- if (delta_interval > delta) {
- delta_interval -= delta;
- } else {
- delta_interval = 0;
- }
- } else {
- /*
- * Someone put us in the past.
- */
- delta = last_snapshot - snapshot;
- delta_interval += delta;
- }
- first_watchdog->delta_interval = delta_interval;
+ if ( first->delta_interval > delta ) {
+ first->delta_interval -= delta;
+ } else {
+ first->delta_interval = 0;
}
- ts->TOD_watchdogs.last_snapshot = snapshot;
- _ISR_Enable( level );
+ }
- _Watchdog_Insert( &ts->TOD_watchdogs.Header, &timer->Ticker );
+ _Watchdog_Insert_locked(
+ &watchdogs->Header,
+ &timer->Ticker,
+ &lock_context
+ );
- if ( !ts->active ) {
- _Timer_server_Reset_tod_system_watchdog( ts );
- }
- }
+ ++watchdogs->generation;
+
+ _Watchdog_Release( &watchdogs->Header, &lock_context );
- _Thread_Enable_dispatch();
+ _Timer_server_Update_system_watchdog( watchdogs, system_header );
}
static void _Timer_server_Schedule_operation_method(
@@ -215,143 +156,71 @@ static void _Timer_server_Schedule_operation_method(
Timer_Control *timer
)
{
- if ( ts->insert_chain == NULL ) {
- _Timer_server_Insert_timer_and_make_snapshot( ts, timer );
- } else {
- /*
- * We interrupted a critical section of the timer server. The timer
- * server is not preemptible, so we must be in interrupt context here. No
- * thread dispatch will happen until the timer server finishes its
- * critical section. We have to use the protected chain methods because
- * we may be interrupted by a higher priority interrupt.
- */
- _Chain_Append( ts->insert_chain, &timer->Object.Node );
+ if ( timer->the_class == TIMER_INTERVAL_ON_TASK ) {
+ _Timer_server_Insert_timer(
+ &ts->Interval_watchdogs,
+ timer,
+ &_Watchdog_Ticks_header,
+ _Timer_server_Get_ticks
+ );
+ } else if ( timer->the_class == TIMER_TIME_OF_DAY_ON_TASK ) {
+ _Timer_server_Insert_timer(
+ &ts->TOD_watchdogs,
+ timer,
+ &_Watchdog_Seconds_header,
+ _Timer_server_Get_seconds
+ );
}
}
-static void _Timer_server_Process_interval_watchdogs(
+static void _Timer_server_Update_current_snapshot(
Timer_server_Watchdogs *watchdogs,
- Chain_Control *fire_chain
+ Watchdog_Interval (*get_ticks)( void )
)
{
- Watchdog_Interval snapshot = _Watchdog_Ticks_since_boot;
-
- /*
- * We assume adequate unsigned arithmetic here.
- */
- Watchdog_Interval delta = snapshot - watchdogs->last_snapshot;
-
- watchdogs->last_snapshot = snapshot;
+ ISR_lock_Context lock_context;
- _Watchdog_Adjust_to_chain( &watchdogs->Header, delta, fire_chain );
+ _Watchdog_Acquire( &watchdogs->Header, &lock_context );
+ watchdogs->current_snapshot = (*get_ticks)();
+ watchdogs->system_watchdog_delta = 0;
+ _Watchdog_Release( &watchdogs->Header, &lock_context );
}
-static void _Timer_server_Process_tod_watchdogs(
+static void _Timer_server_Tickle(
Timer_server_Watchdogs *watchdogs,
- Chain_Control *fire_chain
+ Watchdog_Header *system_header,
+ Watchdog_Interval (*get_ticks)( void ),
+ bool ticks
)
{
- Watchdog_Interval snapshot = (Watchdog_Interval) _TOD_Seconds_since_epoch();
- Watchdog_Interval last_snapshot = watchdogs->last_snapshot;
- Watchdog_Interval delta;
-
- /*
- * Process the seconds chain. Start by checking that the Time
- * of Day (TOD) has not been set backwards. If it has then
- * we want to adjust the watchdogs->Header to indicate this.
- */
- if ( snapshot > last_snapshot ) {
- /*
- * This path is for normal forward movement and cases where the
- * TOD has been set forward.
- */
- delta = snapshot - last_snapshot;
- _Watchdog_Adjust_to_chain( &watchdogs->Header, delta, fire_chain );
-
- } else if ( snapshot < last_snapshot ) {
- /*
- * The current TOD is before the last TOD which indicates that
- * TOD has been set backwards.
- */
- delta = last_snapshot - snapshot;
- _Watchdog_Adjust_backward( &watchdogs->Header, delta );
- }
-
- watchdogs->last_snapshot = snapshot;
-}
-
-static void _Timer_server_Process_insertions( Timer_server_Control *ts )
-{
- while ( true ) {
- Timer_Control *timer = (Timer_Control *) _Chain_Get( ts->insert_chain );
-
- if ( timer == NULL ) {
- break;
- }
+ ISR_lock_Context lock_context;
+ Watchdog_Interval now;
+ Watchdog_Interval last;
- _Timer_server_Insert_timer( ts, timer );
- }
-}
-
-static void _Timer_server_Get_watchdogs_that_fire_now(
- Timer_server_Control *ts,
- Chain_Control *insert_chain,
- Chain_Control *fire_chain
-)
-{
- /*
- * Afterwards all timer inserts are directed to this chain and the interval
- * and TOD chains will be no more modified by other parties.
- */
- ts->insert_chain = insert_chain;
+ _Watchdog_Acquire( &watchdogs->Header, &lock_context );
- while ( true ) {
- ISR_Level level;
+ now = watchdogs->current_snapshot;
+ last = watchdogs->last_snapshot;
+ watchdogs->last_snapshot = now;
- /*
- * Remove all the watchdogs that need to fire so we can invoke them.
- */
- _Timer_server_Process_interval_watchdogs(
- &ts->Interval_watchdogs,
- fire_chain
+ if ( ticks || now >= last ) {
+ _Watchdog_Adjust_forward_locked(
+ &watchdogs->Header,
+ now - last,
+ &lock_context
+ );
+ } else {
+ _Watchdog_Adjust_backward_locked(
+ &watchdogs->Header,
+ last - now
);
- _Timer_server_Process_tod_watchdogs( &ts->TOD_watchdogs, fire_chain );
-
- /*
- * The insertions have to take place here, because they reference the
- * current time. The previous process methods take a snapshot of the
- * current time. In case someone inserts a watchdog with an initial value
- * of zero it will be processed in the next iteration of the timer server
- * body loop.
- */
- _Timer_server_Process_insertions( ts );
-
- _ISR_Disable( level );
- if ( _Chain_Is_empty( insert_chain ) ) {
- ts->insert_chain = NULL;
- _ISR_Enable( level );
-
- break;
- } else {
- _ISR_Enable( level );
- }
}
-}
-/* FIXME: This locking approach for SMP is improvable! */
+ ++watchdogs->generation;
-static void _Timer_server_SMP_lock_aquire( void )
-{
-#if defined( RTEMS_SMP )
- _Thread_Disable_dispatch();
-#endif
-}
+ _Watchdog_Release( &watchdogs->Header, &lock_context );
-static void _Timer_server_SMP_lock_release( void )
-{
-#if defined( RTEMS_SMP )
- _Thread_Enable_dispatch();
-#endif
+ _Timer_server_Update_system_watchdog( watchdogs, system_header );
}
/**
@@ -368,81 +237,73 @@ static rtems_task _Timer_server_Body(
)
{
Timer_server_Control *ts = (Timer_server_Control *) arg;
- Chain_Control insert_chain;
- Chain_Control fire_chain;
- _Chain_Initialize_empty( &insert_chain );
- _Chain_Initialize_empty( &fire_chain );
+ while ( true ) {
+ rtems_event_set events;
- _Timer_server_SMP_lock_aquire();
+ _Timer_server_Tickle(
+ &ts->Interval_watchdogs,
+ &_Watchdog_Ticks_header,
+ _Timer_server_Get_ticks,
+ true
+ );
- while ( true ) {
- _Timer_server_Get_watchdogs_that_fire_now( ts, &insert_chain, &fire_chain );
-
- if ( !_Chain_Is_empty( &fire_chain ) ) {
- /*
- * Fire the watchdogs.
- */
- while ( true ) {
- Watchdog_Control *watchdog;
- ISR_Level level;
-
- /*
- * It is essential that interrupts are disable here since an interrupt
- * service routine may remove a watchdog from the chain.
- */
- _ISR_Disable( level );
- watchdog = (Watchdog_Control *) _Chain_Get_unprotected( &fire_chain );
- if ( watchdog != NULL ) {
- watchdog->state = WATCHDOG_INACTIVE;
- _ISR_Enable( level );
- } else {
- _ISR_Enable( level );
-
- break;
- }
+ _Timer_server_Tickle(
+ &ts->TOD_watchdogs,
+ &_Watchdog_Seconds_header,
+ _Timer_server_Get_seconds,
+ false
+ );
- _Timer_server_SMP_lock_release();
+ (void) rtems_event_system_receive(
+ RTEMS_EVENT_SYSTEM_TIMER_SERVER,
+ RTEMS_EVENT_ALL | RTEMS_WAIT,
+ RTEMS_NO_TIMEOUT,
+ &events
+ );
+ }
+}
- /*
- * The timer server may block here and wait for resources or time.
- * The system watchdogs are inactive and will remain inactive since
- * the active flag of the timer server is true.
- */
- (*watchdog->routine)( watchdog->id, watchdog->user_data );
+static void _Timer_server_Wakeup(
+ Objects_Id id,
+ void *arg
+)
+{
+ Timer_server_Control *ts = arg;
- _Timer_server_SMP_lock_aquire();
- }
- } else {
- ts->active = false;
+ _Timer_server_Update_current_snapshot(
+ &ts->Interval_watchdogs,
+ _Timer_server_Get_ticks
+ );
- /*
- * Block until there is something to do.
- */
-#if !defined( RTEMS_SMP )
- _Thread_Disable_dispatch();
-#endif
- _Thread_Set_state( ts->thread, STATES_DELAYING );
- _Timer_server_Reset_interval_system_watchdog( ts );
- _Timer_server_Reset_tod_system_watchdog( ts );
-#if !defined( RTEMS_SMP )
- _Thread_Enable_dispatch();
-#endif
+ _Timer_server_Update_current_snapshot(
+ &ts->TOD_watchdogs,
+ _Timer_server_Get_seconds
+ );
- _Timer_server_SMP_lock_release();
- _Timer_server_SMP_lock_aquire();
+ (void) rtems_event_system_send( id, RTEMS_EVENT_SYSTEM_TIMER_SERVER );
+}
- ts->active = true;
+static void _Timer_server_Initialize_watchdogs(
+ Timer_server_Control *ts,
+ rtems_id id,
+ Timer_server_Watchdogs *watchdogs,
+ Watchdog_Interval (*get_ticks)( void )
+)
+{
+ Watchdog_Interval now;
- /*
- * Maybe an interrupt did reset the system timers, so we have to stop
- * them here. Since we are active now, there will be no more resets
- * until we are inactive again.
- */
- _Timer_server_Stop_interval_system_watchdog( ts );
- _Timer_server_Stop_tod_system_watchdog( ts );
- }
- }
+ now = (*get_ticks)();
+ watchdogs->last_snapshot = now;
+ watchdogs->current_snapshot = now;
+
+ _Watchdog_Header_initialize( &watchdogs->Header );
+ _Watchdog_Initialize(
+ &watchdogs->System_watchdog,
+ _Timer_server_Wakeup,
+ id,
+ ts
+ );
}
/**
@@ -486,10 +347,10 @@ rtems_status_code rtems_timer_initiate_server(
/*
* Just to make sure this is only called once.
*/
- _Thread_Disable_dispatch();
+ _Once_Lock();
tmpInitialized = initialized;
initialized = true;
- _Thread_Enable_dispatch();
+ _Once_Unlock();
if ( tmpInitialized )
return RTEMS_INCORRECT_STATE;
@@ -530,50 +391,27 @@ rtems_status_code rtems_timer_initiate_server(
* Timer Server so we do not have to have a critical section.
*/
- /*
- * We work with the TCB pointer, not the ID, so we need to convert
- * to a TCB pointer from here out.
- */
- ts->thread = (Thread_Control *)_Objects_Get_local_object(
- &_RTEMS_tasks_Information,
- _Objects_Get_index(id)
+ _Timer_server_Initialize_watchdogs(
+ ts,
+ id,
+ &ts->Interval_watchdogs,
+ _Timer_server_Get_ticks
);
- /*
- * Initialize the timer lists that the server will manage.
- */
- _Watchdog_Header_initialize( &ts->Interval_watchdogs.Header );
- _Watchdog_Header_initialize( &ts->TOD_watchdogs.Header );
-
- /*
- * Initialize the timers that will be used to control when the
- * Timer Server wakes up and services the task-based timers.
- */
- _Watchdog_Initialize(
- &ts->Interval_watchdogs.System_watchdog,
- _Thread_Delay_ended,
- 0,
- ts->thread
- );
- _Watchdog_Initialize(
- &ts->TOD_watchdogs.System_watchdog,
- _Thread_Delay_ended,
- 0,
- ts->thread
+ _Timer_server_Initialize_watchdogs(
+ ts,
+ id,
+ &ts->TOD_watchdogs,
+ _Timer_server_Get_seconds
);
/*
- * Initialize the pointer to the timer schedule method so applications that
+ * Initialize the pointer to the timer server methods so applications that
* do not use the Timer Server do not have to pull it in.
*/
+ ts->cancel = _Timer_server_Cancel_method;
ts->schedule_operation = _Timer_server_Schedule_operation_method;
- ts->Interval_watchdogs.last_snapshot = _Watchdog_Ticks_since_boot;
- ts->TOD_watchdogs.last_snapshot = (Watchdog_Interval) _TOD_Seconds_since_epoch();
-
- ts->insert_chain = NULL;
- ts->active = false;
-
/*
* The default timer server is now available.
*/
diff --git a/cpukit/rtems/src/timerserverfireafter.c b/cpukit/rtems/src/timerserverfireafter.c
index 125664510f..0636782ae0 100644
--- a/cpukit/rtems/src/timerserverfireafter.c
+++ b/cpukit/rtems/src/timerserverfireafter.c
@@ -50,7 +50,7 @@ rtems_status_code rtems_timer_server_fire_after(
switch ( location ) {
case OBJECTS_LOCAL:
- (void) _Watchdog_Remove( &the_timer->Ticker );
+ _Timer_Cancel( the_timer );
_ISR_Disable( level );
diff --git a/cpukit/rtems/src/timerserverfirewhen.c b/cpukit/rtems/src/timerserverfirewhen.c
index 32695fb0e6..0069af1c3b 100644
--- a/cpukit/rtems/src/timerserverfirewhen.c
+++ b/cpukit/rtems/src/timerserverfirewhen.c
@@ -72,7 +72,7 @@ rtems_status_code rtems_timer_server_fire_when(
switch ( location ) {
case OBJECTS_LOCAL:
- (void) _Watchdog_Remove( &the_timer->Ticker );
+ _Timer_Cancel( the_timer );
the_timer->the_class = TIMER_TIME_OF_DAY_ON_TASK;
_Watchdog_Initialize( &the_timer->Ticker, routine, id, user_data );
the_timer->Ticker.initial = seconds - _TOD_Seconds_since_epoch();