66 lines
2.4 KiB
C
66 lines
2.4 KiB
C
/*
|
|
* clock_nanosleep.c - clock_nanosleep() replacement
|
|
*/
|
|
|
|
/***********************************************************************
|
|
* Copyright © 2006 Rémi Denis-Courmont. *
|
|
* This program is free software; you can redistribute and/or modify *
|
|
* it under the terms of the GNU General Public License as published *
|
|
* by the Free Software Foundation; version 2 of the license, or (at *
|
|
* your option) any later version. *
|
|
* *
|
|
* This program is distributed in the hope that it will be useful, *
|
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
|
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. *
|
|
* See the GNU General Public License for more details. *
|
|
* *
|
|
* You should have received a copy of the GNU General Public License *
|
|
* along with this program; if not, you can get it from: *
|
|
* http://www.gnu.org/copyleft/gpl.html *
|
|
***********************************************************************/
|
|
|
|
#include <errno.h> // for errno, EINVAL
|
|
#include <time.h> // for nanosleep, NULL
|
|
|
|
#include "clock_nanosleep.h"
|
|
#ifdef MISSING_GETTIME
|
|
#include "../clock_gettime/clock_gettime.h" // for clock_gettime
|
|
#endif
|
|
|
|
int clock_nanosleep(clockid_t id, int flags, const struct timespec *ts,
|
|
struct timespec *ots) {
|
|
int ret;
|
|
|
|
if (id != CLOCK_REALTIME)
|
|
return EINVAL;
|
|
|
|
if (flags & TIMER_ABSTIME) {
|
|
struct timespec mine;
|
|
|
|
if (clock_gettime(id, &mine))
|
|
return errno;
|
|
|
|
if (mine.tv_sec > ts->tv_sec)
|
|
return 0; // behind schedule
|
|
|
|
if (mine.tv_nsec > ts->tv_nsec) {
|
|
if (mine.tv_sec == ts->tv_sec)
|
|
return 0; // behind schedule too
|
|
|
|
mine.tv_nsec = 1000000000 + ts->tv_nsec - mine.tv_nsec;
|
|
mine.tv_sec++;
|
|
}
|
|
else
|
|
mine.tv_nsec = ts->tv_nsec - mine.tv_nsec;
|
|
|
|
mine.tv_sec = ts->tv_sec - mine.tv_sec;
|
|
|
|
/* With TIMER_ABSTIME, clock_nanosleep ignores <ots> */
|
|
ret = nanosleep(&mine, NULL);
|
|
}
|
|
else
|
|
ret = nanosleep(ts, ots);
|
|
|
|
return ret ? errno : 0;
|
|
}
|