1/* 2 * Copyright (c) 1995 John Birrell <jb@cimlogic.com.au>. 3 * All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions 7 * are met: 8 * 1. Redistributions of source code must retain the above copyright 9 * notice, this list of conditions and the following disclaimer. 10 * 2. Redistributions in binary form must reproduce the above copyright 11 * notice, this list of conditions and the following disclaimer in the 12 * documentation and/or other materials provided with the distribution. 13 * 3. All advertising materials mentioning features or use of this software 14 * must display the following acknowledgement: 15 * This product includes software developed by John Birrell. 16 * 4. Neither the name of the author nor the names of any co-contributors 17 * may be used to endorse or promote products derived from this software 18 * without specific prior written permission. 19 * 20 * THIS SOFTWARE IS PROVIDED BY JOHN BIRRELL AND CONTRIBUTORS ``AS IS'' AND 21 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 22 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 23 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 24 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 25 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 26 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 27 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 28 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 29 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 30 * SUCH DAMAGE. 31 *
| 1/* 2 * Copyright (c) 1995 John Birrell <jb@cimlogic.com.au>. 3 * All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions 7 * are met: 8 * 1. Redistributions of source code must retain the above copyright 9 * notice, this list of conditions and the following disclaimer. 10 * 2. Redistributions in binary form must reproduce the above copyright 11 * notice, this list of conditions and the following disclaimer in the 12 * documentation and/or other materials provided with the distribution. 13 * 3. All advertising materials mentioning features or use of this software 14 * must display the following acknowledgement: 15 * This product includes software developed by John Birrell. 16 * 4. Neither the name of the author nor the names of any co-contributors 17 * may be used to endorse or promote products derived from this software 18 * without specific prior written permission. 19 * 20 * THIS SOFTWARE IS PROVIDED BY JOHN BIRRELL AND CONTRIBUTORS ``AS IS'' AND 21 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 22 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 23 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 24 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 25 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 26 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 27 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 28 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 29 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 30 * SUCH DAMAGE. 31 *
|
43{ 44 int ret = 0; 45 struct timespec current_time; 46 struct timespec current_time1; 47 struct timespec remaining_time; 48 struct timeval tv; 49 50 _thread_enter_cancellation_point(); 51 /* Check if the time to sleep is legal: */ 52 if (time_to_sleep == NULL || time_to_sleep->tv_sec < 0 || 53 time_to_sleep->tv_nsec < 0 || time_to_sleep->tv_nsec >= 1000000000) { 54 /* Return an EINVAL error : */ 55 errno = EINVAL; 56 ret = -1; 57 } else { 58 /* Get the current time: */ 59 gettimeofday(&tv, NULL); 60 TIMEVAL_TO_TIMESPEC(&tv, ¤t_time); 61 62 /* Calculate the time for the current thread to wake up: */ 63 _thread_run->wakeup_time.tv_sec = current_time.tv_sec + time_to_sleep->tv_sec; 64 _thread_run->wakeup_time.tv_nsec = current_time.tv_nsec + time_to_sleep->tv_nsec; 65 66 /* Check if the nanosecond field has overflowed: */ 67 if (_thread_run->wakeup_time.tv_nsec >= 1000000000) { 68 /* Wrap the nanosecond field: */ 69 _thread_run->wakeup_time.tv_sec += 1; 70 _thread_run->wakeup_time.tv_nsec -= 1000000000; 71 } 72 _thread_run->interrupted = 0; 73 74 /* Reschedule the current thread to sleep: */ 75 _thread_kern_sched_state(PS_SLEEP_WAIT, __FILE__, __LINE__); 76 77 /* Get the current time: */ 78 gettimeofday(&tv, NULL); 79 TIMEVAL_TO_TIMESPEC(&tv, ¤t_time1); 80 81 /* Calculate the remaining time to sleep: */ 82 remaining_time.tv_sec = time_to_sleep->tv_sec + current_time.tv_sec - current_time1.tv_sec; 83 remaining_time.tv_nsec = time_to_sleep->tv_nsec + current_time.tv_nsec - current_time1.tv_nsec; 84 85 /* Check if the nanosecond field has underflowed: */ 86 if (remaining_time.tv_nsec < 0) { 87 /* Handle the underflow: */ 88 remaining_time.tv_sec -= 1; 89 remaining_time.tv_nsec += 1000000000; 90 } 91 92 /* Check if the nanosecond field has overflowed: */ 93 if (remaining_time.tv_nsec >= 1000000000) { 94 /* Handle the overflow: */ 95 remaining_time.tv_sec += 1; 96 remaining_time.tv_nsec -= 1000000000; 97 } 98 99 /* Check if the sleep was longer than the required time: */ 100 if (remaining_time.tv_sec < 0) { 101 /* Reset the time left: */ 102 remaining_time.tv_sec = 0; 103 remaining_time.tv_nsec = 0; 104 } 105 106 /* Check if the time remaining is to be returned: */ 107 if (time_remaining != NULL) { 108 /* Return the actual time slept: */ 109 time_remaining->tv_sec = remaining_time.tv_sec; 110 time_remaining->tv_nsec = remaining_time.tv_nsec; 111 } 112 113 /* Check if the sleep was interrupted: */ 114 if (_thread_run->interrupted) { 115 /* Return an EINTR error : */ 116 errno = EINTR; 117 ret = -1; 118 } 119 } 120 _thread_leave_cancellation_point(); 121 return (ret); 122}
| 43{ 44 int ret = 0; 45 struct timespec current_time; 46 struct timespec current_time1; 47 struct timespec remaining_time; 48 struct timeval tv; 49 50 _thread_enter_cancellation_point(); 51 /* Check if the time to sleep is legal: */ 52 if (time_to_sleep == NULL || time_to_sleep->tv_sec < 0 || 53 time_to_sleep->tv_nsec < 0 || time_to_sleep->tv_nsec >= 1000000000) { 54 /* Return an EINVAL error : */ 55 errno = EINVAL; 56 ret = -1; 57 } else { 58 /* Get the current time: */ 59 gettimeofday(&tv, NULL); 60 TIMEVAL_TO_TIMESPEC(&tv, ¤t_time); 61 62 /* Calculate the time for the current thread to wake up: */ 63 _thread_run->wakeup_time.tv_sec = current_time.tv_sec + time_to_sleep->tv_sec; 64 _thread_run->wakeup_time.tv_nsec = current_time.tv_nsec + time_to_sleep->tv_nsec; 65 66 /* Check if the nanosecond field has overflowed: */ 67 if (_thread_run->wakeup_time.tv_nsec >= 1000000000) { 68 /* Wrap the nanosecond field: */ 69 _thread_run->wakeup_time.tv_sec += 1; 70 _thread_run->wakeup_time.tv_nsec -= 1000000000; 71 } 72 _thread_run->interrupted = 0; 73 74 /* Reschedule the current thread to sleep: */ 75 _thread_kern_sched_state(PS_SLEEP_WAIT, __FILE__, __LINE__); 76 77 /* Get the current time: */ 78 gettimeofday(&tv, NULL); 79 TIMEVAL_TO_TIMESPEC(&tv, ¤t_time1); 80 81 /* Calculate the remaining time to sleep: */ 82 remaining_time.tv_sec = time_to_sleep->tv_sec + current_time.tv_sec - current_time1.tv_sec; 83 remaining_time.tv_nsec = time_to_sleep->tv_nsec + current_time.tv_nsec - current_time1.tv_nsec; 84 85 /* Check if the nanosecond field has underflowed: */ 86 if (remaining_time.tv_nsec < 0) { 87 /* Handle the underflow: */ 88 remaining_time.tv_sec -= 1; 89 remaining_time.tv_nsec += 1000000000; 90 } 91 92 /* Check if the nanosecond field has overflowed: */ 93 if (remaining_time.tv_nsec >= 1000000000) { 94 /* Handle the overflow: */ 95 remaining_time.tv_sec += 1; 96 remaining_time.tv_nsec -= 1000000000; 97 } 98 99 /* Check if the sleep was longer than the required time: */ 100 if (remaining_time.tv_sec < 0) { 101 /* Reset the time left: */ 102 remaining_time.tv_sec = 0; 103 remaining_time.tv_nsec = 0; 104 } 105 106 /* Check if the time remaining is to be returned: */ 107 if (time_remaining != NULL) { 108 /* Return the actual time slept: */ 109 time_remaining->tv_sec = remaining_time.tv_sec; 110 time_remaining->tv_nsec = remaining_time.tv_nsec; 111 } 112 113 /* Check if the sleep was interrupted: */ 114 if (_thread_run->interrupted) { 115 /* Return an EINTR error : */ 116 errno = EINTR; 117 ret = -1; 118 } 119 } 120 _thread_leave_cancellation_point(); 121 return (ret); 122}
|