Example #1
0
/*
 * Read the current time from the clock chip and convert to UNIX form.
 * Assumes that the year in the clock chip is valid.
 * Must be called with tod_lock held.
 */
static timestruc_t
todbq4802_get(void)
{
	timestruc_t ts;
	todinfo_t tod;
	struct rtc_t rtc;

	ASSERT(MUTEX_HELD(&tod_lock));

	read_rtc(&rtc);
	DPRINTF("todbq4802_get: century=%d year=%d dom=%d hrs=%d min=%d"
	    " sec=%d\n", rtc.rtc_century, rtc.rtc_year, rtc.rtc_dom,
	    rtc.rtc_hrs, rtc.rtc_min, rtc.rtc_sec);

	/*
	 * tod_year is base 1900 so this code needs to adjust the true
	 * year retrieved from the rtc's century and year fields.
	 */
	tod.tod_year	= rtc.rtc_year + (rtc.rtc_century * 100) - 1900;
	tod.tod_month	= rtc.rtc_mon;
	tod.tod_day	= rtc.rtc_dom;
	tod.tod_dow	= rtc.rtc_dow;
	tod.tod_hour	= rtc.rtc_hrs;
	tod.tod_min	= rtc.rtc_min;
	tod.tod_sec	= rtc.rtc_sec;

	ts.tv_sec = tod_to_utc(tod);
	ts.tv_nsec = 0;
	return (ts);
}
/*
 * Read the current time from the clock chip and convert to UNIX form.
 * Assumes that the year in the clock chip is valid.
 * Must be called with tod_lock held.
 */
static timestruc_t
todm5819_get(void)
{
	int i;
	timestruc_t ts;
	struct rtc_t rtc;

	ASSERT(MUTEX_HELD(&tod_lock));

	/*
	 * Read from the tod, and if it isnt accessible wait
	 * before retrying.
	 */
	for (i = 0; i < TODM5819_UIP_RETRY_THRESH; i++) {
		if (read_rtc(&rtc))
			break;
		drv_usecwait(TODM5819_UIP_WAIT_USEC);
	}
	if (i == TODM5819_UIP_RETRY_THRESH) {
		/*
		 * We couldnt read from the tod
		 */
		tod_fault_reset();
		return (hrestime);
	}

	DPRINTF("todm5819_get: century=%d year=%d dom=%d hrs=%d\n",
		rtc.rtc_century, rtc.rtc_year, rtc.rtc_dom, rtc.rtc_hrs);

	ts.tv_sec = tod_to_utc(rtc_to_tod(&rtc));
	ts.tv_nsec = 0;
	return (ts);
}
/*
 * Read the current time from the clock chip and convert to UNIX form.
 * Assumes that the year in the clock chip is valid.
 * Must be called with tod_lock held.
 */
static timestruc_t
todds_get(void)
{
	timestruc_t ts;
	todinfo_t tod;
	struct rtc_t rtc;

	ASSERT(MUTEX_HELD(&tod_lock));

	read_rtc(&rtc);
	DPRINTF("todds_get: century=%d year=%d dom=%d hrs=%d\n",
	    rtc.rtc_century, rtc.rtc_year, rtc.rtc_dom, rtc.rtc_hrs);

	/*
	 * tod_year is base 1900 so this code needs to adjust the true
	 * year retrieved from the rtc's century and year fields.
	 */
	tod.tod_year	= rtc.rtc_year + (rtc.rtc_century * 100) - 1900;
	tod.tod_month	= rtc.rtc_mon;
	tod.tod_day	= rtc.rtc_dom;
	tod.tod_dow	= rtc.rtc_dow;
	tod.tod_hour	= rtc.rtc_hrs;
	tod.tod_min	= rtc.rtc_min;
	tod.tod_sec	= rtc.rtc_sec;

	ts.tv_sec = tod_to_utc(tod);
	ts.tv_nsec = 0;

	/* set the hw watchdog timer if it's been activated */
	if (watchdog_activated) {
		int ret = 0;
		ret = tod_ops.tod_set_watchdog_timer(watchdog_timeout_seconds);
		if (ret == 0)
			cmn_err(CE_WARN, "ds1287: failed to set hardware "
			    "watchdog timer.");
	}

	return (ts);
}
Example #4
0
static timestruc_t
todds1307_get(void)
{
    timestruc_t	ts;
    todinfo_t	tod;
    struct	rtc_t	rtc;

    ASSERT(MUTEX_HELD(&tod_lock));

    if (sync_clock_once) {
        todds1307_read_rtc(&soft_rtc);
        sync_clock_once = 0;
    } else {
        tod_fault_reset();
        return (hrestime);
    }

    bcopy(&soft_rtc, &rtc, sizeof (rtc));

    /*
     * 00 - 68 = 2000 thru 2068
     * 69-99 = 1969 thru 1999
     */
    tod.tod_year    = rtc.rtc_year;
    if (rtc.rtc_year <= 68)
        tod.tod_year += 100;
    tod.tod_month	= rtc.rtc_mon;
    tod.tod_day	= rtc.rtc_dom;
    tod.tod_dow	= rtc.rtc_dow;
    tod.tod_hour	= rtc.rtc_hrs;
    tod.tod_min	= rtc.rtc_min;
    tod.tod_sec	= rtc.rtc_sec;

    ts.tv_sec = tod_to_utc(tod);
    ts.tv_nsec = 0;
    return (ts);
}
Example #5
0
static timestruc_t
todxen_get(tod_ops_t *top)
{
	todinfo_t tod;
	timestruc_t ts, wcts;
	shared_info_t *si = HYPERVISOR_shared_info;
	uint32_t xen_wc_version;
	hrtime_t now;

	ASSERT(MUTEX_HELD(&tod_lock));

	/*
	 * Pick up the wallclock base time
	 */
	do {
		xen_wc_version = si->wc_version;

		membar_consumer();

		wcts.tv_sec = si->wc_sec;
		wcts.tv_nsec = si->wc_nsec;

		membar_consumer();

	} while ((si->wc_version & 1) | (xen_wc_version ^ si->wc_version));

	/*
	 * Compute the TOD as the wallclock (boot) time plus time-since-boot
	 * (/not/ hrtime!) and normalize.
	 */
	now = xpv_getsystime() +
	    (hrtime_t)wcts.tv_nsec + (hrtime_t)wcts.tv_sec * NANOSEC;
	ts.tv_sec = (time_t)(now / NANOSEC);
	ts.tv_nsec = (long)(now % NANOSEC);

	/*
	 * Apply GMT lag correction from /etc/rtc_config to get UTC time
	 */
	ts.tv_sec += ggmtl();

	/*
	 * Validate the TOD in case of total insanity
	 */
	tod = utc_to_tod(ts.tv_sec);
	if (tod.tod_year < 69) {
		static int range_warn = 1;	/* warn only once */

		if (range_warn) {
			/*
			 * If we're dom0, go invoke the underlying driver; the
			 * routine should complain if it discovers something
			 * wrong.
			 */
			if (DOMAIN_IS_INITDOMAIN(xen_info))
				(void) TODOP_GET(top->tod_next);

			/*
			 * Check the virtual hardware.
			 */
			if (tod.tod_year > 38)
				cmn_err(CE_WARN,
				    "hypervisor wall clock is out "
				    "of range -- time needs to be reset");
			range_warn = 0;
		}
		tod.tod_year += 100;
		ts.tv_sec = tod_to_utc(tod);
	}

	return (ts);
}