File indexing completed on 2025-05-11 08:24:27
0001
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013
0014
0015
0016
0017
0018
0019
0020
0021
0022
0023
0024
0025
0026
0027
0028
0029
0030
0031
0032
0033
0034
0035
0036
0037
0038
0039 #ifdef HAVE_CONFIG_H
0040 #include "config.h"
0041 #endif
0042
0043 #include <rtems/score/threadqimpl.h>
0044 #include <rtems/score/threadimpl.h>
0045 #include <rtems/score/watchdogimpl.h>
0046
0047 void _Thread_queue_Add_timeout_ticks(
0048 Thread_queue_Queue *queue,
0049 Thread_Control *the_thread,
0050 Per_CPU_Control *cpu_self,
0051 Thread_queue_Context *queue_context
0052 )
0053 {
0054 Watchdog_Interval ticks;
0055
0056 (void) queue;
0057 ticks = queue_context->Timeout.ticks;
0058
0059 if ( ticks != WATCHDOG_NO_TIMEOUT ) {
0060 _Thread_Add_timeout_ticks(
0061 the_thread,
0062 cpu_self,
0063 queue_context->Timeout.ticks
0064 );
0065 }
0066 }
0067
0068 static void _Thread_queue_Add_timeout_timespec(
0069 Thread_queue_Queue *queue,
0070 Thread_Control *the_thread,
0071 Per_CPU_Control *cpu_self,
0072 Thread_queue_Context *queue_context,
0073 Watchdog_Header *header,
0074 const struct timespec *now
0075 )
0076 {
0077 const struct timespec *abstime;
0078 struct timespec base;
0079
0080 if ( queue_context->timeout_absolute ) {
0081 abstime = queue_context->Timeout.arg;
0082 } else {
0083 base = *now;
0084 abstime = _Watchdog_Future_timespec( &base, queue_context->Timeout.arg );
0085 }
0086
0087 if ( _Watchdog_Is_valid_timespec( abstime ) ) {
0088 uint64_t expire;
0089
0090 if ( abstime->tv_sec < 0 ) {
0091 expire = 0;
0092 } else if ( _Watchdog_Is_far_future_timespec( abstime ) ) {
0093 expire = WATCHDOG_MAXIMUM_TICKS;
0094 } else {
0095 expire = _Watchdog_Ticks_from_timespec( abstime );
0096 }
0097
0098 if ( expire > _Watchdog_Ticks_from_timespec( now ) ) {
0099 ISR_lock_Context lock_context;
0100
0101 _ISR_lock_ISR_disable_and_acquire(
0102 &the_thread->Timer.Lock,
0103 &lock_context
0104 );
0105
0106 the_thread->Timer.header = header;
0107 the_thread->Timer.Watchdog.routine = _Thread_Timeout;
0108 _Watchdog_Per_CPU_insert(
0109 &the_thread->Timer.Watchdog,
0110 cpu_self,
0111 header,
0112 expire
0113 );
0114
0115 _ISR_lock_Release_and_ISR_enable(
0116 &the_thread->Timer.Lock,
0117 &lock_context
0118 );
0119 } else {
0120 _Thread_Continue( the_thread, STATUS_TIMEOUT );
0121 }
0122 } else {
0123 _Thread_Continue( the_thread, STATUS_INVALID_NUMBER );
0124 }
0125 }
0126
0127 void _Thread_queue_Add_timeout_monotonic_timespec(
0128 Thread_queue_Queue *queue,
0129 Thread_Control *the_thread,
0130 Per_CPU_Control *cpu_self,
0131 Thread_queue_Context *queue_context
0132 )
0133 {
0134 struct timespec now;
0135
0136 _Timecounter_Nanouptime( &now );
0137 _Thread_queue_Add_timeout_timespec(
0138 queue,
0139 the_thread,
0140 cpu_self,
0141 queue_context,
0142 &cpu_self->Watchdog.Header[ PER_CPU_WATCHDOG_MONOTONIC ],
0143 &now
0144 );
0145 }
0146
0147 void _Thread_queue_Add_timeout_realtime_timespec(
0148 Thread_queue_Queue *queue,
0149 Thread_Control *the_thread,
0150 Per_CPU_Control *cpu_self,
0151 Thread_queue_Context *queue_context
0152 )
0153 {
0154 struct timespec now;
0155
0156 _Timecounter_Nanotime( &now );
0157 _Thread_queue_Add_timeout_timespec(
0158 queue,
0159 the_thread,
0160 cpu_self,
0161 queue_context,
0162 &cpu_self->Watchdog.Header[ PER_CPU_WATCHDOG_REALTIME ],
0163 &now
0164 );
0165 }