1/* ufuncs - sleep and alarm functions that understand fractional values */ 2 3/* Copyright (C) 2008,2009 Free Software Foundation, Inc. 4 5 This file is part of GNU Bash, the Bourne Again SHell. 6 7 Bash is free software: you can redistribute it and/or modify 8 it under the terms of the GNU General Public License as published by 9 the Free Software Foundation, either version 3 of the License, or 10 (at your option) any later version. 11 12 Bash is distributed in the hope that it will be useful, 13 but WITHOUT ANY WARRANTY; without even the implied warranty of 14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 15 GNU General Public License for more details. 16 17 You should have received a copy of the GNU General Public License 18 along with Bash. If not, see <http://www.gnu.org/licenses/>. 19*/ 20 21#include "config.h" 22 23#include "bashtypes.h" 24 25#if defined (TIME_WITH_SYS_TIME) 26# include <sys/time.h> 27# include <time.h> 28#else 29# if defined (HAVE_SYS_TIME_H) 30# include <sys/time.h> 31# else 32# include <time.h> 33# endif 34#endif 35 36#if defined (HAVE_UNISTD_H) 37#include <unistd.h> 38#endif 39 40/* A version of `alarm' using setitimer if it's available. */ 41 42#if defined (HAVE_SETITIMER) 43unsigned int 44falarm(secs, usecs) 45 unsigned int secs, usecs; 46{ 47 struct itimerval it, oit; 48 49 it.it_interval.tv_sec = 0; 50 it.it_interval.tv_usec = 0; 51 52 it.it_value.tv_sec = secs; 53 it.it_value.tv_usec = usecs; 54 55 if (setitimer(ITIMER_REAL, &it, &oit) < 0) 56 return (-1); /* XXX will be converted to unsigned */ 57 58 /* Backwards compatibility with alarm(3) */ 59 if (oit.it_value.tv_usec) 60 oit.it_value.tv_sec++; 61 return (oit.it_value.tv_sec); 62} 63#else 64int 65falarm (secs, usecs) 66 unsigned int secs, usecs; 67{ 68 if (secs == 0 && usecs == 0) 69 return (alarm (0)); 70 71 if (secs == 0 || usecs >= 500000) 72 { 73 secs++; 74 usecs = 0; 75 } 76 return (alarm (secs)); 77} 78#endif /* !HAVE_SETITIMER */ 79 80/* A version of sleep using fractional seconds and select. I'd like to use 81 `usleep', but it's already taken */ 82 83#if defined (HAVE_TIMEVAL) && defined (HAVE_SELECT) 84int 85fsleep(sec, usec) 86 unsigned int sec, usec; 87{ 88 struct timeval tv; 89 90 tv.tv_sec = sec; 91 tv.tv_usec = usec; 92 93 return select(0, (fd_set *)0, (fd_set *)0, (fd_set *)0, &tv); 94} 95#else /* !HAVE_TIMEVAL || !HAVE_SELECT */ 96int 97fsleep(sec, usec) 98 long sec, usec; 99{ 100 if (usec >= 500000) /* round */ 101 sec++; 102 return (sleep(sec)); 103} 104#endif /* !HAVE_TIMEVAL || !HAVE_SELECT */ 105