Exemple #1
0
static void
stop_adjust(void)
{
  struct timeval T1;
  struct timeval zeroadj, remadj;
  double adjustment_remaining, adjustment_achieved;
  double elapsed, elapsed_plus_adjust;

  zeroadj.tv_sec = 0;
  zeroadj.tv_usec = 0;

  if (adjtime(&zeroadj, &remadj) < 0) {
    LOG_FATAL(LOGF_SysNetBSD, "adjtime() failed");
  }

  if (gettimeofday(&T1, NULL) < 0) {
    LOG_FATAL(LOGF_SysNetBSD, "gettimeofday() failed");
  }
  
  UTI_DiffTimevalsToDouble(&elapsed, &T1, &T0);
  UTI_TimevalToDouble(&remadj, &adjustment_remaining);

  adjustment_achieved = adjustment_requested - adjustment_remaining;
  elapsed_plus_adjust = elapsed - adjustment_achieved;

  offset_register += current_freq * elapsed_plus_adjust - adjustment_remaining;

  adjustment_requested = 0.0;
  T0 = T1;

}
Exemple #2
0
static Boolean
setFrequency (ClockDriver *self, double adj, double tau) {

    if (self->config.readOnly){
		DBGV("adjFreq2: noAdjust on, returning\n");
		return FALSE;
	}

	self->_tau = tau;

/*
 * adjFreq simulation for QNX: correct clock by x ns per tick over clock adjust interval,
 * to make it equal adj ns per second. Makes sense only if intervals are regular.
 */

#ifdef __QNXNTO__

      struct _clockadjust clockadj;
      struct _clockperiod period;
      if (ClockPeriod (CLOCK_REALTIME, 0, &period, 0) < 0)
          return FALSE;

	adj = clampDouble(adj, self->maxFrequency);

	/* adjust clock for the duration of 0.9 clock update period in ticks (so we're done before the next) */
	clockadj.tick_count = 0.9 * tau * 1E9 / (period.nsec + 0.0);

	/* scale adjustment per second to adjustment per single tick */
	clockadj.tick_nsec_inc = (adj * tau / clockadj.tick_count) / 0.9;

	DBGV("QNX: adj: %.09f, dt: %.09f, ticks per dt: %d, inc per tick %d\n",
		adj, tau, clockadj.tick_count, clockadj.tick_nsec_inc);

	if (ClockAdjust(CLOCK_REALTIME, &clockadj, NULL) < 0) {
	    DBGV("QNX: failed to call ClockAdjust: %s\n", strERROR(THIS_COMPONENTerrno));
	}
/* regular adjFreq */
#elif defined(HAVE_SYS_TIMEX_H)
	DBG2("     adjFreq2: call adjfreq to %.09f us \n", adj / DBG_UNIT);
	adjFreq_unix(self, adj);
/* otherwise use adjtime */
#else
	struct timeval tv;

	adj = clampDouble(adj, self->maxFrequency);

	tv.tv_sec = 0;
	tv.tv_usec = (adj / 1000);
	if((tau > 0) && (tau < 1.0)) {
	    tv.tv_usec *= tau;
	}
	adjtime(&tv, NULL);
#endif

    self->lastFrequency = adj;

    return TRUE;
}
Exemple #3
0
void GnssDevice::slotSetSystemTime(const qint32& tow)
{
    // The Host uses UTC time, but currentTow() applies the leap-second offset (currently 16s).
    const qint32 currentHostTow = GnssTime::currentTow();

    // First, what time is it now?
    struct timeval system;
    gettimeofday(&system, NULL);

    // SecondsPerWeek - CurrentSecondInWeek is number of seconds till rollover
    const quint32 secondsToRollOver = (7 * 86400) - (tow / 1000);

    const qint32 offsetHostToGnss = tow - currentHostTow + 7; // Oscilloscope indicates 7ms offset is a good value.
    qDebug() << "GnssDevice::slotSetSystemTime(): time rollover in" << ((float)secondsToRollOver)/86400.0f << "d, offset host time" << currentHostTow << "to gnss time" << tow << "is" << offsetHostToGnss/1000 << "s and" << (offsetHostToGnss%1000) << "ms";

    // For small clock drifts, adjust clock. Else, set clock
    if(abs(offsetHostToGnss) < 10)
    {
        qDebug() << __PRETTY_FUNCTION__ << "unix-time now is" << QDateTime::currentMSecsSinceEpoch() / 1000 << "- offset smaller than 10ms, using adjtime to correct clock drift...";
        system.tv_sec = 0;
        system.tv_usec = offsetHostToGnss * 1000;
        if(adjtime(&system, NULL) < 0)
        {
            qDebug() << __PRETTY_FUNCTION__ << "adjtime failed, tried to set to" << system.tv_sec << "s and" << system.tv_usec << "usecs";
            if(errno == EINVAL) qFatal("couldn't adjust system time, values invalid.");
            else if(errno == EPERM) qFatal("couldn't adjust system time, insufficient permissions.");
            else qFatal("couldn't adjust system time, no idea why, error %d.", errno);
        }
    }
    else
    {
        qDebug() << "GnssDevice::slotSetSystemTime(): unix-time now is" << QDateTime::currentMSecsSinceEpoch() / 1000 << "- offset larger than 10ms, using settimeofday to set clock...";
        system.tv_sec += offsetHostToGnss/1000;
        system.tv_usec += (offsetHostToGnss%1000)*1000;

        // usec can under/overflow; fix it
        if(system.tv_usec > 1000000)
        {
            qDebug() << __PRETTY_FUNCTION__ << "system.tv" << system.tv_sec << "system.tv_usec > 1000000:" << system.tv_usec << "subtracting 1000000";
            system.tv_usec -= 1000000;
            system.tv_sec += 1;
            qDebug() << __PRETTY_FUNCTION__ << "system.tv" << system.tv_sec << "system.tv_usec" << system.tv_usec;
        }

        if(settimeofday(&system, NULL) < 0)
        {
            qDebug() << __PRETTY_FUNCTION__ << "settimeofday failed, tried to set to" << system.tv_sec << "s and" << system.tv_usec << "usecs";
            if(errno == EFAULT) qFatal("couldn't set system time, values outside of range.");
            else if(errno == EINVAL) qFatal("couldn't set system time, values invalid.");
            else if(errno == EPERM) qFatal("couldn't set system time, insufficient permissions.");
            else qFatal("couldn't set system time, no idea why, error %d.", errno);
        }
    }

    qDebug() << __PRETTY_FUNCTION__ << "time synchronized, offset host to gnss was" << offsetHostToGnss << "ms, unix-time now is" << QDateTime::currentMSecsSinceEpoch() / 1000;
    emit systemTimeSynchronized();
}
Exemple #4
0
 bool performGradualAdjustment(const uavcan::UtcDuration adjustment)
 {
     gradual_adj_cnt_++;
     const std::int64_t usec = adjustment.toUSec();
     timeval tv;
     tv.tv_sec  = usec / Int1e6;
     tv.tv_usec = usec % Int1e6;
     return adjtime(&tv, nullptr) == 0;
 }
Exemple #5
0
void
reset_adjtime(void)
{
	struct timeval	tv;

	timerclear(&tv);
	if (adjtime(&tv, NULL) == -1)
		log_warn("reset adjtime failed");
}
Exemple #6
0
static void
start_adjust(void)
{
  struct timeval newadj, oldadj;
  struct timeval T1;
  double elapsed, accrued_error;
  double adjust_required;
  struct timeval exact_newadj;
  long delta, tickdelta;
  double rounding_error;
  double old_adjust_remaining;

  /* Determine the amount of error built up since the last adjustment */
  if (gettimeofday(&T1, NULL) < 0) {
    LOG_FATAL(LOGF_SysNetBSD, "gettimeofday() failed");
  }

  UTI_DiffTimevalsToDouble(&elapsed, &T1, &T0);
  accrued_error = elapsed * current_freq;
  
  adjust_required = - (accrued_error + offset_register);

  UTI_DoubleToTimeval(adjust_required, &exact_newadj);

  /* At this point, we need to round the required adjustment the
     same way the kernel does. */

  delta = exact_newadj.tv_sec * 1000000 + exact_newadj.tv_usec;
  if (delta > kern_bigadj || delta < -kern_bigadj)
    tickdelta = 10 * kern_tickadj;
  else
    tickdelta = kern_tickadj;
  if (delta % tickdelta)
	delta = delta / tickdelta * tickdelta;
  newadj.tv_sec = 0;
  newadj.tv_usec = delta;
  UTI_NormaliseTimeval(&newadj);

  /* Add rounding error back onto offset register. */
  UTI_DiffTimevalsToDouble(&rounding_error, &newadj, &exact_newadj);

  if (adjtime(&newadj, &oldadj) < 0) {
    LOG_FATAL(LOGF_SysNetBSD, "adjtime() failed");
  }

  UTI_TimevalToDouble(&oldadj, &old_adjust_remaining);

  offset_register = rounding_error - old_adjust_remaining;

  T0 = T1;
  UTI_TimevalToDouble(&newadj, &adjustment_requested);

}
Exemple #7
0
int
priv_adjtime_setup(int asroot, int injail, struct test *test)
{

    if (initialized)
        return (0);
    if (adjtime(NULL, &query_tv) < 0) {
        warn("priv_adjtime_setup: adjtime(NULL)");
        return (-1);
    }
    initialized = 1;
    return (0);
}
Exemple #8
0
/*
 * step_systime - step the system clock.
 */
int step_systime(double now)
{
	struct timeval timetv, adjtv, oldtimetv;
	int isneg = 0;
	double dtemp;

	dtemp = now;
	if (dtemp < 0) {
		isneg = 1;
		dtemp = - dtemp;
		adjtv.tv_sec = (int32_t)dtemp;
		adjtv.tv_usec = (uint32_t)((dtemp -
		    (double)adjtv.tv_sec) * 1e6 + .5);
	} else {
		adjtv.tv_sec = (int32_t)dtemp;
		adjtv.tv_usec = (uint32_t)((dtemp -
		    (double)adjtv.tv_sec) * 1e6 + .5);
	}
    gettimeofday(&timetv, NULL);
	oldtimetv = timetv;

	if (isneg) {
		timetv.tv_sec -= adjtv.tv_sec;
		timetv.tv_usec -= adjtv.tv_usec;
		if (timetv.tv_usec < 0) {
			timetv.tv_sec--;
			timetv.tv_usec += 1000000;
		}
	} else {
		timetv.tv_sec += adjtv.tv_sec;
		timetv.tv_usec += adjtv.tv_usec;
		if (timetv.tv_usec >= 1000000) {
			timetv.tv_sec++;
			timetv.tv_usec -= 1000000;
		}
	}

	/*
	 * Some broken systems don't reset adjtime() when the
	 * clock is stepped.
	 */
	adjtv.tv_sec = adjtv.tv_usec = 0;
	adjtime(&adjtv, NULL);

	if (settimeofday(&timetv, NULL) < 0) {
		//msyslog(LOG_ERR, "step-systime: failed to set system time");
		return (0);
	}
	return (1);
}
Exemple #9
0
void
priv_adjtime_set(int asroot, int injail, struct test *test)
{
    int error;

    error = adjtime(&query_tv, NULL);
    if (asroot && injail)
        expect("priv_adjtime(asroot, injail)", error, -1, EPERM);
    if (asroot && !injail)
        expect("priv_adjtime(asroot, !injail)", error, 0, 0);
    if (!asroot && injail)
        expect("priv_adjtime(!asroot, injail)", error, -1, EPERM);
    if (!asroot && !injail)
        expect("priv_adjtime(!asroot, !injail)", error, -1, EPERM);
}
Exemple #10
0
int
timeout(
    int sig,
    int code,
    struct sigcontext *scp
)
{
    signal (SIGALRM, timeout);
    if (adjtime(&adjustment, &result))
        printf("adjtime call failed\n");
    if (result.tv_sec != 0 || result.tv_usec != 0) {
        printf("result.u = %d.%06.6d  ", (int) result.tv_sec,
               (int) result.tv_usec);
    }
}
Exemple #11
0
int				/* 0 okay, 1 error */
adj_systime(
	double now		/* adjustment (s) */
	)
{
	struct timeval adjtv;	/* new adjustment */
	struct timeval oadjtv;	/* residual adjustment */
	double	dtemp;
	long	ticks;
	int	isneg = 0;
	
	os_trace("Adjust: %f", now);
	/*
	 * Most Unix adjtime() implementations adjust the system clock
	 * in microsecond quanta, but some adjust in 10-ms quanta. We
	 * carefully round the adjustment to the nearest quantum, then
	 * adjust in quanta and keep the residue for later.
	 */
	dtemp = now + sys_residual;
	if (dtemp < 0) {
		isneg = 1;
		dtemp = -dtemp;
	}
	adjtv.tv_sec = (long)dtemp;
	dtemp -= adjtv.tv_sec;
	ticks = (long)(dtemp / sys_tick + .5);
	adjtv.tv_usec = (long)(ticks * sys_tick * 1e6);
	dtemp -= adjtv.tv_usec / 1e6;
	sys_residual = dtemp;

	/*
	 * Convert to signed seconds and microseconds for the Unix
	 * adjtime() system call. Note we purposely lose the adjtime()
	 * leftover.
	 */
	if (isneg) {
		adjtv.tv_sec = -adjtv.tv_sec;
		adjtv.tv_usec = -adjtv.tv_usec;
		sys_residual = -sys_residual;
	}
	if (adjtv.tv_sec != 0 || adjtv.tv_usec != 0) {
		if (adjtime(&adjtv, &oadjtv) < 0) {
			msyslog(LOG_ERR, "adj_systime: %m");
			return (0);
		}
	}
	return (1);
}
Exemple #12
0
int UpdateSystemClock(struct timeval *Time)
{
uint64_t usec_diff=0, sec_diff=0;
struct timeval adjust_tm;
int result=FALSE;

/*
if (stime(&NewTime)!=0) return(FALSE);
*/

sec_diff=TimeNow.tv_sec - Time->tv_sec;
if (Time->tv_usec > 0) usec_diff=abs(TimeNow.tv_usec - Time->tv_usec);
if ((sec_diff==0) && (usec_diff==0)) 
{
	printf("Clock already synchroized\n");
	return(TRUE);
}

if (
		(sec_diff ==0) && 
 		(usec_diff < 40000) 
	)
{
	adjust_tm.tv_sec=0;
	adjust_tm.tv_usec=TimeNow.tv_usec - Time->tv_usec;
	if (adjtime(&adjust_tm, NULL) ==0) result=TRUE;
}
else if (settimeofday(Time, NULL) ==0) result=TRUE;

if (! result) 
{
	LastError=CopyStr(LastError, strerror(errno));
	if (Args->Flags & FLAG_SYSLOG) syslog(LOG_ERR, "Failed to update system clock by %ld millisecs. Error was: %s", (long) diff_millisecs(&TimeNow, Time), LastError);
	printf("Failed to update system clock by %ld millisecs. Error was: %s\n", (long) diff_millisecs(&TimeNow, Time), LastError);
}
else
{
	if (Args->Flags & FLAG_SYSLOG) syslog(LOG_INFO, "updated system clock by %ld millisecs", (long) diff_millisecs(&TimeNow, Time));
	printf("updated system clock by %ld millisecs\n", (long) diff_millisecs(&TimeNow, Time));
}
return(TRUE);
}
Exemple #13
0
int
ntpd_adjtime(double d)
{
	struct timeval	tv, olddelta;
	int		synced = 0;
	static int	firstadj = 1;

	if (d >= (double)LOG_NEGLIGEE / 1000 ||
	    d <= -1 * (double)LOG_NEGLIGEE / 1000)
		log_info("adjusting local clock by %fs", d);
	else
		log_debug("adjusting local clock by %fs", d);
	d_to_tv(d, &tv);
	if (adjtime(&tv, &olddelta) == -1)
		log_warn("adjtime failed");
	else if (!firstadj && olddelta.tv_sec == 0 && olddelta.tv_usec == 0)
		synced = 1;
	firstadj = 0;
	return (synced);
}
Exemple #14
0
static void
clock_initialise(void)
{
  struct timeval newadj, oldadj;

  offset_register = 0.0;
  adjustment_requested = 0.0;
  current_freq = 0.0;

  if (gettimeofday(&T0, NULL) < 0) {
    LOG_FATAL(LOGF_SysNetBSD, "gettimeofday() failed");
  }

  newadj.tv_sec = 0;
  newadj.tv_usec = 0;

  if (adjtime(&newadj, &oldadj) < 0) {
    LOG_FATAL(LOGF_SysNetBSD, "adjtime() failed");
  }

}
Exemple #15
0
int 
main (int ac, char **av)
{

	struct timeval tv;
	time_t dt;
	int err;


	if (ac < 2) {
		fprintf(stderr,
				"*** can't set time : options for rfatime missing ***\n");
		exit(-1);
	}
	if ((dt = atol(av[1])) == 0L) {
		fprintf(stderr,"*** can't set time : invalid time delta %s ***\n",
				av[1]);
		exit(-2);
	}
	if (dt > 0) {
		/*--- clock "jumps" forwards ---*/
		gettimeofday(&tv, NULL);
		tv.tv_sec += dt;
		if (settimeofday(&tv, NULL) == -1) {
			err = errno;
			fprintf(stderr,"*** can't set time : %s ***\n", sys_errname(errno));
			exit(err);
		}
	} else {
		tv.tv_sec = dt;
		tv.tv_usec = 0L;
		if (adjtime(&tv, NULL) == -1) {
			err = errno;
			fprintf(stderr,"*** can't set time : %s ***\n", sys_errname(errno));
			exit(err);
		}
	}
	exit(0);
}
Exemple #16
0
static void
setthetime(const char *p)
{
	struct timeval tv;
	time_t new_time;
	struct tm *lt;
	const char *dot, *t;
	size_t len;
	int yearset;

	for (t = p, dot = NULL; *t; ++t) {
		if (isdigit((unsigned char)*t))
			continue;
		if (*t == '.' && dot == NULL) {
			dot = t;
			continue;
		}
		badformat();
	}

	lt = localtime(&tval);

	lt->tm_isdst = -1;			/* Divine correct DST */

	if (dot != NULL) {			/* .ss */
		len = strlen(dot);
		if (len != 3)
			badformat();
		++dot;
		lt->tm_sec = ATOI2(dot);
		if (lt->tm_sec > 61)
			badvalue("seconds");
	} else {
		len = 0;
		lt->tm_sec = 0;
	}

	yearset = 0;
	switch (strlen(p) - len) {
	case 12:				/* cc */
		lt->tm_year = ATOI2(p) * 100 - TM_YEAR_BASE;
		if (lt->tm_year < 0)
			badtime();
		yearset = 1;
		/* FALLTHROUGH */
	case 10:				/* yy */
		if (yearset) {
			lt->tm_year += ATOI2(p);
		} else {
			yearset = ATOI2(p);
			if (yearset < 69)
				lt->tm_year = yearset + 2000 - TM_YEAR_BASE;
			else
				lt->tm_year = yearset + 1900 - TM_YEAR_BASE;
		}
		/* FALLTHROUGH */
	case 8:					/* mm */
		lt->tm_mon = ATOI2(p);
		if (lt->tm_mon > 12 || lt->tm_mon == 0)
			badvalue("month");
		--lt->tm_mon;			/* time struct is 0 - 11 */
		/* FALLTHROUGH */
	case 6:					/* dd */
		lt->tm_mday = ATOI2(p);
		switch (lt->tm_mon) {
		case 0:
		case 2:
		case 4:
		case 6:
		case 7:
		case 9:
		case 11:
			if (lt->tm_mday > 31 || lt->tm_mday == 0)
				badvalue("day of month");
			break;
		case 3:
		case 5:
		case 8:
		case 10:
			if (lt->tm_mday > 30 || lt->tm_mday == 0)
				badvalue("day of month");
			break;
		case 1:
			if (lt->tm_mday > 29 || lt->tm_mday == 0 ||
			    (lt->tm_mday == 29 &&
			     !isleap(lt->tm_year + TM_YEAR_BASE)))
				badvalue("day of month");
			break;
		default:
			badvalue("month");
			break;
		}
		/* FALLTHROUGH */
	case 4:					/* hh */
		lt->tm_hour = ATOI2(p);
		if (lt->tm_hour > 23)
			badvalue("hour");
		/* FALLTHROUGH */
	case 2:					/* mm */
		lt->tm_min = ATOI2(p);
		if (lt->tm_min > 59)
			badvalue("minute");
		break;
	case 0:					/* was just .sss */
		if (len != 0)
			break;
		/* FALLTHROUGH */
	default:
		badformat();
	}

	/* convert broken-down time to UTC clock time */
	if ((new_time = mktime(lt)) == -1)
		badtime();

	/* if jflag is set, don't actually change the time, just return */
	if (jflag) {
		tval = new_time;
		return;
	}

	/* set the time */
	if (nflag || netsettime(new_time)) {
		logwtmp("|", "date", "");
		if (aflag) {
			tv.tv_sec = new_time - tval;
			tv.tv_usec = 0;
			if (adjtime(&tv, NULL))
				err(EXIT_FAILURE, "adjtime");
		} else {
			tval = new_time;
			tv.tv_sec = tval;
			tv.tv_usec = 0;
			if (settimeofday(&tv, NULL))
				err(EXIT_FAILURE, "settimeofday");
		}
		logwtmp("{", "date", "");
	}

	if ((p = getlogin()) == NULL)
		p = "???";
	syslog(LOG_AUTH | LOG_NOTICE, "date set by %s", p);
}
Exemple #17
0
int
ntp_set_tod(
	struct timeval *tvp,
	void *tzp
	)
{
	static int tod;
	int rc = -1;
	int saved_errno = 0;

#ifdef DEBUG
	if (debug)
	    printf("In ntp_set_tod\n");
#endif

#ifdef HAVE_CLOCK_SETTIME
	if (rc && (SET_TOD_CLOCK_SETTIME == tod || !tod)) {
		struct timespec ts;

		/* Convert timeval to timespec */
		ts.tv_sec = tvp->tv_sec;
		ts.tv_nsec = 1000 *  tvp->tv_usec;

		errno = 0;
		rc = clock_settime(CLOCK_REALTIME, &ts);
		saved_errno = errno;
#ifdef DEBUG
		if (debug) {
			printf("ntp_set_tod: clock_settime: %d: %s\n",
			       rc, strerror(saved_errno));
		}
#endif
		if (!tod && !rc)
			tod = SET_TOD_CLOCK_SETTIME;

	}
#endif /* HAVE_CLOCK_SETTIME */
#ifdef HAVE_SETTIMEOFDAY
	if (rc && (SET_TOD_SETTIMEOFDAY == tod || !tod)) {
		struct timeval adjtv;

		/*
		 * Some broken systems don't reset adjtime() when the
		 * clock is stepped.
		 */
		adjtv.tv_sec = adjtv.tv_usec = 0;
		adjtime(&adjtv, NULL);
		errno = 0;
		rc = SETTIMEOFDAY(tvp, tzp);
		saved_errno = errno;
#ifdef DEBUG
		if (debug) {
			printf("ntp_set_tod: settimeofday: %d: %s\n",
			       rc, strerror(saved_errno));
		}
#endif
		if (!tod && !rc)
			tod = SET_TOD_SETTIMEOFDAY;
	}
#endif /* HAVE_SETTIMEOFDAY */
#ifdef HAVE_STIME
	if (rc && (SET_TOD_STIME == tod || !tod)) {
		long tp = tvp->tv_sec;

		errno = 0;
		rc = stime(&tp); /* lie as bad as SysVR4 */
		saved_errno = errno;
#ifdef DEBUG
		if (debug) {
			printf("ntp_set_tod: stime: %d: %s\n",
			       rc, strerror(saved_errno));
		}
#endif
		if (!tod && !rc)
			tod = SET_TOD_STIME;
	}
#endif /* HAVE_STIME */

#ifdef DEBUG
	if (debug) {
		printf("ntp_set_tod: Final result: %s: %d: %s\n",
			set_tod_used[tod], rc, strerror(saved_errno));
	}
#endif
	/*
	 * Say how we're setting the time of day
	 */
	if (!rc && NULL != set_tod_using) {
		(*set_tod_using)(set_tod_used[tod]);
		set_tod_using = NULL;
	}

	if (rc)
		errno = saved_errno;

	return rc;
}
Exemple #18
0
static void decode_msg(void *base, size_t len, struct timeval *tv,
		struct timespec *mrx_time)
{
	struct ntp_msg *msg = base;
	double m_delta, org, rec, xmt, dst;
	double delay, offset;
	static guint transmit_delay;

	if (len < sizeof(*msg)) {
		connman_error("Invalid response from time server");
		return;
	}

	if (!tv) {
		connman_error("Invalid packet timestamp from time server");
		return;
	}

	DBG("flags      : 0x%02x", msg->flags);
	DBG("stratum    : %u", msg->stratum);
	DBG("poll       : %f seconds (%d)",
				LOGTOD(msg->poll), msg->poll);
	DBG("precision  : %f seconds (%d)",
				LOGTOD(msg->precision), msg->precision);
	DBG("root delay : %u seconds (fraction %u)",
			msg->rootdelay.seconds, msg->rootdelay.fraction);
	DBG("root disp. : %u seconds (fraction %u)",
			msg->rootdisp.seconds, msg->rootdisp.fraction);
	DBG("reference  : 0x%04x", msg->refid);

	transmit_delay = LOGTOD(msg->poll);

	if (NTP_FLAGS_LI_DECODE(msg->flags) == NTP_FLAG_LI_NOTINSYNC) {
		DBG("ignoring unsynchronized peer");
		return;
	}


	if (NTP_FLAGS_VN_DECODE(msg->flags) != NTP_FLAG_VN_VER4) {
		if (NTP_FLAGS_VN_DECODE(msg->flags) == NTP_FLAG_VN_VER3) {
			DBG("requested version %d, accepting version %d",
				NTP_FLAG_VN_VER4, NTP_FLAGS_VN_DECODE(msg->flags));
		} else {
			DBG("unsupported version %d", NTP_FLAGS_VN_DECODE(msg->flags));
			return;
		}
	}

	if (NTP_FLAGS_MD_DECODE(msg->flags) != NTP_FLAG_MD_SERVER) {
		DBG("unsupported mode %d", NTP_FLAGS_MD_DECODE(msg->flags));
		return;
	}

	m_delta = mrx_time->tv_sec - mtx_time.tv_sec +
		1.0e-9 * (mrx_time->tv_nsec - mtx_time.tv_nsec);

	org = tv->tv_sec + (1.0e-6 * tv->tv_usec) - m_delta + OFFSET_1900_1970;
	rec = ntohl(msg->rectime.seconds) +
			((double) ntohl(msg->rectime.fraction) / UINT_MAX);
	xmt = ntohl(msg->xmttime.seconds) +
			((double) ntohl(msg->xmttime.fraction) / UINT_MAX);
	dst = tv->tv_sec + (1.0e-6 * tv->tv_usec) + OFFSET_1900_1970;

	DBG("org=%f rec=%f xmt=%f dst=%f", org, rec, xmt, dst);

	offset = ((rec - org) + (xmt - dst)) / 2;
	delay = (dst - org) - (xmt - rec);

	DBG("offset=%f delay=%f", offset, delay);

	/* Remove the timeout, as timeserver has responded */

	reset_timeout();

	/*
	 * Now poll the server every transmit_delay seconds
	 * for time correction.
	 */
	if (poll_id > 0)
		g_source_remove(poll_id);

	DBG("Timeserver %s, next sync in %d seconds", timeserver, transmit_delay);

	poll_id = g_timeout_add_seconds(transmit_delay, next_poll, NULL);

	connman_info("ntp: time slew %+.6f s", offset);

	if (offset < STEPTIME_MIN_OFFSET && offset > -STEPTIME_MIN_OFFSET) {
		struct timeval adj;

		adj.tv_sec = (long) offset;
		adj.tv_usec = (offset - adj.tv_sec) * 1000000;

		DBG("adjusting time");

		if (adjtime(&adj, &adj) < 0) {
			connman_error("Failed to adjust time");
			return;
		}

		DBG("%lu seconds, %lu msecs", adj.tv_sec, adj.tv_usec);
	} else {
		struct timeval cur;
		double dtime;

		gettimeofday(&cur, NULL);
		dtime = offset + cur.tv_sec + 1.0e-6 * cur.tv_usec;
		cur.tv_sec = (long) dtime;
		cur.tv_usec = (dtime - cur.tv_sec) * 1000000;

		DBG("setting time");

		if (settimeofday(&cur, NULL) < 0) {
			connman_error("Failed to set time");
			return;
		}

		DBG("%lu seconds, %lu msecs", cur.tv_sec, cur.tv_usec);
	}
}
Exemple #19
0
void CRCInput::getMsg_us(neutrino_msg_t * msg, neutrino_msg_data_t * data, uint64_t Timeout, bool bAllowRepeatLR)
{
	static uint64_t last_keypress = 0ULL;
	//uint64_t getKeyBegin;

	//static __u16 rc_last_key =  KEY_MAX;
	static __u16 rc_last_repeat_key =  KEY_MAX;

	struct timeval tv;
	struct timeval tvselect;
	uint64_t InitialTimeout = Timeout;
	int64_t targetTimeout;

	int timer_id;
	fd_set rfds;
	t_input_event ev;

	*data = 0;

	// wiederholung reinmachen - dass wirklich die ganze zeit bis timeout gewartet wird!
#ifdef USE_GETTIMEOFDAY
	gettimeofday( &tv, NULL );
	uint64_t getKeyBegin = (uint64_t) tv.tv_usec + (uint64_t)((uint64_t) tv.tv_sec * (uint64_t) 1000000);
#else
	uint64_t getKeyBegin = time_monotonic_us();
#endif
	while(1) {
		timer_id = 0;
		if ( !timers.empty() )
		{
#ifdef USE_GETTIMEOFDAY
			gettimeofday( &tv, NULL );
			uint64_t t_n= (uint64_t) tv.tv_usec + (uint64_t)((uint64_t) tv.tv_sec * (uint64_t) 1000000);
#else
			uint64_t t_n = time_monotonic_us();
#endif
			if ( timers[0].times_out< t_n )
			{
				timer_id = checkTimers();
				*msg = NeutrinoMessages::EVT_TIMER;
				*data = timer_id;
				return;
			}
			else
			{
				targetTimeout = timers[0].times_out - t_n;
				if ( (uint64_t) targetTimeout> Timeout)
					targetTimeout= Timeout;
				else
					timer_id = timers[0].id;
			}
		}
		else
			targetTimeout= Timeout;

		tvselect.tv_sec = targetTimeout/1000000;
		tvselect.tv_usec = targetTimeout%1000000;

		FD_ZERO(&rfds);
		for (int i = 0; i < NUMBER_OF_EVENT_DEVICES; i++)
		{
			if (fd_rc[i] != -1)
				FD_SET(fd_rc[i], &rfds);
		}
#ifdef KEYBOARD_INSTEAD_OF_REMOTE_CONTROL
		if (true)
#else
			if (fd_keyb> 0)
#endif /* KEYBOARD_INSTEAD_OF_REMOTE_CONTROL */
				FD_SET(fd_keyb, &rfds);

		FD_SET(fd_event, &rfds);
		FD_SET(fd_pipe_high_priority[0], &rfds);
		FD_SET(fd_pipe_low_priority[0], &rfds);

		int status =  select(fd_max+1, &rfds, NULL, NULL, &tvselect);

		if ( status == -1 )
		{
			perror("[neutrino - getMsg_us]: select returned ");
			// in case of an error return timeout...?!
			*msg = RC_timeout;
			*data = 0;
			return;
		}
		else if ( status == 0 ) // Timeout!
		{
			if ( timer_id != 0 )
			{
				timer_id = checkTimers();
				if ( timer_id != 0 )
				{
					*msg = NeutrinoMessages::EVT_TIMER;
					*data = timer_id;
					return;
				}
				else
					continue;
			}
			else
			{
				*msg = RC_timeout;
				*data = 0;
				return;
			}
		}

		if(FD_ISSET(fd_pipe_high_priority[0], &rfds))
		{
			struct event buf;

			read(fd_pipe_high_priority[0], &buf, sizeof(buf));

			*msg  = buf.msg;
			*data = buf.data;

			// printf("got event from high-pri pipe %x %x\n", *msg, *data );

			return;
		}


#ifdef KEYBOARD_INSTEAD_OF_REMOTE_CONTROL
		if (FD_ISSET(fd_keyb, &rfds))
		{
			int trkey;
			char key = 0;
			read(fd_keyb, &key, sizeof(key));

			switch(key)
			{
				case 27: // <- Esc
					trkey = KEY_HOME;
					break;
				case 10: // <- Return
				case 'o':
					trkey = KEY_OK;
					break;
				case 'p':
					trkey = KEY_POWER;
					break;
				case 's':
					trkey = KEY_SETUP;
					break;
				case 'h':
					trkey = KEY_HELP;
					break;
				case 'i':
					trkey = KEY_UP;
					break;
				case 'm':
					trkey = KEY_DOWN;
					break;
				case 'j':
					trkey = KEY_LEFT;
					break;
				case 'k':
					trkey = KEY_RIGHT;
					break;
				case 'r':
					trkey = KEY_RED;
					break;
				case 'g':
					trkey = KEY_GREEN;
					break;
				case 'y':
					trkey = KEY_YELLOW;
					break;
				case 'b':
					trkey = KEY_BLUE;
					break;
				case '0':
					trkey = RC_0;
					break;
				case '1':
					trkey = RC_1;
					break;
				case '2':
					trkey = RC_2;
					break;
				case '3':
					trkey = RC_3;
					break;
				case '4':
					trkey = RC_4;
					break;
				case '5':
					trkey = RC_5;
					break;
				case '6':
					trkey = RC_6;
					break;
				case '7':
					trkey = RC_7;
					break;
				case '8':
					trkey = RC_8;
					break;
				case '9':
					trkey = RC_9;
					break;
				case '+':
					trkey = RC_plus;
					break;
				case '-':
					trkey = RC_minus;
					break;
				case 'a':
					trkey = KEY_A;
					break;
				case 'u':
					trkey = KEY_U;
					break;
				case '/':
					trkey = KEY_SLASH;
					break;
				case '\\':
					trkey = KEY_BACKSLASH;
					break;
				default:
					trkey = RC_nokey;
			}
			if (trkey != RC_nokey)
			{
				*msg = trkey;
				*data = 0; /* <- button pressed */
				return;
			}
		}
#else
		/*
		   if(FD_ISSET(fd_keyb, &rfds))
		   {
		   char key = 0;
		   read(fd_keyb, &key, sizeof(key));
		   printf("keyboard: %d\n", rc_key);
		   }
		   */
#endif /* KEYBOARD_INSTEAD_OF_REMOTE_CONTROL */

		if(FD_ISSET(fd_event, &rfds)) {
			//printf("[neutrino] event - accept!\n");
			socklen_t          clilen;
			struct sockaddr_in cliaddr;
			clilen = sizeof(cliaddr);
			int fd_eventclient = accept(fd_event, (struct sockaddr *) &cliaddr, &clilen);

			*msg = RC_nokey;
			//printf("[neutrino] network event - read!\n");
			CEventServer::eventHead emsg;
			int read_bytes= recv(fd_eventclient, &emsg, sizeof(emsg), MSG_WAITALL);
			//printf("[neutrino] event read %d bytes - following %d bytes\n", read_bytes, emsg.dataSize );
			if ( read_bytes == sizeof(emsg) ) {
				bool dont_delete_p = false;

				unsigned char* p;
				p= new unsigned char[ emsg.dataSize + 1 ];
				if ( p!=NULL )
				{
					read_bytes= recv(fd_eventclient, p, emsg.dataSize, MSG_WAITALL);
					//printf("[neutrino] eventbody read %d bytes - initiator %x\n", read_bytes, emsg.initiatorID );

#if 0
					if ( emsg.initiatorID == CEventServer::INITID_CONTROLD )
					{
						switch(emsg.eventID)
						{
							case CControldClient::EVT_VOLUMECHANGED :
								*msg = NeutrinoMessages::EVT_VOLCHANGED;
								*data = 0;
								break;
							case CControldClient::EVT_MUTECHANGED :
								*msg = NeutrinoMessages::EVT_MUTECHANGED;
								*data = (unsigned) p;
								dont_delete_p = true;
								break;
							case CControldClient::EVT_VCRCHANGED :
								*msg = NeutrinoMessages::EVT_VCRCHANGED;
								*data = *(int*) p;
								break;
							case CControldClient::EVT_MODECHANGED :
								*msg = NeutrinoMessages::EVT_MODECHANGED;
								*data = *(int*) p;
								break;
							default:
								printf("[neutrino] event INITID_CONTROLD - unknown eventID 0x%x\n",  emsg.eventID );
						}
					}
					else 
#endif
					if ( emsg.initiatorID == CEventServer::INITID_HTTPD )
					{
						switch(emsg.eventID)
						{
							case NeutrinoMessages::SHUTDOWN :
								*msg = NeutrinoMessages::SHUTDOWN;
								*data = 0;
								break;
							case NeutrinoMessages::REBOOT :
								*msg = NeutrinoMessages::REBOOT;
								*data = 0;
								break;
							case NeutrinoMessages::EVT_POPUP :
								*msg = NeutrinoMessages::EVT_POPUP;
								*data = (unsigned) p;
								dont_delete_p = true;
								break;
							case NeutrinoMessages::EVT_EXTMSG :
								*msg = NeutrinoMessages::EVT_EXTMSG;
								*data = (unsigned) p;
								dont_delete_p = true;
								break;
							case NeutrinoMessages::CHANGEMODE :	// Change
								*msg = NeutrinoMessages::CHANGEMODE;
								*data = *(unsigned*) p;
								break;
							case NeutrinoMessages::STANDBY_TOGGLE :
								*msg = NeutrinoMessages::STANDBY_TOGGLE;
								*data = 0;
								break;
							case NeutrinoMessages::STANDBY_ON :
								*msg = NeutrinoMessages::STANDBY_ON;
								*data = 0;
								break;
							case NeutrinoMessages::STANDBY_OFF :
								*msg = NeutrinoMessages::STANDBY_OFF;
								*data = 0;
								break;
							case NeutrinoMessages::EVT_START_PLUGIN :
								*msg = NeutrinoMessages::EVT_START_PLUGIN;
								*data = (unsigned) p;
								dont_delete_p = true;
								break;
							case NeutrinoMessages::LOCK_RC :
								*msg = NeutrinoMessages::LOCK_RC;
								*data = 0;
								break;
							case NeutrinoMessages::UNLOCK_RC :
								*msg = NeutrinoMessages::UNLOCK_RC;
								*data = 0;
								break;
							case NeutrinoMessages::RELOAD_SETUP :
								*msg = NeutrinoMessages::RELOAD_SETUP;
								*data = 0;
								break;
							case NeutrinoMessages::EVT_HDMI_CEC_VIEW_ON:
								*msg          = NeutrinoMessages::EVT_HDMI_CEC_VIEW_ON;
								*data         = 0;
								break;
							case NeutrinoMessages::EVT_HDMI_CEC_STANDBY:
								*msg          = NeutrinoMessages::EVT_HDMI_CEC_STANDBY;
								*data         = 0;
								break;
							case NeutrinoMessages::EVT_SET_MUTE :
								*msg = NeutrinoMessages::EVT_SET_MUTE;
								*data = *(char*) p;
								break;
							case NeutrinoMessages::EVT_SET_VOLUME :
								*msg = NeutrinoMessages::EVT_SET_VOLUME;
								*data = *(char*) p;
								break;
							default:
								printf("[neutrino] event INITID_HTTPD - unknown eventID 0x%x\n",  emsg.eventID );
						}
					}
					else if ( emsg.initiatorID == CEventServer::INITID_SECTIONSD )
					{
						//printf("[neutrino] event - from SECTIONSD %x %x\n", emsg.eventID, *(unsigned*) p);
						switch(emsg.eventID)
						{
							case CSectionsdClient::EVT_TIMESET:
							{
#if 0
								struct timeval ltv;
								gettimeofday(&ltv, NULL);
								int64_t timeOld = ltv.tv_usec + ltv.tv_sec * (int64_t)1000000;
								time_t dvbtime = *((time_t*)p);
								if (dvbtime) {
									printf("[neutrino] timeset event. ");
									time_t difftime = dvbtime - ltv.tv_sec;
									if (abs(difftime) > 120) 
									{
										printf("difference is %ld s, stepping...\n", difftime);
										if (stime(&dvbtime))
											perror("stime");
									} else if (difftime != 0) {
										struct timeval oldd;
										ltv.tv_sec = difftime;
										ltv.tv_usec = 0;
										if (adjtime(&ltv, &oldd))
											perror("adjtime");
										int64_t t = oldd.tv_sec * 1000000LL + oldd.tv_usec;
										printf("difference is %ld s, using adjtime(). oldd: %lld us\n", difftime, t);
									} else
										printf("difference is 0 s, nothing to do...\n");
								}
								gettimeofday( &ltv, NULL );
								int64_t timeNew = ltv.tv_usec + ltv.tv_sec * (int64_t)1000000;

								delete[] p;//new [] delete []
								p = new unsigned char[sizeof(int64_t)];
								*(int64_t*) p = timeNew - timeOld;
#endif
								printf("[neutrino] CSectionsdClient::EVT_TIMESET: timediff %" PRId64 "\n", *(int64_t*) p);
								/* FIXME what this code really do ? */
								if ((int64_t)last_keypress > *(int64_t*)p)
									last_keypress += *(int64_t *)p;

#ifdef USE_GETTIMEOFDAY
								// Timer anpassen
								for(std::vector<timer>::iterator e = timers.begin(); e != timers.end(); ++e)
									if (e->correct_time)
										e->times_out+= *(int64_t*) p;
#endif
								*msg          = NeutrinoMessages::EVT_TIMESET;
								*data         = (neutrino_msg_data_t) p;
								dont_delete_p = true;
								break;
							}
							case CSectionsdClient::EVT_GOT_CN_EPG:
								printf("[neutrino] CSectionsdClient::EVT_GOT_CN_EPG\n");
								*msg          = NeutrinoMessages::EVT_CURRENTNEXT_EPG;
								*data         = (neutrino_msg_data_t) p;
								dont_delete_p = true;
								break;
							case CSectionsdClient::EVT_WRITE_SI_FINISHED:
								*msg          = NeutrinoMessages::EVT_SI_FINISHED;
								*data         = 0;
								break;
							case CSectionsdClient::EVT_EIT_COMPLETE:
								printf("[neutrino] CSectionsdClient::EVT_EIT_COMPLETE\n");
								*msg          = NeutrinoMessages::EVT_EIT_COMPLETE;
								*data         = (neutrino_msg_data_t) p;
								dont_delete_p = true;
								break;
#if 0
							case CSectionsdClient::EVT_SERVICES_UPDATE:
								*msg          = NeutrinoMessages::EVT_SERVICES_UPD;
								*data         = 0;
								break;
							case CSectionsdClient::EVT_BOUQUETS_UPDATE:
								break;
#endif
							default:
								printf("[neutrino] event INITID_SECTIONSD - unknown eventID 0x%x\n",  emsg.eventID );
						}
					}
					else if ( emsg.initiatorID == CEventServer::INITID_ZAPIT )
					{
						//printf("[neutrino] event - from ZAPIT %x %x\n", emsg.eventID, *(unsigned*) p);
						switch(emsg.eventID)
						{
							case CZapitClient::EVT_RECORDMODE_ACTIVATED:
								*msg  = NeutrinoMessages::EVT_RECORDMODE;
								*data = true;
								break;
							case CZapitClient::EVT_RECORDMODE_DEACTIVATED:
								*msg  = NeutrinoMessages::EVT_RECORDMODE;
								*data = false;
								break;
							case CZapitClient::EVT_ZAP_COMPLETE:
								*msg = NeutrinoMessages::EVT_ZAP_COMPLETE;
								break;
							case CZapitClient::EVT_ZAP_FAILED:
								*msg = NeutrinoMessages::EVT_ZAP_FAILED;
								break;
							case CZapitClient::EVT_ZAP_SUB_FAILED:
								*msg = NeutrinoMessages::EVT_ZAP_SUB_FAILED;
								break;
							case CZapitClient::EVT_ZAP_COMPLETE_IS_NVOD:
								*msg = NeutrinoMessages::EVT_ZAP_ISNVOD;
								break;
							case CZapitClient::EVT_ZAP_SUB_COMPLETE:
								*msg = NeutrinoMessages::EVT_ZAP_SUB_COMPLETE;
								break;
							case CZapitClient::EVT_SCAN_COMPLETE:
								*msg  = NeutrinoMessages::EVT_SCAN_COMPLETE;
								*data = 0;
								break;
							case CZapitClient::EVT_SCAN_NUM_TRANSPONDERS:
								*msg  = NeutrinoMessages::EVT_SCAN_NUM_TRANSPONDERS;
								*data = *(unsigned*) p;
								break;
							case CZapitClient::EVT_SCAN_REPORT_NUM_SCANNED_TRANSPONDERS:
								*msg  = NeutrinoMessages::EVT_SCAN_REPORT_NUM_SCANNED_TRANSPONDERS;
								*data = *(unsigned*) p;
								break;
							case CZapitClient::EVT_SCAN_REPORT_FREQUENCY:
								*msg = NeutrinoMessages::EVT_SCAN_REPORT_FREQUENCY;
								*data = *(unsigned*) p;
								break;
							case CZapitClient::EVT_SCAN_FOUND_A_CHAN:
								*msg = NeutrinoMessages::EVT_SCAN_FOUND_A_CHAN;
								break;
							case CZapitClient::EVT_SCAN_SERVICENAME:
								*msg = NeutrinoMessages::EVT_SCAN_SERVICENAME;
								break;
							case CZapitClient::EVT_SCAN_FOUND_TV_CHAN:
								*msg  = NeutrinoMessages::EVT_SCAN_FOUND_TV_CHAN;
								*data = *(unsigned*) p;
								break;
							case CZapitClient::EVT_SCAN_FOUND_RADIO_CHAN:
								*msg  = NeutrinoMessages::EVT_SCAN_FOUND_RADIO_CHAN;
								*data = *(unsigned*) p;
								break;
							case CZapitClient::EVT_SCAN_FOUND_DATA_CHAN:
								*msg  = NeutrinoMessages::EVT_SCAN_FOUND_DATA_CHAN;
								*data = *(unsigned*) p;
								break;
							case CZapitClient::EVT_SCAN_REPORT_FREQUENCYP:
								*msg  = NeutrinoMessages::EVT_SCAN_REPORT_FREQUENCYP;
								*data = *(unsigned*) p;
								break;
							case CZapitClient::EVT_SCAN_NUM_CHANNELS:
								*msg = NeutrinoMessages::EVT_SCAN_NUM_CHANNELS;
								*data = *(unsigned*) p;
								break;
							case CZapitClient::EVT_SCAN_PROVIDER:
								*msg = NeutrinoMessages::EVT_SCAN_PROVIDER;
								break;
							case CZapitClient::EVT_SCAN_SATELLITE:
								*msg = NeutrinoMessages::EVT_SCAN_SATELLITE;
								break;
							case CZapitClient::EVT_BOUQUETS_CHANGED:
								*msg  = NeutrinoMessages::EVT_BOUQUETSCHANGED;
								*data = 0;
								break;
							case CZapitClient::EVT_SERVICES_CHANGED:
								*msg  = NeutrinoMessages::EVT_SERVICESCHANGED;
								*data = 0;
								break;
							case CZapitClient::EVT_ZAP_CA_CLEAR:
								*msg  = NeutrinoMessages::EVT_ZAP_CA_CLEAR;
								*data = *(unsigned*) p;
								break;
							case CZapitClient::EVT_ZAP_CA_LOCK:
								*msg  = NeutrinoMessages::EVT_ZAP_CA_LOCK;
								*data = *(unsigned*) p;
								break;
							case CZapitClient::EVT_ZAP_CA_FTA:
								*msg  = NeutrinoMessages::EVT_ZAP_CA_FTA;
								*data = *(unsigned*) p;
								break;
							case CZapitClient::EVT_ZAP_CA_ID :
								*msg = NeutrinoMessages::EVT_ZAP_CA_ID;
								*data = *(unsigned*) p;
								break;
							case CZapitClient::EVT_SCAN_FAILED:
								*msg  = NeutrinoMessages::EVT_SCAN_FAILED;
								*data = 0;
								break;
							case CZapitClient::EVT_ZAP_MOTOR:
								*msg  = NeutrinoMessages::EVT_ZAP_MOTOR;
								*data = *(unsigned*) p;
								break;
							case CZapitClient::EVT_SDT_CHANGED:
								*msg          = NeutrinoMessages::EVT_SERVICES_UPD;
								*data         = 0;
								break;
							case CZapitClient::EVT_PMT_CHANGED:
								*msg          = NeutrinoMessages::EVT_PMT_CHANGED;
								*data = (neutrino_msg_data_t) p;
								break;
							case CZapitClient::EVT_TUNE_COMPLETE:
								*msg          = NeutrinoMessages::EVT_TUNE_COMPLETE;
								*data = (neutrino_msg_data_t) p;
								break;
							case CZapitClient::EVT_BACK_ZAP_COMPLETE:
								*msg          = NeutrinoMessages::EVT_BACK_ZAP_COMPLETE;
								*data = (neutrino_msg_data_t) p;
								break;
							default:
								printf("[neutrino] event INITID_ZAPIT - unknown eventID 0x%x\n",  emsg.eventID );
						}
						if (((*msg) >= CRCInput::RC_WithData) && ((*msg) < CRCInput::RC_WithData + 0x10000000))
						{
							*data         = (neutrino_msg_data_t) p;
							dont_delete_p = true;
						}
					}
					else if ( emsg.initiatorID == CEventServer::INITID_TIMERD )
					{
						/*
						   if (emsg.eventID==CTimerdClient::EVT_ANNOUNCE_NEXTPROGRAM)
						   {
						   }

						   if (emsg.eventID==CTimerdClient::EVT_NEXTPROGRAM)
						   {
						 *msg = NeutrinoMessages::EVT_NEXTPROGRAM;
						 *data = (neutrino_msg_data_t) p;
						 dont_delete_p = true;
						 }
						 */
						switch(emsg.eventID)
						{
							case CTimerdClient::EVT_ANNOUNCE_RECORD :
								*msg = NeutrinoMessages::ANNOUNCE_RECORD;
								*data = (unsigned) p;
								dont_delete_p = true;
								break;
							case CTimerdClient::EVT_ANNOUNCE_ZAPTO :
								*msg = NeutrinoMessages::ANNOUNCE_ZAPTO;
								*data = (neutrino_msg_data_t)p;
								dont_delete_p = true;
								break;
							case CTimerdClient::EVT_ANNOUNCE_SHUTDOWN :
								*msg = NeutrinoMessages::ANNOUNCE_SHUTDOWN;
								*data = 0;
								break;
							case CTimerdClient::EVT_ANNOUNCE_SLEEPTIMER :
								*msg = NeutrinoMessages::ANNOUNCE_SLEEPTIMER;
								*data = 0;
								break;
							case CTimerdClient::EVT_SLEEPTIMER :
								*msg = NeutrinoMessages::SLEEPTIMER;
								*data = 0;
								break;
							case CTimerdClient::EVT_RECORD_START :
								*msg = NeutrinoMessages::RECORD_START;
								*data = (unsigned) p;
								dont_delete_p = true;
								break;
							case CTimerdClient::EVT_RECORD_STOP :
								*msg = NeutrinoMessages::RECORD_STOP;
								*data = (unsigned) p;
								dont_delete_p = true;
								break;
							case CTimerdClient::EVT_ZAPTO :
								*msg = NeutrinoMessages::ZAPTO;
								*data = (unsigned)  p;
								dont_delete_p = true;
								break;
							case CTimerdClient::EVT_SHUTDOWN :
								*msg = NeutrinoMessages::SHUTDOWN;
								*data = 0;
								break;
							case CTimerdClient::EVT_STANDBY_ON :
								*msg = NeutrinoMessages::STANDBY_ON;
								*data = 0;
								break;
							case CTimerdClient::EVT_STANDBY_OFF :
								*msg = NeutrinoMessages::STANDBY_OFF;
								*data = 0;
								break;
							case CTimerdClient::EVT_REMIND :
								*msg = NeutrinoMessages::REMIND;
								*data = (unsigned) p;
								dont_delete_p = true;
								break;
							case CTimerdClient::EVT_EXEC_PLUGIN :
								*msg = NeutrinoMessages::EVT_START_PLUGIN;
								*data = (unsigned) p;
								dont_delete_p = true;
								break;

							default :
								printf("[neutrino] event INITID_TIMERD - unknown eventID 0x%x\n",  emsg.eventID );

						}
					}
					else if (emsg.initiatorID == CEventServer::INITID_NEUTRINO)
					{
#if 0
						if ((emsg.eventID == NeutrinoMessages::EVT_RECORDING_ENDED) &&
								(read_bytes == sizeof(stream2file_status2_t)))
						{
							*msg  = NeutrinoMessages::EVT_RECORDING_ENDED;
							*data = (neutrino_msg_data_t) p;
							dont_delete_p = true;
						}
#endif
					}
					else if (emsg.initiatorID == CEventServer::INITID_GENERIC_INPUT_EVENT_PROVIDER)
					{
						if (read_bytes == sizeof(int))
						{
							*msg  = *(int *)p;
							*data = emsg.eventID;
						}
					}
					else
						printf("[neutrino] event - unknown initiatorID 0x%x\n",  emsg.initiatorID);
					if ( !dont_delete_p )
					{
						delete[] p;//new [] delete []
						p= NULL;
					}
				}
			}
			else
			{
				printf("[neutrino] event - read failed!\n");
			}

			::close(fd_eventclient);

			if ( *msg != RC_nokey )
			{
				// raus hier :)
				//printf("[neutrino] event 0x%x\n", *msg);
				return;
			}
		}

		for (int i = 0; i < NUMBER_OF_EVENT_DEVICES; i++) {
			if ((fd_rc[i] != -1) && (FD_ISSET(fd_rc[i], &rfds))) {
				int ret;
				ret = read(fd_rc[i], &ev, sizeof(t_input_event));

				if(ret != sizeof(t_input_event))
					continue;
				SHTDCNT::getInstance()->resetSleepTimer();
				if (firstKey) {
					firstKey = false;
					CTimerManager::getInstance()->cancelShutdownOnWakeup();
				}
				uint32_t trkey = translate(ev.code, i);
#ifdef DEBUG
				printf("key: %04x value %d, translate: %04x -%s-\n", ev.code, ev.value, trkey, getKeyName(trkey).c_str());
#endif
				if (trkey == RC_nokey)
					continue;
				if (ev.value) {
#ifdef RCDEBUG
					printf("got keydown native key: %04x %04x, translate: %04x -%s-\n", ev.code, ev.code&0x1f, translate(ev.code, 0), getKeyName(translate(ev.code, 0)).c_str());
					printf("rc_last_key %04x rc_last_repeat_key %04x\n\n", rc_last_key, rc_last_repeat_key);
#endif
					uint64_t now_pressed;
					bool keyok = true;

					tv = ev.time;
					now_pressed = (uint64_t) tv.tv_usec + (uint64_t)((uint64_t) tv.tv_sec * (uint64_t) 1000000);
					if (ev.code == rc_last_key) {
						/* only allow selected keys to be repeated */
						/* (why?)                                  */
						if( 	(trkey == RC_up) || (trkey == RC_down   ) ||
							(trkey == RC_plus   ) || (trkey == RC_minus  ) ||
							(trkey == RC_page_down   ) || (trkey == RC_page_up  ) ||
							((bAllowRepeatLR) && ((trkey == RC_left ) || (trkey == RC_right))) ||
							(g_settings.shutdown_real_rcdelay && ((trkey == RC_standby) && (cs_get_revision() > 7))) )
						{
#ifdef ENABLE_REPEAT_CHECK
							if (rc_last_repeat_key != ev.code) {
								if ((now_pressed > last_keypress + repeat_block) ||
										/* accept all keys after time discontinuity: */
										(now_pressed < last_keypress))
									rc_last_repeat_key = ev.code;
								else
									keyok = false;
							}
#endif
						}
						else
							keyok = false;
					}
					else
						rc_last_repeat_key = KEY_MAX;

					rc_last_key = ev.code;

					if (keyok) {
#ifdef ENABLE_REPEAT_CHECK
						if ((now_pressed > last_keypress + repeat_block_generic) ||
								/* accept all keys after time discontinuity: */
								(now_pressed < last_keypress))
#endif
						{
							last_keypress = now_pressed;

							*msg = trkey;
							*data = 0; /* <- button pressed */
							if(g_settings.key_click)
								play_click();
							return;
						}
					} /*if keyok */
				} /* if (ev.value) */
				else {
					// clear rc_last_key on keyup event
#ifdef RCDEBUG
					printf("got keyup native key: %04x %04x, translate: %04x -%s-\n", ev.code, ev.code&0x1f, translate(ev.code, 0), getKeyName(translate(ev.code, 0)).c_str() );
#endif
					rc_last_key = KEY_MAX;
					if (trkey == RC_standby) {
						*msg = RC_standby;
						*data = 1; /* <- button released */
						return;
					}
				}
			}/* if FDSET */
		} /* for NUMBER_OF_EVENT_DEVICES */

		if(FD_ISSET(fd_pipe_low_priority[0], &rfds))
		{
			struct event buf;

			read(fd_pipe_low_priority[0], &buf, sizeof(buf));

			*msg  = buf.msg;
			*data = buf.data;

			// printf("got event from low-pri pipe %x %x\n", *msg, *data );

			return;
		}

		if ( InitialTimeout == 0 )
		{
			//nicht warten wenn kein key da ist
			*msg = RC_timeout;
			*data = 0;
			return;
		}
		else
		{
			//timeout neu kalkulieren
#ifdef USE_GETTIMEOFDAY
			gettimeofday( &tv, NULL );
			int64_t getKeyNow = (int64_t) tv.tv_usec + (int64_t)((int64_t) tv.tv_sec * (int64_t) 1000000);
#else
			int64_t getKeyNow = time_monotonic_us();
#endif
			int64_t diff = (getKeyNow - getKeyBegin);
			if( Timeout <= (uint64_t) diff )
			{
				*msg = RC_timeout;
				*data = 0;
				return;
			}
			else
				Timeout -= diff;
		}
	}
}
Exemple #20
0
void
setthetime(char *p)
{
	struct tm *lt;
	struct timeval tv;
	char *dot, *t;
	int yearset = 0;

	for (t = p, dot = NULL; *t; ++t) {
		if (isdigit((unsigned char)*t))
			continue;
		if (*t == '.' && dot == NULL) {
			dot = t;
			continue;
		}
		badformat();
	}

	lt = localtime(&tval);

	lt->tm_isdst = -1;			/* correct for DST */

	if (dot != NULL) {			/* .SS */
		*dot++ = '\0';
		if (strlen(dot) != 2)
			badformat();
		lt->tm_sec = ATOI2(dot);
		if (lt->tm_sec > 61)
			badformat();
	} else
		lt->tm_sec = 0;

	switch (strlen(p)) {
	case 12:				/* cc */
		lt->tm_year = ATOI2(p) * 100 - TM_YEAR_BASE;
		yearset = 1;
		/* FALLTHROUGH */
	case 10:				/* yy */
		if (!yearset) {
			/* mask out current year, leaving only century */
			lt->tm_year = ((lt->tm_year / 100) * 100);
		}
		lt->tm_year += ATOI2(p);
		/* FALLTHROUGH */
	case 8:					/* mm */
		lt->tm_mon = ATOI2(p);
		if ((lt->tm_mon > 12) || !lt->tm_mon)
			badformat();
		--lt->tm_mon;			/* time struct is 0 - 11 */
		/* FALLTHROUGH */
	case 6:					/* dd */
		lt->tm_mday = ATOI2(p);
		if ((lt->tm_mday > 31) || !lt->tm_mday)
			badformat();
		/* FALLTHROUGH */
	case 4:					/* HH */
		lt->tm_hour = ATOI2(p);
		if (lt->tm_hour > 23)
			badformat();
		/* FALLTHROUGH */
	case 2:					/* MM */
		lt->tm_min = ATOI2(p);
		if (lt->tm_min > 59)
			badformat();
		break;
	default:
		badformat();
	}

	/* convert broken-down time to UTC clock time */
	if ((tval = mktime(lt)) < 0)
		errx(1, "specified date is outside allowed range");

	if (jflag)
		return;

	/* set the time */
	if (slidetime) {
		struct timeval tv_current;

		if (gettimeofday(&tv_current, NULL) == -1)
			err(1, "Could not get local time of day");

		tv.tv_sec = tval - tv_current.tv_sec;
		tv.tv_usec = 0;
		if (adjtime(&tv, NULL) == -1)
			errx(1, "adjtime");
	} else {
#ifndef SMALL
		logwtmp("|", "date", "");
#endif
		tv.tv_sec = tval;
		tv.tv_usec = 0;
		if (settimeofday(&tv, NULL))
			err(1, "settimeofday");
#ifndef SMALL
		logwtmp("{", "date", "");
#endif
	}

	if ((p = getlogin()) == NULL)
		p = "???";
	syslog(LOG_AUTH | LOG_NOTICE, "date set by %s", p);
}
Exemple #21
0
void
setthetime(char *p)
{
	struct tm *lt;
	struct timeval tv;
	char *dot, *t;
	const char *pc;
	int bigyear;
	int yearset = 0;

	for (t = p, dot = NULL; *t; ++t) {
		if (isdigit(*t))
			continue;
		if (*t == '.' && dot == NULL) {
			dot = t;
			continue;
		}
		badformat();
	}

	lt = localtime(&tval);

	lt->tm_isdst = -1;			/* correct for DST */

	if (dot != NULL) {			/* .SS */
		*dot++ = '\0';
		if (strlen(dot) != 2)
			badformat();
		lt->tm_sec = ATOI2(dot);
		if (lt->tm_sec > 61)
			badformat();
	} else
		lt->tm_sec = 0;

	switch (strlen(p)) {
	case 12:				/* cc */
		bigyear = ATOI2(p);
		lt->tm_year = bigyear * 100 - TM_YEAR_BASE;
		yearset = 1;
		/* FALLTHROUGH */
	case 10:				/* yy */
		if (yearset) {
			lt->tm_year += ATOI2(p);
		} else {
			lt->tm_year = ATOI2(p);
			if (lt->tm_year < 69)		/* hack for 2000 ;-} */
				lt->tm_year += (2000 - TM_YEAR_BASE);
			else
				lt->tm_year += (1900 - TM_YEAR_BASE);
		}
		/* FALLTHROUGH */
	case 8:					/* mm */
		lt->tm_mon = ATOI2(p);
		if ((lt->tm_mon > 12) || !lt->tm_mon)
			badformat();
		--lt->tm_mon;			/* time struct is 0 - 11 */
		/* FALLTHROUGH */
	case 6:					/* dd */
		lt->tm_mday = ATOI2(p);
		if ((lt->tm_mday > 31) || !lt->tm_mday)
			badformat();
		/* FALLTHROUGH */
	case 4:					/* HH */
		lt->tm_hour = ATOI2(p);
		if (lt->tm_hour > 23)
			badformat();
		/* FALLTHROUGH */
	case 2:					/* MM */
		lt->tm_min = ATOI2(p);
		if (lt->tm_min > 59)
			badformat();
		break;
	default:
		badformat();
	}

	/* convert broken-down time to UTC clock time */
	if ((tval = mktime(lt)) < 0)
		errx(1, "specified date is outside allowed range");

	/* set the time */
	if (slidetime) {
		struct timeval tv_current;

		if (gettimeofday(&tv_current, NULL) == -1)
			err(1, "Could not get local time of day");

		tv.tv_sec = tval - tv_current.tv_sec;
		tv.tv_usec = 0;
		if (adjtime(&tv, NULL) == -1)
			errx(1, "adjtime");
	} else {
		tv.tv_sec = tval;
		tv.tv_usec = 0;
		if (settimeofday(&tv, NULL))
			err(1, "settimeofday");
	}

	if ((pc = getlogin()) == NULL)
		pc = "???";
	syslog(LOG_AUTH | LOG_NOTICE, "date set by %s", pc);
}
Exemple #22
0
int set_adj_time(const struct timeval *delta, struct timeval *olddelta)
{
  return adjtime(delta, olddelta);
}
Exemple #23
0
void test_adjtime(void)
{
  int                sc;
  rtems_status_code  status;
  struct timeval     delta;
  struct timeval     olddelta;
  rtems_time_of_day *the_tod;
  rtems_time_of_day  tod;
  rtems_interval     ticks;

  the_tod = &Dates[0];

  print_time( "rtems_clock_set          ", the_tod, "\n" );
  status = rtems_clock_set( the_tod );
  rtems_test_assert( !status );

  delta.tv_sec = 0;
  delta.tv_usec = 0;
  olddelta.tv_sec = 0;
  olddelta.tv_usec = 0;

  puts( "adjtime - NULL delta - EINVAL" );
  sc = adjtime( NULL, &olddelta );
  rtems_test_assert( sc == -1 );
  rtems_test_assert( errno == EINVAL );

  puts( "adjtime - delta out of range - EINVAL" );
  delta.tv_usec = 1000000000; /* 100 seconds worth */
  sc = adjtime( &delta, &olddelta );
  rtems_test_assert( sc == -1 );
  rtems_test_assert( errno == EINVAL );

  puts( "adjtime - delta too small - do nothing" );
  delta.tv_sec = 0;
  delta.tv_usec = 1;
  sc = adjtime( &delta, &olddelta );
  rtems_test_assert( sc == 0 );

  puts( "adjtime - delta too small - do nothing, olddelta=NULL" );
  sc = adjtime( &delta, NULL );
  rtems_test_assert( sc == 0 );

  puts( "adjtime - delta of one second forward, olddelta=NULL" );
  delta.tv_sec = 1;
  delta.tv_usec = 0;
  sc = adjtime( &delta, NULL );
  rtems_test_assert( sc == 0 );

  puts( "adjtime - delta of one second forward" );
  delta.tv_sec = 1;
  delta.tv_usec = 0;
  sc = adjtime( &delta, &olddelta );
  rtems_test_assert( sc == 0 );

  puts( "adjtime - delta of almost two seconds forward" );
  delta.tv_sec = 1;
  delta.tv_usec = 1000000 - 1;
  sc = adjtime( &delta, &olddelta );
  rtems_test_assert( sc == 0 );

  /*
   * spin until over 1/2 of the way to the
   */
  ticks = rtems_clock_get_ticks_per_second();
  rtems_test_assert( ticks );
  ticks /= 2;
  do {
    status = rtems_clock_get_tod( &tod );
    rtems_test_assert( !status );
  } while ( tod.ticks <= ticks );

  puts( "adjtime - delta of almost one second forward which bumps second" );
  delta.tv_sec = 0;
  delta.tv_usec = 1000000 - 1;
  sc = adjtime( &delta, &olddelta );
  rtems_test_assert( sc == 0 );

  status = rtems_clock_get_tod( &tod );
  rtems_test_assert( !status );
  print_time( "rtems_clock_get_tod          ", &tod, "\n" );
}
Exemple #24
0
int
main(int argc, char **argv)
{
	struct tm *tp, tm;
	struct timeval tv;
	char *fmt;
	char *fmtbuf;
	int c, aflag = 0, illflag = 0;
	struct timespec ts;

	(void) setlocale(LC_ALL, "");

#if !defined(TEXT_DOMAIN)
#define	TEXT_DOMAIN "SYS_TEST"
#endif
	(void) textdomain(TEXT_DOMAIN);

	while ((c = getopt(argc, argv, "a:uR")) != EOF)
		switch (c) {
		case 'a':
			aflag++;
			if (get_adj(optarg, &tv) < 0) {
				(void) fprintf(stderr,
				    gettext("date: invalid argument -- %s\n"),
				    optarg);
				illflag++;
			}
			break;
		case 'u':
			uflag++;
			break;
		case 'R':
			Rflag++;
			break;
		default:
			illflag++;
		}

	argc -= optind;
	argv  = &argv[optind];

	/* -a is mutually exclusive with -u and -R */
	if (uflag && aflag)
		illflag++;
	if (Rflag && aflag)
		illflag++;

	if (illflag) {
		(void) fprintf(stderr, gettext(usage));
		exit(1);
	}

	if (clock_gettime(CLOCK_REALTIME, &ts) != 0) {
		perror(gettext("data: Failed to obtain system time"));
		exit(1);
	}
	clock_val = ts.tv_sec;

	if (aflag) {
		if (adjtime(&tv, 0) < 0) {
			perror(gettext("date: Failed to adjust date"));
			exit(1);
		}
		exit(0);
	}

	if (argc > 0) {
		if (*argv[0] == '+')
			fmt = &argv[0][1];
		else {
			if (setdate(localtime(&clock_val), argv[0])) {
				(void) fprintf(stderr, gettext(usage));
				exit(1);
			}
			fmt = nl_langinfo(_DATE_FMT);
		}
	} else if (Rflag) {
		fmt = "%a, %d %h %Y %H:%M:%S %z";
	} else
		fmt = nl_langinfo(_DATE_FMT);

	fmtbuf = fmt_extensions(fmt, &ts);

	if (uflag) {
		(void) putenv("TZ=GMT0");
		tzset();
		tp = gmtime(&clock_val);
	} else
		tp = localtime(&clock_val);
	(void) memcpy(&tm, tp, sizeof (struct tm));
	(void) strftime(buf, BUFSIZ, fmtbuf, &tm);

	(void) puts(buf);

	return (0);
}
/**
 * Try adjust the time using adjtime or similar.
 *
 * @returns true on success, false on failure.
 *
 * @param   pDrift          The time adjustment.
 */
static bool vgsvcTimeSyncAdjust(PCRTTIMESPEC pDrift)
{
#ifdef RT_OS_WINDOWS
/** @todo r=bird: g_hTokenProcess cannot be NULL here.
 *        vgsvcTimeSyncInit will fail and the service will not be started with
 *        it being NULL.  vgsvcTimeSyncInit OTOH will *NOT* be called until the
 *        service thread has terminated.  If anything
 *        else is the case, there is buggy code somewhere.*/
    if (g_hTokenProcess == NULL) /* Is the token already closed when shutting down? */
        return false;

    DWORD dwWinTimeAdjustment, dwWinNewTimeAdjustment, dwWinTimeIncrement;
    BOOL  fWinTimeAdjustmentDisabled;
    if (GetSystemTimeAdjustment(&dwWinTimeAdjustment, &dwWinTimeIncrement, &fWinTimeAdjustmentDisabled))
    {
        DWORD dwDiffMax = g_dwWinTimeAdjustment * 0.50;
        DWORD dwDiffNew =   dwWinTimeAdjustment * 0.10;

        if (RTTimeSpecGetMilli(pDrift) > 0)
        {
            dwWinNewTimeAdjustment = dwWinTimeAdjustment + dwDiffNew;
            if (dwWinNewTimeAdjustment > (g_dwWinTimeAdjustment + dwDiffMax))
            {
                dwWinNewTimeAdjustment = g_dwWinTimeAdjustment + dwDiffMax;
                dwDiffNew = dwDiffMax;
            }
        }
        else
        {
            dwWinNewTimeAdjustment = dwWinTimeAdjustment - dwDiffNew;
            if (dwWinNewTimeAdjustment < (g_dwWinTimeAdjustment - dwDiffMax))
            {
                dwWinNewTimeAdjustment = g_dwWinTimeAdjustment - dwDiffMax;
                dwDiffNew = dwDiffMax;
            }
        }

        VGSvcVerbose(3, "vgsvcTimeSyncAdjust: Drift=%lldms\n", RTTimeSpecGetMilli(pDrift));
        VGSvcVerbose(3, "vgsvcTimeSyncAdjust: OrgTA=%ld, CurTA=%ld, NewTA=%ld, DiffNew=%ld, DiffMax=%ld\n",
                     g_dwWinTimeAdjustment, dwWinTimeAdjustment, dwWinNewTimeAdjustment, dwDiffNew, dwDiffMax);
        if (SetSystemTimeAdjustment(dwWinNewTimeAdjustment, FALSE /* Periodic adjustments enabled. */))
        {
            g_cTimeSyncErrors = 0;
            return true;
        }

        if (g_cTimeSyncErrors++ < 10)
             VGSvcError("vgsvcTimeSyncAdjust: SetSystemTimeAdjustment failed, error=%u\n", GetLastError());
    }
    else if (g_cTimeSyncErrors++ < 10)
        VGSvcError("vgsvcTimeSyncAdjust: GetSystemTimeAdjustment failed, error=%ld\n", GetLastError());

#elif defined(RT_OS_OS2) || defined(RT_OS_HAIKU)
    /* No API for doing gradual time adjustments. */

#else /* PORTME */
    /*
     * Try use adjtime(), most unix-like systems have this.
     */
    struct timeval tv;
    RTTimeSpecGetTimeval(pDrift, &tv);
    if (adjtime(&tv, NULL) == 0)
    {
        if (g_cVerbosity >= 1)
            VGSvcVerbose(1, "vgsvcTimeSyncAdjust: adjtime by %RDtimespec\n", pDrift);
        g_cTimeSyncErrors = 0;
        return true;
    }
#endif

    /* failed */
    return false;
}
Exemple #26
0
int
main(const int argc, char *argv[])
{
	register const char *	format;
	register const char *	value;
	register const char *	cp;
	register int		ch;
	register int		dousg;
	register int		aflag = 0;
	register int		dflag = 0;
	register int		nflag = 0;
	register int		tflag = 0;
	register int		minuteswest;
	register int		dsttime;
	register double		adjust;
	time_t			now;
	time_t			t;

	INITIALIZE(dousg);
	INITIALIZE(minuteswest);
	INITIALIZE(dsttime);
	INITIALIZE(adjust);
	INITIALIZE(t);
#ifdef LC_ALL
	(void) setlocale(LC_ALL, "");
#endif /* defined(LC_ALL) */
#if HAVE_GETTEXT
#ifdef TZ_DOMAINDIR
	(void) bindtextdomain(TZ_DOMAIN, TZ_DOMAINDIR);
#endif /* defined(TEXTDOMAINDIR) */
	(void) textdomain(TZ_DOMAIN);
#endif /* HAVE_GETTEXT */
	(void) time(&now);
	format = value = NULL;
	while ((ch = getopt(argc, argv, "ucnd:t:a:")) != EOF && ch != -1) {
		switch (ch) {
		default:
			usage();
		case 'u':		/* do it in UTC */
		case 'c':
			dogmt();
			break;
		case 'n':		/* don't set network */
			nflag = 1;
			break;
		case 'd':		/* daylight saving time */
			if (dflag) {
				(void) fprintf(stderr,
					_("date: error: multiple -d's used"));
				usage();
			}
			dflag = 1;
			cp = optarg;
			dsttime = atoi(cp);
			if (*cp == '\0' || *nondigit(cp) != '\0')
				wildinput(_("-t value"), optarg,
					_("must be a non-negative number"));
			break;
		case 't':		/* minutes west of UTC */
			if (tflag) {
				(void) fprintf(stderr,
					_("date: error: multiple -t's used"));
				usage();
			}
			tflag = 1;
			cp = optarg;
			minuteswest = atoi(cp);
			if (*cp == '+' || *cp == '-')
				++cp;
			if (*cp == '\0' || *nondigit(cp) != '\0')
				wildinput(_("-d value"), optarg,
					_("must be a number"));
			break;
		case 'a':		/* adjustment */
			if (aflag) {
				(void) fprintf(stderr,
					_("date: error: multiple -a's used"));
				usage();
			}
			aflag = 1;
			cp = optarg;
			adjust = atof(cp);
			if (*cp == '+' || *cp == '-')
				++cp;
			if (*cp == '\0' || strcmp(cp, ".") == 0)
				wildinput(_("-a value"), optarg,
					_("must be a number"));
			cp = nondigit(cp);
			if (*cp == '.')
				++cp;
			if (*nondigit(cp) != '\0')
				wildinput(_("-a value"), optarg,
					_("must be a number"));
			break;
		}
	}
	while (optind < argc) {
		cp = argv[optind++];
		if (*cp == '+')
			if (format == NULL)
				format = cp + 1;
			else {
				(void) fprintf(stderr,
_("date: error: multiple formats in command line\n"));
				usage();
			}
		else	if (value == NULL)
				value = cp;
			else {
				(void) fprintf(stderr,
_("date: error: multiple values in command line\n"));
				usage();
			}
	}
	if (value != NULL) {
		/*
		** This order ensures that "reasonable" twelve-digit inputs
		** (such as 120203042006) won't be misinterpreted
		** even if time_t's range all the way back to the thirteenth
		** century.  Do not change the order.
		*/
		t = convert(value, (dousg = TRUE), now);
		if (t == -1)
			t = convert(value, (dousg = FALSE), now);
		if (t == -1) {
			/*
			** Out of range values,
			** or time that falls in a DST transition hole?
			*/
			if ((cp = strchr(value, '.')) != NULL) {
				/*
				** Ensure that the failure of
				**	TZ=America/New_York date 8712312359.60
				** doesn't get misdiagnosed.  (It was
				**	TZ=America/New_York date 8712311859.60
				** when the leap second was inserted.)
				** The normal check won't work since
				** the given time is valid in UTC.
				*/
				if (atoi(cp + 1) >= SECSPERMIN)
					wildinput(_("time"), value,
					    _("out of range seconds given"));
			}
			dogmt();
			t = convert(value, FALSE, now);
			if (t == -1)
				t = convert(value, TRUE, now);
			wildinput(_("time"), value,
				(t == -1) ?
				_("out of range value given") :
				_("time skipped when clock springs forward"));
		}
	}
	/*
	** Entire command line has now been checked.
	*/
	if (aflag) {
#if HAVE_ADJTIME
		struct timeval	tv;

		tv.tv_sec = (int) adjust;
		tv.tv_usec = (int) ((adjust - tv.tv_sec) * 1000000L);
		if (adjtime(&tv, NULL) != 0)
			oops("adjtime");
#endif /* HAVE_ADJTIME */
#if !HAVE_ADJTIME
		reset(now + adjust, nflag);
#endif /* !HAVE_ADJTIME */
		/*
		** Sun silently ignores everything else; we follow suit.
		*/
		exit(retval);
	}
	if (dflag || tflag) {
#if HAVE_SETTIMEOFDAY == 2
		struct timezone	tz;

		if (!dflag || !tflag)
			if (gettimeofday(NULL, &tz) != 0)
				oops("gettimeofday");
		if (dflag)
			tz.tz_dsttime = dsttime;
		if (tflag)
			tz.tz_minuteswest = minuteswest;
		if (settimeofday(NULL, &tz) != 0)
			oops("settimeofday");
#endif /* HAVE_SETTIMEOFDAY == 2 */
#if HAVE_SETTIMEOFDAY != 2
		(void) fprintf(stderr,
_("date: warning: kernel doesn't keep -d/-t information, option ignored\n"));
#endif /* HAVE_SETTIMEOFDAY != 2 */
	}

	if (value == NULL)
		display(format);

	reset(t, nflag);

	checkfinal(value, dousg, t, now);

#ifdef EBUG
	{
		struct tm	tm;

		tm = *localtime(&t);
		timeout(stdout, "%c\n", &tm);
		exit(retval);
	}
#endif /* defined EBUG */

	display(format);

	/* gcc -Wall pacifier */
	for ( ; ; )
		continue;
}
void eDVBLocalTimeHandler::updateTime( time_t tp_time, eDVBChannel *chan, int update_count )
{
	int time_difference;
	bool restart_tdt = false;
	if (!tp_time)
		restart_tdt = true;
	else if (tp_time == -1)
	{
		restart_tdt = true;

		eDebug("[eDVBLocalTimerHandler] no transponder tuned... or no TDT/TOT avail .. try to use RTC :)");
		time_t rtc_time = getRTC();
		if (rtc_time) // RTC Ready?
		{
			tm now;

			localtime_r(&rtc_time, &now);
			eDebug("[eDVBLocalTimerHandler] RTC time is %02d:%02d:%02d", now.tm_hour, now.tm_min, now.tm_sec);
			time_t linuxTime=time(0);
			localtime_r(&linuxTime, &now);
			eDebug("[eDVBLocalTimerHandler] Receiver time is %02d:%02d:%02d", now.tm_hour, now.tm_min, now.tm_sec);
			time_difference = rtc_time - linuxTime;
			eDebug("[eDVBLocalTimerHandler] RTC to Receiver time difference is %ld seconds", linuxTime - rtc_time );

			if (time_difference)
			{
				if ((time_difference >= -15) && (time_difference <= 15))
				{
					timeval tdelta, tolddelta;

					// Slew small diffs ...
					// Even good transponders can differ by 0-5 sec, if we would step these
					// the system clock would permanentely jump around when zapping.

					tdelta.tv_sec = time_difference;

					if(adjtime(&tdelta, &tolddelta) == 0)
						eDebug("[eDVBLocalTimerHandler] slewing Linux Time by %03d seconds", time_difference);
					else
						eDebug("[eDVBLocalTimerHandler] slewing Linux Time by %03d seconds FAILED", time_difference);
				}
				else
				{
					timeval tnow;

					// ... only step larger diffs

					gettimeofday(&tnow, 0);
					tnow.tv_sec = rtc_time;
					settimeofday(&tnow, 0);
					linuxTime = time(0);
					localtime_r(&linuxTime, &now);
					eDebug("[eDVBLocalTimerHandler] stepped Linux Time to %02d:%02d:%02d", now.tm_hour, now.tm_min, now.tm_sec);
				}
			}
			else if ( !time_difference )
				eDebug("[eDVBLocalTimerHandler] no change needed");
			else
				eDebug("[eDVBLocalTimerHandler] set to RTC time");
			/*emit*/ m_timeUpdated();
		}
		else
			eDebug("[eDVBLocalTimerHandler]    getRTC returned time=0. RTC problem?");
	}
	else
	{
		std::map< eDVBChannelID, int >::iterator it( m_timeOffsetMap.find( chan->getChannelID() ) );

 // current linux time
		time_t linuxTime = time(0);

	// difference between current enigma time and transponder time
		int enigma_diff = tp_time-linuxTime;

		int new_diff=0;

		bool updated = m_time_ready;

		if ( m_time_ready )  // ref time ready?
		{
			// difference between reference time (current enigma time)
			// and the transponder time
			eDebug("[eDVBLocalTimerHandler] diff is %d", enigma_diff);
			if ( abs(enigma_diff) < 120 )
			{
				eDebug("[eDVBLocalTimerHandler] diff < 120 .. use Transponder Time");
				m_timeOffsetMap[chan->getChannelID()] = 0;
				new_diff = enigma_diff;
			}
			else if ( it != m_timeOffsetMap.end() ) // correction saved?
			{
				eDebug("[eDVBLocalTimerHandler] we have correction %d", it->second);
				time_t CorrectedTpTime = tp_time+it->second;
				int ddiff = CorrectedTpTime-linuxTime;
				eDebug("[eDVBLocalTimerHandler] diff after add correction is %d", ddiff);
				if ( abs(it->second) < 300 ) // stored correction < 5 min
				{
					eDebug("[eDVBLocalTimerHandler] use stored correction(<5 min)");
					new_diff = ddiff;
				}
				else if ( getRTC() )
				{
					time_t rtc=getRTC();
					m_timeOffsetMap[chan->getChannelID()] = rtc-tp_time;
					new_diff = rtc-linuxTime;  // set enigma time to rtc
					eDebug("[eDVBLocalTimerHandler] update stored correction to %ld (calced against RTC time)", rtc-tp_time );
				}
				else if ( abs(ddiff) <= 120 )
				{
// with stored correction calced time difference is lower 2 min
// this don't help when a transponder have a clock running to slow or to fast
// then its better to have a DM7020 with always running RTC
					eDebug("[eDVBLocalTimerHandler] use stored correction(corr < 2 min)");
					new_diff = ddiff;
				}
				else  // big change in calced correction.. hold current time and update correction
				{
					eDebug("[eDVBLocalTimerHandler] update stored correction to %d", -enigma_diff);
					m_timeOffsetMap[chan->getChannelID()] = -enigma_diff;
				}
			}
			else
			{
				eDebug("[eDVBLocalTimerHandler] no correction found... store calced correction(%d)",-enigma_diff);
				m_timeOffsetMap[chan->getChannelID()] = -enigma_diff;
			}
		}
		else  // no time setted yet
		{
			if ( it != m_timeOffsetMap.end() )
			{
				enigma_diff += it->second;
				eDebug("[eDVBLocalTimerHandler] we have correction (%d)... use", it->second );
			}
			else
				eDebug("[eDVBLocalTimerHandler] dont have correction.. set Transponder Diff");
			new_diff=enigma_diff;
			m_time_ready=true;
		}

		time_t t = linuxTime+new_diff;
		m_last_tp_time_difference=tp_time-t;

		if (!new_diff &&
			updated) // overrride this check on first received TDT
		{
			eDebug("[eDVBLocalTimerHandler] not changed");
			return;
		}

		if ( !update_count )
		{
			// set rtc to calced transponder time when the first tdt is received on this
			// transponder
			setRTC(t);
			eDebug("[eDVBLocalTimerHandler] update RTC");
		}
		else if (getRTC())
		{
			if (abs(getRTC() - t) > 60)
			{
				eDebug("[eDVBLocalTimerHandler] difference between new linux time and RTC time is > 60 sec... transponder time looks not ok... use rtc time");
				t = getRTC();
			}
			else
				eDebug("[eDVBLocalTimerHandler] difference between linux time and RTC time is < 60 sec... so the transponder time looks ok");
		}
		else
			eDebug("[eDVBLocalTimerHandler] no RTC available :(");

		tm now;
		localtime_r(&t, &now);
		eDebug("[eDVBLocalTimerHandler] time update to %02d:%02d:%02d",
			now.tm_hour,
			now.tm_min,
			now.tm_sec);

		time_difference = t - linuxTime;   // calc our new linux_time -> enigma_time correction
		eDebug("[eDVBLocalTimerHandler] m_time_difference is %d", time_difference );

		if ( time_difference )
		{
			eDebug("[eDVBLocalTimerHandler] set Linux Time");
			timeval tnow;
			gettimeofday(&tnow,0);
			tnow.tv_sec=t;
			settimeofday(&tnow,0);
		}

 		 /*emit*/ m_timeUpdated();
	}

	if ( restart_tdt )
	{
		std::map<iDVBChannel*, channel_data>::iterator it =
			m_knownChannels.find(chan);
		if ( it != m_knownChannels.end() )
		{
			int system = iDVBFrontend::feSatellite;
			ePtr<iDVBFrontendParameters> parms;
			chan->getCurrentFrontendParameters(parms);
			if (parms)
			{
				parms->getSystem(system);
			}

			int updateCount = it->second.timetable->getUpdateCount();
			it->second.timetable = NULL;

			if (system == iDVBFrontend::feATSC)
			{
				it->second.timetable = new STT(chan, updateCount);
			}
			else
			{
				it->second.timetable = new TDT(chan, updateCount);
			}
			it->second.timetable->startTimer(TIME_UPDATE_INTERVAL); // restart TDT for this transponder in 30min
		}
	}
}
Exemple #28
0
int				/* 0 okay, 1 error */
adj_systime(
	double now		/* adjustment (s) */
	)
{
	struct timeval adjtv;	/* new adjustment */
	struct timeval oadjtv;	/* residual adjustment */
	double	quant;		/* quantize to multiples of */
	double	dtemp;
	long	ticks;
	int	isneg = 0;

	/*
	 * The Windows port adj_systime() depends on being called each
	 * second even when there's no additional correction, to allow
	 * emulation of adjtime() behavior on top of an API that simply
	 * sets the current rate.  This POSIX implementation needs to
	 * ignore invocations with zero correction, otherwise ongoing
	 * EVNT_NSET adjtime() can be aborted by a tiny adjtime()
	 * triggered by sys_residual.
	 */
	if (0. == now)
		return TRUE;

	/*
	 * Most Unix adjtime() implementations adjust the system clock
	 * in microsecond quanta, but some adjust in 10-ms quanta. We
	 * carefully round the adjustment to the nearest quantum, then
	 * adjust in quanta and keep the residue for later.
	 */
	dtemp = now + sys_residual;
	if (dtemp < 0) {
		isneg = 1;
		dtemp = -dtemp;
	}
	adjtv.tv_sec = (long)dtemp;
	dtemp -= adjtv.tv_sec;
	if (sys_tick > sys_fuzz)
		quant = sys_tick;
	else
		quant = 1e-6;
	ticks = (long)(dtemp / quant + .5);
	adjtv.tv_usec = (long)(ticks * quant * 1e6);
	dtemp -= adjtv.tv_usec / 1e6;
	sys_residual = dtemp;

	/*
	 * Convert to signed seconds and microseconds for the Unix
	 * adjtime() system call. Note we purposely lose the adjtime()
	 * leftover.
	 */
	if (isneg) {
		adjtv.tv_sec = -adjtv.tv_sec;
		adjtv.tv_usec = -adjtv.tv_usec;
		sys_residual = -sys_residual;
	}
	if (adjtv.tv_sec != 0 || adjtv.tv_usec != 0) {
		if (adjtime(&adjtv, &oadjtv) < 0) {
			msyslog(LOG_ERR, "adj_systime: %m");
			return FALSE;
		}
	}
	return TRUE;
}
Exemple #29
0
/*
 * The timedaemons synchronize the clocks of hosts in a local area network.
 * One daemon runs as master, all the others as slaves. The master
 * performs the task of computing clock differences and sends correction
 * values to the slaves.
 * Slaves start an election to choose a new master when the latter disappears
 * because of a machine crash, network partition, or when killed.
 * A resolution protocol is used to kill all but one of the masters
 * that happen to exist in segments of a partitioned network when the
 * network partition is fixed.
 *
 * Authors: Riccardo Gusella & Stefano Zatti
 *
 * overhauled at Silicon Graphics
 */
int
main(int argc, char *argv[])
{
	int on;
	int ret;
	int nflag, iflag;
	struct timeval ntime;
	struct servent *srvp;
	char buf[BUFSIZ], *cp, *cplim;
	struct ifconf ifc;
	struct ifreq ifreq, ifreqf, *ifr;
	register struct netinfo *ntp;
	struct netinfo *ntip;
	struct netinfo *savefromnet;
	struct netent *nentp;
	struct nets *nt;
	struct sockaddr_in server;
	u_short port;
	int c;

#ifdef lint
	ntip = NULL;
#endif

	on = 1;
	nflag = OFF;
	iflag = OFF;


	opterr = 0;
	while ((c = getopt(argc, argv, "Mtdn:i:F:G:P:")) != -1) {
		switch (c) {
		case 'M':
			Mflag = 1;
			break;

		case 't':
			trace = 1;
			break;

		case 'n':
			if (iflag) {
				errx(1, "-i and -n make no sense together");
			} else {
				nflag = ON;
				addnetname(optarg);
			}
			break;

		case 'i':
			if (nflag) {
				errx(1, "-i and -n make no sense together");
			} else {
				iflag = ON;
				addnetname(optarg);
			}
			break;

		case 'F':
			add_good_host(optarg,1);
			while (optind < argc && argv[optind][0] != '-')
				add_good_host(argv[optind++], 1);
			break;

		case 'd':
			debug = 1;
			break;
		case 'G':
			if (goodgroup != NULL)
				errx(1, "only one net group");
			goodgroup = optarg;
			break;

		default:
			usage();
			break;
		}
	}
	if (optind < argc)
		usage();

	/* If we care about which machine is the master, then we must
	 *	be willing to be a master
	 */
	if (goodgroup != NULL || goodhosts != NULL)
		Mflag = 1;

	if (gethostname(hostname, sizeof(hostname) - 1) < 0)
		err(1, "gethostname");
	self.l_bak = &self;
	self.l_fwd = &self;
	self.h_bak = &self;
	self.h_fwd = &self;
	self.head = 1;
	self.good = 1;

	if (goodhosts != NULL)		/* trust ourself */
		add_good_host(hostname,1);

	srvp = getservbyname("timed", "udp");
	if (srvp == NULL)
		errx(1, "timed/udp: unknown service");
	port = srvp->s_port;
	bzero(&server, sizeof(struct sockaddr_in));
	server.sin_port = srvp->s_port;
	server.sin_family = AF_INET;
	sock = socket(AF_INET, SOCK_DGRAM, 0);
	if (sock < 0)
		err(1, "socket");
	if (setsockopt(sock, SOL_SOCKET, SO_BROADCAST, (char *)&on,
							sizeof(on)) < 0)
		err(1, "setsockopt");
	if (bind(sock, (struct sockaddr*)&server, sizeof(server))) {
		if (errno == EADDRINUSE)
			warnx("time daemon already running");
		else
			warn("bind");
		exit(1);
	}

	sequence = arc4random();     /* initial seq number */

	(void)gettimeofday(&ntime, NULL);
	/* rounds kernel variable time to multiple of 5 ms. */
	ntime.tv_sec = 0;
	ntime.tv_usec = -((ntime.tv_usec/1000) % 5) * 1000;
	(void)adjtime(&ntime, (struct timeval *)0);

	for (nt = nets; nt; nt = nt->next) {
		nentp = getnetbyname(nt->name);
		if (nentp == NULL) {
			nt->net = inet_network(nt->name);
			if (nt->net != INADDR_NONE)
				nentp = getnetbyaddr(nt->net, AF_INET);
		}
		if (nentp != NULL) {
			nt->net = nentp->n_net;
		} else if (nt->net == INADDR_NONE) {
			errx(1, "unknown net %s", nt->name);
		} else if (nt->net == INADDR_ANY) {
			errx(1, "bad net %s", nt->name);
		} else {
			warnx("warning: %s unknown in /etc/networks",
				nt->name);
		}

		if (0 == (nt->net & 0xff000000))
		    nt->net <<= 8;
		if (0 == (nt->net & 0xff000000))
		    nt->net <<= 8;
		if (0 == (nt->net & 0xff000000))
		    nt->net <<= 8;
	}
	ifc.ifc_len = sizeof(buf);
	ifc.ifc_buf = buf;
	if (ioctl(sock, SIOCGIFCONF, (char *)&ifc) < 0)
		err(1, "get interface configuration");
	ntp = NULL;
#define size(p)	max((p).sa_len, sizeof(p))
	cplim = buf + ifc.ifc_len; /*skip over if's with big ifr_addr's */
	for (cp = buf; cp < cplim;
			cp += sizeof (ifr->ifr_name) + size(ifr->ifr_addr)) {
		ifr = (struct ifreq *)cp;
		if (ifr->ifr_addr.sa_family != AF_INET)
			continue;
		if (!ntp)
			ntp = (struct netinfo*)malloc(sizeof(struct netinfo));
		bzero(ntp,sizeof(*ntp));
		ntp->my_addr=((struct sockaddr_in *)&ifr->ifr_addr)->sin_addr;
		ntp->status = NOMASTER;
		ifreq = *ifr;
		ifreqf = *ifr;

		if (ioctl(sock, SIOCGIFFLAGS, (char *)&ifreqf) < 0) {
			warn("get interface flags");
			continue;
		}
		if ((ifreqf.ifr_flags & IFF_UP) == 0)
			continue;
		if ((ifreqf.ifr_flags & IFF_BROADCAST) == 0 &&
		    (ifreqf.ifr_flags & IFF_POINTOPOINT) == 0) {
			continue;
		}


		if (ioctl(sock, SIOCGIFNETMASK, (char *)&ifreq) < 0) {
			warn("get netmask");
			continue;
		}
		ntp->mask = ((struct sockaddr_in *)
			&ifreq.ifr_addr)->sin_addr.s_addr;

		if (ifreqf.ifr_flags & IFF_BROADCAST) {
			if (ioctl(sock, SIOCGIFBRDADDR, (char *)&ifreq) < 0) {
				warn("get broadaddr");
				continue;
			}
			ntp->dest_addr = *(struct sockaddr_in *)&ifreq.ifr_broadaddr;
			/* What if the broadcast address is all ones?
			 * So we cannot just mask ntp->dest_addr.  */
			ntp->net = ntp->my_addr;
			ntp->net.s_addr &= ntp->mask;
		} else {
			if (ioctl(sock, SIOCGIFDSTADDR,
						(char *)&ifreq) < 0) {
				warn("get destaddr");
				continue;
			}
			ntp->dest_addr = *(struct sockaddr_in *)&ifreq.ifr_dstaddr;
			ntp->net = ntp->dest_addr.sin_addr;
		}

		ntp->dest_addr.sin_port = port;

		for (nt = nets; nt; nt = nt->next) {
			if (ntp->net.s_addr == htonl(nt->net))
				break;
		}
		if ((nflag && !nt) || (iflag && nt))
			continue;

		ntp->next = NULL;
		if (nettab == NULL) {
			nettab = ntp;
		} else {
			ntip->next = ntp;
		}
		ntip = ntp;
		ntp = NULL;
	}
	if (ntp)
		(void) free((char *)ntp);
	if (nettab == NULL)
		errx(1, "no network usable");

	/* microseconds to delay before responding to a broadcast */
	delay1 = casual(1, 100*1000);

	/* election timer delay in secs. */
	delay2 = casual(MINTOUT, MAXTOUT);

	if (!debug)
		daemon(debug, 0);

	if (trace)
		traceon();
	openlog("timed", LOG_CONS|LOG_PID, LOG_DAEMON);

	/*
	 * keep returning here
	 */
	ret = setjmp(jmpenv);
	savefromnet = fromnet;
	setstatus();

	if (Mflag) {
		switch (ret) {

		case 0:
			checkignorednets();
			pickslavenet(0);
			break;
		case 1:
			/* Just lost our master */
			if (slavenet != NULL)
				slavenet->status = election(slavenet);
			if (!slavenet || slavenet->status == MASTER) {
				checkignorednets();
				pickslavenet(0);
			} else {
				makeslave(slavenet);	/* prune extras */
			}
			break;

		case 2:
			/* Just been told to quit */
			justquit = 1;
			pickslavenet(savefromnet);
			break;
		}

		setstatus();
		if (!(status & MASTER) && sock_raw != -1) {
			/* sock_raw is not being used now */
			(void)close(sock_raw);
			sock_raw = -1;
		}

		if (status == MASTER)
			master();
		else
			slave();

	} else {
		if (sock_raw != -1) {
			(void)close(sock_raw);
			sock_raw = -1;
		}

		if (ret) {
			/* we just lost our master or were told to quit */
			justquit = 1;
		}
		for (ntp = nettab; ntp != NULL; ntp = ntp->next) {
			if (ntp->status == MASTER) {
				rmnetmachs(ntp);
				ntp->status = NOMASTER;
			}
		}
		checkignorednets();
		pickslavenet(0);
		setstatus();

		slave();
	}
	/* NOTREACHED */
	return(0);
}
Exemple #30
0
void *POSIX_Init(
  void *argument
)
{
  unsigned int      remaining;
  int               sc;
  struct sigaction  act;
  sigset_t          mask;
  struct timeval    delta;

  TEST_BEGIN();

  /* install a signal handler for SIGALRM and unblock it */

  sc = sigemptyset( &act.sa_mask );
  rtems_test_assert( !sc );

  act.sa_handler = Signal_handler;
  act.sa_flags   = 0;

  sigaction( SIGALRM, &act, NULL );

  sc = sigemptyset( &mask );
  rtems_test_assert( !sc );

  sc = sigaddset( &mask, SIGALRM );
  rtems_test_assert( !sc );

  puts( "Init: Unblock SIGALRM" );
  sc = sigprocmask( SIG_UNBLOCK, &mask, NULL );
  rtems_test_assert( !sc );

  /* schedule the alarm */

  puts( "Init: Firing alarm in 1 second" );
  remaining = alarm( 1 );
  printf( "Init: %d seconds left on previous alarm\n", sc );
  rtems_test_assert( !sc );

  puts( "Init: Wait for alarm" );
  sleep( 2 );

  rtems_test_assert( Signal_count == 1 );

  puts( "Init: Cancel alarm" );
  remaining = alarm( 0 );
  printf( "Init: %d seconds left on previous alarm\n", remaining );
  rtems_test_assert( remaining == 0 );

  remaining = alarm( 1 );
  rtems_test_assert( remaining == 0 );

  delta.tv_sec = 2;
  delta.tv_usec = 0;
  sc = adjtime( &delta, NULL );
  rtems_test_assert( sc == 0 );

  rtems_test_assert( Signal_count == 1 );

  remaining = alarm( 0 );
  rtems_test_assert( remaining == 1 );

  TEST_END();
  rtems_test_exit( 0 );

  return NULL; /* just so the compiler thinks we returned something */
}