Exemple #1
0
static int ntp_init(void)
{
	int ret = gettime();
	if (ret) return ret;
	peer_clear(&peer);
	return NTP_OK;
}
Exemple #2
0
/*
 * clear_all - flush all time values for all associations
 */
void
clear_all(void)
{
	struct peer *peer, *next_peer;
	int n;

	/*
	 * This routine is called when the clock is stepped, and so all
	 * previously saved time values are untrusted.
	 */
	for (n = 0; n < NTP_HASH_SIZE; n++) {
		for (peer = peer_hash[n]; peer != 0; peer = next_peer) {
			next_peer = peer->next;
			if (!(peer->cast_flags & (MDF_ACAST | MDF_MCAST |
			    MDF_BCAST))) {
				peer->hpoll = peer->minpoll;
				peer_clear(peer, "STEP");
			}
		}
	}
#ifdef DEBUG
	if (debug)
		printf("clear_all: at %lu\n", current_time);
#endif
}
Exemple #3
0
static int clock_adjust(struct p *p)
{
	int i;
	int ret = NTP_OK;
	double old;
	double offset;
	struct timex tx;
	dprint("clock_adjust: p->offset:%f\n", p->offset);
	if (p->offset < CLOCK_MAX) {
		memset(&tx, 0, sizeof(tx));
		tx.modes = ADJ_OFFSET_SINGLESHOT;
		ret = get_old_offset(&old);
		if (ret) return ret;
		offset = p->offset + old;
		tx.offset = (long)(offset * USEC_IN_SEC);
		if (adjtimex(&tx) < 0) return NTP_ERR_SYS;
		for (i = 0; i < NSTAGE; i++)
			if (p->f[i].t > p->t && p->f[i].disp < MAXDISPERSE)
				p->f[i].offset -= p->offset;
		ret = freq_adjust(p);
		dprint("clock_adjust: freq_adjust_ret:%i\n", ret);
	}
	else {
		ret = movetime(p->offset);
		offset = p->offset;
		peer_clear(p);
		if (ret) return ret;
	}

	p->effective_offset = offset;
	return ret;
}
Exemple #4
0
static int l_set_peer(lua_State *L)
{
	double value;
	luaL_argcheck(L, lua_istable(L, 1), 1, "table expected");

	peer_clear(&peer);

	lua_getfield(L, 1, "poll");
	value = luaL_checknumber(L, -1);
	lua_pop(L, 1);
	peer.poll = (long)value;

	return 0;
}
Exemple #5
0
/*
 * clear_all - flush all time values for all associations
 */
void
clear_all(void)
{
	struct peer *p;

	/*
	 * This routine is called when the clock is stepped, and so all
	 * previously saved time values are untrusted.
	 */
	for (p = peer_list; p != NULL; p = p->p_link)
		if (!(MDF_TXONLY_MASK & p->cast_flags))
			peer_clear(p, "STEP");

	DPRINTF(1, ("clear_all: at %lu\n", current_time));
}
Exemple #6
0
static int l_clock_update(lua_State *L)
{
	double t[4];
	if (lua_gettop(L) < 1)
		return ntp_pushresult(L, ntp_process(&peer, 0, 0));
	else if (lua_gettop(L) < 4) {
		int ret;
		t[0] = luaL_checknumber(L, 1);
		ret = settime(t[0]);
		if (ret)
			return ntp_pushresult(L, ret);
		peer_clear(&peer);
		return ntp_pushresult(L, NTP_OK);
	}
	t[0] = luaL_checknumber(L, 1);
	t[1] = luaL_checknumber(L, 2);
	t[2] = luaL_checknumber(L, 3);
	t[3] = luaL_checknumber(L, 4);
	return ntp_pushresult(L, ntp_process(&peer, t, 0));
}
Exemple #7
0
/*
 * peer_config - configure a new association
 */
struct peer *
peer_config(
	struct sockaddr_storage *srcadr,
	struct interface *dstadr,
	int hmode,
	int version,
	int minpoll,
	int maxpoll,
	u_int flags,
	int ttl,
	keyid_t key,
	u_char *keystr
	)
{
	register struct peer *peer;
	u_char cast_flags;

	/*
	 * First search from the beginning for an association with given
	 * remote address and mode. If an interface is given, search
	 * from there to find the association which matches that
	 * destination.  If the given interface is "any", track down
	 * the actual interface, because that's what gets put into the
	 * peer structure.
	 */
	peer = findexistingpeer(srcadr, (struct peer *)0, hmode);
	if (dstadr != 0) {
		while (peer != 0) {
			if (peer->dstadr == dstadr)
				break;
			if (dstadr == ANY_INTERFACE_CHOOSE(srcadr) &&
			    peer->dstadr == findinterface(srcadr))
			     break;
			peer = findexistingpeer(srcadr, peer, hmode);
		}
	}

	/*
	 * We do a dirty little jig to figure the cast flags. This is
	 * probably not the best place to do this, at least until the
	 * configure code is rebuilt. Note only one flag can be set.
	 */
	switch (hmode) {

	case MODE_BROADCAST:
		if(srcadr->ss_family == AF_INET) {
			if (IN_CLASSD(ntohl(((struct sockaddr_in*)srcadr)->sin_addr.s_addr)))
				cast_flags = MDF_MCAST;
			else
				cast_flags = MDF_BCAST;
			break;
		}
		else {
                        if (IN6_IS_ADDR_MULTICAST(&((struct sockaddr_in6*)srcadr)->sin6_addr))
        	                cast_flags = MDF_MCAST;
	        	else
                        	cast_flags = MDF_BCAST;
                	break;
                }

	case MODE_CLIENT:
		if(srcadr->ss_family == AF_INET) {
			if (IN_CLASSD(ntohl(((struct sockaddr_in*)srcadr)->sin_addr.s_addr)))
				cast_flags = MDF_ACAST;
			else
				cast_flags = MDF_UCAST;
			break;
		}
		else {
			if (IN6_IS_ADDR_MULTICAST(&((struct sockaddr_in6*)srcadr)->sin6_addr))
				cast_flags = MDF_ACAST;
			else
				cast_flags = MDF_UCAST;
			break;
		}

	default:
		cast_flags = MDF_UCAST;
	}

	/*
	 * If the peer is already configured, some dope has a duplicate
	 * configureation entry or another dope is wiggling from afar.
	 */
	if (peer != 0) {
		peer->hmode = (u_char)hmode;
		peer->version = (u_char) version;
		peer->minpoll = (u_char) minpoll;
		peer->maxpoll = (u_char) maxpoll;
		peer->flags = flags | FLAG_CONFIG |
			(peer->flags & FLAG_REFCLOCK);
		peer->cast_flags = cast_flags;
		peer->ttl = (u_char) ttl;
		peer->keyid = key;
		peer->precision = sys_precision;
		peer_clear(peer, "RMOT");
		return (peer);
	}

	/*
	 * Here no match has been found, so presumably this is a new
	 * persistent association. Mobilize the thing and initialize its
	 * variables. If emulating ntpdate, force iburst.
	 */
	if (mode_ntpdate)
		flags |= FLAG_IBURST;
	peer = newpeer(srcadr, dstadr, hmode, version, minpoll, maxpoll,
	    flags | FLAG_CONFIG, cast_flags, ttl, key);
	return (peer);
}
/*
 * refclock_transmit - simulate the transmit procedure
 *
 * This routine implements the NTP transmit procedure for a reference
 * clock. This provides a mechanism to call the driver at the NTP poll
 * interval, as well as provides a reachability mechanism to detect a
 * broken radio or other madness.
 */
void
refclock_transmit(
	struct peer *peer	/* peer structure pointer */
	)
{
	u_char clktype;
	int unit;
	int hpoll;
	u_long next;

	clktype = peer->refclktype;
	unit = peer->refclkunit;
	peer->sent++;

	/*
	 * This is a ripoff of the peer transmit routine, but
	 * specialized for reference clocks. We do a little less
	 * protocol here and call the driver-specific transmit routine.
	 */
	hpoll = peer->hpoll;
	next = peer->outdate;
	if (peer->burst == 0) {
		u_char oreach;
#ifdef DEBUG
		if (debug)
			printf("refclock_transmit: at %ld %s\n",
			    current_time, ntoa(&(peer->srcadr)));
#endif

		/*
		 * Update reachability and poll variables like the
		 * network code.
		 */
		oreach = peer->reach;
		peer->reach <<= 1;
		if (!peer->reach) {
			if (oreach) {
				report_event(EVNT_UNREACH, peer);
				peer->timereachable = current_time;
				peer_clear(peer);
			}
		} else {
			if (!(oreach & 0x03)) {
				clock_filter(peer, 0., 0., MAXDISPERSE);
				clock_select();
			}
			if (!(oreach & 0x0f)) {
				hpoll--;
			} else if ((oreach & 0x0f) == 0x0f)
				hpoll++;
			if (peer->flags & FLAG_BURST)
				peer->burst = NSTAGE;
		}
		next = current_time;
	}
	get_systime(&peer->xmt);
	if (refclock_conf[clktype]->clock_poll != noentry)
		(refclock_conf[clktype]->clock_poll)(unit, peer);
	peer->outdate = next;
	if (peer->burst > 0)
		peer->burst--;
	poll_update(peer, hpoll);
}